loggregator_emitter 0.0.13.pre → 0.0.15.pre
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/.gitignore +1 -0
- data/Gemfile.lock +2 -2
- data/lib/loggregator_emitter/emit.rb +24 -15
- data/loggregator_emitter.gemspec +1 -1
- data/spec/loggregator_emitter/emit_spec.rb +81 -70
- data/spec/support/fake_loggregator_server.rb +28 -19
- metadata +2 -2
data/.gitignore
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
loggregator_emitter (0.0.
|
4
|
+
loggregator_emitter (0.0.15.pre)
|
5
5
|
beefcake (~> 0.3.7)
|
6
6
|
|
7
7
|
GEM
|
@@ -15,7 +15,7 @@ GEM
|
|
15
15
|
rspec-expectations (~> 2.14.0)
|
16
16
|
rspec-mocks (~> 2.14.0)
|
17
17
|
rspec-core (2.14.5)
|
18
|
-
rspec-expectations (2.14.
|
18
|
+
rspec-expectations (2.14.3)
|
19
19
|
diff-lcs (>= 1.1.3, < 2.0)
|
20
20
|
rspec-mocks (2.14.3)
|
21
21
|
|
@@ -3,31 +3,40 @@ require 'socket'
|
|
3
3
|
module LoggregatorEmitter
|
4
4
|
class Emitter
|
5
5
|
def initialize(loggregator_server, source_type, source_id = nil)
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
6
|
+
raise ArgumentError, "Must provide valid source type" unless valid_source_type?(source_type)
|
7
|
+
|
8
|
+
@host, @port = loggregator_server.split(/:([^:]*$)/)
|
9
|
+
raise ArgumentError, "Must provide valid loggregator server: #{loggregator_server}" if !valid_hostname || !valid_port
|
10
10
|
|
11
|
-
raise RuntimeError, "Must provide valid source type" unless valid_source_type?(source_type)
|
12
11
|
@source_type = source_type
|
13
12
|
@source_id = source_id && source_id.to_s
|
14
13
|
end
|
15
14
|
|
16
15
|
def emit(app_id, message)
|
17
|
-
|
18
|
-
lm = create_log_message(app_id, message, LogMessage::MessageType::OUT)
|
19
|
-
send_message(lm)
|
20
|
-
end
|
16
|
+
emit_message(app_id, message, LogMessage::MessageType::OUT)
|
21
17
|
end
|
22
18
|
|
23
19
|
def emit_error(app_id, message)
|
20
|
+
emit_message(app_id, message, LogMessage::MessageType::ERR)
|
21
|
+
end
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def valid_port
|
26
|
+
@port && @port.match(/^\d+$/)
|
27
|
+
end
|
28
|
+
|
29
|
+
def valid_hostname
|
30
|
+
@host && !@host.match(/:\/\//)
|
31
|
+
end
|
32
|
+
|
33
|
+
def emit_message(app_id, message, type)
|
24
34
|
if app_id
|
25
|
-
lm = create_log_message(app_id, message,
|
35
|
+
lm = create_log_message(app_id, message, type)
|
26
36
|
send_message(lm)
|
27
37
|
end
|
28
38
|
end
|
29
39
|
|
30
|
-
private
|
31
40
|
def create_log_message(app_id, message, type)
|
32
41
|
lm = LogMessage.new()
|
33
42
|
lm.time = Time.now
|
@@ -40,13 +49,13 @@ module LoggregatorEmitter
|
|
40
49
|
end
|
41
50
|
|
42
51
|
def send_message(lm)
|
43
|
-
s = UDPSocket.new
|
44
|
-
s.do_not_reverse_lookup = true
|
45
|
-
|
46
52
|
result = lm.encode.buf
|
47
53
|
result.unpack("C*")
|
48
54
|
|
49
|
-
|
55
|
+
addrinfo_udp = Addrinfo.udp(@host, @port)
|
56
|
+
s = addrinfo_udp.ipv4?() ? UDPSocket.new : UDPSocket.new(Socket::AF_INET6)
|
57
|
+
s.do_not_reverse_lookup = true
|
58
|
+
s.sendmsg_nonblock(result, 0, addrinfo_udp)
|
50
59
|
end
|
51
60
|
|
52
61
|
def valid_source_type?(source_type)
|
data/loggregator_emitter.gemspec
CHANGED
@@ -1,117 +1,128 @@
|
|
1
|
-
require
|
2
|
-
require
|
1
|
+
require "support/fake_loggregator_server"
|
2
|
+
require "loggregator_emitter"
|
3
3
|
|
4
4
|
describe LoggregatorEmitter do
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
end
|
10
|
-
|
11
|
-
it 'raises if loggregator_server is invalid' do
|
12
|
-
expect { LoggregatorEmitter::Emitter.new('0.0.0.0', LogMessage::SourceType::DEA) }.to raise_error(RuntimeError)
|
5
|
+
class FreePort
|
6
|
+
def self.next_free_port
|
7
|
+
@@next_free_port ||= 12345
|
8
|
+
@@next_free_port += 1
|
13
9
|
end
|
10
|
+
end
|
11
|
+
let(:free_port) do
|
12
|
+
FreePort.next_free_port
|
13
|
+
end
|
14
14
|
|
15
|
-
|
16
|
-
|
17
|
-
|
15
|
+
describe "configuring emitter" do
|
16
|
+
describe "valid configurations" do
|
17
|
+
it "is valid with IP and proper source type" do
|
18
|
+
expect { LoggregatorEmitter::Emitter.new("0.0.0.0:12345", LogMessage::SourceType::DEA) }.not_to raise_error
|
19
|
+
end
|
18
20
|
|
19
|
-
|
20
|
-
|
21
|
-
|
21
|
+
it "is valid with resolveable hostname and proper source type" do
|
22
|
+
expect { LoggregatorEmitter::Emitter.new("localhost:12345", LogMessage::SourceType::DEA) }.not_to raise_error
|
23
|
+
end
|
22
24
|
|
23
|
-
|
24
|
-
|
25
|
+
it "is valid if a server name is given" do
|
26
|
+
expect { LoggregatorEmitter::Emitter.new("some-unknown-address:12345", LogMessage::SourceType::DEA) }.not_to raise_error
|
27
|
+
end
|
25
28
|
end
|
26
29
|
|
27
|
-
|
28
|
-
|
30
|
+
describe "invalid configurations" do
|
31
|
+
describe "error based on loggregator_server" do
|
32
|
+
it "raises if host has protocol" do
|
33
|
+
expect { LoggregatorEmitter::Emitter.new("http://0.0.0.0:12345", LogMessage::SourceType::DEA) }.to raise_error(ArgumentError)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
describe "error based on source_type" do
|
38
|
+
it "raises if source_type is invalid" do
|
39
|
+
expect { LoggregatorEmitter::Emitter.new("0.0.0.0:12345", 40) }.to raise_error(ArgumentError)
|
40
|
+
end
|
41
|
+
end
|
29
42
|
end
|
30
43
|
end
|
31
44
|
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
45
|
+
{"emit" => LogMessage::MessageType::OUT, "emit_error" => LogMessage::MessageType::ERR}.each do |emit_method, message_type|
|
46
|
+
describe "##{emit_method}" do
|
47
|
+
def make_emitter(host)
|
48
|
+
LoggregatorEmitter::Emitter.new("#{host}:#{free_port}", LogMessage::SourceType::CLOUD_CONTROLLER, 42)
|
49
|
+
end
|
36
50
|
|
37
|
-
|
38
|
-
|
39
|
-
|
51
|
+
before do
|
52
|
+
@server = FakeLoggregatorServer.new(free_port)
|
53
|
+
@server.start
|
54
|
+
end
|
40
55
|
|
41
|
-
|
42
|
-
|
43
|
-
|
56
|
+
it "successfully writes protobuffers using ipv4" do
|
57
|
+
emitter = make_emitter("0.0.0.0")
|
58
|
+
emitter.send(emit_method, "my_app_id", "Hello there!")
|
59
|
+
emitter.send(emit_method, "my_app_id", "Hello again!")
|
60
|
+
emitter.send(emit_method, nil, "Hello again!")
|
44
61
|
|
45
|
-
|
62
|
+
@server.wait_for_messages_and_stop(2)
|
46
63
|
|
47
|
-
|
64
|
+
messages = @server.messages
|
48
65
|
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
66
|
+
expect(messages.length).to eq 2
|
67
|
+
message = messages[0]
|
68
|
+
expect(message.message).to eq "Hello there!"
|
69
|
+
expect(message.app_id).to eq "my_app_id"
|
70
|
+
expect(message.source_type).to eq LogMessage::SourceType::CLOUD_CONTROLLER
|
71
|
+
expect(message.source_id).to eq "42"
|
72
|
+
expect(message.message_type).to eq message_type
|
56
73
|
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
end
|
74
|
+
message = messages[1]
|
75
|
+
expect(message.message).to eq "Hello again!"
|
76
|
+
end
|
61
77
|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
end
|
66
|
-
|
67
|
-
it 'successfully writes protobuffer to a socket' do
|
68
|
-
server = FakeLoggregatorServer.new(12345)
|
69
|
-
server.start
|
78
|
+
it "successfully writes protobuffers using ipv6" do
|
79
|
+
emitter = make_emitter("::1")
|
80
|
+
emitter.send(emit_method, "my_app_id", "Hello there!")
|
70
81
|
|
71
|
-
|
72
|
-
@emitter.emit_error("my_app_id", 'Hello again!')
|
73
|
-
@emitter.emit_error(nil, 'Hello again!')
|
82
|
+
@server.wait_for_messages_and_stop(1)
|
74
83
|
|
75
|
-
|
84
|
+
messages = @server.messages
|
85
|
+
expect(messages.length).to eq 1
|
86
|
+
expect(messages[0].message).to eq "Hello there!"
|
87
|
+
end
|
76
88
|
|
77
|
-
|
89
|
+
it "successfully writes protobuffers using a dns name" do
|
90
|
+
emitter = make_emitter("localhost")
|
91
|
+
emitter.send(emit_method, "my_app_id", "Hello there!")
|
78
92
|
|
79
|
-
|
80
|
-
message = messages[0]
|
81
|
-
expect(message.message).to eq 'Hello there!'
|
82
|
-
expect(message.app_id).to eq "my_app_id"
|
83
|
-
expect(message.source_type).to eq LogMessage::SourceType::CLOUD_CONTROLLER
|
84
|
-
expect(message.message_type).to eq LogMessage::MessageType::ERR
|
93
|
+
@server.wait_for_messages_and_stop(1)
|
85
94
|
|
86
|
-
|
87
|
-
|
95
|
+
messages = @server.messages
|
96
|
+
expect(messages.length).to eq 1
|
97
|
+
expect(messages[0].message).to eq "Hello there!"
|
98
|
+
end
|
88
99
|
end
|
89
100
|
end
|
90
101
|
|
91
102
|
describe "source id" do
|
92
103
|
let(:emit_message) do
|
93
|
-
server = FakeLoggregatorServer.new(
|
104
|
+
server = FakeLoggregatorServer.new(free_port)
|
94
105
|
server.start
|
95
106
|
|
96
|
-
@emitter.emit_error("my_app_id",
|
107
|
+
@emitter.emit_error("my_app_id", "Hello there!")
|
97
108
|
|
98
|
-
server.
|
109
|
+
server.wait_for_messages_and_stop(2)
|
99
110
|
|
100
111
|
server.messages[0]
|
101
112
|
end
|
102
113
|
|
103
114
|
it "can be nil" do
|
104
|
-
@emitter = LoggregatorEmitter::Emitter.new(
|
115
|
+
@emitter = LoggregatorEmitter::Emitter.new("0.0.0.0:#{free_port}", LogMessage::SourceType::CLOUD_CONTROLLER)
|
105
116
|
expect(emit_message.source_id).to eq nil
|
106
117
|
end
|
107
118
|
|
108
119
|
it "can be passed in as a string" do
|
109
|
-
@emitter = LoggregatorEmitter::Emitter.new(
|
120
|
+
@emitter = LoggregatorEmitter::Emitter.new("0.0.0.0:#{free_port}", LogMessage::SourceType::CLOUD_CONTROLLER, "some_source_id")
|
110
121
|
expect(emit_message.source_id).to eq "some_source_id"
|
111
122
|
end
|
112
123
|
|
113
124
|
it "can be passed in as an integer" do
|
114
|
-
@emitter = LoggregatorEmitter::Emitter.new(
|
125
|
+
@emitter = LoggregatorEmitter::Emitter.new("0.0.0.0:#{free_port}", LogMessage::SourceType::CLOUD_CONTROLLER, 13)
|
115
126
|
expect(emit_message.source_id).to eq "13"
|
116
127
|
end
|
117
128
|
end
|
@@ -3,40 +3,49 @@ require 'loggregator_messages/log_message.pb'
|
|
3
3
|
|
4
4
|
class FakeLoggregatorServer
|
5
5
|
|
6
|
-
attr_reader :messages, :port
|
6
|
+
attr_reader :messages, :port
|
7
7
|
|
8
8
|
def initialize(port)
|
9
9
|
@messages = []
|
10
10
|
@port = port
|
11
|
-
|
11
|
+
|
12
|
+
#this server starts listening on ipv4 and ipv6, so we make two sockets
|
13
|
+
@sockets = [UDPSocket.new, UDPSocket.new(Socket::AF_INET6)]
|
14
|
+
@threads = []
|
12
15
|
end
|
13
16
|
|
14
17
|
def start
|
15
|
-
|
16
|
-
|
17
|
-
@thread = Thread.new do
|
18
|
-
while true
|
19
|
-
begin
|
20
|
-
stuff = @sock.recv(65536)
|
21
|
-
messages << LogMessage.decode(stuff)
|
22
|
-
rescue Beefcake::Message::WrongTypeError, Beefcake::Message::RequiredFieldNotSetError, Beefcake::Message::InvalidValueError => e
|
23
|
-
puts "ERROR"
|
24
|
-
puts e
|
25
|
-
end
|
26
|
-
|
27
|
-
end
|
28
|
-
end
|
18
|
+
bind_and_record(0, @sockets[0], "localhost")
|
19
|
+
bind_and_record(0, @sockets[1], "::1")
|
29
20
|
end
|
30
21
|
|
31
|
-
def
|
22
|
+
def wait_for_messages_and_stop(number_expected_messages)
|
32
23
|
max_tries = 0
|
33
24
|
while messages.length < number_expected_messages
|
34
25
|
sleep 0.2
|
35
26
|
max_tries += 1
|
36
27
|
break if max_tries > 10
|
37
28
|
end
|
38
|
-
@sock.close
|
39
29
|
|
40
|
-
|
30
|
+
@sockets.each { |socket| socket.close}
|
31
|
+
@threads.each { |thread| Thread.kill(thread) }
|
32
|
+
end
|
33
|
+
|
34
|
+
private
|
35
|
+
|
36
|
+
def bind_and_record(index, socket, server)
|
37
|
+
socket.bind(server, port)
|
38
|
+
|
39
|
+
@threads[index] = Thread.new do
|
40
|
+
while true
|
41
|
+
begin
|
42
|
+
stuff = socket.recv(65536)
|
43
|
+
messages << LogMessage.decode(stuff)
|
44
|
+
rescue Beefcake::Message::WrongTypeError, Beefcake::Message::RequiredFieldNotSetError, Beefcake::Message::InvalidValueError => e
|
45
|
+
puts "ERROR"
|
46
|
+
puts e
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
41
50
|
end
|
42
51
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: loggregator_emitter
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.15.pre
|
5
5
|
prerelease: 7
|
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-10-
|
12
|
+
date: 2013-10-09 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: beefcake
|