bitcoin 0.1.2 → 0.2.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.
Files changed (68) hide show
  1. metadata +17 -288
  2. data/.rspec +0 -1
  3. data/.rvmrc +0 -1
  4. data/Gemfile +0 -4
  5. data/Gemfile.lock +0 -98
  6. data/Guardfile +0 -38
  7. data/README.markdown +0 -24
  8. data/Rakefile +0 -1
  9. data/bin/rbcoin +0 -8
  10. data/bitcoin.gemspec +0 -40
  11. data/config/cucumber.yml +0 -5
  12. data/config/darcs.boring +0 -121
  13. data/doc/DEFINITION_OF_DONE.markdown +0 -12
  14. data/doc/HISTORY.markdown +0 -19
  15. data/doc/LICENCE.markdown +0 -25
  16. data/doc/TODO.markdown +0 -31
  17. data/doc/UBIQUITOUS_LANGUAGE.markdown +0 -15
  18. data/features/descriptions/command_help.feature +0 -31
  19. data/features/descriptions/satoshi_wallet/add_address.feature +0 -49
  20. data/features/descriptions/satoshi_wallet/show_addresses.feature +0 -18
  21. data/features/descriptions/satoshi_wallet/show_version.feature +0 -17
  22. data/features/descriptions/satoshi_wallet/subcommand_help.feature +0 -20
  23. data/features/fixtures/ABOUT_FIXTURES.markdown +0 -6
  24. data/features/fixtures/addressbook_wallet.dat +0 -0
  25. data/features/fixtures/new_wallet.dat +0 -0
  26. data/features/step_definitions/command_steps.rb +0 -3
  27. data/features/step_definitions/wallet_steps.rb +0 -11
  28. data/features/support/env.rb +0 -9
  29. data/lib/bitcoin.rb +0 -5
  30. data/lib/bitcoin/cli.rb +0 -35
  31. data/lib/bitcoin/commands.rb +0 -3
  32. data/lib/bitcoin/commands/help_command.rb +0 -32
  33. data/lib/bitcoin/commands/satoshi_wallet.rb +0 -11
  34. data/lib/bitcoin/commands/satoshi_wallet/add_address_command.rb +0 -61
  35. data/lib/bitcoin/commands/satoshi_wallet/show_addresses_command.rb +0 -16
  36. data/lib/bitcoin/commands/satoshi_wallet/show_version_command.rb +0 -15
  37. data/lib/bitcoin/commands/satoshi_wallet_command.rb +0 -37
  38. data/lib/bitcoin/commands/satoshi_wallet_command_environment.rb +0 -28
  39. data/lib/bitcoin/console/capturing_stream_bundle.rb +0 -42
  40. data/lib/bitcoin/console/stream_bundle.rb +0 -21
  41. data/lib/bitcoin/data_access/satoshi/bdb_satoshi_wallet_repository.rb +0 -155
  42. data/lib/bitcoin/data_access/satoshi/satoshi_version.rb +0 -58
  43. data/lib/bitcoin/data_access/satoshi/satoshi_wallet.rb +0 -39
  44. data/lib/bitcoin/domain/address_book.rb +0 -19
  45. data/lib/bitcoin/domain/bitcoin_address.rb +0 -33
  46. data/lib/bitcoin/filesystem/empty_temp_dir.rb +0 -74
  47. data/lib/bitcoin/rspec/argument_matchers.rb +0 -1
  48. data/lib/bitcoin/rspec/argument_matchers/block_evaluating_to_matcher.rb +0 -23
  49. data/lib/bitcoin/rspec/directory_helpers.rb +0 -22
  50. data/lib/bitcoin/version.rb +0 -3
  51. data/spec/bitcoin/cli_spec.rb +0 -128
  52. data/spec/bitcoin/commands/help_command_spec.rb +0 -53
  53. data/spec/bitcoin/commands/satoshi_wallet/add_address_command_spec.rb +0 -149
  54. data/spec/bitcoin/commands/satoshi_wallet/show_addresses_command_spec.rb +0 -26
  55. data/spec/bitcoin/commands/satoshi_wallet/show_version_command_spec.rb +0 -26
  56. data/spec/bitcoin/commands/satoshi_wallet_command_environment_spec.rb +0 -76
  57. data/spec/bitcoin/commands/satoshi_wallet_command_spec.rb +0 -73
  58. data/spec/bitcoin/console/_contracts/stream_bundle_contract.rb +0 -29
  59. data/spec/bitcoin/console/capturing_stream_bundle_spec.rb +0 -74
  60. data/spec/bitcoin/console/stream_bundle_spec.rb +0 -13
  61. data/spec/bitcoin/data_access/satoshi/bdb_satoshi_wallet_repository_spec.rb +0 -78
  62. data/spec/bitcoin/data_access/satoshi/satoshi_version_spec.rb +0 -112
  63. data/spec/bitcoin/data_access/satoshi/satoshi_wallet_spec.rb +0 -102
  64. data/spec/bitcoin/domain/address_book_spec.rb +0 -63
  65. data/spec/bitcoin/domain/bitcoin_address_spec.rb +0 -52
  66. data/spec/bitcoin/filesystem/empty_temp_dir_spec.rb +0 -170
  67. data/spec/bitcoin/rspec/argument_matchers/block_evaluating_to_matcher_spec.rb +0 -36
  68. data/spec/spec_helper.rb +0 -29
@@ -1,149 +0,0 @@
1
- # -*- encoding: utf-8 -*-
2
-
3
- require 'spec_helper'
4
-
5
- require 'bitcoin/commands/satoshi_wallet/add_address_command'
6
-
7
- # Dependencies required only in the spec
8
- require 'bitcoin/console/capturing_stream_bundle'
9
- require 'bitcoin/data_access/satoshi/satoshi_wallet'
10
-
11
- module Bitcoin
12
- module Commands
13
- module SatoshiWallet
14
- describe AddAddressCommand do
15
- let(:stream_bundle) { Console::CapturingStreamBundle.test_bundle }
16
- let(:wallet) { mock(DataAccess::Satoshi::SatoshiWallet, add_address: nil) }
17
-
18
- let(:subject) { AddAddressCommand.new(stream_bundle) }
19
-
20
- context "the input args are valid" do
21
- def run_command
22
- subject.run(wallet, args: [ "14Z1mazY4HfysZyMaKudFr63EwHqQT2njz", "Bitcoin Monitor" ])
23
- end
24
-
25
- it "adds the address" do
26
- wallet.should_receive(:add_address).with(
27
- Domain::BitcoinAddress.new("14Z1mazY4HfysZyMaKudFr63EwHqQT2njz"),
28
- name: "Bitcoin Monitor"
29
- )
30
- run_command
31
- end
32
-
33
- it "informs the user that the address was added" do
34
- run_command
35
- stream_bundle.captured_output.should eq "Address added successfully\n"
36
- end
37
- end
38
-
39
- context "the input args are invalid" do
40
- context "missing arguments" do
41
- invalid_arg_sets = [
42
- %w[ ], # Pressed enter too soon
43
- %w[ 14Z1mazY4HfysZyMaKudFr63EwHqQT2njz ] # Missing name
44
- ]
45
-
46
- invalid_arg_sets.each do |invalid_args|
47
- it "prints an error message" do
48
- expect {
49
- subject.run(wallet, args: invalid_args)
50
- }.to raise_error
51
-
52
- stream_bundle.captured_error.should include("You must provide both a Bitcoin address and a name to add to a wallet")
53
- stream_bundle.captured_error.should =~ /No changes were made to the wallet\n\Z/
54
- end
55
-
56
- it "raises an error" do
57
- expect {
58
- subject.run(wallet, args: invalid_args)
59
- }.to raise_error(CLI::CommandError)
60
- end
61
- end
62
- end
63
-
64
- context "too many args" do
65
- def run_command
66
- subject.run(wallet, args: %w[ 14Z1mazY4HfysZyMaKudFr63EwHqQT2njz foo bar baz ])
67
- end
68
-
69
- it "prints a helpful error message" do
70
- expect { run_command }.to raise_error
71
-
72
- stream_bundle.captured_error.should include(
73
- -%{
74
- Received too many arguments
75
-
76
- To make sure the name is formatted correctly we ask you to use use quotes
77
- around the name, e.g.: "foo bar baz"
78
-
79
- No changes were made to the wallet
80
- }
81
- )
82
- stream_bundle.captured_error.should =~ /\n\Z/
83
- end
84
-
85
- it "raises an error" do
86
- expect { run_command }.to raise_error(CLI::CommandError)
87
- end
88
- end
89
-
90
- context "invalid Bitcoin address" do
91
- def run_command
92
- subject.run(wallet, args: [ "Invalid Bitcoin address", "Bitcoin Monitor" ])
93
- end
94
-
95
- it "prints an error message" do
96
- expect {
97
- run_command
98
- }.to raise_error
99
-
100
- # Ugh! There's got to be a better way of getting the error message than this,
101
- # hopefully without having to stub out the creating of a value object...
102
- expected_error =
103
- begin
104
- Domain::BitcoinAddress.new("Invalid Bitcoin address")
105
- rescue Domain::BitcoinAddress::InvalidBitcoinAddressError => error
106
- error.message
107
- end
108
-
109
- stream_bundle.captured_error.should include(error.message)
110
- stream_bundle.captured_error.should =~ /The address was not added to the wallet\n\Z/
111
- end
112
-
113
- it "raises an error" do
114
- expect {
115
- run_command
116
- }.to raise_error(CLI::CommandError)
117
- end
118
- end
119
-
120
- # This is paranoid, but currently we don't handle string length properly in the Berkeley DB code
121
- # (This error handling is not publically documented)
122
- context "excessively long names" do
123
- string_253_bytes_long = "#{"☃" * 84}."
124
-
125
- define_method :run_command do
126
- subject.run(wallet, args: [ "14Z1mazY4HfysZyMaKudFr63EwHqQT2njz", string_253_bytes_long ])
127
- end
128
-
129
- it "prints an error message" do
130
- expect {
131
- run_command
132
- }.to raise_error
133
-
134
- stream_bundle.captured_error.should include(%'The address name "#{string_253_bytes_long}" is too long\n')
135
- stream_bundle.captured_error.should include("Currently we do not allow address names over 252 bytes long\n")
136
- stream_bundle.captured_error.should =~ /The address was not added to the wallet\n\Z/
137
- end
138
-
139
- it "raises an error" do
140
- expect {
141
- run_command
142
- }.to raise_error(CLI::CommandError)
143
- end
144
- end
145
- end
146
- end
147
- end
148
- end
149
- end
@@ -1,26 +0,0 @@
1
- require 'spec_helper'
2
-
3
- require 'bitcoin/commands/satoshi_wallet/show_addresses_command'
4
-
5
- # Dependencies required only in the spec
6
- require 'bitcoin/console/capturing_stream_bundle'
7
- require 'bitcoin/data_access/satoshi/satoshi_wallet'
8
-
9
- module Bitcoin
10
- module Commands
11
- module SatoshiWallet
12
- describe ShowAddressesCommand do
13
- let(:stream_bundle) { Console::CapturingStreamBundle.test_bundle }
14
- let(:address_book) { mock(Domain::AddressBook, to_s: "addresses") }
15
- let(:wallet) { mock(DataAccess::Satoshi::SatoshiWallet, addresses: address_book) }
16
-
17
- let(:subject) { ShowAddressesCommand.new(stream_bundle) }
18
-
19
- it "prints the addresses to the output stream" do
20
- subject.run(wallet, wallet_filename: "wallet.dat")
21
- stream_bundle.captured_output.should eq "# All addresses in wallet.dat\naddresses\n"
22
- end
23
- end
24
- end
25
- end
26
- end
@@ -1,26 +0,0 @@
1
- require 'spec_helper'
2
-
3
- require 'bitcoin/commands/satoshi_wallet/show_version_command'
4
-
5
- # Dependencies required only in the spec
6
- require 'bitcoin/console/capturing_stream_bundle'
7
- require 'bitcoin/data_access/satoshi/satoshi_version'
8
- require 'bitcoin/data_access/satoshi/satoshi_wallet'
9
-
10
- module Bitcoin
11
- module Commands
12
- module SatoshiWallet
13
- describe ShowVersionCommand do
14
- let(:stream_bundle) { Console::CapturingStreamBundle.test_bundle }
15
- let(:wallet) { mock(DataAccess::Satoshi::SatoshiWallet, version: DataAccess::Satoshi::SatoshiVersion.new(0, 3, 24)) }
16
-
17
- let(:subject) { ShowVersionCommand.new(stream_bundle) }
18
-
19
- it "prints the wallet's version" do
20
- subject.run(wallet)
21
- stream_bundle.captured_output.should eq "0.3.24\n"
22
- end
23
- end
24
- end
25
- end
26
- end
@@ -1,76 +0,0 @@
1
- require 'spec_helper'
2
-
3
- require 'bitcoin/commands/satoshi_wallet_command_environment'
4
-
5
- # Dependencies required only in the spec
6
- require 'bitcoin/data_access/satoshi/satoshi_wallet'
7
- require 'bitcoin/console/capturing_stream_bundle'
8
-
9
- module Bitcoin
10
- module Commands
11
- describe SatoshiWalletCommandEnvironment do
12
- include FakeFS::SpecHelpers
13
-
14
- let(:empty_temp_dir) { mock(FileSystem::EmptyTempDir, absolute_path: "/path/to/temp/dir") }
15
- let(:satoshi_wallet) { mock(DataAccess::Satoshi::SatoshiWallet) }
16
-
17
- before(:each) do
18
- FileSystem::EmptyTempDir.stub(:open).and_yield(empty_temp_dir)
19
- DataAccess::Satoshi::SatoshiWallet.stub(:open).and_yield(satoshi_wallet)
20
- end
21
-
22
- let(:command) { mock(Commands::SatoshiWallet, run: nil) }
23
- let(:stream_bundle) { Console::CapturingStreamBundle.test_bundle }
24
-
25
- subject { SatoshiWalletCommandEnvironment.new(stream_bundle) }
26
-
27
- context "the wallet file exists" do
28
- before(:each) { File.open("wallet.dat", "w") { |file| file << "unused wallet data" } }
29
-
30
- it "create temp dir" do
31
- FileSystem::EmptyTempDir.should_receive(:open).with(with_name: "bitcoinrb_db_tmp", parallel_to: PROJECT_ROOT + "/wallet.dat")
32
- subject.run_command(command, %w[ wallet.dat foo bar ])
33
- end
34
-
35
- it "opens the wallet" do
36
- DataAccess::Satoshi::SatoshiWallet.should_receive(:open).with(
37
- wallet_filename: File.join(PROJECT_ROOT, "/wallet.dat"), # because this is the directory the specs run in
38
- db_dirname: "/path/to/temp/dir"
39
- )
40
- subject.run_command(command, %w[ wallet.dat foo bar ])
41
- end
42
-
43
- it "runs the command" do
44
- command.should_receive(:run).with(satoshi_wallet, wallet_filename: "wallet.dat", args: %w[ foo bar ])
45
- subject.run_command(command, %w[ wallet.dat foo bar ])
46
- end
47
- end
48
-
49
- context "the wallet file does not exist" do
50
- it "prints an error" do
51
- expect {
52
- subject.run_command(command, %w[ missing_wallet.dat foo bar ])
53
- }.to raise_error
54
-
55
- stream_bundle.captured_error.should eq "Couldn't find wallet file: missing_wallet.dat\n"
56
- end
57
-
58
- it "raises a CLI::CommandError" do
59
- expect {
60
- subject.run_command(command, %w[ missing_wallet.dat foo bar ])
61
- }.to raise_error(CLI::CommandError)
62
- end
63
-
64
- it "does not attempt the rest of the code" do
65
- # Although this does involve a lot of knowledge about the code, as
66
- # it's not immediately obvious why this proves nothing else is run
67
- FileSystem::EmptyTempDir.should_not_receive(:open)
68
-
69
- expect {
70
- subject.run_command(command, %w[ missing_wallet.dat foo bar ])
71
- }.to raise_error
72
- end
73
- end
74
- end
75
- end
76
- end
@@ -1,73 +0,0 @@
1
- require 'spec_helper'
2
-
3
- require 'bitcoin/commands/satoshi_wallet_command'
4
-
5
- # Dependencies only used in the spec
6
- require 'bitcoin/domain/address_book'
7
- require 'bitcoin/console/capturing_stream_bundle'
8
- require 'bitcoin/commands/satoshi_wallet_command_environment'
9
-
10
- module Bitcoin
11
- module Commands
12
- describe SatoshiWalletCommand do
13
- let(:stream_bundle) { Console::CapturingStreamBundle.test_bundle }
14
- let(:command_environment) { mock(SatoshiWalletCommandEnvironment, run_command: nil) }
15
-
16
- subject { SatoshiWalletCommand.new(stream_bundle, command_environment) }
17
-
18
- describe "#run" do
19
- shared_examples_for "SatoshiWalletCommand#run" do |options|
20
- let(:command) { mock(options[:command_class]) }
21
-
22
- before(:each) do
23
- options[:command_class].stub(new: command)
24
- end
25
-
26
- it "makes a command" do
27
- options[:command_class].should_receive(:new).with(stream_bundle)
28
- subject.run([ options[:command_name], "wallet.dat", "foo", "bar" ])
29
- end
30
-
31
- it "runs the command" do
32
- command_environment.should_receive(:run_command).with(command, %w[ wallet.dat foo bar ])
33
- subject.run([ options[:command_name], "wallet.dat", "foo", "bar" ])
34
- end
35
- end
36
-
37
- context "show-version" do
38
- it_behaves_like "SatoshiWalletCommand#run",
39
- command_name: "show-version",
40
- command_class: Commands::SatoshiWallet::ShowVersionCommand
41
- end
42
-
43
- context "show-addresses" do
44
- it_behaves_like "SatoshiWalletCommand#run",
45
- command_name: "show-addresses",
46
- command_class: Commands::SatoshiWallet::ShowAddressesCommand
47
- end
48
-
49
- context "add-address" do
50
- it_behaves_like "SatoshiWalletCommand#run",
51
- command_name: "add-address",
52
- command_class: Commands::SatoshiWallet::AddAddressCommand
53
- end
54
-
55
- context "<unknown subcommand>" do
56
- it "prints an error" do
57
- expect {
58
- subject.run(%w[ unknown-subcommand wallet.dat foo bar ])
59
- }.to raise_error
60
-
61
- stream_bundle.captured_error.should eq %'Unknown satoshi-wallet subcommand: "unknown-subcommand"\n'
62
- end
63
-
64
- it "raises an error" do
65
- expect {
66
- subject.run(%w[ unknown-subcommand wallet.dat foo bar ])
67
- }.to raise_error(CLI::CommandError)
68
- end
69
- end
70
- end
71
- end
72
- end
73
- end
@@ -1,29 +0,0 @@
1
- contract "StreamBundle" do
2
- let(:input) { StringIO.new }
3
- let(:output) { StringIO.new }
4
- let(:error) { StringIO.new }
5
-
6
- let(:subject) { described_class.new(input, output, error) }
7
-
8
- describe "#puts_output" do
9
- it "writes a line to the output" do
10
- subject.puts_output("foo")
11
- subject.puts_output("bar")
12
- subject.puts_output("baz")
13
-
14
- output.rewind
15
- output.read.should eq "foo\nbar\nbaz\n"
16
- end
17
- end
18
-
19
- describe "#puts_error" do
20
- it "writes a line to the output" do
21
- subject.puts_error("foo")
22
- subject.puts_error("bar")
23
- subject.puts_error("baz")
24
-
25
- error.rewind
26
- error.read.should eq "foo\nbar\nbaz\n"
27
- end
28
- end
29
- end
@@ -1,74 +0,0 @@
1
- require 'spec_helper'
2
-
3
- require 'bitcoin/console/capturing_stream_bundle'
4
-
5
- require_relative '_contracts/stream_bundle_contract'
6
-
7
- module Bitcoin
8
- module Console
9
- describe CapturingStreamBundle do
10
- it_satisfies_contract "StreamBundle"
11
-
12
- let(:input) { StringIO.new }
13
- let(:output) { StringIO.new }
14
- let(:error) { StringIO.new }
15
-
16
- let(:subject) { CapturingStreamBundle.new(input, output, error) }
17
-
18
- describe ".test_bundle" do
19
- it "creates a CapturingStreamBundle with three StringIO streams", because: "we only care about captured output" do
20
- # Really should be a separate factory object, but not for the sake of one method
21
- CapturingStreamBundle.should_receive(:new).with(
22
- an_instance_of(StringIO), an_instance_of(StringIO), an_instance_of(StringIO)
23
- ).and_return(:stream_bundle)
24
- CapturingStreamBundle.test_bundle.should eq :stream_bundle
25
- end
26
- end
27
-
28
- # The output and error streams are effectively the same with different names,
29
- # but the duplication is only textual and I don't see a neat way to remove it yet
30
-
31
- describe "#captured_output" do
32
- before(:each) do
33
- subject.puts_output("foo")
34
- subject.puts_output("bar")
35
- subject.puts_output("baz")
36
- end
37
-
38
- its(:captured_output) { should eq "foo\nbar\nbaz\n" }
39
-
40
- it "doesn't manipulate the output stream" do
41
- output.stub(:rewind).and_raise(RuntimeError.new)
42
- expect { subject.captured_output }.to_not raise_error
43
- end
44
-
45
- it "accumulates output across reads" do
46
- subject.captured_output
47
- subject.puts_output("quux")
48
- subject.captured_output.should eq "foo\nbar\nbaz\nquux\n"
49
- end
50
- end
51
-
52
- describe "#captured_error" do
53
- before(:each) do
54
- subject.puts_error("foo")
55
- subject.puts_error("bar")
56
- subject.puts_error("baz")
57
- end
58
-
59
- its(:captured_error) { should eq "foo\nbar\nbaz\n" }
60
-
61
- it "doesn't manipulate the error stream" do
62
- error.stub(:rewind).and_raise(RuntimeError.new)
63
- expect { subject.captured_error }.to_not raise_error
64
- end
65
-
66
- it "accumulates output across reads" do
67
- subject.captured_error
68
- subject.puts_error("quux")
69
- subject.captured_error.should eq "foo\nbar\nbaz\nquux\n"
70
- end
71
- end
72
- end
73
- end
74
- end