zold 0.26.15 → 0.26.16

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5f13f402152afeb770656e632fff9b86f48f4bb99669da498b74f4d78e42dca9
4
- data.tar.gz: 26e4591a34a4b9b7405181b584df64e04290c62777620ccac4ebf5afa85d8270
3
+ metadata.gz: 7b0ae546cf6416b998bfd75490dae5b662d89c3e6e598958f1c73c86e51fda17
4
+ data.tar.gz: bcc69294f383f7832b3ac832742c89630eb7d8a880741aefd7c0397a88cb9042
5
5
  SHA512:
6
- metadata.gz: 3bb478289ca360a81006c2d7eeac834e87fe08805a7374086cd0996babb2099122ef769131ea98c8d59a6d2d2fa9ea9156db6a9457642a2b6dabd8efdbf56b8a
7
- data.tar.gz: 2b82edcc6fc0ebd2bbeea606ab24206dd6358bbf6472ddcb3ca7e5869f2b79df07253786e0f123abb56c2c3541999f465187e98eb4a1be6894245bd74b5af014
6
+ metadata.gz: f746fba3dad2802bce2170facba75809d44fee26f29cf61a95c1c74245c61668f1fd75fed47722ab50bfc7676093b287b16e4e1683b280f99fd18715321e8574
7
+ data.tar.gz: fe15c859e3ff938901b7ef369e80346dc005be4451e4c2abd2cd45bd778b0b5b8939c3d0201ae78e4802c8d3aec6475779d94ab96a12857eec61e3e8d9476a7b
data/.rubocop.yml CHANGED
@@ -20,7 +20,7 @@ Metrics/BlockNesting:
20
20
  Metrics/BlockLength:
21
21
  Max: 130
22
22
  Metrics/ClassLength:
23
- Max: 500
23
+ Max: 600
24
24
  Layout/EndOfLine:
25
25
  EnforcedStyle: lf
26
26
  Metrics/ParameterLists:
@@ -171,7 +171,7 @@ run 'zold remote update' or use --tolerate-quorum=1"
171
171
  raise "The balance of #{id} is #{wallet.balance} and it's not a root wallet"
172
172
  end
173
173
  copy = cps.add(IO.read(f), score.host, score.port, score.value, master: r.master?)
174
- @log.info("#{r} returned #{wallet.mnemo} #{Age.new(json['mtime'])}/#{json['copies']}c \
174
+ @log.debug("#{r} returned #{wallet.mnemo} #{Age.new(json['mtime'])}/#{json['copies']}c \
175
175
  as copy ##{copy}/#{cps.all.count} in #{Age.new(start, limit: 4)}: \
176
176
  #{Rainbow(score.value).green} (#{json['version']})")
177
177
  end
@@ -45,6 +45,7 @@ require_relative '../node/async_entrance'
45
45
  require_relative '../node/sync_entrance'
46
46
  require_relative '../node/nodup_entrance'
47
47
  require_relative '../node/nospam_entrance'
48
+ require_relative '../node/journaled_entrance'
48
49
  require_relative '../node/front'
49
50
  require_relative '../node/trace'
50
51
  require_relative '../node/farm'
@@ -235,10 +236,10 @@ the node won\'t connect to the network like that; try to do "zold remote reset"
235
236
  #{@remotes.all.map { |r| "#{r[:host]}:#{r[:port]}" }.join(', ')}")
236
237
  @log.info("Wallets at: #{@wallets.path}")
237
238
  if opts['standalone']
238
- @remotes = Zold::Remotes::Empty.new
239
+ @remotes = Remotes::Empty.new
239
240
  @log.info('Running in standalone mode! (will never talk to other remotes)')
240
241
  elsif @remotes.exists?(host, port)
241
- Zold::Remote.new(remotes: @remotes).run(['remote', 'remove', host, port.to_s])
242
+ Remote.new(remotes: @remotes).run(['remote', 'remove', host, port.to_s])
242
243
  @log.info("Removed current node (#{address}) from list of remotes")
243
244
  end
244
245
  if File.exist?(@copies)
@@ -249,8 +250,8 @@ the node won\'t connect to the network like that; try to do "zold remote reset"
249
250
  if opts['not-hungry']
250
251
  @log.info('Hungry pulling disabled because of --not-hungry')
251
252
  else
252
- hungry = Zold::ThreadPool.new('hungry', log: @log)
253
- wts = Zold::HungryWallets.new(@wallets, @remotes, @copies, hungry, log: @log, network: opts['network'])
253
+ hungry = ThreadPool.new('hungry', log: @log)
254
+ wts = HungryWallets.new(@wallets, @remotes, @copies, hungry, log: @log, network: opts['network'])
254
255
  end
255
256
  Front.set(:zache, Zache.new(dirty: true))
256
257
  Front.set(:wallets, wts)
@@ -266,17 +267,29 @@ the node won\'t connect to the network like that; try to do "zold remote reset"
266
267
  async_dir = File.join(home, '.zoldata/async-entrance')
267
268
  FileUtils.mkdir_p(async_dir)
268
269
  Front.set(:async_dir, async_dir)
270
+ journal_dir = File.join(home, '.zoldata/journal')
271
+ FileUtils.mkdir_p(journal_dir)
272
+ Front.set(:journal_dir, journal_dir)
269
273
  Front.set(:node_alias, node_alias(opts, address))
274
+ jlog = Logger.new(File.join(journal_dir, 'journal'))
275
+ jlog.level = Logger::DEBUG
276
+ jlog.formatter = Log::COMPACT
270
277
  entrance = SafeEntrance.new(
271
278
  NoSpamEntrance.new(
272
279
  NoDupEntrance.new(
273
280
  AsyncEntrance.new(
274
281
  SpreadEntrance.new(
275
282
  SyncEntrance.new(
276
- Entrance.new(
277
- wts, @remotes, @copies, address,
278
- ledger: ledger,
279
- log: @log, network: opts['network']
283
+ JournaledEntrance.new(
284
+ Entrance.new(
285
+ wts, @remotes, @copies, address,
286
+ ledger: ledger,
287
+ log: Log::Tee.new(@log, jlog), network: opts['network']
288
+ ),
289
+ wts,
290
+ journal_dir,
291
+ jlog,
292
+ 'journal'
280
293
  ),
281
294
  File.join(home, '.zoldata/sync-entrance'),
282
295
  log: @log
@@ -135,10 +135,8 @@ out of #{nodes.value} in #{Age.new(start)}, total score for #{id} is #{total.val
135
135
  r.assert_valid_score(score)
136
136
  r.assert_score_ownership(score)
137
137
  r.assert_score_strength(score) unless opts['ignore-score-weakness']
138
- if @log.info?
139
- @log.info("#{r} accepted #{@wallets.acq(id, &:mnemo)} in #{Age.new(start, limit: 4)}: \
138
+ @log.debug("#{r} accepted #{@wallets.acq(id, &:mnemo)} in #{Age.new(start, limit: 4)}: \
140
139
  #{Rainbow(score.value).green} (#{json['version']})")
141
- end
142
140
  score.value
143
141
  end
144
142
  end
@@ -153,7 +151,7 @@ out of #{nodes.value} in #{Age.new(start)}, total score for #{id} is #{total.val
153
151
  r.http(uri).put(f)
154
152
  end
155
153
  if response.status == 304
156
- @log.info("#{r}: same version of #{@wallets.acq(id, &:mnemo)} there, didn't push \
154
+ @log.debug("#{r}: same version of #{@wallets.acq(id, &:mnemo)} there, didn't push \
157
155
  in #{Age.new(start, limit: 0.5)}")
158
156
  return 0
159
157
  end
@@ -164,7 +162,7 @@ in #{Age.new(start, limit: 0.5)}")
164
162
  rescue JsonPage::CantParse, Score::CantParse, RemoteNode::CantAssert => e
165
163
  attempt += 1
166
164
  if attempt < opts['retry']
167
- @log.error("#{r} failed to push #{id}, trying again (attempt no.#{attempt}): #{e.message}")
165
+ @log.debug("#{r} failed to push #{id}, trying again (attempt no.#{attempt}): #{e.message}")
168
166
  retry
169
167
  end
170
168
  raise e
@@ -316,7 +316,7 @@ Available options:"
316
316
  rescue JsonPage::CantParse, Score::CantParse, RemoteNode::CantAssert => e
317
317
  attempt += 1
318
318
  if attempt < opts['retry']
319
- @log.error("#{r} failed to read, trying again (attempt no.#{attempt}): #{e.message}")
319
+ @log.debug("#{r} failed to read, trying again (attempt no.#{attempt}): #{e.message}")
320
320
  retry
321
321
  end
322
322
  raise e
@@ -354,7 +354,7 @@ it's recommended to reboot, but I don't do it because of --never-reboot")
354
354
  @remotes.remove(r[:host], r[:port])
355
355
  @log.debug("Remote #{r[:host]}:#{r[:port]}/#{r[:score]}/#{r[:errors]}e removed from the list")
356
356
  end
357
- @log.info("#{@remotes.all.count} remote nodes were selected to stay in the list")
357
+ @log.info("#{@remotes.all.count} best remote nodes were selected to stay in the list")
358
358
  end
359
359
 
360
360
  def terminate
@@ -368,7 +368,7 @@ it's recommended to reboot, but I don't do it because of --never-reboot")
368
368
  res = Http.new(uri: "http://#{host}:#{port}/version", network: opts['network']).get
369
369
  return true if res.status == 200
370
370
  raise "The node #{host}:#{port} is not responding, #{res.status}:#{res.status_line}" unless opts['ignore-ping']
371
- @log.error("The node #{host}:#{port} is not responding, #{res.status}:#{res.status_line}")
371
+ @log.error("The node #{host}:#{port} is not responding but we --ignore-ping, #{res.status}:#{res.status_line}")
372
372
  false
373
373
  end
374
374
  end
@@ -57,12 +57,13 @@ module Zold
57
57
  unless wallet.exists?
58
58
  if @queue.size > 256
59
59
  @log.error("Hungry queue is full with #{@queue.size} wallets, can't add #{id}")
60
- elsif @missed.exists?(id)
61
- @log.error("Hungry queue has seen #{id} just #{Age.new(@missed.mtime(id))} ago and it was not-found")
60
+ elsif @missed.exists?(id.to_s)
61
+ @log.debug("Hungry queue has seen #{id} just #{Age.new(@missed.mtime(id.to_s))} ago
62
+ (amoung #{@missed.size} others) and it was not found")
62
63
  else
63
64
  @mutex.synchronize do
64
65
  unless @queue.include?(id)
65
- @missed.put(id, lifetime: 5 * 60)
66
+ @missed.put(id.to_s, lifetime: 5 * 60)
66
67
  @queue << id
67
68
  @log.debug("Hungry queue got #{id}, at the pos no.#{@queue.size - 1}")
68
69
  end
@@ -85,7 +86,7 @@ module Zold
85
86
  Pull.new(wallets: @wallets, remotes: @remotes, copies: @copies, log: @log).run(
86
87
  ['pull', id.to_s, "--network=#{@network}", '--tolerate-edges', '--tolerate-quorum=1']
87
88
  )
88
- @missed.remove(id)
89
+ @missed.remove(id.to_s)
89
90
  rescue Fetch::Error => e
90
91
  @log.error("Can't hungry-pull #{id}: #{e.message}")
91
92
  end
data/lib/zold/log.rb CHANGED
@@ -104,5 +104,36 @@ module Zold
104
104
  ERRORS.level = Logger::ERROR
105
105
  ERRORS.formatter = COMPACT
106
106
  ERRORS.freeze
107
+
108
+ # Tee logger.
109
+ class Tee
110
+ def initialize(first, second)
111
+ @first = first
112
+ @second = second
113
+ end
114
+
115
+ def debug(msg)
116
+ @first.debug(msg)
117
+ @second.debug(msg)
118
+ end
119
+
120
+ def debug?
121
+ @first.debug? || @second.debug?
122
+ end
123
+
124
+ def info(msg)
125
+ @first.info(msg)
126
+ @second.info(msg)
127
+ end
128
+
129
+ def info?
130
+ @first.info? || @second.info?
131
+ end
132
+
133
+ def error(msg)
134
+ @first.error(msg)
135
+ @second.error(msg)
136
+ end
137
+ end
107
138
  end
108
139
  end
@@ -82,6 +82,7 @@ module Zold
82
82
  set :node_alias, nil # to be injected at node.rb
83
83
  set :zache, nil # to be injected at node.rb
84
84
  set :async_dir, nil # to be injected at node.rb
85
+ set :journal_dir, nil # to be injected at node.rb
85
86
  end
86
87
  use Rack::Deflater
87
88
 
@@ -136,7 +137,7 @@ while #{settings.address} is in '#{settings.opts['network']}'")
136
137
  headers['X-Zold-Thread'] = Thread.current.object_id.to_s
137
138
  unless @start.nil?
138
139
  if Time.now - @start > 1
139
- settings.log.info("Slow response to #{request.request_method} #{request.url} \
140
+ settings.log.debug("Slow response to #{request.request_method} #{request.url} \
140
141
  from #{request.ip} in #{Age.new(@start, limit: 1)}")
141
142
  end
142
143
  headers['X-Zold-Milliseconds'] = ((Time.now - @start) * 1000).round.to_s
@@ -317,6 +318,43 @@ this is not a normal behavior, you may want to report a bug to our GitHub reposi
317
318
  end
318
319
  end
319
320
 
321
+ get %r{/wallet/(?<id>[A-Fa-f0-9]{16})\.html} do
322
+ fetch do |wallet|
323
+ [
324
+ '<!DOCTYPE html><html><head>',
325
+ '<title>' + wallet.id.to_s + '</title>',
326
+ '<link href="https://cdn.jsdelivr.net/gh/yegor256/tacit@gh-pages/tacit-css-1.4.2.min.css" rel="stylesheet"/>',
327
+ '<style>table { width: 100%; } td, th { padding: 0.2em .4em }</style>',
328
+ '</head><body><section>',
329
+ "<p>#{wallet.network}<br/>",
330
+ "#{wallet.protocol}<br/>",
331
+ "#{wallet.id}<br/>",
332
+ "#{wallet.key.to_pub}</p>",
333
+ '<table><thead><tr><th>Id</th><th>Date</th><th>Amount</th><th>Wallet</th><th>Details</th></thead>',
334
+ '<tbody>',
335
+ wallet.txns.map do |t|
336
+ [
337
+ '<tr>',
338
+ '<td style="color:' + (t.amount.negative? ? 'red' : 'green') + "\">#{t.id}</td>",
339
+ "<td>#{t.date.utc.iso8601}</td>",
340
+ '<td style="text-align:right">' + t.amount.to_zld(4) + '</td>',
341
+ "<td><a href='/wallet/#{t.bnf}.html'>#{t.bnf}</td>",
342
+ "<td>#{t.details}</td>",
343
+ '</tr>'
344
+ ].join
345
+ end.join,
346
+ '<p>&mdash;<br/>',
347
+ "Balance: #{wallet.balance.to_zld(8)} ZLD (#{wallet.balance.to_i} zents)<br/>",
348
+ "Transactions: #{wallet.txns.count}<br/>",
349
+ "Taxes: #{Tax.new(wallet).paid} paid, the debt is #{Tax.new(wallet).debt}<br/>",
350
+ "File size: #{Size.new(wallet.size)}/#{wallet.size}, \
351
+ #{Copies.new(File.join(settings.copies, wallet.id)).all.count} copies<br/>",
352
+ "Modified: #{wallet.mtime.utc.iso8601} (#{Age.new(wallet.mtime.utc.iso8601)} ago)<br/>",
353
+ "Digest: #{wallet.digest}</p></section></body></html>"
354
+ ].join
355
+ end
356
+ end
357
+
320
358
  get %r{/wallet/(?<id>[A-Fa-f0-9]{16})\.bin} do
321
359
  fetch { |w| send_file(w.path) }
322
360
  end
@@ -442,6 +480,25 @@ this is not a normal behavior, you may want to report a bug to our GitHub reposi
442
480
  end.join("\n")
443
481
  end
444
482
 
483
+ get '/journal' do
484
+ content_type('text/html')
485
+ [
486
+ '<!DOCTYPE html><html><head>',
487
+ '<title>/journal</title>',
488
+ '<link href="https://cdn.jsdelivr.net/gh/yegor256/tacit@gh-pages/tacit-css-1.4.2.min.css" rel="stylesheet"/>',
489
+ '</head><body><section>',
490
+ DirItems.new(settings.journal_dir).fetch.sort.map do |f|
491
+ "<p><a href='/journal/item?id=#{f}'>#{f}</a></p>"
492
+ end.join,
493
+ '</section></body></html>'
494
+ ].join
495
+ end
496
+
497
+ get '/journal/item' do
498
+ content_type('text/plain')
499
+ IO.read(File.join(settings.journal_dir, params[:id]))
500
+ end
501
+
445
502
  not_found do
446
503
  status(404)
447
504
  content_type('text/plain')
@@ -0,0 +1,96 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (c) 2018-2019 Zerocracy, Inc.
4
+ #
5
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ # of this software and associated documentation files (the 'Software'), to deal
7
+ # in the Software without restriction, including without limitation the rights
8
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ # copies of the Software, and to permit persons to whom the Software is
10
+ # furnished to do so, subject to the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be included in all
13
+ # copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFINGEMENT. IN NO EVENT SHALL THE
18
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ # SOFTWARE.
22
+
23
+ require 'tempfile'
24
+ require_relative '../log'
25
+ require_relative '../remotes'
26
+ require_relative '../copies'
27
+ require_relative '../tax'
28
+ require_relative '../age'
29
+ require_relative '../commands/clean'
30
+ require_relative '../commands/merge'
31
+ require_relative '../commands/fetch'
32
+ require_relative '../commands/push'
33
+
34
+ # The entrance with journals.
35
+ # Author:: Yegor Bugayenko (yegor256@gmail.com)
36
+ # Copyright:: Copyright (c) 2018 Yegor Bugayenko
37
+ # License:: MIT
38
+ module Zold
39
+ # The entrance that keeps a journal for each wallet
40
+ class JournaledEntrance
41
+ # Decorated wallets
42
+ class Wallets < SimpleDelegator
43
+ def initialize(wallets, log)
44
+ @wallets = wallets
45
+ @log = log
46
+ super(wallets)
47
+ end
48
+
49
+ def acq(id, exclusive: false)
50
+ @wallets.acq(id, exclusive: exclusive) do |wallet|
51
+ return yield wallet unless exclusive
52
+ before = wallet.exists? ? IO.read(wallet.path) : ''
53
+ res = yield wallet
54
+ after = wallet.exists? ? IO.read(wallet.path) : ''
55
+ unless before == after
56
+ diff = Diffy::Diff.new(before, after, context: 0).to_s
57
+ @log.info("The wallet #{id} was modified:\n #{diff.gsub("\n", "\n ")}")
58
+ end
59
+ res
60
+ end
61
+ end
62
+ end
63
+
64
+ def initialize(entrance, wallets, dir, log, journal)
65
+ @wallets = JournaledEntrance::Wallets.new(wallets, log)
66
+ @entrance = entrance
67
+ @dir = File.expand_path(dir)
68
+ @log = log
69
+ @journal = File.join(@dir, journal)
70
+ end
71
+
72
+ def start
73
+ raise 'Block must be given to start()' unless block_given?
74
+ FileUtils.mkdir_p(@dir)
75
+ yield(self)
76
+ end
77
+
78
+ def to_json
79
+ @entrance.to_json.merge(
80
+ 'dir': @dir
81
+ )
82
+ end
83
+
84
+ # Returns a list of modifed wallets (as Zold::Id)
85
+ def push(id, body)
86
+ DirItems.new(@dir).fetch.each do |f|
87
+ f = File.join(@dir, f)
88
+ File.delete(f) if File.mtime(f) < Time.now - 24 * 60 * 60
89
+ end
90
+ @log.info("push(#{id}, #{body.length} bytes)")
91
+ modified = @entrance.push(id, body)
92
+ IO.write(File.join(@dir, "#{Time.now.utc.iso8601.gsub(/[^0-9]/, '-')}-#{id}"), IO.read(@journal))
93
+ modified
94
+ end
95
+ end
96
+ end
data/lib/zold/patch.rb CHANGED
@@ -172,7 +172,7 @@ doesn't have this transaction: \"#{txn.to_text}\"")
172
172
  end
173
173
  temp.refurbish
174
174
  if temp.balance.negative? && !temp.id.root? && !allow_negative_balance
175
- @log.info("The balance is negative, won't merge: #{wallet.mnemo}")
175
+ @log.info("The balance is negative, won't merge #{temp.mnemo} on top of #{wallet.mnemo}")
176
176
  else
177
177
  FileUtils.mkdir_p(File.dirname(file))
178
178
  IO.write(file, IO.read(f.path))
data/lib/zold/txn.rb CHANGED
@@ -128,7 +128,7 @@ module Zold
128
128
  end
129
129
 
130
130
  def to_text
131
- start = @amount.negative? ? "##{@id}" : '-'
131
+ start = @amount.negative? ? "##{@id}" : "(#{@id})"
132
132
  "#{start} #{@date.utc.iso8601} #{@amount} #{@bnf} #{@details}"
133
133
  end
134
134
 
data/lib/zold/version.rb CHANGED
@@ -25,7 +25,7 @@
25
25
  # Copyright:: Copyright (c) 2018 Yegor Bugayenko
26
26
  # License:: MIT
27
27
  module Zold
28
- VERSION = '0.26.15'
28
+ VERSION = '0.26.16'
29
29
  PROTOCOL = 2
30
30
  REPO = 'zold-io/zold'
31
31
  end
@@ -63,27 +63,6 @@ class TestMerge < Zold::Test
63
63
  end
64
64
  end
65
65
 
66
- def test_merges_into_empty_wallet
67
- FakeHome.new(log: test_log).run do |home|
68
- wallet = home.create_wallet
69
- first = home.create_wallet
70
- IO.write(first.path, IO.read(wallet.path))
71
- second = home.create_wallet
72
- IO.write(second.path, IO.read(wallet.path))
73
- Zold::Pay.new(wallets: home.wallets, copies: home.dir, remotes: home.remotes, log: test_log).run(
74
- ['pay', wallet.id.to_s, "NOPREFIX@#{Zold::Id.new}", '14.95', '--force', '--private-key=fixtures/id_rsa']
75
- )
76
- copies = home.copies(wallet)
77
- copies.add(IO.read(first.path), 'host-1', 80, 5)
78
- copies.add(IO.read(second.path), 'host-2', 80, 5)
79
- modified = Zold::Merge.new(wallets: home.wallets, remotes: home.remotes, copies: copies.root, log: test_log).run(
80
- ['merge', wallet.id.to_s]
81
- )
82
- assert(1, modified.count)
83
- assert(wallet.id, modified[0])
84
- end
85
- end
86
-
87
66
  def test_merges_with_a_broken_copy
88
67
  FakeHome.new(log: test_log).run do |home|
89
68
  wallet = home.create_wallet
@@ -45,7 +45,7 @@ class FrontTest < Zold::Test
45
45
  def test_memory_leakage
46
46
  skip
47
47
  report = MemoryProfiler.report(top: 10) do
48
- FakeNode.new(log: test_log).run(['--no-metronome', '--network=foo', '--threads=0']) do |port|
48
+ FakeNode.new(log: test_log).run(opts('--network=foo')) do |port|
49
49
  100.times do
50
50
  Zold::Http.new(uri: "http://localhost:#{port}/", network: 'foo').get
51
51
  end
@@ -55,7 +55,7 @@ class FrontTest < Zold::Test
55
55
  end
56
56
 
57
57
  def test_renders_front_json
58
- FakeNode.new(log: test_log).run(['--no-metronome', '--network=foo', '--threads=0']) do |port|
58
+ FakeNode.new(log: test_log).run(opts('--network=foo')) do |port|
59
59
  res = Zold::Http.new(uri: "http://localhost:#{port}/", network: 'foo').get
60
60
  json = JSON.parse(res.body)
61
61
  assert_equal(Zold::VERSION, json['version'])
@@ -73,7 +73,7 @@ class FrontTest < Zold::Test
73
73
  end
74
74
 
75
75
  def test_renders_public_pages
76
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--no-metronome', '--threads=0']) do |port|
76
+ FakeNode.new(log: test_log).run(opts) do |port|
77
77
  {
78
78
  200 => [
79
79
  '/robots.txt',
@@ -85,6 +85,7 @@ class FrontTest < Zold::Test
85
85
  '/ledger',
86
86
  '/ledger.json',
87
87
  '/metronome',
88
+ '/journal',
88
89
  '/score',
89
90
  '/queue',
90
91
  '/trace',
@@ -115,7 +116,7 @@ class FrontTest < Zold::Test
115
116
  end
116
117
 
117
118
  def test_updates_list_of_remotes
118
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--no-metronome', '--no-cache']) do |port|
119
+ FakeNode.new(log: test_log).run(['--no-metronome', '--ignore-score-weakness', '--no-cache']) do |port|
119
120
  (Zold::Remotes::MAX_NODES + 5).times do |i|
120
121
  score = Zold::Score.new(
121
122
  host: 'localhost', port: i + 1, invoice: 'NOPREFIX@ffffffffffffffff', strength: 1
@@ -136,7 +137,7 @@ class FrontTest < Zold::Test
136
137
  end
137
138
 
138
139
  def test_increments_score
139
- FakeNode.new(log: test_log).run(['--threads=1', '--strength=1', '--no-metronome', '--no-cache']) do |port|
140
+ FakeNode.new(log: test_log).run(opts('--threads=1')) do |port|
140
141
  3.times do |i|
141
142
  assert_equal_wait(true) do
142
143
  response = Zold::Http.new(uri: "http://localhost:#{port}/").get
@@ -150,28 +151,20 @@ class FrontTest < Zold::Test
150
151
 
151
152
  def test_renders_wallet_pages
152
153
  FakeHome.new(log: test_log).run do |home|
153
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--standalone']) do |port|
154
+ FakeNode.new(log: test_log).run(opts) do |port|
154
155
  wallet = home.create_wallet(txns: 2)
155
156
  base = "http://localhost:#{port}"
156
157
  response = Zold::Http.new(uri: "#{base}/wallet/#{wallet.id}").put(wallet.path)
157
158
  assert_equal(200, response.status, response.body)
158
159
  assert_equal_wait(200) { Zold::Http.new(uri: "#{base}/wallet/#{wallet.id}").get.status }
159
160
  [
160
- "/wallet/#{wallet.id}.txt",
161
- "/wallet/#{wallet.id}/balance",
162
- "/wallet/#{wallet.id}/key",
163
- "/wallet/#{wallet.id}/mtime",
164
- "/wallet/#{wallet.id}/digest",
165
- "/wallet/#{wallet.id}/size",
166
- "/wallet/#{wallet.id}/age",
167
- "/wallet/#{wallet.id}/mnemo",
168
- "/wallet/#{wallet.id}/debt",
169
- "/wallet/#{wallet.id}/txns",
170
- "/wallet/#{wallet.id}/txns.json",
171
- "/wallet/#{wallet.id}.bin",
172
- "/wallet/#{wallet.id}/copies"
161
+ '.txt', '.html',
162
+ '/balance', '/key', '/mtime',
163
+ '/digest', '/size',
164
+ '/age', '/mnemo', '/debt', '/txns',
165
+ '/txns.json', '.bin', '/copies'
173
166
  ].each do |u|
174
- assert_equal_wait(200) { Zold::Http.new(uri: "#{base}#{u}").get.status }
167
+ assert_equal_wait(200) { Zold::Http.new(uri: "#{base}/wallet/#{wallet.id}#{u}").get.status }
175
168
  end
176
169
  end
177
170
  end
@@ -179,7 +172,7 @@ class FrontTest < Zold::Test
179
172
 
180
173
  def test_renders_wallets_page
181
174
  FakeHome.new(log: test_log).run do |home|
182
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--standalone']) do |port|
175
+ FakeNode.new(log: test_log).run(opts) do |port|
183
176
  wallet = home.create_wallet(txns: 2)
184
177
  base = "http://localhost:#{port}"
185
178
  response = Zold::Http.new(uri: "#{base}/wallet/#{wallet.id}").put(wallet.path)
@@ -193,7 +186,7 @@ class FrontTest < Zold::Test
193
186
  end
194
187
 
195
188
  def test_fetch_in_multiple_threads
196
- FakeNode.new(log: test_log).run(['--no-metronome', '--threads=0', '--standalone']) do |port|
189
+ FakeNode.new(log: test_log).run(opts) do |port|
197
190
  FakeHome.new(log: test_log).run do |home|
198
191
  wallet = home.create_wallet
199
192
  base = "http://localhost:#{port}"
@@ -214,7 +207,7 @@ class FrontTest < Zold::Test
214
207
  end
215
208
 
216
209
  def test_pushes_twice
217
- FakeNode.new(log: test_log).run(['--no-metronome', '--threads=0', '--standalone']) do |port|
210
+ FakeNode.new(log: test_log).run(opts) do |port|
218
211
  FakeHome.new(log: test_log).run do |home|
219
212
  wallet = home.create_wallet
220
213
  base = "http://localhost:#{port}"
@@ -232,7 +225,7 @@ class FrontTest < Zold::Test
232
225
  end
233
226
 
234
227
  def test_pushes_many_wallets
235
- FakeNode.new(log: test_log).run(['--no-metronome', '--threads=0', '--standalone']) do |port|
228
+ FakeNode.new(log: test_log).run(opts) do |port|
236
229
  base = "http://localhost:#{port}"
237
230
  FakeHome.new(log: test_log).run do |home|
238
231
  Threads.new(5).assert do
@@ -278,7 +271,7 @@ class FrontTest < Zold::Test
278
271
  end
279
272
 
280
273
  def test_gzip
281
- FakeNode.new(log: test_log).run(['--ignore-score-weakness']) do |port|
274
+ FakeNode.new(log: test_log).run(opts) do |port|
282
275
  response = Zold::Http.new(uri: URI("http://localhost:#{port}/version")).get
283
276
  assert_equal(200, response.status, response)
284
277
  assert_operator(300, :>, response.body.length.to_i, 'Expected the content to be small')
@@ -287,7 +280,7 @@ class FrontTest < Zold::Test
287
280
 
288
281
  def test_performance
289
282
  times = Queue.new
290
- FakeNode.new(log: test_log).run(['--threads=4', '--strength=6', '--no-metronome']) do |port|
283
+ FakeNode.new(log: test_log).run(opts('--threads=4', '--strength=6')) do |port|
291
284
  Threads.new(10).assert(100) do
292
285
  start = Time.now
293
286
  Zold::Http.new(uri: URI("http://localhost:#{port}/")).get
@@ -304,7 +297,7 @@ class FrontTest < Zold::Test
304
297
  # HTTP request. This value is enough to identify a valueable node, and filter
305
298
  # out those that are too weak.
306
299
  def test_score_is_reduced
307
- FakeNode.new(log: test_log).run(['--threads=1', '--strength=1', '--no-metronome', '--farmer=plain']) do |port|
300
+ FakeNode.new(log: test_log).run(opts('--threads=1', '--strength=1', '--farmer=plain')) do |port|
308
301
  scores = []
309
302
  50.times do
310
303
  res = Zold::Http.new(uri: URI("http://localhost:#{port}/")).get
@@ -316,7 +309,7 @@ class FrontTest < Zold::Test
316
309
  end
317
310
 
318
311
  def test_headers_are_being_set_correctly
319
- FakeNode.new(log: test_log).run(['--expose-version=9.9.9', '--no-metronome', '--threads=0']) do |port|
312
+ FakeNode.new(log: test_log).run(opts('--expose-version=9.9.9')) do |port|
320
313
  response = Zold::Http.new(uri: URI("http://localhost:#{port}/")).get
321
314
  assert_equal('no-cache', response.headers['Cache-Control'])
322
315
  assert_equal('close', response.headers['Connection'])
@@ -330,7 +323,7 @@ class FrontTest < Zold::Test
330
323
 
331
324
  def test_alias_parameter
332
325
  name = SecureRandom.hex(4)
333
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', "--alias=#{name}"]) do |port|
326
+ FakeNode.new(log: test_log).run(opts("--alias=#{name}")) do |port|
334
327
  uri = URI("http://localhost:#{port}/")
335
328
  response = Zold::Http.new(uri: uri).get
336
329
  assert_match(
@@ -342,7 +335,7 @@ class FrontTest < Zold::Test
342
335
  end
343
336
 
344
337
  def test_default_alias_parameter
345
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--no-metronome']) do |port|
338
+ FakeNode.new(log: test_log).run(opts) do |port|
346
339
  uri = URI("http://localhost:#{port}/")
347
340
  response = Zold::Http.new(uri: uri).get
348
341
  assert_match(
@@ -355,7 +348,7 @@ class FrontTest < Zold::Test
355
348
 
356
349
  def test_invalid_alias
357
350
  exception = assert_raises RuntimeError do
358
- FakeNode.new(log: test_log).run(['--ignore-score-weakness', '--alias=invalid-alias']) do |port|
351
+ FakeNode.new(log: test_log).run(opts('--alias=invalid-alias')) do |port|
359
352
  uri = URI("http://localhost:#{port}/")
360
353
  Zold::Http.new(uri: uri).get
361
354
  end
@@ -365,7 +358,7 @@ class FrontTest < Zold::Test
365
358
 
366
359
  def test_push_fetch_in_multiple_threads
367
360
  key = Zold::Key.new(text: IO.read('fixtures/id_rsa'))
368
- FakeNode.new(log: test_log).run(['--no-metronome', '--threads=0', '--standalone']) do |port|
361
+ FakeNode.new(log: test_log).run(opts) do |port|
369
362
  FakeHome.new(log: test_log).run do |home|
370
363
  wallet = home.create_wallet(Zold::Id::ROOT)
371
364
  base = "http://localhost:#{port}"
@@ -383,4 +376,10 @@ class FrontTest < Zold::Test
383
376
  end
384
377
  end
385
378
  end
379
+
380
+ private
381
+
382
+ def opts(*extra)
383
+ ['--no-metronome', '--ignore-score-weakness', '--standalone', '--threads=0', '--strength=1'] + extra
384
+ end
386
385
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: zold
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.26.15
4
+ version: 0.26.16
5
5
  platform: ruby
6
6
  authors:
7
7
  - Yegor Bugayenko
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-03-12 00:00:00.000000000 Z
11
+ date: 2019-03-15 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: backtrace
@@ -671,6 +671,7 @@ files:
671
671
  - lib/zold/node/farm.rb
672
672
  - lib/zold/node/farmers.rb
673
673
  - lib/zold/node/front.rb
674
+ - lib/zold/node/journaled_entrance.rb
674
675
  - lib/zold/node/nodup_entrance.rb
675
676
  - lib/zold/node/nospam_entrance.rb
676
677
  - lib/zold/node/safe_entrance.rb
@@ -779,7 +780,7 @@ licenses:
779
780
  - MIT
780
781
  metadata: {}
781
782
  post_install_message: |-
782
- Thanks for installing Zold 0.26.15!
783
+ Thanks for installing Zold 0.26.16!
783
784
  Study our White Paper: https://papers.zold.io/wp.pdf
784
785
  Read our blog posts: https://blog.zold.io
785
786
  Try ZLD online wallet at: https://wts.zold.io