crossover 0.1.2 → 0.1.6
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 +4 -4
- data/.byebug_history +46 -0
- data/.gitignore +1 -0
- data/DESIGN.adoc +19 -0
- data/Guardfile +24 -0
- data/README.md +20 -3
- data/STDOUT +0 -0
- data/command.sh +3 -0
- data/crossover +0 -0
- data/crossover.gemspec +6 -0
- data/crossover.log +0 -0
- data/exe/crossover +5 -0
- data/lib/crossover.rb +3 -0
- data/lib/crossover/cli.rb +62 -0
- data/lib/crossover/client.rb +38 -0
- data/lib/crossover/server.rb +46 -0
- data/lib/crossover/version.rb +1 -1
- data/notes.adoc +3 -0
- data/out.log +1 -0
- data/result.log +5 -0
- metadata +88 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 9b899c2105ebaff384c93a29f21c352e19725b42
|
|
4
|
+
data.tar.gz: da6cfbdb3698445fc4b79c6974be8c3fd0ba7f16
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 10fbc2eb8adcab9500310ee8e30c3803122410c97d6aef834165165829c53c99bbeb264bad8b61f998a6ae38f89c533c6637dd0c94819a7beed550dcd284a66e
|
|
7
|
+
data.tar.gz: 786fe50501d564c9156868962dfd246ba53b95670f1551b25f8c1320c41cf89bf447254bb8d63d0f547bc6e23d1f8a04954c615fa4624e9596ab777598a80420
|
data/.byebug_history
ADDED
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
quit
|
|
2
|
+
n
|
|
3
|
+
quit
|
|
4
|
+
n
|
|
5
|
+
stdlog
|
|
6
|
+
quit
|
|
7
|
+
io.peeraddr
|
|
8
|
+
io.peername
|
|
9
|
+
io.getsockname
|
|
10
|
+
io.gethostname
|
|
11
|
+
quit
|
|
12
|
+
io.getpeername.force_encoding(Encoding::UTF_8).to_s
|
|
13
|
+
io.getpeername.force_encoding(Encoding::UTF_8)
|
|
14
|
+
io.getpeername.encoding
|
|
15
|
+
io.getpeername.to_s
|
|
16
|
+
io.getpeername
|
|
17
|
+
io.local_address
|
|
18
|
+
io.connect_address
|
|
19
|
+
io.recvfrom
|
|
20
|
+
io.public_methods
|
|
21
|
+
io
|
|
22
|
+
quit
|
|
23
|
+
GServer.in_service? 10001
|
|
24
|
+
GServer.in_service?
|
|
25
|
+
Server.methods
|
|
26
|
+
p Server.methods
|
|
27
|
+
pp Server.methods
|
|
28
|
+
Server.methods
|
|
29
|
+
Server.in_service?( 10001, '127.0.0.1')
|
|
30
|
+
c
|
|
31
|
+
Server.in_service?(port)
|
|
32
|
+
quit
|
|
33
|
+
c
|
|
34
|
+
n
|
|
35
|
+
Server.in_service? port.to_i
|
|
36
|
+
GServer.in_service? port.to_i
|
|
37
|
+
port.to_i
|
|
38
|
+
port
|
|
39
|
+
GServer.in_service? port
|
|
40
|
+
Server.in_service? port
|
|
41
|
+
Server.in_service?
|
|
42
|
+
Servre.in_service?
|
|
43
|
+
c
|
|
44
|
+
GServer.in_service?(port)
|
|
45
|
+
Server.in_service?(port)
|
|
46
|
+
n
|
data/.gitignore
CHANGED
data/DESIGN.adoc
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
= Design Document
|
|
2
|
+
Christian Kyony <ckyony@changamuka.com>
|
|
3
|
+
v0.1.5
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
== High level requirement analysis
|
|
8
|
+
|
|
9
|
+
== High level presentation of the data model
|
|
10
|
+
|
|
11
|
+
== Architecture diagrams describing the composition and working of the system, explaining the component interaction and process, control and data flows.
|
|
12
|
+
|
|
13
|
+
// Architecture diagrams describing the composition and working of the system,
|
|
14
|
+
// explaining the component interaction and process, control and data flows.
|
|
15
|
+
|
|
16
|
+
== Explain the breakdown of the system into components with technical implementation details of each component along with the design patterns involved and with reasons that justify your choices.
|
|
17
|
+
|
|
18
|
+
== Use both visual elements (diagrams) and text descriptions to maximize the amount of information conveyed while keeping the document as compact as possible
|
|
19
|
+
|
data/Guardfile
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# A sample Guardfile
|
|
2
|
+
# More info at https://github.com/guard/guard#readme
|
|
3
|
+
|
|
4
|
+
## Uncomment and set this to only include directories you want to watch
|
|
5
|
+
# directories %w(app lib config test spec features) \
|
|
6
|
+
# .select{|d| Dir.exists?(d) ? d : UI.warning("Directory #{d} does not exist")}
|
|
7
|
+
|
|
8
|
+
## Note: if you are using the `directories` clause above and you are not
|
|
9
|
+
## watching the project directory ('.'), then you will want to move
|
|
10
|
+
## the Guardfile to a watched dir and symlink it back, e.g.
|
|
11
|
+
#
|
|
12
|
+
# $ mkdir config
|
|
13
|
+
# $ mv Guardfile config/
|
|
14
|
+
# $ ln -s config/Guardfile .
|
|
15
|
+
#
|
|
16
|
+
# and, you'll have to watch "config/Guardfile" instead of "Guardfile"
|
|
17
|
+
|
|
18
|
+
guard :minitest do
|
|
19
|
+
# with Minitest::Unit
|
|
20
|
+
watch(%r{^test/(.*)\/?test_(.*)\.rb$})
|
|
21
|
+
watch(%r{^lib/(.*/)?([^/]+)\.rb$}) { |m| "test/#{m[1]}test_#{m[2]}.rb" }
|
|
22
|
+
watch(%r{^test/test_helper\.rb$}) { 'test' }
|
|
23
|
+
watch(%r{^test/test_helper\.rb$}) { 'test' }
|
|
24
|
+
end
|
data/README.md
CHANGED
|
@@ -26,9 +26,10 @@ TODO: Write usage instructions here
|
|
|
26
26
|
|
|
27
27
|
## Development
|
|
28
28
|
|
|
29
|
-
After checking out the repo, run `bin/setup` to install dependencies.
|
|
30
|
-
|
|
31
|
-
To install this gem onto your local machine, run `bundle exec rake install`.
|
|
29
|
+
After checking out the repo, run `bin/setup` to install dependencies.
|
|
30
|
+
Then, run `rake test` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
|
31
|
+
To install this gem onto your local machine, run `bundle exec rake install`.
|
|
32
|
+
To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
|
|
32
33
|
|
|
33
34
|
## Contributing
|
|
34
35
|
|
|
@@ -39,3 +40,19 @@ Bug reports and pull requests are welcome on GitHub at https://github.com/[USERN
|
|
|
39
40
|
|
|
40
41
|
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
|
|
41
42
|
|
|
43
|
+
Create a text file with the following information
|
|
44
|
+
|
|
45
|
+
Instructions to install and configure prerequisites or dependencies, if any
|
|
46
|
+
|
|
47
|
+
Instructions to create and initialize any data (if required)
|
|
48
|
+
|
|
49
|
+
Assumptions you have made - it is good to explain your thought process and the assumptions you have made
|
|
50
|
+
|
|
51
|
+
Requirements that you have not covered in your submission, if any
|
|
52
|
+
|
|
53
|
+
Instructions to configure and prepare the source code to build and run properly
|
|
54
|
+
|
|
55
|
+
Issues you have faced while completing the assignment, if any
|
|
56
|
+
|
|
57
|
+
Constructive feedback for improving the assignment
|
|
58
|
+
|
data/STDOUT
ADDED
|
Binary file
|
data/command.sh
ADDED
data/crossover
ADDED
|
File without changes
|
data/crossover.gemspec
CHANGED
|
@@ -28,11 +28,17 @@ Gem::Specification.new do |spec|
|
|
|
28
28
|
end
|
|
29
29
|
spec.bindir = "exe"
|
|
30
30
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
|
31
|
+
# spec.executables = "crossover"
|
|
31
32
|
spec.require_paths = ["lib"]
|
|
32
33
|
|
|
33
34
|
spec.add_development_dependency "bundler", "~> 1.13"
|
|
34
35
|
spec.add_development_dependency "rake", "~> 10.0"
|
|
35
36
|
spec.add_development_dependency "minitest", "~> 5.0"
|
|
37
|
+
spec.add_development_dependency "guard"
|
|
38
|
+
spec.add_development_dependency "guard-minitest"
|
|
39
|
+
spec.add_development_dependency "byebug"
|
|
40
|
+
spec.add_development_dependency "simplecov"
|
|
36
41
|
|
|
37
42
|
spec.add_dependency "thor", "~> 0"
|
|
43
|
+
spec.add_dependency "gserver"
|
|
38
44
|
end
|
data/crossover.log
ADDED
|
Binary file
|
data/exe/crossover
ADDED
data/lib/crossover.rb
CHANGED
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
require 'thor'
|
|
2
|
+
|
|
3
|
+
module Crossover
|
|
4
|
+
class CLI < Thor
|
|
5
|
+
|
|
6
|
+
desc 'client', 'Send data to a remote HOST listening on PORT'
|
|
7
|
+
method_option :host, aliases: '-h', default: '127.0.0.1'
|
|
8
|
+
method_option :port, aliases: '-p', default: 50000, type: :numeric
|
|
9
|
+
method_option :data, aliases: '-d'
|
|
10
|
+
def client
|
|
11
|
+
begin
|
|
12
|
+
remote_host = options[:host]
|
|
13
|
+
port = options[:port]
|
|
14
|
+
data = options[:data] || Client.clean_data
|
|
15
|
+
puts Client.post(data, remote_host, port)
|
|
16
|
+
|
|
17
|
+
rescue Errno::ECONNREFUSED
|
|
18
|
+
puts "Sorry! Connection refused by #{remote_host} on port #{port}"
|
|
19
|
+
|
|
20
|
+
rescue Errno::EADDRNOTAVAIL
|
|
21
|
+
puts "Sorry! Can't assign requested address for #{remote_host} on port #{port}"
|
|
22
|
+
|
|
23
|
+
rescue Interrupt
|
|
24
|
+
puts "\nExiting ..."
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
desc 'server', 'Launch a server listening on PORT'
|
|
29
|
+
method_option :host, aliases: '-h', default: '127.0.0.1', type: :string
|
|
30
|
+
method_option :port, aliases: "-p", default: 50000, type: :numeric
|
|
31
|
+
method_option :logfile, aliases: "-l", default: "~/crossover.log", type: :string
|
|
32
|
+
method_option :max_connections, aliases: '-c', default: 1000, type: :numeric
|
|
33
|
+
def server
|
|
34
|
+
begin
|
|
35
|
+
host = options[:host]
|
|
36
|
+
port = options[:port].to_i
|
|
37
|
+
logfile = options[:logfile]
|
|
38
|
+
max_connections = options[:max_connections]
|
|
39
|
+
@server = Server.new( port, host, max_connections, logfile, true )
|
|
40
|
+
@server.start
|
|
41
|
+
@server.join
|
|
42
|
+
|
|
43
|
+
rescue Errno::EADDRINUSE
|
|
44
|
+
puts "Sorry! The port #{port} is already in use."
|
|
45
|
+
|
|
46
|
+
rescue Errno::EACCES => e
|
|
47
|
+
puts "Sorry! Ensure that you have the correct permissions as per message below:\n#{e} "
|
|
48
|
+
|
|
49
|
+
rescue Interrupt
|
|
50
|
+
puts "\nExiting ..."
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
map %w[--version -v] => :version
|
|
55
|
+
desc "--version, -v", "Print the version"
|
|
56
|
+
def version
|
|
57
|
+
puts "Crossover version #{Crossover::VERSION}"
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
end
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
require 'socket'
|
|
2
|
+
module Crossover
|
|
3
|
+
module Client
|
|
4
|
+
def self.read_1024_bytes_from_dev_urandom
|
|
5
|
+
File.read("/dev/urandom", 1024)
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
# Returns a copy of String
|
|
9
|
+
def self.clean_out_non_UTF8_compliant_chars(str, token = '')
|
|
10
|
+
str.encode(Encoding::UTF_8, invalid: :replace, undef: :replace, replace: token)
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def self.replace_all_spaces_with_asterisk(str)
|
|
14
|
+
str.gsub(/\s/, '*')
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def self.clean_data(token = '')
|
|
18
|
+
str = read_1024_bytes_from_dev_urandom
|
|
19
|
+
clean = clean_out_non_UTF8_compliant_chars(str, token)
|
|
20
|
+
replace_all_spaces_with_asterisk(clean)
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def self.post(data , server, port)
|
|
24
|
+
begin
|
|
25
|
+
size = data.bytesize
|
|
26
|
+
puts "Sending #{size} bytes to port #{port} on #{server}."
|
|
27
|
+
socket = TCPSocket.open(server, port)
|
|
28
|
+
puts data
|
|
29
|
+
socket.write( data )
|
|
30
|
+
puts "\nBye!"
|
|
31
|
+
socket.close
|
|
32
|
+
rescue Errno::ECONNREFUSED
|
|
33
|
+
puts "Sorry! Connection refused by #{server} on port #{port}"
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
end
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
require 'gserver'
|
|
2
|
+
require 'logger'
|
|
3
|
+
|
|
4
|
+
# listen to a given port
|
|
5
|
+
# accepts data from client
|
|
6
|
+
# send ack to client
|
|
7
|
+
# close the connection
|
|
8
|
+
#
|
|
9
|
+
# Can accept multiple client
|
|
10
|
+
# Can listen on multiple ports
|
|
11
|
+
|
|
12
|
+
module Crossover
|
|
13
|
+
class Server < GServer
|
|
14
|
+
|
|
15
|
+
def initialize(port, host='127.0.0.1', max_connections = 10, stdlog = $stdout, audit = true, debug = false )
|
|
16
|
+
if stdlog != $stdout
|
|
17
|
+
@logger = Logger.new(File.expand_path(stdlog) )
|
|
18
|
+
end
|
|
19
|
+
super(port, host, max_connections, $stdout, audit, debug )
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def serve(io)
|
|
23
|
+
data = io.read(1024)
|
|
24
|
+
log "client:#{io.peeraddr[1]} #{io.peeraddr[2]}<#{io.peeraddr[3]}> post #{data.bytesize} bytes\n#{data}"
|
|
25
|
+
puts ""
|
|
26
|
+
io.puts('Bye!')
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def stopping
|
|
30
|
+
log("#{self.class.to_s} #{@host}:#{@port} stop")
|
|
31
|
+
@logger.close
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
def log message
|
|
35
|
+
if @stdlog
|
|
36
|
+
@stdlog.puts("[#{Time.new.ctime}] %s" % message)
|
|
37
|
+
@stdlog.flush
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
if @logger
|
|
41
|
+
@logger.info message
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
end
|
|
46
|
+
end
|
data/lib/crossover/version.rb
CHANGED
data/notes.adoc
ADDED
data/out.log
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
|
data/result.log
ADDED
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: crossover
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.1.
|
|
4
|
+
version: 0.1.6
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Christian Kyony
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2017-01-
|
|
11
|
+
date: 2017-01-25 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: bundler
|
|
@@ -52,6 +52,62 @@ dependencies:
|
|
|
52
52
|
- - "~>"
|
|
53
53
|
- !ruby/object:Gem::Version
|
|
54
54
|
version: '5.0'
|
|
55
|
+
- !ruby/object:Gem::Dependency
|
|
56
|
+
name: guard
|
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
|
58
|
+
requirements:
|
|
59
|
+
- - ">="
|
|
60
|
+
- !ruby/object:Gem::Version
|
|
61
|
+
version: '0'
|
|
62
|
+
type: :development
|
|
63
|
+
prerelease: false
|
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
65
|
+
requirements:
|
|
66
|
+
- - ">="
|
|
67
|
+
- !ruby/object:Gem::Version
|
|
68
|
+
version: '0'
|
|
69
|
+
- !ruby/object:Gem::Dependency
|
|
70
|
+
name: guard-minitest
|
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
|
72
|
+
requirements:
|
|
73
|
+
- - ">="
|
|
74
|
+
- !ruby/object:Gem::Version
|
|
75
|
+
version: '0'
|
|
76
|
+
type: :development
|
|
77
|
+
prerelease: false
|
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
79
|
+
requirements:
|
|
80
|
+
- - ">="
|
|
81
|
+
- !ruby/object:Gem::Version
|
|
82
|
+
version: '0'
|
|
83
|
+
- !ruby/object:Gem::Dependency
|
|
84
|
+
name: byebug
|
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
|
86
|
+
requirements:
|
|
87
|
+
- - ">="
|
|
88
|
+
- !ruby/object:Gem::Version
|
|
89
|
+
version: '0'
|
|
90
|
+
type: :development
|
|
91
|
+
prerelease: false
|
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
93
|
+
requirements:
|
|
94
|
+
- - ">="
|
|
95
|
+
- !ruby/object:Gem::Version
|
|
96
|
+
version: '0'
|
|
97
|
+
- !ruby/object:Gem::Dependency
|
|
98
|
+
name: simplecov
|
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
|
100
|
+
requirements:
|
|
101
|
+
- - ">="
|
|
102
|
+
- !ruby/object:Gem::Version
|
|
103
|
+
version: '0'
|
|
104
|
+
type: :development
|
|
105
|
+
prerelease: false
|
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
107
|
+
requirements:
|
|
108
|
+
- - ">="
|
|
109
|
+
- !ruby/object:Gem::Version
|
|
110
|
+
version: '0'
|
|
55
111
|
- !ruby/object:Gem::Dependency
|
|
56
112
|
name: thor
|
|
57
113
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -66,24 +122,53 @@ dependencies:
|
|
|
66
122
|
- - "~>"
|
|
67
123
|
- !ruby/object:Gem::Version
|
|
68
124
|
version: '0'
|
|
125
|
+
- !ruby/object:Gem::Dependency
|
|
126
|
+
name: gserver
|
|
127
|
+
requirement: !ruby/object:Gem::Requirement
|
|
128
|
+
requirements:
|
|
129
|
+
- - ">="
|
|
130
|
+
- !ruby/object:Gem::Version
|
|
131
|
+
version: '0'
|
|
132
|
+
type: :runtime
|
|
133
|
+
prerelease: false
|
|
134
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
135
|
+
requirements:
|
|
136
|
+
- - ">="
|
|
137
|
+
- !ruby/object:Gem::Version
|
|
138
|
+
version: '0'
|
|
69
139
|
description: Sample Client-Server App using TCP Socket.
|
|
70
140
|
email:
|
|
71
141
|
- ckyony@changamuka.com
|
|
72
|
-
executables:
|
|
142
|
+
executables:
|
|
143
|
+
- crossover
|
|
73
144
|
extensions: []
|
|
74
145
|
extra_rdoc_files: []
|
|
75
146
|
files:
|
|
147
|
+
- ".byebug_history"
|
|
76
148
|
- ".gitignore"
|
|
77
149
|
- ".travis.yml"
|
|
150
|
+
- DESIGN.adoc
|
|
78
151
|
- Gemfile
|
|
152
|
+
- Guardfile
|
|
79
153
|
- LICENSE.txt
|
|
80
154
|
- README.md
|
|
81
155
|
- Rakefile
|
|
156
|
+
- STDOUT
|
|
82
157
|
- bin/console
|
|
83
158
|
- bin/setup
|
|
159
|
+
- command.sh
|
|
160
|
+
- crossover
|
|
84
161
|
- crossover.gemspec
|
|
162
|
+
- crossover.log
|
|
163
|
+
- exe/crossover
|
|
85
164
|
- lib/crossover.rb
|
|
165
|
+
- lib/crossover/cli.rb
|
|
166
|
+
- lib/crossover/client.rb
|
|
167
|
+
- lib/crossover/server.rb
|
|
86
168
|
- lib/crossover/version.rb
|
|
169
|
+
- notes.adoc
|
|
170
|
+
- out.log
|
|
171
|
+
- result.log
|
|
87
172
|
homepage: ''
|
|
88
173
|
licenses:
|
|
89
174
|
- MIT
|