ayadn 1.8.2 → 2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (81) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +4 -0
  3. data/CHANGELOG.md +73 -52
  4. data/README.md +17 -3
  5. data/ayadn.gemspec +3 -4
  6. data/doc/01-index.md +6 -5
  7. data/doc/02-install.md +23 -1
  8. data/doc/03-first-steps.md +22 -28
  9. data/doc/04-options.md +1 -1
  10. data/doc/05-streams.md +29 -9
  11. data/doc/06-post.md +13 -5
  12. data/doc/07-actions.md +63 -1
  13. data/doc/08-listings.md +112 -4
  14. data/doc/09-accounts.md +17 -3
  15. data/doc/10-nicerank.md +5 -5
  16. data/doc/11-blacklist.md +8 -14
  17. data/doc/12-alias.md +1 -13
  18. data/doc/14-set.md +8 -110
  19. data/doc/15-nowplaying.md +16 -4
  20. data/doc/18-contact.md +14 -13
  21. data/doc/19-examples.md +2 -0
  22. data/lib/ayadn/action.rb +322 -183
  23. data/lib/ayadn/alias.rb +17 -45
  24. data/lib/ayadn/annotations.rb +1 -1
  25. data/lib/ayadn/api.rb +7 -8
  26. data/lib/ayadn/app.rb +99 -12
  27. data/lib/ayadn/authorize.rb +92 -57
  28. data/lib/ayadn/blacklist.rb +52 -62
  29. data/lib/ayadn/check.rb +81 -74
  30. data/lib/ayadn/cnx.rb +77 -26
  31. data/lib/ayadn/databases.rb +890 -105
  32. data/lib/ayadn/debug.rb +30 -89
  33. data/lib/ayadn/descriptions.rb +876 -329
  34. data/lib/ayadn/endpoints.rb +2 -2
  35. data/lib/ayadn/errors.rb +9 -9
  36. data/lib/ayadn/extend.rb +8 -1
  37. data/lib/ayadn/fileops.rb +10 -8
  38. data/lib/ayadn/mark.rb +79 -56
  39. data/lib/ayadn/migration.rb +427 -0
  40. data/lib/ayadn/nicerank.rb +74 -72
  41. data/lib/ayadn/nowplaying.rb +123 -60
  42. data/lib/ayadn/nowwatching.rb +26 -10
  43. data/lib/ayadn/pinboard.rb +12 -7
  44. data/lib/ayadn/post.rb +40 -37
  45. data/lib/ayadn/profile.rb +5 -2
  46. data/lib/ayadn/scroll.rb +20 -5
  47. data/lib/ayadn/search.rb +30 -22
  48. data/lib/ayadn/set.rb +146 -50
  49. data/lib/ayadn/settings.rb +66 -67
  50. data/lib/ayadn/status.rb +459 -234
  51. data/lib/ayadn/stream.rb +80 -46
  52. data/lib/ayadn/switch.rb +51 -47
  53. data/lib/ayadn/tvshow.rb +47 -15
  54. data/lib/ayadn/version.rb +1 -1
  55. data/lib/ayadn/view.rb +119 -60
  56. data/lib/ayadn/workers.rb +144 -92
  57. data/lib/ayadn.rb +7 -8
  58. data/spec/mock/ayadn/accounts.sqlite +0 -0
  59. data/spec/mock/ayadn.sqlite +0 -0
  60. data/spec/unit/annotations_spec.rb +12 -13
  61. data/spec/unit/api_spec.rb +3 -4
  62. data/spec/unit/blacklistworkers_spec.rb +18 -23
  63. data/spec/unit/databases_spec.rb +51 -36
  64. data/spec/unit/endpoints_spec.rb +5 -2
  65. data/spec/unit/extend_spec.rb +24 -0
  66. data/spec/unit/nicerank_spec.rb +13 -13
  67. data/spec/unit/post_spec.rb +47 -36
  68. data/spec/unit/set_spec.rb +67 -96
  69. data/spec/unit/view_spec.rb +12 -6
  70. data/spec/unit/workers_spec.rb +38 -12
  71. data/tags +1285 -0
  72. metadata +29 -39
  73. data/spec/mock/aliases.db +0 -0
  74. data/spec/mock/blacklist.db +0 -0
  75. data/spec/mock/bookmarks.db +0 -0
  76. data/spec/mock/channels.db +0 -0
  77. data/spec/mock/index.db +0 -0
  78. data/spec/mock/nicerank.db +0 -0
  79. data/spec/mock/pagination.db +0 -0
  80. data/spec/mock/users.db +0 -0
  81. data/spec/unit/status_spec.rb +0 -9
@@ -0,0 +1,427 @@
1
+ # encoding: utf-8
2
+ module Ayadn
3
+ class Migration
4
+
5
+ begin
6
+ require 'daybreak'
7
+ rescue LoadError => e
8
+ puts "\nAYADN: Error while loading Gems\n\n"
9
+ puts "RUBY: #{e}\n\n"
10
+ exit
11
+ end
12
+
13
+ def initialize
14
+ @still = false
15
+ @thor = Thor::Shell::Color.new
16
+ accounts_old = Dir.home + "/ayadn/accounts.db"
17
+ unless File.exist?(accounts_old)
18
+ puts "\n"
19
+ @thor.say_status :error, "can't find the Ayadn 1.x accounts database", :red
20
+ @thor.say_status :canceled, "migration canceled", :red
21
+ puts "\n"
22
+ exit
23
+ end
24
+ begin
25
+ @accounts = Daybreak::DB.new(accounts_old)
26
+ # just in case of a previous canceled migration
27
+ # which could have left the accounts.db in place
28
+ if @accounts.size == 1 || @accounts.size == 0
29
+ @accounts.close
30
+ File.delete(Dir.home + "/ayadn/accounts.db")
31
+ @thor.say_status :delete, Dir.home + "/ayadn/accounts.db", :yellow
32
+ @thor.say_status :stopped, "no more accounts to migrate", :green
33
+ exit
34
+ end
35
+ @active_old = @accounts['ACTIVE']
36
+ @home = @accounts[@active_old][:path]
37
+ bookmarks_old = "#{@home}/db/bookmarks.db"
38
+ aliases_old = "#{@home}/db/aliases.db"
39
+ blacklist_old = "#{@home}/db/blacklist.db"
40
+ users_old = "#{@home}/db/users.db"
41
+ @pagination_old = "#{@home}/pagination/pagination.db"
42
+ @index_old = "#{@home}/pagination/index.db"
43
+
44
+ @config_path_old = "#{@home}/config/config.yml"
45
+
46
+ @bookmarks = Daybreak::DB.new(bookmarks_old) if File.exist?(bookmarks_old)
47
+ @aliases = Daybreak::DB.new(aliases_old) if File.exist?(aliases_old)
48
+ @blacklist = Daybreak::DB.new(blacklist_old) if File.exist?(blacklist_old)
49
+ @users = Daybreak::DB.new(users_old) if File.exist?(users_old)
50
+ @pagination = Daybreak::DB.new(@pagination_old) if File.exist?(@pagination_old)
51
+ @index = Daybreak::DB.new(@index_old) if File.exist?(@index_old)
52
+
53
+ @sqlfile = "#{@home}/db/ayadn.sqlite"
54
+ @sql = Amalgalite::Database.new(@sqlfile)
55
+ rescue Exception => e
56
+ puts "\n"
57
+ @thor.say_status :error, "#{e}", :red
58
+ @thor.say_status :stack, "#{caller}", :red
59
+ @thor.say_status :canceled, "migration canceled", :red
60
+ puts "\n"
61
+ exit
62
+ end
63
+ end
64
+
65
+ def all
66
+ # DON'T MODIFY THE ORDER!
67
+ puts banner()
68
+ puts "\n"
69
+ @thor.say_status :start, "migration", :yellow
70
+ old_backup = "#{@home}/backup"
71
+ if Dir.exist?(old_backup)
72
+ if Dir.entries(old_backup).size > 2
73
+ FileUtils.mv(Dir.glob("#{old_backup}/*"), "#{@home}/downloads")
74
+ @thor.say_status :move, "files from 'backup' to 'downloads'", :green
75
+ end
76
+ Dir.rmdir(old_backup)
77
+ @thor.say_status :delete, old_backup, :green
78
+ end
79
+ old_channels = "#{@home}/db/channels.db"
80
+ if File.exist?(old_channels)
81
+ @thor.say_status :delete, old_channels, :green
82
+ File.delete(old_channels)
83
+ end
84
+ if File.exist?("#{@home}/db/ayadn_pinboard.db")
85
+ @thor.say_status :move, "pinboard credentials", :green
86
+ FileUtils.mv("#{@home}/db/ayadn_pinboard.db", "#{@home}/auth/pinboard.data")
87
+ end
88
+ bookmarks()
89
+ aliases()
90
+ blacklist()
91
+ niceranks()
92
+ users()
93
+ pagination()
94
+ index()
95
+ accounts()
96
+ config()
97
+ @thor.say_status :done, "migration", :yellow
98
+ puts "\n"
99
+ if @still != false
100
+ @thor.say_status :WARNING, "another user, @#{@still}, is still in the old database", :red
101
+ @thor.say_status :PLEASE, "you should run `ayadn migrate` again right now", :yellow
102
+ puts "\n"
103
+ else
104
+ @thor.say_status :ok, "ready to go!", :green
105
+ @thor.say_status :thanks, "you can use Ayadn now", :cyan
106
+ puts "\n"
107
+ end
108
+ end
109
+
110
+ def bookmarks
111
+ @sql.execute_batch <<-SQL
112
+ CREATE TABLE Bookmarks (
113
+ post_id INTEGER,
114
+ bookmark TEXT
115
+ );
116
+ SQL
117
+ @sql.reload_schema!
118
+ if File.exist?("#{@home}/db/bookmarks.db")
119
+ @thor.say_status :import, "Bookmarks database", :cyan
120
+ @sql.transaction do |db_in_transaction|
121
+ @bookmarks.each do |k,v|
122
+ insert_data = {}
123
+ insert_data[":k"] = k.to_i
124
+ insert_data[":v"] = v.to_json.to_s
125
+ db_in_transaction.prepare("INSERT INTO Bookmarks(post_id, bookmark) VALUES(:k, :v);") do |insert|
126
+ insert.execute(insert_data)
127
+ end
128
+ end
129
+ end
130
+ @thor.say_status :done, "#{@bookmarks.size} objects", :green
131
+ @bookmarks.close
132
+ File.delete("#{@home}/db/bookmarks.db")
133
+ @thor.say_status :delete, "#{@home}/db/bookmarks.db", :green
134
+ end
135
+ end
136
+
137
+ def aliases
138
+ @sql.execute_batch <<-SQL
139
+ CREATE TABLE Aliases (
140
+ channel_id INTEGER,
141
+ alias VARCHAR(255)
142
+ );
143
+ SQL
144
+ @sql.reload_schema!
145
+ if File.exist?("#{@home}/db/aliases.db")
146
+ @thor.say_status :import, "Aliases database", :cyan
147
+ @sql.transaction do |db_in_transaction|
148
+ @aliases.each do |k,v|
149
+ insert_data = {}
150
+ insert_data[":k"] = v.to_i
151
+ insert_data[":v"] = k
152
+ db_in_transaction.prepare("INSERT INTO Aliases(channel_id, alias) VALUES(:k, :v);") do |insert|
153
+ insert.execute(insert_data)
154
+ end
155
+ end
156
+ end
157
+ @thor.say_status :done, "#{@aliases.size} objects", :green
158
+ @aliases.close
159
+ File.delete("#{@home}/db/aliases.db")
160
+ @thor.say_status :delete, "#{@home}/db/aliases.db", :green
161
+ end
162
+ end
163
+
164
+ def blacklist
165
+ @sql.execute_batch <<-SQL
166
+ CREATE TABLE Blacklist (
167
+ type VARCHAR(255),
168
+ content TEXT
169
+ );
170
+ SQL
171
+ @sql.reload_schema!
172
+ if File.exist?("#{@home}/db/blacklist.db")
173
+ @thor.say_status :import, "Blacklist database", :cyan
174
+ @sql.transaction do |db_in_transaction|
175
+ @blacklist.each do |k,v|
176
+ insert_data = {}
177
+ ks = k.dup.to_s
178
+ ks[0] = "" if ks[0] == "-"
179
+ ks[0] = "" if ks[0] == "@"
180
+ insert_data[":k"] = v.to_s
181
+ insert_data[":v"] = ks
182
+ db_in_transaction.prepare("INSERT INTO Blacklist(type, content) VALUES(:k, :v);") do |insert|
183
+ insert.execute(insert_data)
184
+ end
185
+ end
186
+ end
187
+ @thor.say_status :done, "#{@blacklist.size} objects", :green
188
+ @blacklist.close
189
+ File.delete("#{@home}/db/blacklist.db")
190
+ @thor.say_status :delete, "#{@home}/db/blacklist.db", :green
191
+ end
192
+ end
193
+
194
+ def niceranks
195
+ if File.exist?("#{@home}/db/nicerank.db")
196
+ File.delete("#{@home}/db/nicerank.db")
197
+ @thor.say_status :delete, "#{@home}/db/nicerank.db", :green
198
+ end
199
+ end
200
+
201
+ def users
202
+ @sql.execute_batch <<-SQL
203
+ CREATE TABLE Users (
204
+ user_id INTEGER,
205
+ username VARCHAR(20),
206
+ name TEXT
207
+ );
208
+ SQL
209
+ @sql.reload_schema!
210
+ if File.exist?("#{@home}/db/users.db")
211
+ @thor.say_status :import, "Users database", :cyan
212
+ @sql.transaction do |db_in_transaction|
213
+ @users.each do |k,v|
214
+ insert_data = {}
215
+ insert_data[":id"] = k.to_i
216
+ insert_data[":username"] = v.keys[0]
217
+ insert_data[":name"] = v.values[0]
218
+ db_in_transaction.prepare("INSERT INTO Users(user_id, username, name) VALUES(:id, :username, :name);") do |insert|
219
+ insert.execute(insert_data)
220
+ end
221
+ end
222
+ end
223
+ @thor.say_status :done, "#{@users.size} objects", :green
224
+ @users.close
225
+ File.delete("#{@home}/db/users.db")
226
+ @thor.say_status :delete, "#{@home}/db/users.db", :green
227
+ end
228
+ end
229
+
230
+ def pagination
231
+ @sql.execute_batch <<-SQL
232
+ CREATE TABLE Pagination (
233
+ name TEXT,
234
+ post_id INTEGER
235
+ );
236
+ SQL
237
+ @sql.reload_schema!
238
+ if File.exist?(@pagination_old)
239
+ @thor.say_status :import, "Pagination database", :cyan
240
+ @sql.transaction do |db_in_transaction|
241
+ @pagination.each do |k,v|
242
+ insert_data = {}
243
+ insert_data[":post_id"] = v.to_i
244
+ insert_data[":name"] = k.to_s
245
+ db_in_transaction.prepare("INSERT INTO Pagination(name, post_id) VALUES(:name, :post_id);") do |insert|
246
+ insert.execute(insert_data)
247
+ end
248
+ end
249
+ end
250
+ @thor.say_status :done, "#{@pagination.size} objects", :green
251
+ @pagination.close
252
+ File.delete(@pagination_old)
253
+ @thor.say_status :delete, @pagination_old, :green
254
+ end
255
+ end
256
+
257
+ def index
258
+ @sql.execute_batch <<-SQL
259
+ CREATE TABLE TLIndex (
260
+ count INTEGER,
261
+ post_id INTEGER,
262
+ content TEXT
263
+ );
264
+ SQL
265
+ @sql.reload_schema!
266
+ if File.exist?(@index_old)
267
+ @thor.say_status :import, "Index database", :cyan
268
+ @sql.transaction do |db_in_transaction|
269
+ @index.each do |k,v|
270
+ insert_data = {}
271
+ insert_data[":post_id"] = v[:id]
272
+ insert_data[":count"] = v[:count]
273
+ insert_data[":content"] = v.to_json.to_s
274
+ db_in_transaction.prepare("INSERT INTO TLIndex(count, post_id, content) VALUES(:count, :post_id, :content);") do |insert|
275
+ insert.execute(insert_data)
276
+ end
277
+ end
278
+ end
279
+ @thor.say_status :done, "#{@index.size} objects", :green
280
+ @index.close
281
+ File.delete(@index_old)
282
+ @thor.say_status :delete, @index_old, :green
283
+ Dir.rmdir("#{@home}/pagination")
284
+ @thor.say_status :delete, "#{@home}/pagination", :green
285
+ end
286
+ end
287
+
288
+ def accounts
289
+ @thor.say_status :create, Dir.home + "/ayadn/accounts.sqlite", :blue
290
+ sql = Amalgalite::Database.new(Dir.home + "/ayadn/accounts.sqlite")
291
+ @thor.say_status :import, "account informations", :cyan
292
+ if sql.schema.tables.empty?
293
+ sql.execute_batch <<-SQL
294
+ CREATE TABLE Accounts (
295
+ username VARCHAR(20),
296
+ user_id INTEGER,
297
+ handle VARCHAR(21),
298
+ account_path TEXT,
299
+ active INTEGER,
300
+ token TEXT
301
+ );
302
+ SQL
303
+ sql.reload_schema!
304
+ end
305
+ active, active_account = ""
306
+ @accounts.each do |k,v|
307
+ if k == "ACTIVE"
308
+ active_account = v
309
+ next
310
+ end
311
+ end
312
+ actives = sql.execute("SELECT user_id FROM Accounts WHERE active=1")
313
+ sql.execute("UPDATE Accounts SET active=0") unless actives.empty?
314
+ sql.transaction do |db_in_transaction|
315
+ active = [@accounts[active_account]]
316
+ @thor.say_status :delete, "old @#{active_account} account", :green
317
+ @accounts.delete(active_account)
318
+ if @accounts.size == 1 # only the 'ACTIVE' label, so it's like 0
319
+ @accounts.close
320
+ File.delete(Dir.home + "/ayadn/accounts.db")
321
+ @thor.say_status :delete, Dir.home + "/ayadn/accounts.db", :green
322
+ else
323
+ @accounts.each do |k,v|
324
+ next if k == "ACTIVE"
325
+ @accounts['ACTIVE'] = v[:username]
326
+ @still = v[:username]
327
+ break
328
+ end
329
+ @accounts.close
330
+ end
331
+ active.each do |obj|
332
+ insert_data = {}
333
+ insert_data[":username"] = obj[:username]
334
+ insert_data[":user_id"] = obj[:id].to_i
335
+ insert_data[":handle"] = obj[:handle]
336
+ insert_data[":account_path"] = obj[:path]
337
+ insert_data[":active"] = 1
338
+ template = Dir.home + "/ayadn/#{obj[:username]}/auth/token"
339
+ insert_data[":token"] = File.read(template)
340
+ db_in_transaction.prepare("INSERT INTO Accounts(username, user_id, handle, account_path, active, token) VALUES(:username, :user_id, :handle, :account_path, :active, :token);") do |insert|
341
+ insert.execute(insert_data)
342
+ end
343
+ end
344
+ end
345
+ @thor.say_status :imported, "@#{active_account} account", :green
346
+ end
347
+
348
+ def config
349
+ @thor.say_status :load, "config file", :blue
350
+ old_conf = YAML.load(File.read(@config_path_old))
351
+ conf = Settings.defaults
352
+ @thor.say_status :convert, "settings", :cyan
353
+ conf[:timeline][:source] = old_conf[:timeline][:show_source] || true
354
+ conf[:timeline][:symbols] = old_conf[:timeline][:show_symbols] || true
355
+ conf[:timeline][:name] = old_conf[:timeline][:show_real_name] || true
356
+ conf[:timeline][:date] = old_conf[:timeline][:show_date] || true
357
+ conf[:timeline][:debug] = old_conf[:timeline][:show_debug] || false
358
+ conf[:timeline][:compact] = old_conf[:timeline][:compact] || false
359
+ if old_conf[:timeline][:directed] == 1 || old_conf[:timeline][:directed] == true
360
+ conf[:timeline][:directed] = true
361
+ else
362
+ conf[:timeline][:directed] = false
363
+ end
364
+ conf[:marker][:messages] = old_conf[:marker][:update_messages] || true
365
+ conf[:backup][:posts] = old_conf[:backup][:auto_save_sent_posts] || false
366
+ conf[:backup][:messages] = old_conf[:backup][:auto_save_sent_messages] || false
367
+ conf[:backup][:lists] = old_conf[:backup][:auto_save_lists] || false
368
+ conf[:colors][:id] = old_conf[:colors][:id] || :blue
369
+ conf[:colors][:index] = old_conf[:colors][:index] || :red
370
+ conf[:colors][:username] = old_conf[:colors][:username] || :green
371
+ conf[:colors][:name] = old_conf[:colors][:name] || :magenta
372
+ conf[:colors][:debug] = old_conf[:colors][:debug] || :red
373
+ conf[:colors][:date] = old_conf[:colors][:date] || :cyan
374
+ conf[:colors][:link] = old_conf[:colors][:link] || :yellow
375
+ conf[:colors][:dots] = old_conf[:colors][:dots] || :blue
376
+ conf[:colors][:hashtags] = old_conf[:colors][:hashtags] || :cyan
377
+ conf[:colors][:debug] = old_conf[:colors][:debug] || :red
378
+ conf[:colors][:mentions] = old_conf[:colors][:mentions] || :red
379
+ conf[:colors][:source] = old_conf[:colors][:source] || :cyan
380
+ conf[:colors][:symbols] = old_conf[:colors][:symbols] || :green
381
+ conf[:colors][:unread] = old_conf[:colors][:unread] || :cyan
382
+ conf[:formats][:list] = old_conf[:formats][:list] || {}
383
+ conf[:formats][:list][:reverse] = old_conf[:formats][:list][:reverse] || true
384
+ conf[:formats][:table] = old_conf[:formats][:table] || {}
385
+ conf[:formats][:table][:width] = old_conf[:formats][:table][:width] || 75
386
+ conf[:formats][:table][:borders] = old_conf[:formats][:table][:borders] || true
387
+ conf[:scroll][:spinner] = old_conf[:timeline][:show_spinner] || true
388
+ conf[:scroll][:timer] = old_conf[:scroll][:timer] || 3
389
+ conf[:movie][:hashtag] = old_conf[:movie][:hashtag] || 'nowwatching'
390
+ conf[:tvshow][:hashtag] = old_conf[:tvshow][:hashtag] || 'nowwatching'
391
+ conf[:channels][:links] = old_conf[:timeline][:show_channel_oembed] || true
392
+ conf[:nicerank][:threshold] = old_conf[:nicerank][:threshold] || 2.1
393
+ conf[:nicerank][:filter] = old_conf[:nicerank][:filter] || true
394
+ conf[:counts][:defaults] = old_conf[:counts][:defaults] || 50
395
+ conf[:counts][:unified] = old_conf[:counts][:unified] || 50
396
+ conf[:counts][:global] = old_conf[:counts][:global] || 50
397
+ conf[:counts][:checkins] = old_conf[:counts][:checkins] || 50
398
+ conf[:counts][:conversations] = old_conf[:counts][:conversations] || 50
399
+ conf[:counts][:photos] = old_conf[:counts][:photos] || 50
400
+ conf[:counts][:trending] = old_conf[:counts][:trending] || 50
401
+ conf[:counts][:mentions] = old_conf[:counts][:mentions] || 50
402
+ conf[:counts][:convo] = old_conf[:counts][:convo] || 50
403
+ conf[:counts][:posts] = old_conf[:counts][:posts] || 50
404
+ conf[:counts][:messages] = old_conf[:counts][:messages] || 50
405
+ conf[:counts][:search] = old_conf[:counts][:search] || 200
406
+ conf[:counts][:whoreposted] = old_conf[:counts][:whoreposted] || 20
407
+ conf[:counts][:whostarred] = old_conf[:counts][:whostarred] || 20
408
+ conf[:counts][:whatstarred] = old_conf[:counts][:whatstarred] || 100
409
+ conf[:counts][:files] = old_conf[:counts][:files] || 50
410
+ @thor.say_status :save, "config file", :green
411
+ File.write(@config_path_old, conf.to_yaml)
412
+ end
413
+
414
+ def banner
415
+ <<-BANNER
416
+
417
+ \t\t _____ __ __ _____ ____ _____
418
+ \t\t | _ | | | _ | \\| | |
419
+ \t\t | |_ _| | | | | | |
420
+ \t\t |__|__| |_| |__|__|____/|_|___|
421
+
422
+
423
+ BANNER
424
+ end
425
+
426
+ end
427
+ end
@@ -2,10 +2,81 @@
2
2
  module Ayadn
3
3
  class NiceRank
4
4
 
5
+ attr_reader :store
6
+
5
7
  def initialize
6
8
  @url = 'http://api.nice.social/user/nicerank?ids='
9
+ @store = FastCache::Cache.new(5_000, 120*60) # 5000 items with 2 hours TTL each
10
+ @hits = 0
11
+ @ids = 0
12
+ @posts = 0
13
+ end
14
+
15
+ # Get posts
16
+ # Get unique posters
17
+ # Get NR response
18
+ # Fetch IDs from store
19
+ # if absent, decode + save to dic + cache in store
20
+ # if present, save to dic from store (and count hits for debug)
21
+ def get_ranks stream
22
+ user_ids, niceranks = [], {}
23
+ stream['data'].each do |post|
24
+ id = post['user']['id']
25
+ user_ids << id if @store[id].nil?
26
+ end
27
+ user_ids.uniq!
28
+ got = CNX.get "#{@url}#{user_ids.join(',')}&show_details=Y" unless user_ids.empty?
29
+ if got.nil? || got == ""
30
+ parsed = {'meta' => {'code' => 404}, 'data' => []}
31
+ else
32
+ parsed = JSON.parse(got)
33
+ end
34
+ parsed['data'].each do |obj|
35
+ res = @store[obj['user_id']]
36
+ if res.nil?
37
+ obj['account']['is_human'] == true ? is_human = 1 : is_human = 0
38
+ obj['account']['real_person'] == true ? real_person = 1 : real_person = 0
39
+ content = {
40
+ username: obj['user']['username'],
41
+ rank: obj['rank'],
42
+ is_human: is_human,
43
+ real_person: real_person
44
+ }
45
+ @store[obj['user_id']] = content
46
+ niceranks[obj['user_id']] = content
47
+ else
48
+ @hits += 1
49
+ niceranks[obj['user_id']] = res
50
+ end
51
+
52
+ end
53
+
54
+ @posts += stream['data'].size
55
+ @ids += user_ids.size
56
+
57
+ if Settings.options[:timeline][:debug] == true
58
+ deb = "\n"
59
+ deb << "+ NICERANK\n"
60
+ deb << "* t#{Time.now.to_i}\n"
61
+ deb << "Posts:\t\t#{stream['data'].size}\n"
62
+ deb << "Requested NR:\t#{user_ids.size}\n"
63
+ deb << "* TOTALS\n"
64
+ deb << "Posts:\t\t#{@posts}\n"
65
+ deb << "Fetched ranks:\t#{@ids}\n"
66
+ deb << "DB hits:\t#{@hits}\n"
67
+ deb << "Uniques:\t#{@store.count}\n"
68
+ deb << "\n"
69
+ puts deb.color(Settings.options[:colors][:debug])
70
+ Logs.rec.debug "NICERANK/POSTS: #{@posts}"
71
+ Logs.rec.debug "NICERANK/NR CALLS: #{@ids}"
72
+ Logs.rec.debug "NICERANK/CACHE HITS: #{@hits}"
73
+ Logs.rec.debug "NICERANK/CACHED IDS: #{@store.count}"
74
+ end
75
+
76
+ return niceranks
7
77
  end
8
78
 
79
+ # This is for user info, no scrolling: no need to cache
9
80
  def get_posts_day ids
10
81
  resp = JSON.parse(CNX.get("#{@url}#{ids.join(',')}&show_details=Y"))
11
82
  if resp.nil? || resp['meta']['code'] != 200
@@ -21,6 +92,9 @@ module Ayadn
21
92
  end
22
93
  end
23
94
 
95
+ # This is for user lists, no scrolling: no need to cache
96
+ # Even with a lot of requests, it's within the NR limits
97
+ # because of the slicing (upto 200 objects / call)
24
98
  def from_ids ids
25
99
  blocs, ranks = [], []
26
100
  blank = JSON.parse({'meta' => {'code' => 404}, 'data' => []}.to_json)
@@ -39,77 +113,5 @@ module Ayadn
39
113
  return ranks.flatten!
40
114
  end
41
115
 
42
- def get_ranks stream
43
- user_ids, get_these, table, niceranks = [], [], {}, {}
44
-
45
- stream['data'].each do |post|
46
- user_ids << post['user']['id'].to_i
47
- table[post['user']['id'].to_i] = post['user']['username']
48
- end
49
- user_ids.uniq!
50
-
51
- db_ranks = Databases.get_niceranks user_ids
52
- expire = Settings.options[:nicerank][:cache] * 3600 # Time.now needs seconds
53
-
54
- db_ranks.each do |id, ranks|
55
- if ranks.nil? || (Time.now - ranks[:cached]) > expire
56
- get_these << id
57
- else
58
- niceranks[id] = {
59
- username: ranks[:username],
60
- rank: ranks[:rank],
61
- is_human: ranks[:is_human],
62
- real_person: ranks[:real_person],
63
- cached: ranks[:cached]
64
- }
65
- end
66
- end
67
-
68
- Debug.how_many_ranks niceranks, get_these
69
-
70
- unless get_these.empty?
71
- got = CNX.get "#{@url}#{get_these.join(',')}&show_details=Y"
72
- blank = JSON.parse({'meta' => {'code' => 404}, 'data' => []}.to_json)
73
- if got.nil? || got == ""
74
- parsed = blank
75
- else
76
- parsed = JSON.parse(got)
77
- end
78
- if parsed['meta']['code'] != 200
79
- resp = blank
80
- else
81
- resp = parsed
82
- end
83
-
84
- if resp['meta']['code'] != 200
85
- Debug.niceranks_error resp
86
- Errors.nr "REQUESTED: #{get_these.join(' ')}"
87
- Errors.nr "RESPONSE: #{resp}"
88
- if niceranks
89
- Debug.ranks_pool niceranks
90
- return niceranks
91
- else
92
- return {}
93
- end
94
- end
95
-
96
- resp['data'].each do |obj|
97
- niceranks[obj['user_id']] = {
98
- username: table[obj['user_id']],
99
- rank: obj['rank'],
100
- is_human: obj['is_human'],
101
- real_person: obj['account']['real_person'],
102
- cached: Time.now
103
- }
104
- end
105
-
106
- Debug.total_ranks niceranks
107
- end
108
-
109
- Databases.add_niceranks niceranks
110
-
111
- niceranks
112
- end
113
-
114
116
  end
115
117
  end