lpxc 0.0.5 → 0.0.7
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/lib/lpxc.rb +51 -33
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a9a59ea66505168840a485b178c9f805df781f4b
|
4
|
+
data.tar.gz: 1181f1e2976a3a6a0fccf4e88a006c66bca90815
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 2c7f0c812aa0f867262d7e178bafa9e804704d0493d5951b65334d479253c3566162cbde8a6ebd9c82f4534e0b650d5780d7bee6b721aee27d57b48d411d02ff
|
7
|
+
data.tar.gz: ef326d1790d550779e7c6e86851228d0dc16fc1da8e87b735ce7a05dab91154ba99291184212c2134b2a6a644f39f983fc757376a47c5f34ab4b2ce7f3362dde
|
data/lib/lpxc.rb
CHANGED
@@ -4,6 +4,30 @@ require 'uri'
|
|
4
4
|
require 'thread'
|
5
5
|
require 'timeout'
|
6
6
|
|
7
|
+
class LogMsgQueue
|
8
|
+
def initialize(max)
|
9
|
+
@locker = Mutex.new
|
10
|
+
@max = max
|
11
|
+
@array = []
|
12
|
+
end
|
13
|
+
|
14
|
+
def enqueue(msg)
|
15
|
+
@locker.synchronize {@array << msg}
|
16
|
+
end
|
17
|
+
|
18
|
+
def flush
|
19
|
+
@locker.synchronize do
|
20
|
+
old = @array
|
21
|
+
@array = []
|
22
|
+
return old
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def full?
|
27
|
+
@locker.synchronize {@array.size >= @max}
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
7
31
|
class Lpxc
|
8
32
|
|
9
33
|
#After parsing opts and initializing defaults, the initializer
|
@@ -50,24 +74,19 @@ class Lpxc
|
|
50
74
|
Thread.new {delay_flush} if opts[:disable_delay_flush].nil?
|
51
75
|
end
|
52
76
|
|
53
|
-
#
|
54
|
-
#
|
55
|
-
#
|
56
|
-
|
57
|
-
|
58
|
-
# was not specified in the initializer, then the user portion of the
|
59
|
-
# LOGPLEX_URL will be used.
|
60
|
-
def puts(msg, tok=nil)
|
77
|
+
#The interface to publish logs into the stream.
|
78
|
+
#This function will set the log message to the current time in UTC.
|
79
|
+
#If the buffer for this token's log messages is full, it will flush the buffer.
|
80
|
+
def puts(msg, tok=@default_token)
|
81
|
+
q = nil
|
61
82
|
@hash_lock.synchronize do
|
62
83
|
#Messages are grouped by their token since 1 http request
|
63
84
|
#to logplex must only contain log messages belonging to a single token.
|
64
|
-
q = @hash[tok] ||=
|
65
|
-
#This call will block if the queue is full.
|
66
|
-
#However this should never happen since the next command will flush
|
67
|
-
#the queue if we add the last item.
|
68
|
-
q.enq({:t => Time.now.utc, :token => (tok || default_token), :msg => msg})
|
69
|
-
flush if q.size == q.max
|
85
|
+
q = @hash[tok] ||= LogMsgQueue.new(@batch_size)
|
70
86
|
end
|
87
|
+
q.enqueue({:t => Time.now.utc, :token => tok, :msg => msg})
|
88
|
+
# Flush all of the queues if any queue is full.
|
89
|
+
flush if q.full?
|
71
90
|
end
|
72
91
|
|
73
92
|
#Wait until all of the data has been cleared from memory.
|
@@ -80,22 +99,25 @@ class Lpxc
|
|
80
99
|
@req_in_flight.zero?
|
81
100
|
end
|
82
101
|
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
102
|
+
# Empty all log messages into a request queue. Messages will be grouped
|
103
|
+
# by token such that each request contains messages with homogeneus tokens.
|
104
|
+
# A seperate thread will process the requests.
|
105
|
+
def flush
|
106
|
+
to_be_processed = nil
|
107
|
+
@hash_lock.synchronize do
|
108
|
+
to_be_processed = @hash
|
109
|
+
@hash = {}
|
110
|
+
end
|
111
|
+
process_hash(to_be_processed)
|
87
112
|
end
|
88
113
|
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
def flush
|
94
|
-
@hash.each do |tok, msgs|
|
114
|
+
private
|
115
|
+
|
116
|
+
def process_hash(h)
|
117
|
+
h.each do |tok, queue|
|
95
118
|
#Copy the messages from the queue into the payload array.
|
96
|
-
payloads =
|
97
|
-
|
98
|
-
return if payloads.nil? || payloads.empty?
|
119
|
+
payloads = queue.flush
|
120
|
+
next if payloads.nil? || payloads.empty?
|
99
121
|
|
100
122
|
#Use the payloads array to build a string that will be
|
101
123
|
#used as the http body for the logplex request.
|
@@ -107,16 +129,14 @@ class Lpxc
|
|
107
129
|
#Build a new HTTP request and place it into the queue
|
108
130
|
#to be processed by the HTTP connection.
|
109
131
|
req = Net::HTTP::Post.new(@logplex_url.path)
|
110
|
-
req.basic_auth("token",
|
132
|
+
req.basic_auth("token", tok)
|
111
133
|
req.add_field('Content-Type', 'application/logplex-1')
|
112
134
|
req.body = body
|
113
135
|
@request_queue.enq(req)
|
114
|
-
@hash.delete(tok)
|
115
136
|
@last_flush = Time.now
|
116
137
|
end
|
117
138
|
end
|
118
139
|
|
119
|
-
|
120
140
|
#This method must be called in order for the messages to be sent to Logplex.
|
121
141
|
#This method also spawns a thread that allows the messages to be batched.
|
122
142
|
#Messages are flushed from memory every 500ms or when we have 300 messages,
|
@@ -124,9 +144,7 @@ class Lpxc
|
|
124
144
|
def delay_flush
|
125
145
|
loop do
|
126
146
|
begin
|
127
|
-
if interval_ready?
|
128
|
-
@hash_lock.synchronize {flush}
|
129
|
-
end
|
147
|
+
flush if interval_ready?
|
130
148
|
sleep(0.01)
|
131
149
|
rescue => e
|
132
150
|
$stderr.puts("at=start-error error=#{e.message}") if ENV['DEBUG']
|