profit 0.1.1 → 0.1.2
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.
- data/README.md +4 -3
- data/bin/profit_server +23 -1
- data/lib/profit.rb +1 -2
- data/lib/profit/server.rb +47 -43
- data/lib/profit/version.rb +1 -1
- data/spec/lib/client_spec.rb +8 -8
- data/spec/lib/server_spec.rb +3 -3
- data/spec/spec_helper.rb +1 -1
- metadata +21 -6
- data/lib/profit/message_handler.rb +0 -26
data/README.md
CHANGED
@@ -14,9 +14,10 @@ client.stop("some_suspect_code")
|
|
14
14
|
```
|
15
15
|
|
16
16
|
Here's the server
|
17
|
-
```
|
18
|
-
|
19
|
-
|
17
|
+
``` shell
|
18
|
+
$ profit_server --redis-address 127.0.0.1:6379 \
|
19
|
+
--zmq-address tcp://*:5556 \
|
20
|
+
--pool-size 10
|
20
21
|
```
|
21
22
|
|
22
23
|
And if you looked in Redis
|
data/bin/profit_server
CHANGED
@@ -1,5 +1,27 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
+
require 'optparse'
|
3
4
|
require 'profit'
|
4
5
|
|
5
|
-
|
6
|
+
options = {}
|
7
|
+
OptionParser.new { |opts|
|
8
|
+
opts.banner = "Usage: profit_server [options]"
|
9
|
+
|
10
|
+
opts.on("-r", "--redis-address [STRING]", String,
|
11
|
+
"Redis Address (127.0.0.1:6379)") do |ra|
|
12
|
+
options[:redis_address] = ra.split(":").first
|
13
|
+
options[:redis_port] = ra.split(":").last.to_i
|
14
|
+
end
|
15
|
+
|
16
|
+
opts.on("-z", "--zmq-address [STRING]", String,
|
17
|
+
"ZMQ Address (tcp://*:5556)") do |za|
|
18
|
+
options[:zmq_address] = za
|
19
|
+
end
|
20
|
+
|
21
|
+
opts.on("-n", "--pool-size [DECIMAL]", OptionParser::DecimalInteger,
|
22
|
+
"Redis client pool size (10)") do |n|
|
23
|
+
options[:pool_size] = n
|
24
|
+
end
|
25
|
+
}.parse!
|
26
|
+
|
27
|
+
Profit::Server.new(options).run
|
data/lib/profit.rb
CHANGED
data/lib/profit/server.rb
CHANGED
@@ -4,64 +4,68 @@ module Profit
|
|
4
4
|
|
5
5
|
attr_reader :ctx
|
6
6
|
|
7
|
-
def initialize
|
7
|
+
def initialize(options = {})
|
8
|
+
@options = {}
|
9
|
+
@options[:redis_address] = options[:redis_address] || "127.0.0.1"
|
10
|
+
@options[:redis_port] = options[:redis_port] || 6379
|
11
|
+
@options[:zmq_address] = options[:zmq_address] || "tcp://*:5556"
|
12
|
+
@options[:pool_size] = options[:pool_size] || 10
|
8
13
|
@ctx = ZMQ::Context.new
|
9
14
|
end
|
10
15
|
|
11
|
-
def shutdown!
|
12
|
-
@shutdown = true
|
13
|
-
end
|
14
|
-
|
15
|
-
def setup_trap_int
|
16
|
-
trap :INT do
|
17
|
-
puts "\nSIGINT received, quitting!"
|
18
|
-
EM.stop
|
19
|
-
end
|
20
|
-
end
|
21
|
-
|
22
16
|
def run
|
23
|
-
@run = true
|
24
17
|
EM.run do
|
25
18
|
|
26
|
-
|
27
|
-
|
28
|
-
@redis_pool.on_error { |conn| spawn[] }
|
29
|
-
10.times { spawn[] }
|
30
|
-
|
31
|
-
@puller = @ctx.bind(:PULL, "tcp://127.0.0.1:5556")
|
19
|
+
# startup the EM::Hiredis connections
|
20
|
+
spawn_redis_connections
|
32
21
|
|
33
22
|
# gives us a graceful exit
|
34
|
-
|
35
|
-
|
36
|
-
if @shutdown
|
37
|
-
EM.next_tick do # change to add_timer(1) for more delay
|
38
|
-
@run = false
|
39
|
-
end
|
40
|
-
end
|
23
|
+
setup_interrupt_handling
|
41
24
|
|
42
|
-
#
|
25
|
+
# this is the entry to message handling
|
43
26
|
EM.add_periodic_timer do
|
44
|
-
unless @run
|
45
|
-
EM.stop unless @run
|
46
|
-
end
|
47
|
-
end
|
48
27
|
|
49
|
-
|
50
|
-
|
28
|
+
# blocking ZMQ socket
|
29
|
+
message = puller.recv || ""
|
51
30
|
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
31
|
+
# take a worker from the pool to save the metric to Redis
|
32
|
+
redis_pool.perform do |conn|
|
33
|
+
|
34
|
+
message_hash = JSON.parse(message)
|
35
|
+
metric_type = message_hash.delete("metric_type")
|
36
|
+
|
37
|
+
response = conn.rpush "profit:metric:#{metric_type}", message_hash.to_json
|
38
|
+
response.callback { |resp| puts "callback: #{resp}"}
|
39
|
+
response.errback { |resp| puts "errback: #{resp}"}
|
40
|
+
response
|
62
41
|
end
|
63
42
|
end
|
64
43
|
end
|
65
44
|
end
|
45
|
+
|
46
|
+
private
|
47
|
+
|
48
|
+
def setup_interrupt_handling
|
49
|
+
trap(:INT) { EM.stop }
|
50
|
+
EM.add_shutdown_hook { ctx.destroy }
|
51
|
+
end
|
52
|
+
|
53
|
+
def spawn_redis_connections
|
54
|
+
spawn = lambda { redis_pool.add(EM::Hiredis.connect(redis_address)) }
|
55
|
+
redis_pool.on_error { |conn| spawn[] }
|
56
|
+
@options[:pool_size].times { spawn[] }
|
57
|
+
end
|
58
|
+
|
59
|
+
def puller
|
60
|
+
@puller ||= ctx.bind(:PULL, @options[:zmq_address])
|
61
|
+
end
|
62
|
+
|
63
|
+
def redis_pool
|
64
|
+
@redis_pool ||= EM::Pool.new
|
65
|
+
end
|
66
|
+
|
67
|
+
def redis_address
|
68
|
+
"redis://#{@options[:redis_address]}:#{@options[:redis_port]}/"
|
69
|
+
end
|
66
70
|
end
|
67
71
|
end
|
data/lib/profit/version.rb
CHANGED
data/spec/lib/client_spec.rb
CHANGED
@@ -8,11 +8,11 @@ describe Profit::Client do
|
|
8
8
|
let!(:server_thread) { TestServer.server_thread }
|
9
9
|
|
10
10
|
after do
|
11
|
-
redis.del("some_foo_measurement")
|
11
|
+
redis.del("profit:metric:some_foo_measurement")
|
12
12
|
end
|
13
13
|
|
14
14
|
it "sends the amount of time it takes to run some code" do
|
15
|
-
metrics = redis.lrange("some_foo_measurement", 0, -1)
|
15
|
+
metrics = redis.lrange("profit:metric:some_foo_measurement", 0, -1)
|
16
16
|
expect(metrics).to be_empty
|
17
17
|
|
18
18
|
client.start("some_foo_measurement")
|
@@ -21,7 +21,7 @@ describe Profit::Client do
|
|
21
21
|
|
22
22
|
server_thread.join(0.1)
|
23
23
|
|
24
|
-
metrics = redis.lrange("some_foo_measurement", 0, -1)
|
24
|
+
metrics = redis.lrange("profit:metric:some_foo_measurement", 0, -1)
|
25
25
|
metric = JSON.parse(metrics.first)
|
26
26
|
expect(metric['recorded_time']).to be_within(0.1).of(1)
|
27
27
|
end
|
@@ -80,8 +80,8 @@ describe Profit::Client do
|
|
80
80
|
describe "#stop" do
|
81
81
|
|
82
82
|
after do
|
83
|
-
redis.del("m_1")
|
84
|
-
redis.del("m_2")
|
83
|
+
redis.del("profit:metric:m_1")
|
84
|
+
redis.del("profit:metric:m_2")
|
85
85
|
end
|
86
86
|
|
87
87
|
it "matches up with the start marker" do
|
@@ -101,8 +101,8 @@ describe Profit::Client do
|
|
101
101
|
|
102
102
|
server_thread.join(0.1)
|
103
103
|
|
104
|
-
first_measurement_list = redis.lrange("m_1", 0, -1)
|
105
|
-
second_measurement_list = redis.lrange("m_2", 0, -1)
|
104
|
+
first_measurement_list = redis.lrange("profit:metric:m_1", 0, -1)
|
105
|
+
second_measurement_list = redis.lrange("profit:metric:m_2", 0, -1)
|
106
106
|
|
107
107
|
expect(first_measurement_list.count).to eq 2
|
108
108
|
expect(second_measurement_list.count).to eq 1
|
@@ -121,7 +121,7 @@ describe Profit::Client do
|
|
121
121
|
|
122
122
|
server_thread.join(0.1)
|
123
123
|
|
124
|
-
measurements = redis.lrange("m_1", 0, -1)
|
124
|
+
measurements = redis.lrange("profit:metric:m_1", 0, -1)
|
125
125
|
metric = JSON.parse(measurements[0])
|
126
126
|
expect(metric['stop_file']).to eq stop_file
|
127
127
|
expect(metric['stop_line']).to eq stop_line
|
data/spec/lib/server_spec.rb
CHANGED
@@ -7,7 +7,7 @@ describe Profit::Server do
|
|
7
7
|
let!(:server_thread) { TestServer.server_thread }
|
8
8
|
|
9
9
|
after do
|
10
|
-
redis.del("some_slow_piece_of_code")
|
10
|
+
redis.del("profit:metric:some_slow_piece_of_code")
|
11
11
|
end
|
12
12
|
|
13
13
|
it "stores metrics messages" do
|
@@ -22,9 +22,9 @@ describe Profit::Server do
|
|
22
22
|
end_file: "/foo/bar/biz.rb" }.to_json)
|
23
23
|
server_thread.join(0.1)
|
24
24
|
|
25
|
-
list = redis.lrange("some_slow_piece_of_code", 0, -1)
|
25
|
+
list = redis.lrange("profit:metric:some_slow_piece_of_code", 0, -1)
|
26
26
|
expect(list.count).to eq 1
|
27
|
-
expect(redis.llen("some_slow_piece_of_code")).to eq 1
|
27
|
+
expect(redis.llen("profit:metric:some_slow_piece_of_code")).to eq 1
|
28
28
|
|
29
29
|
metric = JSON.parse(list[0])
|
30
30
|
expect(metric["total_time"]).to eq 12.012
|
data/spec/spec_helper.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: profit
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-06-
|
12
|
+
date: 2013-06-11 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: eventmachine
|
@@ -44,7 +44,7 @@ dependencies:
|
|
44
44
|
- !ruby/object:Gem::Version
|
45
45
|
version: '0'
|
46
46
|
- !ruby/object:Gem::Dependency
|
47
|
-
name:
|
47
|
+
name: em-hiredis
|
48
48
|
requirement: !ruby/object:Gem::Requirement
|
49
49
|
none: false
|
50
50
|
requirements:
|
@@ -75,6 +75,22 @@ dependencies:
|
|
75
75
|
- - ! '>='
|
76
76
|
- !ruby/object:Gem::Version
|
77
77
|
version: '0'
|
78
|
+
- !ruby/object:Gem::Dependency
|
79
|
+
name: redis
|
80
|
+
requirement: !ruby/object:Gem::Requirement
|
81
|
+
none: false
|
82
|
+
requirements:
|
83
|
+
- - ! '>='
|
84
|
+
- !ruby/object:Gem::Version
|
85
|
+
version: '0'
|
86
|
+
type: :development
|
87
|
+
prerelease: false
|
88
|
+
version_requirements: !ruby/object:Gem::Requirement
|
89
|
+
none: false
|
90
|
+
requirements:
|
91
|
+
- - ! '>='
|
92
|
+
- !ruby/object:Gem::Version
|
93
|
+
version: '0'
|
78
94
|
- !ruby/object:Gem::Dependency
|
79
95
|
name: rspec
|
80
96
|
requirement: !ruby/object:Gem::Requirement
|
@@ -117,7 +133,6 @@ extensions: []
|
|
117
133
|
extra_rdoc_files: []
|
118
134
|
files:
|
119
135
|
- lib/profit/client.rb
|
120
|
-
- lib/profit/message_handler.rb
|
121
136
|
- lib/profit/server.rb
|
122
137
|
- lib/profit/version.rb
|
123
138
|
- lib/profit.rb
|
@@ -140,7 +155,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
140
155
|
version: '0'
|
141
156
|
segments:
|
142
157
|
- 0
|
143
|
-
hash: -
|
158
|
+
hash: -1836147071158890398
|
144
159
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
145
160
|
none: false
|
146
161
|
requirements:
|
@@ -149,7 +164,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
149
164
|
version: '0'
|
150
165
|
segments:
|
151
166
|
- 0
|
152
|
-
hash: -
|
167
|
+
hash: -1836147071158890398
|
153
168
|
requirements: []
|
154
169
|
rubyforge_project:
|
155
170
|
rubygems_version: 1.8.23
|
@@ -1,26 +0,0 @@
|
|
1
|
-
|
2
|
-
module Profit
|
3
|
-
|
4
|
-
class MessageHandler
|
5
|
-
|
6
|
-
include EM::Deferrable
|
7
|
-
|
8
|
-
attr_reader :text
|
9
|
-
|
10
|
-
def initialize(json, conn)
|
11
|
-
@json, @conn = json, conn
|
12
|
-
end
|
13
|
-
|
14
|
-
def run
|
15
|
-
return succeed("Starting") if @json.empty?
|
16
|
-
message_hash = JSON.parse(@json)
|
17
|
-
key = message_hash.delete("metric_type")
|
18
|
-
response = @conn.rpush key, message_hash.to_json
|
19
|
-
if response == "OK"
|
20
|
-
succeed response
|
21
|
-
else
|
22
|
-
fail response
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|