diff --git a/.gitignore b/.gitignore index 31cafb5..76a7781 100644 --- a/.gitignore +++ b/.gitignore @@ -20,3 +20,6 @@ tmp *.o *.a mkmf.log + +#swapfiles +*.swp diff --git a/.rspec b/.rspec new file mode 100644 index 0000000..8af9203 --- /dev/null +++ b/.rspec @@ -0,0 +1,4 @@ +--color +--format documentation +--backtrace +--order random diff --git a/Gemfile b/Gemfile index 3a85be5..6388d47 100644 --- a/Gemfile +++ b/Gemfile @@ -5,7 +5,8 @@ gemspec gem 'rake' -group :test do +group :test, :development do + gem 'pry-byebug' + gem 'awesome_print' gem 'rspec' - gem 'pry' end diff --git a/README.md b/README.md index 732f0e7..b106ddf 100644 --- a/README.md +++ b/README.md @@ -42,4 +42,4 @@ client = BN::P2P::Client.connect(host) client.send(BN::Protocol::Messages.version) client.send(BN::Protocol::Messages.ping) client.send(BN::Protocol::Messages.getaddr) -``` \ No newline at end of file +``` diff --git a/lib/bitcoin_node/p2p/server.rb b/lib/bitcoin_node/p2p/server.rb index b484939..6d69fce 100644 --- a/lib/bitcoin_node/p2p/server.rb +++ b/lib/bitcoin_node/p2p/server.rb @@ -9,7 +9,7 @@ class Server def initialize(port = 3333, probe = LoggingProbe.new('server')) @server = TCPServer.new('localhost', port) - @probe = probe + @probe = probe @peers = Peers.new async.run end @@ -40,7 +40,7 @@ def handle_messages(socket) @probe << { receiving: command } if command == 'version' - payload = BN::Protocol::Version.new(addr_recv: ['127.0.0.1', port]) + payload = BN::Protocol::Version.new(addr_recv: ['127.0.0.1', port]) message = BN::Protocol::Message.new(payload) @probe << { sending: 'version' } @peers.update(host, :version) @@ -68,7 +68,7 @@ def handle_messages(socket) require 'monitor' - class Peers + class Peers include MonitorMixin def initialize @@ -89,7 +89,7 @@ def status(peer) end def to_s - @peers.to_s + @peers.to_s end end end diff --git a/spec/P2p/server_spec.rb b/spec/P2p/server_spec.rb new file mode 100644 index 0000000..dde1959 --- /dev/null +++ b/spec/P2p/server_spec.rb @@ -0,0 +1,15 @@ +require 'spec_helper' + +describe 'Server' do + + let(:addr) { '127.0.0.1' } + let(:port) { random_port } + + it 'returns socket' do + server = BN::P2p::Server.new(port) + thread = Thread.new { server.accept } + socket = within_io_actor { Celluloid::IO::TCPSocket.open(addr, port) } + expect(socket).to be_a(Celluloid::IO::TCPSocket) + end + +end diff --git a/spec/integration/version_handshake_spec.rb b/spec/integration/version_handshake_spec.rb index 7d4875b..7026e4e 100644 --- a/spec/integration/version_handshake_spec.rb +++ b/spec/integration/version_handshake_spec.rb @@ -2,11 +2,11 @@ describe 'Version handshake' do - let(:port) { 3333 } + let(:addr) { '127.0.0.1' } + let(:port) { random_port } it 'peers exchanges version properly' do - server = BN::P2p::Server.new - + server = BN::P2p::Server.new(port) client_probe = BN::P2p::StoreProbe.new client = BN::P2p::Client.connect('localhost', port, probe: client_probe) client.version = 60001 @@ -15,7 +15,7 @@ message = BN::Protocol::Message.new(payload) expect(client.handshaked?).to eql false - + client.send(message) expect(client.handshaked?).to eql true @@ -29,9 +29,9 @@ end it 'server does not answer to verack if no version exchanged beforehand' do - server = BN::P2p::Server.new + server = BN::P2p::Server.new(port) client = BN::P2p::Client.connect('localhost', port, read_timeout: 1) - + expect(client.handshaked?).to eql false expect { client.send(BN::Protocol::Messages.verack) @@ -44,12 +44,12 @@ class BadPeer include Celluloid::IO def initialize(port) - @server = TCPServer.new('localhost', port) + @server = TCPServer.new('localhost', port) async.run end def run - loop { async.on_connection @server.accept } + loop { async.on_connection @server.accept } end def on_connection(socket) diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 3b7d581..2ccd489 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -1,4 +1,25 @@ require File.expand_path('../lib/bitcoin_node.rb', __dir__) +require 'celluloid/io' require 'pry' +require 'awesome_print' +class WrapperActor + include Celluloid::IO + execute_block_on_receiver :wrap + + def wrap + yield + end +end + +def random_port + port = 12_000 + Random.rand(1024) +end + +def within_io_actor(&block) + actor = WrapperActor.new + actor.wrap(&block) +ensure + actor.terminate if actor.alive? rescue nil +end