sanford 0.10.1 → 0.11.0
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/Gemfile +1 -1
- data/README.md +41 -56
- data/Rakefile +0 -1
- data/bench/client.rb +8 -3
- data/bench/{services.rb → config.sanford} +11 -6
- data/bench/{runner.rb → report.rb} +2 -2
- data/bench/report.txt +32 -32
- data/lib/sanford/cli.rb +42 -28
- data/lib/sanford/config_file.rb +79 -0
- data/lib/sanford/{worker.rb → connection_handler.rb} +28 -20
- data/lib/sanford/error_handler.rb +7 -7
- data/lib/sanford/pid_file.rb +42 -0
- data/lib/sanford/process.rb +136 -0
- data/lib/sanford/process_signal.rb +20 -0
- data/lib/sanford/route.rb +48 -0
- data/lib/sanford/router.rb +36 -0
- data/lib/sanford/runner.rb +30 -58
- data/lib/sanford/sanford_runner.rb +19 -9
- data/lib/sanford/server.rb +211 -42
- data/lib/sanford/server_data.rb +47 -0
- data/lib/sanford/service_handler.rb +8 -46
- data/lib/sanford/template_source.rb +19 -2
- data/lib/sanford/test_runner.rb +27 -28
- data/lib/sanford/version.rb +1 -1
- data/lib/sanford.rb +1 -23
- data/sanford.gemspec +4 -5
- data/test/helper.rb +3 -20
- data/test/support/app_server.rb +142 -0
- data/test/support/config.sanford +7 -0
- data/test/support/config_invalid_run.sanford +3 -0
- data/test/support/config_no_run.sanford +0 -0
- data/test/support/fake_server_connection.rb +58 -0
- data/test/support/pid_file_spy.rb +19 -0
- data/test/support/template.erb +1 -0
- data/test/system/server_tests.rb +378 -0
- data/test/system/service_handler_tests.rb +224 -0
- data/test/unit/cli_tests.rb +187 -0
- data/test/unit/config_file_tests.rb +59 -0
- data/test/unit/connection_handler_tests.rb +254 -0
- data/test/unit/error_handler_tests.rb +30 -35
- data/test/unit/pid_file_tests.rb +70 -0
- data/test/unit/process_signal_tests.rb +61 -0
- data/test/unit/process_tests.rb +428 -0
- data/test/unit/route_tests.rb +92 -0
- data/test/unit/router_tests.rb +65 -0
- data/test/unit/runner_tests.rb +61 -15
- data/test/unit/sanford_runner_tests.rb +162 -28
- data/test/unit/sanford_tests.rb +0 -8
- data/test/unit/server_data_tests.rb +87 -0
- data/test/unit/server_tests.rb +502 -21
- data/test/unit/service_handler_tests.rb +114 -219
- data/test/unit/template_engine_tests.rb +1 -1
- data/test/unit/template_source_tests.rb +56 -16
- data/test/unit/test_runner_tests.rb +206 -0
- metadata +67 -67
- data/bench/tasks.rb +0 -41
- data/lib/sanford/config.rb +0 -28
- data/lib/sanford/host.rb +0 -129
- data/lib/sanford/host_data.rb +0 -65
- data/lib/sanford/hosts.rb +0 -38
- data/lib/sanford/manager.rb +0 -275
- data/test/support/fake_connection.rb +0 -36
- data/test/support/helpers.rb +0 -17
- data/test/support/service_handlers.rb +0 -154
- data/test/support/services.rb +0 -123
- data/test/support/simple_client.rb +0 -62
- data/test/system/request_handling_tests.rb +0 -306
- data/test/unit/config_tests.rb +0 -56
- data/test/unit/host_data_tests.rb +0 -71
- data/test/unit/host_tests.rb +0 -141
- data/test/unit/hosts_tests.rb +0 -50
- data/test/unit/manager_tests.rb +0 -195
- data/test/unit/worker_tests.rb +0 -24
data/lib/sanford/host_data.rb
DELETED
@@ -1,65 +0,0 @@
|
|
1
|
-
require 'sanford/service_handler'
|
2
|
-
require 'sanford/sanford_runner'
|
3
|
-
|
4
|
-
module Sanford
|
5
|
-
|
6
|
-
class HostData
|
7
|
-
|
8
|
-
# When trying to run a server for a host, we need to build up the host's
|
9
|
-
# data to increase the performance of the server. This is done by
|
10
|
-
# constantizing a host's handlers and merging a host's configuration with
|
11
|
-
# optional overrides.
|
12
|
-
|
13
|
-
# NOTE: The `name` attribute shouldn't be removed, it is used to identify
|
14
|
-
# a `HostData`, particularly in error handlers
|
15
|
-
|
16
|
-
attr_reader :name, :logger, :verbose, :keep_alive, :error_procs
|
17
|
-
|
18
|
-
def initialize(service_host, options = nil)
|
19
|
-
service_host.configuration.init_procs.each(&:call)
|
20
|
-
|
21
|
-
overrides = self.remove_nil_values(options || {})
|
22
|
-
configuration = service_host.configuration.to_hash.merge(overrides)
|
23
|
-
|
24
|
-
@name = configuration[:name]
|
25
|
-
@logger = configuration[:logger]
|
26
|
-
@verbose = configuration[:verbose_logging]
|
27
|
-
@keep_alive = configuration[:receives_keep_alive]
|
28
|
-
@error_procs = configuration[:error_procs]
|
29
|
-
|
30
|
-
@handlers = service_host.services.inject({}) do |h, (name, handler_class_name)|
|
31
|
-
h.merge({ name => self.constantize(handler_class_name) })
|
32
|
-
end
|
33
|
-
end
|
34
|
-
|
35
|
-
def handler_class_for(service)
|
36
|
-
@handlers[service] || raise(Sanford::NotFoundError)
|
37
|
-
end
|
38
|
-
|
39
|
-
def run(handler_class, request)
|
40
|
-
SanfordRunner.new(handler_class, request, self.logger).run
|
41
|
-
end
|
42
|
-
|
43
|
-
protected
|
44
|
-
|
45
|
-
def constantize(handler_class_name)
|
46
|
-
Sanford::ServiceHandler.constantize(handler_class_name) ||
|
47
|
-
raise(Sanford::NoHandlerClassError.new(handler_class_name))
|
48
|
-
end
|
49
|
-
|
50
|
-
def remove_nil_values(hash)
|
51
|
-
hash.inject({}){|h, (k, v)| !v.nil? ? h.merge({ k => v }) : h }
|
52
|
-
end
|
53
|
-
|
54
|
-
end
|
55
|
-
|
56
|
-
NotFoundError = Class.new(RuntimeError)
|
57
|
-
|
58
|
-
class NoHandlerClassError < RuntimeError
|
59
|
-
def initialize(handler_class_name)
|
60
|
-
super "Sanford couldn't find the service handler '#{handler_class_name}'."\
|
61
|
-
" It doesn't exist or hasn't been required in yet."
|
62
|
-
end
|
63
|
-
end
|
64
|
-
|
65
|
-
end
|
data/lib/sanford/hosts.rb
DELETED
@@ -1,38 +0,0 @@
|
|
1
|
-
require 'set'
|
2
|
-
require 'sanford/host'
|
3
|
-
|
4
|
-
module Sanford
|
5
|
-
|
6
|
-
class Hosts
|
7
|
-
|
8
|
-
def initialize(values = [])
|
9
|
-
@set = Set.new(values)
|
10
|
-
end
|
11
|
-
|
12
|
-
def method_missing(method, *args, &block)
|
13
|
-
@set.send(method, *args, &block)
|
14
|
-
end
|
15
|
-
|
16
|
-
def respond_to?(method)
|
17
|
-
super || @set.respond_to?(method)
|
18
|
-
end
|
19
|
-
|
20
|
-
# We want class names to take precedence over a configured name, so that if
|
21
|
-
# a user specifies a specific class, they always get it
|
22
|
-
def find(name)
|
23
|
-
find_by_class_name(name) || find_by_name(name)
|
24
|
-
end
|
25
|
-
|
26
|
-
private
|
27
|
-
|
28
|
-
def find_by_class_name(class_name)
|
29
|
-
@set.detect{|host_class| host_class.to_s == class_name.to_s }
|
30
|
-
end
|
31
|
-
|
32
|
-
def find_by_name(name)
|
33
|
-
@set.detect{|host_class| host_class.name == name.to_s }
|
34
|
-
end
|
35
|
-
|
36
|
-
end
|
37
|
-
|
38
|
-
end
|
data/lib/sanford/manager.rb
DELETED
@@ -1,275 +0,0 @@
|
|
1
|
-
require 'sanford/cli'
|
2
|
-
require 'sanford/server'
|
3
|
-
|
4
|
-
module Sanford
|
5
|
-
|
6
|
-
module Manager
|
7
|
-
|
8
|
-
def self.call(action, options = nil)
|
9
|
-
get_handler_class(action).new(options).tap{ |manager| manager.send(action) }
|
10
|
-
end
|
11
|
-
|
12
|
-
def self.get_handler_class(action)
|
13
|
-
case action.to_sym
|
14
|
-
when :start, :run
|
15
|
-
ServerHandler
|
16
|
-
when :stop, :restart
|
17
|
-
SignalHandler
|
18
|
-
end
|
19
|
-
end
|
20
|
-
|
21
|
-
class Config
|
22
|
-
attr_reader :host_name, :host, :ip, :port, :pid, :pid_file, :restart_dir
|
23
|
-
attr_reader :file_descriptor, :client_file_descriptors
|
24
|
-
|
25
|
-
def initialize(opts = nil)
|
26
|
-
options = OpenStruct.new(opts || {})
|
27
|
-
@host_name = ENV['SANFORD_HOST'] || options.host
|
28
|
-
|
29
|
-
@host = @host_name ? Sanford.hosts.find(@host_name) : Sanford.hosts.first
|
30
|
-
@host ||= NullHost.new
|
31
|
-
|
32
|
-
@file_descriptor = ENV['SANFORD_SERVER_FD'] || options.file_descriptor
|
33
|
-
@file_descriptor = @file_descriptor.to_i if @file_descriptor
|
34
|
-
@ip = ENV['SANFORD_IP'] || options.ip || @host.ip
|
35
|
-
@port = ENV['SANFORD_PORT'] || options.port || @host.port
|
36
|
-
@port = @port.to_i if @port
|
37
|
-
|
38
|
-
client_fds_str = ENV['SANFORD_CLIENT_FDS'] || options.client_fds || ""
|
39
|
-
@client_file_descriptors = client_fds_str.split(',').map(&:to_i)
|
40
|
-
|
41
|
-
@pid_file = PIDFile.new(ENV['SANFORD_PID_FILE'] || options.pid_file || @host.pid_file)
|
42
|
-
@pid = options.pid || @pid_file.pid
|
43
|
-
|
44
|
-
@restart_dir = ENV['SANFORD_RESTART_DIR'] || options.restart_dir
|
45
|
-
end
|
46
|
-
|
47
|
-
def listen_args
|
48
|
-
@file_descriptor ? [ @file_descriptor ] : [ @ip, @port ]
|
49
|
-
end
|
50
|
-
|
51
|
-
def has_listen_args?
|
52
|
-
!!@file_descriptor || !!(@ip && @port)
|
53
|
-
end
|
54
|
-
|
55
|
-
def found_host?
|
56
|
-
!@host.kind_of?(NullHost)
|
57
|
-
end
|
58
|
-
|
59
|
-
class NullHost
|
60
|
-
[ :ip, :port, :pid_file ].each do |method_name|
|
61
|
-
define_method(method_name){ }
|
62
|
-
end
|
63
|
-
end
|
64
|
-
|
65
|
-
class PIDFile
|
66
|
-
DEF_FILE = '/dev/null'
|
67
|
-
|
68
|
-
def initialize(path)
|
69
|
-
@path = (path || DEF_FILE).to_s
|
70
|
-
end
|
71
|
-
|
72
|
-
def pid
|
73
|
-
pid = File.read(@path).strip if File.exists?(@path)
|
74
|
-
pid.to_i if pid && !pid.empty?
|
75
|
-
end
|
76
|
-
|
77
|
-
def write
|
78
|
-
begin
|
79
|
-
File.open(@path, 'w'){|f| f.puts Process.pid }
|
80
|
-
rescue Errno::ENOENT => err
|
81
|
-
e = RuntimeError.new("Can't write pid to file `#{@path}`")
|
82
|
-
e.set_backtrace(err.backtrace)
|
83
|
-
raise e
|
84
|
-
end
|
85
|
-
end
|
86
|
-
|
87
|
-
def remove
|
88
|
-
FileUtils.rm_f(@path)
|
89
|
-
end
|
90
|
-
|
91
|
-
def to_s
|
92
|
-
@path
|
93
|
-
end
|
94
|
-
end
|
95
|
-
|
96
|
-
end
|
97
|
-
|
98
|
-
class ServerHandler
|
99
|
-
|
100
|
-
def initialize(options = nil)
|
101
|
-
@config = Config.new(options)
|
102
|
-
raise Sanford::NoHostError.new(@config.host_name) if !@config.found_host?
|
103
|
-
raise Sanford::InvalidHostError.new(@config.host) if !@config.has_listen_args?
|
104
|
-
@host = @config.host
|
105
|
-
@logger = @host.logger
|
106
|
-
|
107
|
-
@server_options = {}
|
108
|
-
# FUTURE allow passing through dat-tcp options (min/max workers)
|
109
|
-
# FUTURE merge in host options for verbose / keep_alive
|
110
|
-
|
111
|
-
@restart_cmd = RestartCmd.new(@config)
|
112
|
-
end
|
113
|
-
|
114
|
-
def run
|
115
|
-
self.run! false
|
116
|
-
end
|
117
|
-
|
118
|
-
def start
|
119
|
-
self.run! true
|
120
|
-
end
|
121
|
-
|
122
|
-
protected
|
123
|
-
|
124
|
-
def run!(daemonize = false)
|
125
|
-
daemonize!(true) if daemonize && !ENV['SANFORD_SKIP_DAEMONIZE']
|
126
|
-
Sanford::Server.new(@host, @server_options).tap do |server|
|
127
|
-
log "Starting #{@host.name} server..."
|
128
|
-
|
129
|
-
server.listen(*@config.listen_args)
|
130
|
-
$0 = ProcessName.new(@host.name, server.ip, server.port)
|
131
|
-
log "Listening on #{server.ip}:#{server.port}"
|
132
|
-
|
133
|
-
@config.pid_file.write
|
134
|
-
log "PID: #{Process.pid}"
|
135
|
-
|
136
|
-
Signal.trap("TERM"){ self.stop!(server) }
|
137
|
-
Signal.trap("INT"){ self.halt!(server) }
|
138
|
-
Signal.trap("USR2"){ self.restart!(server) }
|
139
|
-
|
140
|
-
server_thread = server.run(@config.client_file_descriptors)
|
141
|
-
log "#{@host.name} server started and ready."
|
142
|
-
server_thread.join
|
143
|
-
end
|
144
|
-
rescue RuntimeError => err
|
145
|
-
log "Error: #{err.message}"
|
146
|
-
log "#{@host.name} server never started."
|
147
|
-
ensure
|
148
|
-
@config.pid_file.remove
|
149
|
-
end
|
150
|
-
|
151
|
-
def restart!(server)
|
152
|
-
log "Restarting #{@host.name} server..."
|
153
|
-
server.pause
|
154
|
-
log "server paused"
|
155
|
-
|
156
|
-
ENV['SANFORD_HOST'] = @host.name
|
157
|
-
ENV['SANFORD_SERVER_FD'] = server.file_descriptor.to_s
|
158
|
-
ENV['SANFORD_CLIENT_FDS'] = server.client_file_descriptors.join(',')
|
159
|
-
ENV['SANFORD_SKIP_DAEMONIZE'] = 'yes'
|
160
|
-
|
161
|
-
log "calling exec ..."
|
162
|
-
Dir.chdir @restart_cmd.dir
|
163
|
-
Kernel.exec(*@restart_cmd.argv)
|
164
|
-
end
|
165
|
-
|
166
|
-
def stop!(server)
|
167
|
-
log "Stopping #{@host.name} server..."
|
168
|
-
server.stop
|
169
|
-
log "#{@host.name} server stopped."
|
170
|
-
end
|
171
|
-
|
172
|
-
def halt!(server)
|
173
|
-
log "Halting #{@host.name} server..."
|
174
|
-
server.halt false
|
175
|
-
log "#{@host.name} server halted."
|
176
|
-
end
|
177
|
-
|
178
|
-
# Full explanation: http://www.steve.org.uk/Reference/Unix/faq_2.html#SEC16
|
179
|
-
def daemonize!(no_chdir = false, no_close = false)
|
180
|
-
exit if fork
|
181
|
-
Process.setsid
|
182
|
-
exit if fork
|
183
|
-
Dir.chdir "/" unless no_chdir
|
184
|
-
if !no_close
|
185
|
-
null = File.open "/dev/null", 'w'
|
186
|
-
STDIN.reopen null
|
187
|
-
STDOUT.reopen null
|
188
|
-
STDERR.reopen null
|
189
|
-
end
|
190
|
-
return 0
|
191
|
-
end
|
192
|
-
|
193
|
-
def log(message)
|
194
|
-
@logger.info "[Sanford] #{message}"
|
195
|
-
end
|
196
|
-
|
197
|
-
class ProcessName < String
|
198
|
-
def initialize(name, ip, port)
|
199
|
-
super "#{[ name, ip, port ].join('_')}"
|
200
|
-
end
|
201
|
-
end
|
202
|
-
|
203
|
-
class RestartCmd
|
204
|
-
attr_reader :argv, :dir
|
205
|
-
|
206
|
-
def initialize(config = nil)
|
207
|
-
require 'rubygems'
|
208
|
-
config ||= OpenStruct.new
|
209
|
-
@dir = config.restart_dir || get_pwd
|
210
|
-
@argv = [ Gem.ruby, $0, ARGV.dup ].flatten
|
211
|
-
end
|
212
|
-
|
213
|
-
protected
|
214
|
-
|
215
|
-
# Trick from puma/unicorn. Favor PWD because it contains an unresolved
|
216
|
-
# symlink. This is useful when restarting after deploying; the original
|
217
|
-
# directory may be removed, but the symlink is pointing to a new
|
218
|
-
# directory.
|
219
|
-
def get_pwd
|
220
|
-
env_stat = File.stat(ENV['PWD'])
|
221
|
-
pwd_stat = File.stat(Dir.pwd)
|
222
|
-
if env_stat.ino == pwd_stat.ino && env_stat.dev == pwd_stat.dev
|
223
|
-
ENV['PWD']
|
224
|
-
else
|
225
|
-
Dir.pwd
|
226
|
-
end
|
227
|
-
end
|
228
|
-
|
229
|
-
end
|
230
|
-
|
231
|
-
end
|
232
|
-
|
233
|
-
class SignalHandler
|
234
|
-
|
235
|
-
def initialize(options = nil)
|
236
|
-
@config = Config.new(options)
|
237
|
-
raise Sanford::NoPIDError.new if !@config.pid
|
238
|
-
end
|
239
|
-
|
240
|
-
def stop
|
241
|
-
Process.kill("TERM", @config.pid)
|
242
|
-
end
|
243
|
-
|
244
|
-
def restart
|
245
|
-
Process.kill("USR2", @config.pid)
|
246
|
-
end
|
247
|
-
|
248
|
-
end
|
249
|
-
|
250
|
-
end
|
251
|
-
|
252
|
-
class NoHostError < CLIRB::Error
|
253
|
-
def initialize(host_name)
|
254
|
-
message = if Sanford.hosts.empty?
|
255
|
-
"No hosts have been defined. Please define a host before trying to run Sanford."
|
256
|
-
else
|
257
|
-
"A host couldn't be found with the name #{host_name.inspect}. "
|
258
|
-
end
|
259
|
-
super message
|
260
|
-
end
|
261
|
-
end
|
262
|
-
|
263
|
-
class InvalidHostError < CLIRB::Error
|
264
|
-
def initialize(host)
|
265
|
-
super "A port must be configured or provided to run a server for '#{host}'"
|
266
|
-
end
|
267
|
-
end
|
268
|
-
|
269
|
-
class NoPIDError < CLIRB::Error
|
270
|
-
def initialize
|
271
|
-
super "A PID or PID file is required"
|
272
|
-
end
|
273
|
-
end
|
274
|
-
|
275
|
-
end
|
@@ -1,36 +0,0 @@
|
|
1
|
-
class FakeConnection
|
2
|
-
|
3
|
-
attr_reader :read_data, :response, :write_stream_closed
|
4
|
-
|
5
|
-
def self.with_request(name, params = {}, raise_on_write = false)
|
6
|
-
request = Sanford::Protocol::Request.new(name, params)
|
7
|
-
self.new(request.to_hash, raise_on_write)
|
8
|
-
end
|
9
|
-
|
10
|
-
def initialize(*args)
|
11
|
-
if args.first.kind_of?(Sanford::Protocol::Connection)
|
12
|
-
protocol_connection = args.first
|
13
|
-
@read_data = proc{ protocol_connection.read }
|
14
|
-
@write_data = proc{|data| protocol_connection.write(data) }
|
15
|
-
else
|
16
|
-
@read_data, @raise_on_write = args
|
17
|
-
end
|
18
|
-
end
|
19
|
-
|
20
|
-
def read_data
|
21
|
-
@read_data.kind_of?(Proc) ? @read_data.call : @read_data
|
22
|
-
end
|
23
|
-
|
24
|
-
def write_data(data)
|
25
|
-
if @raise_on_write
|
26
|
-
@raise_on_write = false
|
27
|
-
raise 'test fail'
|
28
|
-
end
|
29
|
-
@response = Sanford::Protocol::Response.parse(data)
|
30
|
-
end
|
31
|
-
|
32
|
-
def close_write
|
33
|
-
@write_stream_closed = true
|
34
|
-
end
|
35
|
-
|
36
|
-
end
|
data/test/support/helpers.rb
DELETED
@@ -1,17 +0,0 @@
|
|
1
|
-
module Test
|
2
|
-
module SpawnServerHelper
|
3
|
-
|
4
|
-
def start_server(host, &block)
|
5
|
-
begin
|
6
|
-
server = Sanford::Server.new(host, { :ready_timeout => 0.1 })
|
7
|
-
server.listen(host.ip, host.port)
|
8
|
-
thread = server.run
|
9
|
-
yield
|
10
|
-
ensure
|
11
|
-
server.halt if server
|
12
|
-
thread.join if thread
|
13
|
-
end
|
14
|
-
end
|
15
|
-
|
16
|
-
end
|
17
|
-
end
|
@@ -1,154 +0,0 @@
|
|
1
|
-
class BasicServiceHandler
|
2
|
-
include Sanford::ServiceHandler
|
3
|
-
|
4
|
-
def run!
|
5
|
-
{ 'name' => 'Joe Test', 'email' => "joe.test@example.com" }
|
6
|
-
end
|
7
|
-
|
8
|
-
end
|
9
|
-
|
10
|
-
class SerializeErrorServiceHandler
|
11
|
-
include Sanford::ServiceHandler
|
12
|
-
|
13
|
-
# return data that fails BSON serialization
|
14
|
-
# BSON errors if it is sent date/datetime values
|
15
|
-
def run!
|
16
|
-
{ 'date' => Date.today,
|
17
|
-
'datetime' => DateTime.now
|
18
|
-
}
|
19
|
-
end
|
20
|
-
|
21
|
-
end
|
22
|
-
|
23
|
-
module CallbackServiceHandler
|
24
|
-
|
25
|
-
def self.included(receiver)
|
26
|
-
receiver.class_eval do
|
27
|
-
attr_reader :before_called, :after_called
|
28
|
-
attr_reader :before_init_called, :init_bang_called, :after_init_called
|
29
|
-
attr_reader :before_run_called, :run_bang_called, :after_run_called
|
30
|
-
attr_reader :second_before_init_called, :second_after_run_called
|
31
|
-
|
32
|
-
before do
|
33
|
-
@before_called = true
|
34
|
-
end
|
35
|
-
after do
|
36
|
-
@after_called = true
|
37
|
-
end
|
38
|
-
|
39
|
-
before_init do
|
40
|
-
@before_init_called = true
|
41
|
-
end
|
42
|
-
before_init do
|
43
|
-
@second_before_init_called = true
|
44
|
-
end
|
45
|
-
|
46
|
-
after_init do
|
47
|
-
@after_init_called = true
|
48
|
-
end
|
49
|
-
|
50
|
-
before_run do
|
51
|
-
@before_run_called = true
|
52
|
-
end
|
53
|
-
|
54
|
-
after_run do
|
55
|
-
@after_run_called = true
|
56
|
-
end
|
57
|
-
after_run do
|
58
|
-
@second_after_run_called = true
|
59
|
-
end
|
60
|
-
|
61
|
-
end
|
62
|
-
|
63
|
-
end
|
64
|
-
|
65
|
-
def init!
|
66
|
-
@init_bang_called = true
|
67
|
-
end
|
68
|
-
|
69
|
-
def run!
|
70
|
-
@run_bang_called = true
|
71
|
-
end
|
72
|
-
|
73
|
-
end
|
74
|
-
|
75
|
-
class FlagServiceHandler
|
76
|
-
include Sanford::ServiceHandler
|
77
|
-
include CallbackServiceHandler
|
78
|
-
|
79
|
-
end
|
80
|
-
|
81
|
-
class HaltingBehaviorServiceHandler
|
82
|
-
include Sanford::ServiceHandler
|
83
|
-
include CallbackServiceHandler
|
84
|
-
|
85
|
-
before_init do
|
86
|
-
halt_when('before_init')
|
87
|
-
end
|
88
|
-
|
89
|
-
def init!
|
90
|
-
super
|
91
|
-
halt_when('init!')
|
92
|
-
end
|
93
|
-
|
94
|
-
after_init do
|
95
|
-
halt_when('after_init')
|
96
|
-
end
|
97
|
-
|
98
|
-
before_run do
|
99
|
-
halt_when('before_run')
|
100
|
-
end
|
101
|
-
|
102
|
-
def run!
|
103
|
-
super
|
104
|
-
halt_when('run!')
|
105
|
-
end
|
106
|
-
|
107
|
-
after_run do
|
108
|
-
halt_when('after_run')
|
109
|
-
end
|
110
|
-
|
111
|
-
def halt_when(method_name)
|
112
|
-
return if ![*params['when']].include?(method_name)
|
113
|
-
halt(200, {
|
114
|
-
:message => "#{method_name} halting",
|
115
|
-
:data => {
|
116
|
-
:before_init_called => @before_init_called,
|
117
|
-
:init_bang_called => @init_bang_called,
|
118
|
-
:after_init_called => @after_init_called,
|
119
|
-
:before_run_called => @before_run_called,
|
120
|
-
:run_bang_called => @run_bang_called,
|
121
|
-
:after_run_called => @after_run_called
|
122
|
-
}
|
123
|
-
})
|
124
|
-
end
|
125
|
-
|
126
|
-
end
|
127
|
-
|
128
|
-
class RenderHandler
|
129
|
-
include Sanford::ServiceHandler
|
130
|
-
|
131
|
-
def run!
|
132
|
-
render params['template_name']
|
133
|
-
end
|
134
|
-
end
|
135
|
-
|
136
|
-
class RunOtherHandler
|
137
|
-
include Sanford::ServiceHandler
|
138
|
-
|
139
|
-
def run!
|
140
|
-
response = run_handler(HaltServiceHandler, 'code' => 200, 'data' => 'RunOtherHandler')
|
141
|
-
response.data
|
142
|
-
end
|
143
|
-
end
|
144
|
-
|
145
|
-
class HaltServiceHandler
|
146
|
-
include Sanford::ServiceHandler
|
147
|
-
|
148
|
-
def run!
|
149
|
-
halt params['code'], :message => params['message'], :data => params['data']
|
150
|
-
end
|
151
|
-
|
152
|
-
end
|
153
|
-
|
154
|
-
class InvalidServiceHandler; end
|
data/test/support/services.rb
DELETED
@@ -1,123 +0,0 @@
|
|
1
|
-
require 'logger'
|
2
|
-
|
3
|
-
class TestHost
|
4
|
-
include Sanford::Host
|
5
|
-
|
6
|
-
attr_accessor :init_has_been_called
|
7
|
-
|
8
|
-
init do
|
9
|
-
self.init_has_been_called = true
|
10
|
-
end
|
11
|
-
|
12
|
-
ip 'localhost'
|
13
|
-
port 12000
|
14
|
-
pid_file File.expand_path('../../../tmp/test_host.pid', __FILE__)
|
15
|
-
|
16
|
-
logger(Logger.new(File.expand_path("../../../log/test.log", __FILE__)).tap do |logger|
|
17
|
-
logger.level = Logger::DEBUG
|
18
|
-
end)
|
19
|
-
verbose_logging false
|
20
|
-
|
21
|
-
error do |exception, host_data, request|
|
22
|
-
if exception.kind_of?(::MyCustomError)
|
23
|
-
Sanford::Protocol::Response.new([ 987, 'custom error!' ])
|
24
|
-
end
|
25
|
-
end
|
26
|
-
|
27
|
-
service_handler_ns 'TestHost'
|
28
|
-
|
29
|
-
service :echo, 'Echo'
|
30
|
-
service 'bad', 'Bad'
|
31
|
-
service 'multiply', 'Multiply'
|
32
|
-
service 'halt_it', '::TestHost::HaltIt'
|
33
|
-
service 'authorized', 'Authorized'
|
34
|
-
service 'custom_error', 'CustomError'
|
35
|
-
|
36
|
-
class Echo
|
37
|
-
include Sanford::ServiceHandler
|
38
|
-
|
39
|
-
def run!
|
40
|
-
params['message']
|
41
|
-
end
|
42
|
-
|
43
|
-
end
|
44
|
-
|
45
|
-
class Bad
|
46
|
-
include Sanford::ServiceHandler
|
47
|
-
|
48
|
-
def run!
|
49
|
-
raise "hahaha"
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
class Multiply
|
54
|
-
include Sanford::ServiceHandler
|
55
|
-
|
56
|
-
def init!
|
57
|
-
@number = params['number'] || 1
|
58
|
-
end
|
59
|
-
|
60
|
-
def run!
|
61
|
-
@number * 2
|
62
|
-
end
|
63
|
-
end
|
64
|
-
|
65
|
-
class HaltIt
|
66
|
-
include Sanford::ServiceHandler
|
67
|
-
|
68
|
-
def run!
|
69
|
-
halt 728, {
|
70
|
-
:message => "I do what I want",
|
71
|
-
:data => [ 1, true, 'yes' ]
|
72
|
-
}
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
class Authorized
|
77
|
-
include Sanford::ServiceHandler
|
78
|
-
|
79
|
-
before_run do
|
80
|
-
halt 401, :message => "Not authorized"
|
81
|
-
end
|
82
|
-
|
83
|
-
end
|
84
|
-
|
85
|
-
::MyCustomError = Class.new(RuntimeError)
|
86
|
-
|
87
|
-
class CustomError
|
88
|
-
include Sanford::ServiceHandler
|
89
|
-
|
90
|
-
def run!
|
91
|
-
raise ::MyCustomError
|
92
|
-
end
|
93
|
-
|
94
|
-
end
|
95
|
-
|
96
|
-
end
|
97
|
-
|
98
|
-
class MyHost
|
99
|
-
include Sanford::Host
|
100
|
-
|
101
|
-
name 'my_host'
|
102
|
-
ip 'my.local'
|
103
|
-
pid_file File.expand_path('../../../tmp/my_host.pid', __FILE__)
|
104
|
-
end
|
105
|
-
|
106
|
-
class InvalidHost
|
107
|
-
include Sanford::Host
|
108
|
-
|
109
|
-
name 'invalid_host'
|
110
|
-
end
|
111
|
-
|
112
|
-
class UndefinedHandlersHost
|
113
|
-
include Sanford::Host
|
114
|
-
|
115
|
-
port 12345
|
116
|
-
|
117
|
-
service 'undefined', 'ThisIsNotDefined'
|
118
|
-
|
119
|
-
end
|
120
|
-
|
121
|
-
class EmptyHost
|
122
|
-
include Sanford::Host
|
123
|
-
end
|