rest-ftp-daemon 0.30.1 → 0.41
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 +8 -8
- data/Gemfile.lock +11 -4
- data/README.md +30 -6
- data/bin/rest-ftp-daemon +16 -9
- data/config.ru +9 -1
- data/lib/rest-ftp-daemon.rb +13 -1
- data/lib/rest-ftp-daemon/api/defaults.rb +58 -0
- data/lib/rest-ftp-daemon/api/jobs.rb +151 -0
- data/lib/rest-ftp-daemon/api/root.rb +79 -0
- data/lib/rest-ftp-daemon/common.rb +49 -0
- data/lib/rest-ftp-daemon/config.rb +9 -2
- data/lib/rest-ftp-daemon/exceptions.rb +6 -1
- data/lib/rest-ftp-daemon/job.rb +69 -23
- data/lib/rest-ftp-daemon/job_queue.rb +105 -0
- data/lib/rest-ftp-daemon/logger.rb +7 -0
- data/lib/rest-ftp-daemon/notification.rb +80 -0
- data/lib/rest-ftp-daemon/worker_pool.rb +63 -0
- data/lib/rest-ftp-daemon/www.rb +6 -0
- data/rest-ftp-daemon.gemspec +2 -2
- metadata +15 -7
- data/lib/rest-ftp-daemon/server.rb +0 -237
@@ -0,0 +1,63 @@
|
|
1
|
+
module RestFtpDaemon
|
2
|
+
class WorkerPool < RestFtpDaemon::Common
|
3
|
+
|
4
|
+
attr_reader :requested, :processed
|
5
|
+
|
6
|
+
def initialize(number_threads)
|
7
|
+
# Check parameters
|
8
|
+
raise "A thread count of #{number_threads} is less than one" if number_threads < 1
|
9
|
+
@wid = "-"
|
10
|
+
|
11
|
+
# Call super
|
12
|
+
super()
|
13
|
+
|
14
|
+
# Create worker threads
|
15
|
+
number_threads.times do
|
16
|
+
Thread.new { run }
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
def wait
|
21
|
+
item = @out.pop
|
22
|
+
@lock.synchronize { @processed += 1 }
|
23
|
+
block_given? ? (yield item) : item
|
24
|
+
end
|
25
|
+
|
26
|
+
def progname
|
27
|
+
"WORKER #{@wid}"
|
28
|
+
end
|
29
|
+
# progname = "Job [#{id}]" unless id.nil?
|
30
|
+
# progname = "Worker [#{id}]" unless worker_id.nil?
|
31
|
+
|
32
|
+
def run
|
33
|
+
# Generate a random key
|
34
|
+
@wid = SecureRandom.hex(2)
|
35
|
+
|
36
|
+
begin
|
37
|
+
loop do
|
38
|
+
info "worker [#{@wid}] waiting for a job... "
|
39
|
+
|
40
|
+
# Wait for a job to come into the queue
|
41
|
+
job = $queue.pop
|
42
|
+
prefix = "working on job [#{job.id}]"
|
43
|
+
|
44
|
+
# Do the job
|
45
|
+
info "job [#{job.id}] processing: #{job.inspect}"
|
46
|
+
job.process
|
47
|
+
|
48
|
+
end
|
49
|
+
rescue Exception => ex
|
50
|
+
info 'WORKER UNHANDLED EXCEPTION: ', ex.message , "\n", ex.backtrace.join("\n")
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def process job
|
55
|
+
|
56
|
+
@lock.synchronize do
|
57
|
+
job.dummy
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
61
|
+
|
62
|
+
end
|
63
|
+
end
|
data/rest-ftp-daemon.gemspec
CHANGED
@@ -4,7 +4,7 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
|
4
4
|
require 'rest-ftp-daemon/config'
|
5
5
|
|
6
6
|
Gem::Specification.new do |spec|
|
7
|
-
spec.name =
|
7
|
+
spec.name = RestFtpDaemon::NAME
|
8
8
|
spec.date = Time.now.strftime("%Y-%m-%d")
|
9
9
|
spec.authors = ["Bruno MEDICI"]
|
10
10
|
spec.email = "rest-ftp-daemon@bmconseil.com"
|
@@ -23,7 +23,7 @@ Gem::Specification.new do |spec|
|
|
23
23
|
spec.add_development_dependency "bundler", "~> 1.6"
|
24
24
|
spec.add_development_dependency "rake"
|
25
25
|
|
26
|
-
spec.add_runtime_dependency "thin"
|
26
|
+
spec.add_runtime_dependency "thin", "~> 1.6"
|
27
27
|
spec.add_runtime_dependency "grape"
|
28
28
|
spec.add_runtime_dependency "json"
|
29
29
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rest-ftp-daemon
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: '0.41'
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bruno MEDICI
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-09-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -42,16 +42,16 @@ dependencies:
|
|
42
42
|
name: thin
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- -
|
45
|
+
- - ~>
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version: '
|
47
|
+
version: '1.6'
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- -
|
52
|
+
- - ~>
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version: '
|
54
|
+
version: '1.6'
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
56
|
name: grape
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
@@ -97,10 +97,18 @@ files:
|
|
97
97
|
- bin/rest-ftp-daemon
|
98
98
|
- config.ru
|
99
99
|
- lib/rest-ftp-daemon.rb
|
100
|
+
- lib/rest-ftp-daemon/api/defaults.rb
|
101
|
+
- lib/rest-ftp-daemon/api/jobs.rb
|
102
|
+
- lib/rest-ftp-daemon/api/root.rb
|
103
|
+
- lib/rest-ftp-daemon/common.rb
|
100
104
|
- lib/rest-ftp-daemon/config.rb
|
101
105
|
- lib/rest-ftp-daemon/exceptions.rb
|
102
106
|
- lib/rest-ftp-daemon/job.rb
|
103
|
-
- lib/rest-ftp-daemon/
|
107
|
+
- lib/rest-ftp-daemon/job_queue.rb
|
108
|
+
- lib/rest-ftp-daemon/logger.rb
|
109
|
+
- lib/rest-ftp-daemon/notification.rb
|
110
|
+
- lib/rest-ftp-daemon/worker_pool.rb
|
111
|
+
- lib/rest-ftp-daemon/www.rb
|
104
112
|
- rest-ftp-daemon.gemspec
|
105
113
|
- test/helper.rb
|
106
114
|
- test/test_rest-ftp-daemon.rb
|
@@ -1,237 +0,0 @@
|
|
1
|
-
module RestFtpDaemon
|
2
|
-
|
3
|
-
class API < Grape::API
|
4
|
-
version 'v1', using: :header, vendor: 'ftven'
|
5
|
-
format :json
|
6
|
-
|
7
|
-
|
8
|
-
######################################################################
|
9
|
-
####### INIT
|
10
|
-
######################################################################
|
11
|
-
def initialize
|
12
|
-
# Setup logger
|
13
|
-
@@logger = Logger.new(APP_LOGTO, 'daily')
|
14
|
-
# @@queue = Queue.new
|
15
|
-
|
16
|
-
# Create new thread group
|
17
|
-
@@threads = ThreadGroup.new
|
18
|
-
|
19
|
-
# Other stuff
|
20
|
-
@@last_worker_id = 0
|
21
|
-
super
|
22
|
-
end
|
23
|
-
|
24
|
-
######################################################################
|
25
|
-
####### HELPERS
|
26
|
-
######################################################################
|
27
|
-
helpers do
|
28
|
-
def api_error exception
|
29
|
-
{
|
30
|
-
:error => exception.class,
|
31
|
-
:errmsg => exception.message,
|
32
|
-
:backtrace => exception.backtrace.first,
|
33
|
-
#:backtrace => exception.backtrace,
|
34
|
-
}
|
35
|
-
end
|
36
|
-
|
37
|
-
def info msg=""
|
38
|
-
@@logger.info msg
|
39
|
-
end
|
40
|
-
|
41
|
-
def threads_with_id job_id
|
42
|
-
@@threads.list.select do |thread|
|
43
|
-
next unless thread[:job].is_a? Job
|
44
|
-
thread[:job].id == job_id
|
45
|
-
end
|
46
|
-
end
|
47
|
-
|
48
|
-
def job_describe job_id
|
49
|
-
# Find threads with tihs id
|
50
|
-
threads = threads_with_id job_id
|
51
|
-
raise RestFtpDaemon::JobNotFound if threads.empty?
|
52
|
-
|
53
|
-
# Find first job with tihs id
|
54
|
-
job = threads.first[:job]
|
55
|
-
raise RestFtpDaemon::JobNotFound unless job.is_a? Job
|
56
|
-
description = job.describe
|
57
|
-
|
58
|
-
# Return job description
|
59
|
-
description
|
60
|
-
end
|
61
|
-
|
62
|
-
def job_delete job_id
|
63
|
-
# Find threads with tihs id
|
64
|
-
threads = threads_with_id job_id
|
65
|
-
raise RestFtpDaemon::JobNotFound if threads.empty?
|
66
|
-
|
67
|
-
# Get description just before terminating the job
|
68
|
-
job = threads.first[:job]
|
69
|
-
raise RestFtpDaemon::JobNotFound unless job.is_a? Job
|
70
|
-
description = job.describe
|
71
|
-
|
72
|
-
# Kill those threads
|
73
|
-
threads.each do |t|
|
74
|
-
Thread.kill(t)
|
75
|
-
end
|
76
|
-
|
77
|
-
# Return job description
|
78
|
-
description
|
79
|
-
end
|
80
|
-
|
81
|
-
def job_list
|
82
|
-
@@threads.list.map do |thread|
|
83
|
-
next unless thread[:job].is_a? Job
|
84
|
-
thread[:job].describe
|
85
|
-
end
|
86
|
-
end
|
87
|
-
|
88
|
-
end
|
89
|
-
|
90
|
-
|
91
|
-
######################################################################
|
92
|
-
####### API DEFINITION
|
93
|
-
######################################################################
|
94
|
-
|
95
|
-
# Spawn a new thread for this new job
|
96
|
-
# post '/push' do
|
97
|
-
# @@queue << rand(999)
|
98
|
-
# end
|
99
|
-
|
100
|
-
# Server global status
|
101
|
-
get '/' do
|
102
|
-
info "GET /"
|
103
|
-
|
104
|
-
status 200
|
105
|
-
{
|
106
|
-
app_name: APP_NAME,
|
107
|
-
hostname: `hostname`.chomp,
|
108
|
-
version: RestFtpDaemon::VERSION,
|
109
|
-
started: APP_STARTED,
|
110
|
-
uptime: (Time.now - APP_STARTED).round(1),
|
111
|
-
}
|
112
|
-
end
|
113
|
-
|
114
|
-
# Server test
|
115
|
-
get '/test' do
|
116
|
-
info "GET /tests"
|
117
|
-
begin
|
118
|
-
raise RestFtpDaemon::DummyException
|
119
|
-
rescue RestFtpDaemon::RestFtpDaemonException => exception
|
120
|
-
status 501
|
121
|
-
api_error exception
|
122
|
-
rescue Exception => exception
|
123
|
-
status 501
|
124
|
-
api_error exception
|
125
|
-
else
|
126
|
-
status 200
|
127
|
-
{}
|
128
|
-
end
|
129
|
-
end
|
130
|
-
|
131
|
-
# List jobs
|
132
|
-
get "/jobs" do
|
133
|
-
info "GET /jobs"
|
134
|
-
begin
|
135
|
-
response = job_list
|
136
|
-
rescue RestFtpDaemonException => exception
|
137
|
-
status 501
|
138
|
-
api_error exception
|
139
|
-
rescue Exception => exception
|
140
|
-
status 501
|
141
|
-
api_error exception
|
142
|
-
else
|
143
|
-
status 200
|
144
|
-
response
|
145
|
-
end
|
146
|
-
end
|
147
|
-
|
148
|
-
# Get job info
|
149
|
-
get "/jobs/:id" do
|
150
|
-
info "GET /jobs/#{params[:id]}"
|
151
|
-
begin
|
152
|
-
response = job_describe params[:id].to_i
|
153
|
-
rescue RestFtpDaemon::JobNotFound => exception
|
154
|
-
status 404
|
155
|
-
api_error exception
|
156
|
-
rescue RestFtpDaemonException => exception
|
157
|
-
status 500
|
158
|
-
api_error exception
|
159
|
-
rescue Exception => exception
|
160
|
-
status 501
|
161
|
-
api_error exception
|
162
|
-
else
|
163
|
-
status 200
|
164
|
-
response
|
165
|
-
end
|
166
|
-
end
|
167
|
-
|
168
|
-
# Delete jobs
|
169
|
-
delete "/jobs/:id" do
|
170
|
-
info "DELETE /jobs/#{params[:name]}"
|
171
|
-
begin
|
172
|
-
response = job_delete params[:id].to_i
|
173
|
-
rescue RestFtpDaemon::JobNotFound => exception
|
174
|
-
status 404
|
175
|
-
api_error exception
|
176
|
-
rescue RestFtpDaemonException => exception
|
177
|
-
status 500
|
178
|
-
api_error exception
|
179
|
-
rescue Exception => exception
|
180
|
-
status 501
|
181
|
-
api_error exception
|
182
|
-
else
|
183
|
-
status 200
|
184
|
-
response
|
185
|
-
end
|
186
|
-
end
|
187
|
-
|
188
|
-
# Spawn a new thread for this new job
|
189
|
-
post '/jobs' do
|
190
|
-
info "POST /jobs: #{request.body.read}"
|
191
|
-
begin
|
192
|
-
# Extract params
|
193
|
-
request.body.rewind
|
194
|
-
params = JSON.parse request.body.read
|
195
|
-
|
196
|
-
# Create a new job
|
197
|
-
job_id = @@last_worker_id += 1
|
198
|
-
job = Job.new(job_id, params)
|
199
|
-
|
200
|
-
# Put it inside a thread
|
201
|
-
th = Thread.new(job) do |thread|
|
202
|
-
# Tnitialize thread
|
203
|
-
Thread.abort_on_exception = true
|
204
|
-
Thread.current[:job] = job
|
205
|
-
|
206
|
-
# Do the job
|
207
|
-
job.process
|
208
|
-
|
209
|
-
# Wait for a few seconds before cleaning up the job
|
210
|
-
job.wander RestFtpDaemon::THREAD_SLEEP_BEFORE_DIE
|
211
|
-
end
|
212
|
-
|
213
|
-
# Stack it to the pool
|
214
|
-
#@@queue << job
|
215
|
-
@@threads.add th
|
216
|
-
|
217
|
-
# And start it asynchronously
|
218
|
-
#job.future.process
|
219
|
-
|
220
|
-
rescue JSON::ParserError => exception
|
221
|
-
status 406
|
222
|
-
api_error exception
|
223
|
-
rescue RestFtpDaemonException => exception
|
224
|
-
status 412
|
225
|
-
api_error exception
|
226
|
-
rescue Exception => exception
|
227
|
-
status 501
|
228
|
-
api_error exception
|
229
|
-
else
|
230
|
-
status 201
|
231
|
-
job.describe
|
232
|
-
end
|
233
|
-
end
|
234
|
-
|
235
|
-
end
|
236
|
-
|
237
|
-
end
|