mns_subscriber 0.5.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: c04ce31b2383049bc525550fb1e1d33a5b104eda
4
- data.tar.gz: '08a25b00c24be3e12dfa206239a710c16e7ae365'
2
+ SHA256:
3
+ metadata.gz: c9a3f061eca9581f000c9fd37c9341da37e29e723a883627b220045bc15daa68
4
+ data.tar.gz: 2c7ac5bb79b3b0bbc7edaf86c512aa06fd63d258ed2429788ee6d2f18644f26d
5
5
  SHA512:
6
- metadata.gz: 369924f7e33d94dccf36096721c6883e654fac7117e1b5a0db56dda0919284ff93a0bd2dc154689cc15c47d4955b17219a0814961ee1e2e46e16ab0c612cc27a
7
- data.tar.gz: 662e9e32f9f5156ad3d2ca66b4b594ce5b837a503c2d08d9370af482c78c28e5e1cccb2ac89359a5d8b78e3e79a9f220fee668ce6134ded52dca9dddb8136716
6
+ metadata.gz: 7ec27ad80dd5ccf4d69e9156a98ee5fc64870be0789f3d0eeaed9a449d52f1abec50eea61821d3e7ef97184c35882d0f1000a071507c7dd99ab45bba88141d44
7
+ data.tar.gz: 2adfaff285eb6677b02a0d4b501cf0f60400e91f0a6abe1dcc11a47602f8ae245b35ffbe66884fce01dc769742ce0201b7fe059e1a58ceb233307ce1f0534d2d
checksums.yaml.gz.sig CHANGED
@@ -1 +1 @@
1
- ��3
1
+ �\S�3�J"ƭ��"��.<��"x�苼�)-�c%\Z;tYnq1��Ю�=�(%2/��eo�Z��I� �܁BV&�^��IW�E��n��p��(�����%�<�y�[®kVYV�2�G�3�U���"�5Tn��bG^�b+Cv�|����#d؅^v]?��~Y�"�����]�ibџ�$�6��f]G��G?���=���:�X;����/U&kM�֤�F��c�x�'�,�.�t���MQ,M�a^lҺmu��#�8�A�"zŒ��* <hp(�7�)�*�IM�z8S��D�a���ЀS�~C��j����88��<$� Fe�8#[��D��k��+��K"=��6��Hb��Y��Y�q�"��|�H-�n��Gc
data.tar.gz.sig CHANGED
Binary file
@@ -7,170 +7,380 @@ require 'mtlite'
7
7
  require 'sps-sub'
8
8
  require 'daily_notices'
9
9
  require 'recordx_sqlite'
10
+ require 'easyimg_utils'
10
11
 
11
12
 
12
- class MNSSubscriber < SPSSub
13
-
14
- def initialize(host: 'sps', port: 59000, dir: '.', options: {},
15
- timeline: nil, log: nil)
16
-
17
- @log = log
18
- log.info 'mns_subscriber/initialize: active' if log
19
-
20
- # note: a valid url_base must be provided
21
-
22
- @options = {
23
- url_base: 'http://yourwebsitehere.co.uk/',
24
- dx_xslt: '/xsl/dynarex.xsl',
25
- rss_xslt: '/xsl/feed.xsl',
26
- target_page: :page,
27
- target_xslt: '/xsl/page.xsl'
28
- }.merge(options)
29
-
30
- super(host: host, port: port, log: log)
31
- @filepath, @timeline = dir, timeline
13
+ module MNSSubscriber
14
+
15
+ class NoticeMgr
16
+ using ColouredText
32
17
 
33
- @index = nil
34
-
35
- end
18
+ def initialize(sps=nil, dir: '.', options: {}, timeline: nil,
19
+ hashtag_url: nil, log: nil, debug: false)
20
+
21
+ @sps, @log, @debug = sps, log, debug
22
+
23
+ # note: a valid url_base must be provided
24
+ @options = {
25
+ url_base: 'http://yourwebsitehere.co.uk/',
26
+ dx_xslt: '/xsl/dynarex.xsl',
27
+ rss_xslt: '/xsl/feed.xsl',
28
+ target_page: :page,
29
+ target_xslt: '/xsl/page.xsl',
30
+ local_media_path: '/home/user/media',
31
+ url_media_path: 'http://media.yourwebsitehere.co.uk/'
32
+ }.merge(options)
36
33
 
37
- def subscribe(topic='notice/*')
38
- super(topic)
39
- end
40
34
 
41
- private
35
+ @filepath, @timeline = dir, timeline
36
+
37
+ @index = nil
38
+ @hashtags = nil
39
+
40
+
41
+ if hashtag_url then
42
+
43
+ @hashtag_url = @options[:url_base] + hashtag_url.sub(/^\//,'')
44
+
45
+ hashtag_path = File.join(dir, 'hashtag')
46
+ tagdb = File.join(hashtag_path, 'index.db')
47
+ FileUtils.mkdir_p File.dirname(tagdb)
48
+
49
+ h = {hashtags: {id: '', tag: '', topic: '', noticeid: ''}}
50
+ @hashtags = RecordxSqlite.new(tagdb, table: h )
42
51
 
43
- def ontopic(topic, msg)
52
+ end
53
+ end
44
54
 
45
- @log.info 'mns_subscriber/ontopic: topic: ' + topic.inspect if @topic
55
+ def incoming(topic, msg)
56
+
57
+ a = topic.split('/')
58
+ context = a.last.to_sym
59
+
60
+ case context
61
+ when :profile
62
+
63
+ update_attributes(:description, subtopic=a[-2], profile=msg)
64
+
65
+ when :link
66
+ puts 'we have a link' if @debug
67
+ update_attributes(:link, subtopic=a[-2], link=msg)
68
+
69
+ when :title
70
+
71
+ update_attributes(:title, subtopic=a[-2], title=msg)
72
+
73
+ when :image
74
+ #puts 'we have an image'
75
+ update_attributes(:image, subtopic=a[-2], title=msg)
76
+
77
+ when :delete
78
+
79
+ delete_notice(subtopic=a[-2], msg)
80
+
81
+ when :json
82
+
83
+ # JSON contains a message and 1 or more media files
84
+ h = JSON.parse msg, symbolize_names: true
85
+ puts 'h: ' + h.inspect if @debug
86
+
87
+ subtopic = a[-2]
88
+
89
+ t = Time.now
90
+ id = t.to_i.to_s + t.strftime("%2N")
91
+
92
+ filepath = File.join(@options[:local_media_path], 'images')
93
+
94
+ a = h[:files].map.with_index do |f,i|
95
+
96
+ # is f an Array object containing various sized images of the 1 file?
97
+ a2 = f.is_a?(Array) ? f : [f]
98
+
99
+ scale = a2.map do |imgfile|
100
+
101
+ scale = imgfile[/(_\w+)\.\w+$/,1].to_s
102
+ file = "%s%s%s" % [(id.to_i + i+1).to_s(36).reverse, scale, File.extname(imgfile)]
103
+ dest = File.join(filepath, file)
104
+
105
+ FileUtils.cp imgfile, dest
106
+ FileUtils.chmod 0755, dest
107
+
108
+ file
109
+
110
+ end
111
+
112
+ index = scale[1] ? 1 : 0
113
+ file1 = scale[index]
114
+
115
+ dir = File.extname(file1) =~ /\.(?:jpg|png)/ ? 'images' : ''
116
+ url = [@options[:url_media_path], dir, file1].join('/')
117
+
118
+ href = [@options[:url_base].sub(/\/$/,''), subtopic, 'status', id,
119
+ 'photo', (i+1).to_s ].join('/')
120
+ # find the best y position for the image letterbox view
121
+ pct = EasyImgUtils.new(a2[index]).best_viewport
122
+ pct2 = (pct / 10.0).to_i * 10
46
123
 
47
- a = topic.split('/')
48
- puts "%s: %s %s" % [topic, Time.now.to_s, msg.inspect]
124
+ align = if pct < 35 then
125
+
126
+ if pct < 10 then
127
+ :top
128
+ else
129
+ 'y' + pct2.to_s
130
+ end
131
+
132
+ elsif pct >= 70
133
+ :bottom
134
+ else
135
+ #'y' + pct.to_s
136
+ :center
137
+ end
138
+
139
+ {url: url, align: align}
140
+
141
+ end
142
+
143
+
144
+ card = if h[:card] and h[:card][:summary_large_image] then
145
+
146
+ h[:card][:summary_large_image][:img] = a[1][:url] if a.any?
147
+ h[:card]
148
+
149
+ elsif a.any?
150
+ {images: a}
151
+ end
152
+ #puts ('card: ' + card.inspect).debug
153
+
154
+ h[:msg] += build(card) if card
155
+ add_notice(subtopic, h[:msg].gsub('<','&lt;')\
156
+ .gsub('>','&gt;').gsub("\r",''), id,
157
+ (card ? card.to_json : nil))
158
+
159
+ else
160
+
161
+ subtopic, id = a[1..-1]
162
+ add_notice(subtopic, msg, id)
163
+
164
+ end
165
+ end
49
166
 
167
+ private
50
168
 
51
- case a.last.to_sym
169
+ def add_notice(topic, raw_msg, raw_id=nil, card=nil)
170
+
171
+ @log.info 'mns_subscriber/add_notice: active' if @log
172
+ topic_dir = File.join(@filepath, 'u', topic)
173
+
174
+ options = @options.clone
175
+ options.delete :local_media_path
176
+ options.delete :url_media_path
177
+
178
+ notices = DailyNotices.new topic_dir, options.merge(identifier: topic,
179
+ title: topic.capitalize + ' daily notices', log: @log)
180
+
181
+ t = Time.now
182
+ id = (raw_id || t.to_i.to_s + t.strftime("%2N")).to_i
52
183
 
53
- when :profile
184
+ # strip out any JSON from the end of the message
185
+ msg, raw_json = raw_msg.split(/(?=\{.*)/)
186
+
187
+ msg = ' ' if msg.nil?
188
+ mtlite = MTLite.new(msg)
189
+
190
+ desc = if mtlite.to_html(para: false) =~ /<\w+/ then
191
+ mtlite.to_html(para: true, ignore_domainlabel:true)
192
+ else
193
+ mtlite.to_s
194
+ end
195
+
196
+ if @hashtag_url then
197
+
198
+ tags = desc.scan(/(?<= #)\w+/)
199
+
200
+ desc.gsub!(/ #\w+/) do |x|
201
+ "<a href='%s%s'>%s</a>" % [@hashtag_url, x[2..-1], x]
202
+ end
203
+
204
+ # add the record to the database
205
+ tags.each do |tag|
54
206
 
55
- update_attributes(:description, subtopic=a[-2], profile=msg)
207
+ t = Time.now
208
+ id2 = (t.to_i.to_s + t.strftime("%2N")).to_i
209
+ h = {id: id2, tag: tag, topic: topic, noticeid: id}
56
210
 
57
- when :link
211
+ @hashtags.create h if @hashtags
58
212
 
59
- update_attributes(:link, subtopic=a[-2], link=msg)
213
+ end
214
+
215
+ end
216
+
217
+ title = mtlite.to_s.lines.first.chomp
218
+ title = title[0..136] + ' ...' if title.length > 140
219
+
220
+ h = {
221
+ title: title,
222
+ description: desc,
223
+ topic: topic,
224
+ card: card
225
+ }
226
+ #puts 'inside add_notice h: ' + h.inspect
227
+ return_status = notices.add(item: h, id: id.to_s)
228
+ #puts 'return_status: ' + return_status.inspect
60
229
 
61
- when :title
230
+ return if return_status == :duplicate
231
+
232
+ rxnotices = RecordxSqlite.new(File.join(topic_dir, 'notices.db'),
233
+ table: {notices: {id: 0, description: '', message: ''}})
234
+
235
+ begin
236
+ rxnotices.create id: id.to_s, description: desc, message: msg
237
+ rescue
238
+ puts 'warning: rxnotices.create -> ' + ($!).inspect
239
+ end
240
+
241
+ if raw_json then
242
+
243
+ record = JSON.parse(raw_json)
244
+ index = RecordxSqlite.new(File.join(topic_dir, 'index.db'),
245
+ table: {items: record})
246
+ index.create record
247
+
248
+ update_index_xml(index, topic_dir)
249
+
250
+ end
251
+
252
+ @sps.notice "%s/add: %s/status/%s" % [@timeline, topic, id] if @timeline
253
+
254
+ sleep 0.3
255
+
256
+ end
257
+
258
+ def delete_notice(topic, msg)
62
259
 
63
- update_attributes(:title, subtopic=a[-2], title=msg)
260
+ topic_dir = File.join(@filepath, topic)
261
+
262
+ id = msg.to_i
64
263
 
65
- when :delete
264
+ feed = DailyNotices.new topic_dir, log: @log
265
+ feed.delete id
66
266
 
67
- delete_notice(subtopic=a[-2], msg)
267
+ notices = RecordxSqlite.new(File.join(topic_dir, 'notices.db'),
268
+ table: 'notices')
269
+ notices.delete id
68
270
 
69
- else
271
+ indexdb = File.join(topic_dir, 'index.db')
70
272
 
71
- subtopic, id = a[1..-1]
72
- add_notice(subtopic, msg, id)
273
+ if File.exists? indexdb then
274
+
275
+ index = RecordxSqlite.new(indexdb, table: 'items')
276
+ index.delete id
277
+ update_index_xml(index, topic_dir)
278
+ end
279
+
280
+ end
281
+
282
+ # builds the HTML for a given card
283
+ #
284
+ def build(card)
285
+
286
+ #return card.inspect
287
+ #next unless card.is_a? Hash
288
+
289
+ if card.is_a? Hash then
73
290
 
74
- end
291
+ card2 = case card.keys.first
292
+ when :images
293
+
294
+ card[:images].map.with_index do |img, i|
295
+
296
+ "<img class='img1' src='%s'/>" % img[:url]
297
+
298
+ end.join
299
+
300
+ when :summary_large_image
75
301
 
76
- end
302
+ h2 = card[:summary_large_image]
77
303
 
78
- def add_notice(topic, raw_msg, raw_id=Time.now)
304
+ rawdesc = h2[:desc]
79
305
 
80
- @log.info 'mns_subscriber/add_notice: active' if @log
81
- topic_dir = File.join(@filepath, topic)
82
- notices = DailyNotices.new topic_dir, @options.merge(identifier: topic,
83
- title: topic.capitalize + ' daily notices', log: @log)
306
+ desc = rawdesc.length > 147 ? rawdesc[0..147] + '...' : rawdesc
307
+ site = h2[:url][/https?:\/\/([^\/]+)(?=\/)/,1].sub(/^www\./,'')
308
+ title = h2[:title]
309
+ img = h2[:img]
310
+ url = h2[:url]
84
311
 
85
- id = (raw_id || Time.now).to_i
86
-
87
- # strip out any JSON from the end of the message
88
- msg, raw_json = raw_msg.split(/(?=\{.*)/)
89
-
90
- mtlite = MTLite.new(msg)
91
-
92
- desc = if mtlite.to_html(para: false) =~ /<\w+/ then
93
- mtlite.to_html(para: true, ignore_domainlabel:true)
94
- else
95
- mtlite.to_s
96
- end
97
-
98
- title = mtlite.to_s.lines.first.chomp
99
- title = title[0..136] + ' ...' if title.length > 140
100
-
101
- h = {
102
- title: title,
103
- description: desc,
104
- topic: topic
105
- }
312
+ # The following Card HTML template is for use with the RSS feed.
313
+ # The actual HTML template for the card is rendered dynamically
314
+ # from the web server.
315
+ "
316
+ <div class='card'><a href='#{url}' target='_blank'>" +
317
+ "<div class='top-crop center'><img src='#{img}'/></div>" +
318
+ "<span class='title'>#{title}</span></a><p>#{desc}</p>" +
319
+ "<span class='link'><span class='linkurl'>#{site}</span></span></div>"
106
320
 
107
- return_status = notices.add(item: h, id: id.to_s)
108
-
109
- return if return_status == :duplicate
110
-
111
- rxnotices = RecordxSqlite.new(File.join(topic_dir, 'notices.db'),
112
- table: {notices: {id: 0, message: ''}})
113
- rxnotices.create id: id.to_s, message: msg
321
+ end
322
+ end
323
+
324
+ end
114
325
 
115
- if raw_json then
326
+ def update_index_xml(index, topic_dir)
327
+
328
+ # create the index.xml file
116
329
 
117
- record = JSON.parse(raw_json)
118
- index = RecordxSqlite.new(File.join(topic_dir, 'index.db'),
119
- table: {items: record})
120
- index.create record
330
+ a = index.order(:desc).first(15)
331
+ a2 = a.map {|x| h = x.to_h; id = h.delete(:id); {item_id: id}.merge(h)}
332
+
333
+ dx = Dynarex.new
334
+ dx.import a2
335
+ dx.order ='descending'
121
336
 
122
- update_index_xml(index, topic_dir)
337
+ dx.save File.join(topic_dir, 'index.xml')
123
338
 
124
339
  end
340
+
341
+ def update_attributes(attribute, topic, value)
342
+
343
+ topic_dir = File.join(@filepath, topic)
344
+ notices = DailyNotices.new topic_dir, @options.merge(identifier: topic)
345
+ notices.method((attribute.to_s + '=').to_sym).call(value)
346
+ notices.save
125
347
 
126
- self.notice "%s/add: %s/status/%s" % [@timeline, topic, id] if @timeline
127
-
128
- sleep 0.3
348
+ end
349
+
129
350
 
130
351
  end
131
-
132
- def delete_notice(topic, msg)
133
-
134
- topic_dir = File.join(@filepath, topic)
135
-
136
- notices = RecordxSqlite.new(File.join(topic_dir, 'notices.db'),
137
- table: 'notices')
138
- id = msg.to_i
139
- notices.delete id
140
-
141
- indexdb = File.join(topic_dir, 'index.db')
142
-
143
- if File.exists? indexdb then
352
+
353
+ class Client < SPSSub
354
+
355
+ def initialize(host: 'sps', port: 59000, dir: '.', options: {},
356
+ timeline: nil, log: nil, hashtag_url: nil)
357
+
358
+ @log = log
359
+ log.info 'mns_subscriber/initialize: active' if log
360
+ @nm = NoticeMgr.new(self, dir: dir, options: options, timeline: timeline,
361
+ hashtag_url: hashtag_url, debug: true)
362
+
363
+ super(host: host, port: port, log: log)
144
364
 
145
- index = RecordxSqlite.new(indexdb, table: 'items')
146
- index.delete id
147
- update_index_xml(index, topic_dir)
148
365
  end
149
-
150
- end
151
-
152
- def update_index_xml(index, topic_dir)
153
-
154
- # create the index.xml file
155
-
156
- a = index.order(:desc).first(15)
157
- a2 = a.map {|x| h = x.to_h; id = h.delete(:id); {item_id: id}.merge(h)}
158
366
 
159
- dx = Dynarex.new
160
- dx.import a2
161
- dx.order ='descending'
162
-
163
- dx.save File.join(topic_dir, 'index.xml')
164
-
165
- end
367
+ def subscribe(topic='notice/*')
368
+ super(topic)
369
+ end
370
+
371
+ private
372
+
373
+ def ontopic(topic, msg)
374
+
375
+ @log.info 'mns_subscriber/ontopic: topic: ' + topic.inspect if @topic
376
+
377
+ a = topic.split('/')
378
+ #puts "%s: %s %s" % [topic, Time.now.to_s, msg.inspect]
379
+
380
+ @nm.incoming topic, msg
381
+
382
+ end
166
383
 
167
- def update_attributes(attribute, topic, value)
168
-
169
- topic_dir = File.join(@filepath, topic)
170
- notices = DailyNotices.new topic_dir, @options.merge(identifier: topic)
171
- notices.method((attribute.to_s + '=').to_sym).call(value)
172
- notices.save
173
-
174
384
  end
175
385
 
176
386
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mns_subscriber
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.0
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - James Robertson
@@ -10,27 +10,32 @@ bindir: bin
10
10
  cert_chain:
11
11
  - |
12
12
  -----BEGIN CERTIFICATE-----
13
- MIIDXjCCAkagAwIBAgIBATANBgkqhkiG9w0BAQUFADAsMSowKAYDVQQDDCFnZW1t
14
- YXN0ZXIvREM9amFtZXNyb2JlcnRzb24vREM9ZXUwHhcNMTgwMjIyMTYxNjE5WhcN
15
- MTkwMjIyMTYxNjE5WjAsMSowKAYDVQQDDCFnZW1tYXN0ZXIvREM9amFtZXNyb2Jl
16
- cnRzb24vREM9ZXUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC7Q008
17
- itK6F90KJgwqB37PaUir/OFCkg7tZb3yHMHwzbvYEZQHCM4lZsIECOTChO4GQr/V
18
- 5TMnasItQ1SauVNw5L61XxEm0udS/vuZi6h0oGLPP1x8M3D7Fe0tRydJY7aUyOSi
19
- flhzvkYWS7wRdPjKQ7xTMSkgx8MJlH2Gv5KObDIZHAG2tElrtPGMhcHWyEac8Shy
20
- RtsXEsjISbbfkgjaJuUOMiCy0liXCtF4G5as3MfbliIiJFYLRpN0gFL125yR5wrg
21
- 8NFkvScfpATXrnCER7LQl6AEJaqr2RKVZECkFMv0qDp/3ljcl8R73M/MSUPvbq7C
22
- zumUj6vjMJOrpNVrAgMBAAGjgYowgYcwCQYDVR0TBAIwADALBgNVHQ8EBAMCBLAw
23
- HQYDVR0OBBYEFKuGRM8Sj+FLDIV92A3xNZMOPauDMCYGA1UdEQQfMB2BG2dlbW1h
24
- c3RlckBqYW1lc3JvYmVydHNvbi5ldTAmBgNVHRIEHzAdgRtnZW1tYXN0ZXJAamFt
25
- ZXNyb2JlcnRzb24uZXUwDQYJKoZIhvcNAQEFBQADggEBAEBLjIu741S83Dx4id8Z
26
- DtnKNmkC7IhCFMc8evNY+qf/QHoTRj8moOHOZKNnVFbisEIWiCK20aLZjHvrScru
27
- NFFBndQTC40ucldalCFZkhhKwo8pTC7n/V+dWiENhxH2+P4WJByujRJzmwfY+jtv
28
- ivECGOzg85UcFESflbMbjbVghGqB++dPeKkgCg8dGhT2S9rzBIHv06UWk3sASZ/u
29
- zRBXpYiOIk0uMcRp1i4iLQqDlr7CVH+LUVWFCtUF65Xv8AuM2vl7845rU4Q7LF7r
30
- UGSaMS9xu6Lrtmfakn86mAz4OAVP58sYf8VD/mAbJ+RaS/jTDilPcd6JrmCirJ/0
31
- Tms=
13
+ MIIEXjCCAsagAwIBAgIBATANBgkqhkiG9w0BAQsFADAsMSowKAYDVQQDDCFnZW1t
14
+ YXN0ZXIvREM9amFtZXNyb2JlcnRzb24vREM9ZXUwHhcNMjEwMjI0MTMzNzMzWhcN
15
+ MjIwMjI0MTMzNzMzWjAsMSowKAYDVQQDDCFnZW1tYXN0ZXIvREM9amFtZXNyb2Jl
16
+ cnRzb24vREM9ZXUwggGiMA0GCSqGSIb3DQEBAQUAA4IBjwAwggGKAoIBgQCrXfm/
17
+ AwR/iY/kgH1QAHFOBfSTgEBjHDUxgQl7Z3+43Tc8UMifQIWh4opLpzwcazVtrOB7
18
+ O2hXRNG9M1Dy1bRSOBSsiKSlDtfcqXfLmGKQGczMK+i2x8TTty4Vc3NPOjQlHaCt
19
+ 3KRPi/JiQ7OT+atmEEkfiDOWY5IpNHGiz93Q2L0+xUvp1fKtVedxeB/+kxuaP+C5
20
+ 3YbxJ2jVRldAe0QA9zM9YITTLe/xoiHS0LpPmtIk+4wNOK/vPh2u+p/BX9PbWiGO
21
+ 3KWzMuyCvtqDNXHdjEJ5KazWkL2By2k64eRVUuPHne8R4LYm3Ik3VfO/H759fdP3
22
+ Ap/L5pUprYRiq1NFBW5Ex3orjuCX/P887tahVho+RN8iUtkhMlQdk0uSRO8KP5Vz
23
+ kU09eIZ7o7JjftQliJ5+8O/hmtvCxXw1eystEVKJW32COaqFgLsM206ncMq4flTZ
24
+ 5mU2/Cwz7SxWQQe0cIzTH+o1pejIS83IRRMgHEtgyki0yUKDcoZVhvNujrMCAwEA
25
+ AaOBijCBhzAJBgNVHRMEAjAAMAsGA1UdDwQEAwIEsDAdBgNVHQ4EFgQU0a7RWUQ4
26
+ bjy71dOj2inlBZ1u+NIwJgYDVR0RBB8wHYEbZ2VtbWFzdGVyQGphbWVzcm9iZXJ0
27
+ c29uLmV1MCYGA1UdEgQfMB2BG2dlbW1hc3RlckBqYW1lc3JvYmVydHNvbi5ldTAN
28
+ BgkqhkiG9w0BAQsFAAOCAYEANZXVYK9Ut5FWc27EOT5ajSB/DVW6GXUMWGXNVLll
29
+ x6o5OX9r4xHlINGsTEI4q01kCBQsJCjQKNFOrUss+TsEFgXremusnniPwypvoCZh
30
+ JAmmUktsIKuKmgkJ6h1hhuJf6g90++v4iVvBHt53nhN8NaGYe4Oc2OwXTfxHam0X
31
+ JfCSR+Aw2QfaQvZKi8inGHgLmM61ABpIGTZ8lwzR6fizANDF6EQ7vNixJMSZExzP
32
+ s1BgeI/oTI1Y7UNeUtwWA8NkQ1bczUBH4FDUab4QRIbBYhXz+Hs8ddtugTzcmRwf
33
+ W0wI6iCh95fKaCbmSS5MY3dYMexH07A1XFGyHWOogCEWWYZ4ho+a44Fm0Uotp5ky
34
+ TjsXYJbdzlsAVQKfCSIfCi3T/k4bp/2wc342j/WYjkKLN4aZID+E9P/VX1Nc0m/s
35
+ yOAycOYzp7fxmPl3/HV5D0YOJwuy1XslA50GQJwq12A5vMyUGUCHuxH/zKZcM/zr
36
+ 0QZaKiVqq5ZeGvni0eQSavhQ
32
37
  -----END CERTIFICATE-----
33
- date: 2018-02-22 00:00:00.000000000 Z
38
+ date: 2021-03-29 00:00:00.000000000 Z
34
39
  dependencies:
35
40
  - !ruby/object:Gem::Dependency
36
41
  name: mtlite
@@ -38,20 +43,20 @@ dependencies:
38
43
  requirements:
39
44
  - - "~>"
40
45
  - !ruby/object:Gem::Version
41
- version: '0.3'
46
+ version: '0.4'
42
47
  - - ">="
43
48
  - !ruby/object:Gem::Version
44
- version: 0.3.5
49
+ version: 0.4.1
45
50
  type: :runtime
46
51
  prerelease: false
47
52
  version_requirements: !ruby/object:Gem::Requirement
48
53
  requirements:
49
54
  - - "~>"
50
55
  - !ruby/object:Gem::Version
51
- version: '0.3'
56
+ version: '0.4'
52
57
  - - ">="
53
58
  - !ruby/object:Gem::Version
54
- version: 0.3.5
59
+ version: 0.4.1
55
60
  - !ruby/object:Gem::Dependency
56
61
  name: sps-sub
57
62
  requirement: !ruby/object:Gem::Requirement
@@ -61,7 +66,7 @@ dependencies:
61
66
  version: '0.3'
62
67
  - - ">="
63
68
  - !ruby/object:Gem::Version
64
- version: 0.3.6
69
+ version: 0.3.7
65
70
  type: :runtime
66
71
  prerelease: false
67
72
  version_requirements: !ruby/object:Gem::Requirement
@@ -71,49 +76,69 @@ dependencies:
71
76
  version: '0.3'
72
77
  - - ">="
73
78
  - !ruby/object:Gem::Version
74
- version: 0.3.6
79
+ version: 0.3.7
75
80
  - !ruby/object:Gem::Dependency
76
81
  name: daily_notices
77
82
  requirement: !ruby/object:Gem::Requirement
78
83
  requirements:
79
84
  - - "~>"
80
85
  - !ruby/object:Gem::Version
81
- version: '0.6'
86
+ version: '0.7'
82
87
  - - ">="
83
88
  - !ruby/object:Gem::Version
84
- version: 0.6.5
89
+ version: 0.7.1
85
90
  type: :runtime
86
91
  prerelease: false
87
92
  version_requirements: !ruby/object:Gem::Requirement
88
93
  requirements:
89
94
  - - "~>"
90
95
  - !ruby/object:Gem::Version
91
- version: '0.6'
96
+ version: '0.7'
92
97
  - - ">="
93
98
  - !ruby/object:Gem::Version
94
- version: 0.6.5
99
+ version: 0.7.1
95
100
  - !ruby/object:Gem::Dependency
96
101
  name: recordx_sqlite
97
102
  requirement: !ruby/object:Gem::Requirement
98
103
  requirements:
99
104
  - - "~>"
100
105
  - !ruby/object:Gem::Version
101
- version: '0.2'
106
+ version: '0.3'
107
+ - - ">="
108
+ - !ruby/object:Gem::Version
109
+ version: 0.3.1
110
+ type: :runtime
111
+ prerelease: false
112
+ version_requirements: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - "~>"
115
+ - !ruby/object:Gem::Version
116
+ version: '0.3'
117
+ - - ">="
118
+ - !ruby/object:Gem::Version
119
+ version: 0.3.1
120
+ - !ruby/object:Gem::Dependency
121
+ name: easyimg_utils
122
+ requirement: !ruby/object:Gem::Requirement
123
+ requirements:
124
+ - - "~>"
125
+ - !ruby/object:Gem::Version
126
+ version: '0.7'
102
127
  - - ">="
103
128
  - !ruby/object:Gem::Version
104
- version: 0.2.7
129
+ version: 0.7.3
105
130
  type: :runtime
106
131
  prerelease: false
107
132
  version_requirements: !ruby/object:Gem::Requirement
108
133
  requirements:
109
134
  - - "~>"
110
135
  - !ruby/object:Gem::Version
111
- version: '0.2'
136
+ version: '0.7'
112
137
  - - ">="
113
138
  - !ruby/object:Gem::Version
114
- version: 0.2.7
139
+ version: 0.7.3
115
140
  description:
116
- email: james@jamesrobertson.eu
141
+ email: digital.robertson@gmail.com
117
142
  executables: []
118
143
  extensions: []
119
144
  extra_rdoc_files: []
@@ -139,7 +164,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
139
164
  version: '0'
140
165
  requirements: []
141
166
  rubyforge_project:
142
- rubygems_version: 2.6.13
167
+ rubygems_version: 2.7.10
143
168
  signing_key:
144
169
  specification_version: 4
145
170
  summary: Creates microblog posts from different identities by subscribing to the SPS
metadata.gz.sig CHANGED
Binary file