service_skeleton 0.0.0.1.ENOTAG → 0.0.0.2.g46c1e0e
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 +5 -5
- data/.gitignore +0 -2
- data/.rubocop.yml +114 -9
- data/.travis.yml +11 -0
- data/README.md +153 -279
- data/lib/service_skeleton/background_worker.rb +80 -0
- data/lib/service_skeleton/config.rb +18 -78
- data/lib/service_skeleton/config_variable.rb +8 -29
- data/lib/service_skeleton/config_variables.rb +68 -54
- data/lib/service_skeleton/error.rb +3 -5
- data/lib/service_skeleton/filtering_logger.rb +0 -2
- data/lib/service_skeleton/logging_helpers.rb +3 -10
- data/lib/service_skeleton/metrics_methods.rb +13 -28
- data/lib/service_skeleton/signal_handler.rb +183 -0
- data/lib/service_skeleton.rb +145 -22
- data/service_skeleton.gemspec +9 -10
- metadata +19 -102
- data/.editorconfig +0 -7
- data/.git-blame-ignore-revs +0 -2
- data/.github/workflows/ci.yml +0 -50
- data/lib/service_skeleton/config_class.rb +0 -16
- data/lib/service_skeleton/config_variable/boolean.rb +0 -21
- data/lib/service_skeleton/config_variable/enum.rb +0 -27
- data/lib/service_skeleton/config_variable/float.rb +0 -25
- data/lib/service_skeleton/config_variable/integer.rb +0 -25
- data/lib/service_skeleton/config_variable/kv_list.rb +0 -26
- data/lib/service_skeleton/config_variable/path_list.rb +0 -13
- data/lib/service_skeleton/config_variable/string.rb +0 -18
- data/lib/service_skeleton/config_variable/url.rb +0 -36
- data/lib/service_skeleton/config_variable/yaml_file.rb +0 -42
- data/lib/service_skeleton/generator.rb +0 -165
- data/lib/service_skeleton/metric_method_name.rb +0 -9
- data/lib/service_skeleton/runner.rb +0 -46
- data/lib/service_skeleton/service_name.rb +0 -20
- data/lib/service_skeleton/signal_manager.rb +0 -202
- data/lib/service_skeleton/signals_methods.rb +0 -15
- data/lib/service_skeleton/ultravisor_children.rb +0 -20
- data/lib/service_skeleton/ultravisor_loggerstash.rb +0 -11
- data/ultravisor/.yardopts +0 -1
- data/ultravisor/Guardfile +0 -9
- data/ultravisor/README.md +0 -404
- data/ultravisor/lib/ultravisor/child/call.rb +0 -21
- data/ultravisor/lib/ultravisor/child/call_receiver.rb +0 -14
- data/ultravisor/lib/ultravisor/child/cast.rb +0 -16
- data/ultravisor/lib/ultravisor/child/cast_receiver.rb +0 -11
- data/ultravisor/lib/ultravisor/child/process_cast_call.rb +0 -39
- data/ultravisor/lib/ultravisor/child.rb +0 -481
- data/ultravisor/lib/ultravisor/error.rb +0 -25
- data/ultravisor/lib/ultravisor/logging_helpers.rb +0 -32
- data/ultravisor/lib/ultravisor.rb +0 -216
- data/ultravisor/spec/example_group_methods.rb +0 -19
- data/ultravisor/spec/example_methods.rb +0 -8
- data/ultravisor/spec/spec_helper.rb +0 -52
- data/ultravisor/spec/ultravisor/add_child_spec.rb +0 -79
- data/ultravisor/spec/ultravisor/child/call_spec.rb +0 -121
- data/ultravisor/spec/ultravisor/child/cast_spec.rb +0 -111
- data/ultravisor/spec/ultravisor/child/id_spec.rb +0 -21
- data/ultravisor/spec/ultravisor/child/new_spec.rb +0 -152
- data/ultravisor/spec/ultravisor/child/restart_delay_spec.rb +0 -40
- data/ultravisor/spec/ultravisor/child/restart_spec.rb +0 -70
- data/ultravisor/spec/ultravisor/child/run_spec.rb +0 -95
- data/ultravisor/spec/ultravisor/child/shutdown_spec.rb +0 -124
- data/ultravisor/spec/ultravisor/child/spawn_spec.rb +0 -107
- data/ultravisor/spec/ultravisor/child/unsafe_instance_spec.rb +0 -55
- data/ultravisor/spec/ultravisor/child/wait_spec.rb +0 -32
- data/ultravisor/spec/ultravisor/new_spec.rb +0 -71
- data/ultravisor/spec/ultravisor/remove_child_spec.rb +0 -49
- data/ultravisor/spec/ultravisor/run_spec.rb +0 -334
- data/ultravisor/spec/ultravisor/shutdown_spec.rb +0 -106
@@ -0,0 +1,183 @@
|
|
1
|
+
require_relative "./background_worker"
|
2
|
+
require_relative "./logging_helpers"
|
3
|
+
|
4
|
+
class ServiceSkeleton
|
5
|
+
# Manage signals in a sane and safe manner.
|
6
|
+
#
|
7
|
+
# Signal handling is a shit of a thing. The code that runs when a signal is
|
8
|
+
# triggered can't use mutexes (which are used in all sorts of places you
|
9
|
+
# might not expect, like Logger!) or anything else that might block. This
|
10
|
+
# greatly constrains what you can do inside a signal handler, so the standard
|
11
|
+
# approach is to stuff a character down a pipe, and then have the *real*
|
12
|
+
# signal handling run later.
|
13
|
+
#
|
14
|
+
# Also, there's always the (slim) possibility that something else might have
|
15
|
+
# hooked into a signal we want to receive. Because only a single signal
|
16
|
+
# handler can be active for a given signal at a time, we need to "chain" the
|
17
|
+
# existing handler, by calling the previous signal handler from our signal
|
18
|
+
# handler after we've done what we need to do. This class takes care of
|
19
|
+
# that, too, because it's a legend.
|
20
|
+
#
|
21
|
+
# So that's what this class does: it allows you to specify signals and
|
22
|
+
# associated blocks of code to run, it sets up signal handlers which send
|
23
|
+
# notifications to a background thread and chain correctly, and it manages
|
24
|
+
# the background thread to receive the notifications and execute the
|
25
|
+
# associated blocks of code outside of the context of the signal handler.
|
26
|
+
#
|
27
|
+
class SignalHandler
|
28
|
+
include ServiceSkeleton::LoggingHelpers
|
29
|
+
include ServiceSkeleton::BackgroundWorker
|
30
|
+
|
31
|
+
# Setup a signal handler instance.
|
32
|
+
#
|
33
|
+
# A single signal handler instance can handle up to 256 hooks, potentially
|
34
|
+
# hooking the same signal more than once. Use #hook_signal to register
|
35
|
+
# signal handling callbacks.
|
36
|
+
#
|
37
|
+
# @param logger [Logger] the logger to use for all the interesting information
|
38
|
+
# about what we're up to.
|
39
|
+
#
|
40
|
+
def initialize(logger:, service:, signal_counter:)
|
41
|
+
@logger, @service, @signal_counter = logger, service, signal_counter
|
42
|
+
|
43
|
+
@signal_registry = []
|
44
|
+
|
45
|
+
super
|
46
|
+
end
|
47
|
+
|
48
|
+
#:nocov:
|
49
|
+
|
50
|
+
# Register a callback to be executed on the receipt of a specified signal.
|
51
|
+
#
|
52
|
+
# @param sig [String, Symbol, Integer] the signal to hook into. Anything that
|
53
|
+
# `Signal.trap` will accept is OK by us, too.
|
54
|
+
#
|
55
|
+
# @param blk [Proc] the code to run when the signal is received.
|
56
|
+
#
|
57
|
+
# @return [void]
|
58
|
+
#
|
59
|
+
# @raise [RuntimeError] if you try to create more than 256 signal hooks.
|
60
|
+
#
|
61
|
+
# @raise [ArgumentError] if `sig` isn't recognised as a valid signal
|
62
|
+
# specifier by `Signal.trap`.
|
63
|
+
#
|
64
|
+
def hook_signal(sig, &blk)
|
65
|
+
@bg_worker_op_mutex.synchronize do
|
66
|
+
handler_num = @signal_registry.length
|
67
|
+
|
68
|
+
if handler_num > 255
|
69
|
+
raise RuntimeError,
|
70
|
+
"Signal hook limit reached. Slow down there, pardner"
|
71
|
+
end
|
72
|
+
|
73
|
+
sigspec = { signal: sig, callback: blk }
|
74
|
+
|
75
|
+
if @bg_worker_thread
|
76
|
+
install_handler(sigspec, handler_num)
|
77
|
+
else
|
78
|
+
# If the background thread isn't running yet, the signal handler will
|
79
|
+
# be installed when that is started.
|
80
|
+
end
|
81
|
+
|
82
|
+
@signal_registry << sigspec
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def start
|
87
|
+
logger.info("SignalHandler#start") { "Starting signal handler with #{@signal_registry.length} hooks" }
|
88
|
+
|
89
|
+
@r, @w = IO.pipe
|
90
|
+
|
91
|
+
install_signal_handlers
|
92
|
+
|
93
|
+
loop do
|
94
|
+
begin
|
95
|
+
if ios = IO.select([@r])
|
96
|
+
if ios.first.include?(@r)
|
97
|
+
if ios.first.first.eof?
|
98
|
+
logger.info("SignalHandler#run") { "Signal pipe closed; shutting down" }
|
99
|
+
break
|
100
|
+
else
|
101
|
+
c = ios.first.first.read_nonblock(1)
|
102
|
+
handle_signal(c)
|
103
|
+
end
|
104
|
+
else
|
105
|
+
logger.error("SignalHandler#run") { "Mysterious return from select: #{ios.inspect}" }
|
106
|
+
end
|
107
|
+
end
|
108
|
+
rescue StandardError => ex
|
109
|
+
log_exception(ex) { "Exception in select loop" }
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
private
|
115
|
+
|
116
|
+
attr_reader :logger
|
117
|
+
|
118
|
+
# Given a character (presumably) received via the signal pipe, execute the
|
119
|
+
# associated handler.
|
120
|
+
#
|
121
|
+
# @param char [String] a single character, corresponding to an entry in the
|
122
|
+
# signal registry.
|
123
|
+
#
|
124
|
+
# @return [void]
|
125
|
+
#
|
126
|
+
def handle_signal(char)
|
127
|
+
handler = @signal_registry[char.ord]
|
128
|
+
|
129
|
+
if handler
|
130
|
+
logger.debug("SignalHandler#handle_signal") { "#{handler[:signal]} received" }
|
131
|
+
@signal_counter.increment(signal: handler[:signal].to_s)
|
132
|
+
begin
|
133
|
+
handler[:callback].call
|
134
|
+
rescue => ex
|
135
|
+
log_exception(ex) { "Exception in signal handler" }
|
136
|
+
end
|
137
|
+
else
|
138
|
+
logger.error("SignalHandler#handle_signal") { "Unrecognised signal character: #{char.inspect}" }
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
def install_signal_handlers
|
143
|
+
@signal_registry.each_with_index do |sigspec, i|
|
144
|
+
install_handler(sigspec, i)
|
145
|
+
end
|
146
|
+
end
|
147
|
+
|
148
|
+
def install_handler(sigspec, i)
|
149
|
+
chain = nil
|
150
|
+
|
151
|
+
p = ->(_) do
|
152
|
+
@w.write_nonblock(i.chr) rescue nil
|
153
|
+
chain.call if chain.respond_to?(:call)
|
154
|
+
end
|
155
|
+
chain = Signal.trap(sigspec[:signal], &p)
|
156
|
+
|
157
|
+
sigspec[:chain] = chain
|
158
|
+
sigspec[:handler] = p
|
159
|
+
end
|
160
|
+
|
161
|
+
def shutdown
|
162
|
+
uninstall_signal_handlers
|
163
|
+
|
164
|
+
@r.close
|
165
|
+
end
|
166
|
+
|
167
|
+
def uninstall_signal_handlers
|
168
|
+
@signal_registry.reverse.each do |sigspec|
|
169
|
+
tmp_sig = Signal.trap(sigspec[:signal], "IGNORE")
|
170
|
+
if tmp_sig == sigspec[:handler]
|
171
|
+
# The current handler is ours, so we can replace
|
172
|
+
# it with the chained handler
|
173
|
+
Signal.trap(sigspec[:signal], sigspec[:chain])
|
174
|
+
else
|
175
|
+
# The current handler *isn't* this one, so we better
|
176
|
+
# put it back, because whoever owns it might get
|
177
|
+
# angry.
|
178
|
+
Signal.trap(sigspec[:signal], tmp_sig)
|
179
|
+
end
|
180
|
+
end
|
181
|
+
end
|
182
|
+
end
|
183
|
+
end
|
data/lib/service_skeleton.rb
CHANGED
@@ -1,13 +1,8 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require_relative "service_skeleton/config_class"
|
1
|
+
require_relative "service_skeleton/config"
|
4
2
|
require_relative "service_skeleton/config_variables"
|
5
|
-
require_relative "service_skeleton/generator"
|
6
3
|
require_relative "service_skeleton/logging_helpers"
|
7
4
|
require_relative "service_skeleton/metrics_methods"
|
8
|
-
require_relative "service_skeleton/
|
9
|
-
require_relative "service_skeleton/signals_methods"
|
10
|
-
require_relative "service_skeleton/ultravisor_children"
|
5
|
+
require_relative "service_skeleton/signal_handler"
|
11
6
|
|
12
7
|
require "frankenstein/ruby_gc_metrics"
|
13
8
|
require "frankenstein/ruby_vm_metrics"
|
@@ -16,26 +11,154 @@ require "frankenstein/server"
|
|
16
11
|
require "prometheus/client/registry"
|
17
12
|
require "sigdump"
|
18
13
|
|
19
|
-
|
14
|
+
class ServiceSkeleton
|
15
|
+
extend ServiceSkeleton::ConfigVariables
|
16
|
+
|
20
17
|
include ServiceSkeleton::LoggingHelpers
|
21
|
-
extend ServiceSkeleton::Generator
|
22
18
|
|
23
|
-
def self.
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
19
|
+
def self.config_class(klass)
|
20
|
+
@config_class = klass
|
21
|
+
end
|
22
|
+
|
23
|
+
def self.service_name
|
24
|
+
self.to_s
|
25
|
+
.gsub("::", "_")
|
26
|
+
.gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
|
27
|
+
.gsub(/([a-z\d])([A-Z])/, '\1_\2')
|
28
|
+
.downcase
|
30
29
|
end
|
31
30
|
|
32
31
|
attr_reader :config, :metrics, :logger
|
33
32
|
|
34
|
-
def initialize(
|
35
|
-
@
|
36
|
-
@config
|
37
|
-
@logger
|
33
|
+
def initialize(env)
|
34
|
+
@env = env
|
35
|
+
@config = (self.class.instance_variable_get(:@config_class) || ServiceSkeleton::Config).new(env, self)
|
36
|
+
@logger = @config.logger
|
37
|
+
|
38
|
+
setup_metrics
|
39
|
+
setup_signals
|
40
|
+
end
|
41
|
+
|
42
|
+
def start
|
43
|
+
begin
|
44
|
+
start_metrics_server
|
45
|
+
start_signal_handler
|
46
|
+
run
|
47
|
+
rescue ServiceSkeleton::Error::InheritanceContractError
|
48
|
+
# We want this one to be fatal
|
49
|
+
raise
|
50
|
+
rescue StandardError => ex
|
51
|
+
log_exception(ex)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
def stop(force = false)
|
56
|
+
shutdown
|
57
|
+
|
58
|
+
if @metrics_server
|
59
|
+
@metrics_server.shutdown
|
60
|
+
@metrics_server = nil
|
61
|
+
end
|
62
|
+
|
63
|
+
@signal_handler.stop!
|
64
|
+
end
|
65
|
+
|
66
|
+
def service_name
|
67
|
+
self.class.service_name
|
68
|
+
end
|
69
|
+
|
70
|
+
def registered_variables
|
71
|
+
self.class.registered_variables
|
72
|
+
end
|
73
|
+
|
74
|
+
def hook_signal(spec, &blk)
|
75
|
+
@signal_handler.hook_signal(spec, &blk)
|
76
|
+
end
|
77
|
+
|
78
|
+
private
|
79
|
+
|
80
|
+
def run
|
81
|
+
raise ServiceSkeleton::Error::InheritanceContractError, "ServiceSkeleton#run method not overridden"
|
38
82
|
end
|
39
|
-
end
|
40
83
|
|
41
|
-
|
84
|
+
def setup_metrics
|
85
|
+
@metrics = Prometheus::Client::Registry.new
|
86
|
+
|
87
|
+
Frankenstein::RubyGCMetrics.register(@metrics)
|
88
|
+
Frankenstein::RubyVMMetrics.register(@metrics)
|
89
|
+
Frankenstein::ProcessMetrics.register(@metrics)
|
90
|
+
|
91
|
+
@metrics.singleton_class.prepend(ServiceSkeleton::MetricsMethods)
|
92
|
+
@metrics.service = self
|
93
|
+
|
94
|
+
end
|
95
|
+
|
96
|
+
def start_metrics_server
|
97
|
+
if config.metrics_port
|
98
|
+
logger.info(self.class.to_s) { "Starting metrics server on port #{config.metrics_port}" }
|
99
|
+
|
100
|
+
@metrics_server = Frankenstein::Server.new(
|
101
|
+
port: config.metrics_port,
|
102
|
+
logger: logger,
|
103
|
+
metrics_prefix: :metrics_server,
|
104
|
+
registry: @metrics,
|
105
|
+
)
|
106
|
+
@metrics_server.run
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
def setup_signals
|
111
|
+
@signal_handler = ServiceSkeleton::SignalHandler.new(logger: logger, service: self, signal_counter: metrics.counter(:"#{service_name}_signals_handled_total", "How many of each type of signal have been handled"))
|
112
|
+
|
113
|
+
@signal_handler.hook_signal("USR1") do
|
114
|
+
logger.level -= 1 unless logger.level == Logger::DEBUG
|
115
|
+
logger.info($0) { "Received SIGUSR1; log level is now #{Logger::SEV_LABEL[logger.level]}." }
|
116
|
+
end
|
117
|
+
|
118
|
+
@signal_handler.hook_signal("USR2") do
|
119
|
+
logger.level += 1 unless logger.level == Logger::ERROR
|
120
|
+
logger.info($0) { "Received SIGUSR2; log level is now #{Logger::SEV_LABEL[logger.level]}." }
|
121
|
+
end
|
122
|
+
|
123
|
+
@signal_handler.hook_signal("HUP") do
|
124
|
+
logger.reopen
|
125
|
+
logger.info($0) { "Received SIGHUP; log file handle reopened" }
|
126
|
+
end
|
127
|
+
|
128
|
+
@signal_handler.hook_signal("QUIT") do
|
129
|
+
Sigdump.dump("+")
|
130
|
+
end
|
131
|
+
|
132
|
+
@signal_handler.hook_signal("INT") do
|
133
|
+
self.stop(!!@terminating)
|
134
|
+
@terminating = true
|
135
|
+
end
|
136
|
+
|
137
|
+
@signal_handler.hook_signal("TERM") do
|
138
|
+
self.stop(!!@terminating)
|
139
|
+
@terminating = true
|
140
|
+
end
|
141
|
+
end
|
142
|
+
|
143
|
+
def start_signal_handler
|
144
|
+
@signal_handler.start!
|
145
|
+
end
|
146
|
+
|
147
|
+
@registered_variables = [
|
148
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_LOG_LEVEL) { "INFO" },
|
149
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_LOG_ENABLE_TIMESTAMPS) { false },
|
150
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_LOG_FILE) { nil },
|
151
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_LOG_MAX_FILE_SIZE) { 1048576 },
|
152
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_LOG_MAX_FILES) { 3 },
|
153
|
+
ServiceSkeleton::ConfigVariable.new(:SERVICE_SKELETON_METRICS_PORT) { nil },
|
154
|
+
]
|
155
|
+
|
156
|
+
def self.inherited(subclass)
|
157
|
+
subclass.string(:"#{subclass.service_name.upcase}_LOG_LEVEL", default: "INFO")
|
158
|
+
subclass.boolean(:"#{subclass.service_name.upcase}_LOG_ENABLE_TIMESTAMPS", default: false)
|
159
|
+
subclass.string(:"#{subclass.service_name.upcase}_LOG_FILE", default: nil)
|
160
|
+
subclass.integer(:"#{subclass.service_name.upcase}_LOG_MAX_FILE_SIZE", default: 1048576, range: 0..Float::INFINITY)
|
161
|
+
subclass.integer(:"#{subclass.service_name.upcase}_LOG_MAX_FILES", default: 3, range: 1..Float::INFINITY)
|
162
|
+
subclass.integer(:"#{subclass.service_name.upcase}_METRICS_PORT", default: nil, range: 1..65535)
|
163
|
+
end
|
164
|
+
end
|
data/service_skeleton.gemspec
CHANGED
@@ -1,5 +1,3 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
1
|
begin
|
4
2
|
require 'git-version-bump'
|
5
3
|
rescue LoadError
|
@@ -24,17 +22,19 @@ Gem::Specification.new do |s|
|
|
24
22
|
common aspects of a system service.
|
25
23
|
EOF
|
26
24
|
|
27
|
-
s.authors = ["Matt Palmer"
|
28
|
-
s.email = ["
|
25
|
+
s.authors = ["Matt Palmer"]
|
26
|
+
s.email = ["matt.palmer@discourse.org"]
|
29
27
|
s.homepage = "https://github.com/discourse/service_skeleton"
|
30
28
|
|
31
29
|
s.files = `git ls-files -z`.split("\0").reject { |f| f =~ /^(G|spec|Rakefile)/ }
|
32
30
|
|
33
|
-
s.required_ruby_version = ">= 2.
|
31
|
+
s.required_ruby_version = ">= 2.3.0"
|
34
32
|
|
35
|
-
s.add_runtime_dependency "frankenstein", "~> 2
|
36
|
-
|
37
|
-
|
33
|
+
s.add_runtime_dependency "frankenstein", "~> 1.2"
|
34
|
+
# prometheus-client provides no guaranteed backwards compatibility,
|
35
|
+
# and in fact happily breaks things with no notice, so we're stuck
|
36
|
+
# with hard-coding a specific version to avoid unexpected disaster.
|
37
|
+
s.add_runtime_dependency "prometheus-client", "0.8.0"
|
38
38
|
s.add_runtime_dependency "sigdump", "~> 0.2"
|
39
39
|
s.add_runtime_dependency "to_regexp", "~> 0.2"
|
40
40
|
|
@@ -44,11 +44,10 @@ Gem::Specification.new do |s|
|
|
44
44
|
s.add_development_dependency 'guard-rspec'
|
45
45
|
s.add_development_dependency 'guard-rubocop'
|
46
46
|
s.add_development_dependency 'rack-test'
|
47
|
-
s.add_development_dependency 'rake'
|
47
|
+
s.add_development_dependency 'rake', "~> 12.0"
|
48
48
|
s.add_development_dependency 'redcarpet'
|
49
49
|
s.add_development_dependency 'rspec'
|
50
50
|
s.add_development_dependency 'rubocop'
|
51
|
-
s.add_development_dependency 'rubocop-discourse'
|
52
51
|
s.add_development_dependency 'simplecov'
|
53
52
|
s.add_development_dependency 'yard'
|
54
53
|
end
|
metadata
CHANGED
@@ -1,15 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: service_skeleton
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.0.
|
4
|
+
version: 0.0.0.2.g46c1e0e
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Matt Palmer
|
8
|
-
- Sam Saffron
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
date:
|
11
|
+
date: 2018-11-15 00:00:00.000000000 Z
|
13
12
|
dependencies:
|
14
13
|
- !ruby/object:Gem::Dependency
|
15
14
|
name: frankenstein
|
@@ -17,48 +16,28 @@ dependencies:
|
|
17
16
|
requirements:
|
18
17
|
- - "~>"
|
19
18
|
- !ruby/object:Gem::Version
|
20
|
-
version: '2
|
19
|
+
version: '1.2'
|
21
20
|
type: :runtime
|
22
21
|
prerelease: false
|
23
22
|
version_requirements: !ruby/object:Gem::Requirement
|
24
23
|
requirements:
|
25
24
|
- - "~>"
|
26
25
|
- !ruby/object:Gem::Version
|
27
|
-
version: '2
|
28
|
-
- !ruby/object:Gem::Dependency
|
29
|
-
name: loggerstash
|
30
|
-
requirement: !ruby/object:Gem::Requirement
|
31
|
-
requirements:
|
32
|
-
- - ">="
|
33
|
-
- !ruby/object:Gem::Version
|
34
|
-
version: 0.0.9
|
35
|
-
- - "<"
|
36
|
-
- !ruby/object:Gem::Version
|
37
|
-
version: '1'
|
38
|
-
type: :runtime
|
39
|
-
prerelease: false
|
40
|
-
version_requirements: !ruby/object:Gem::Requirement
|
41
|
-
requirements:
|
42
|
-
- - ">="
|
43
|
-
- !ruby/object:Gem::Version
|
44
|
-
version: 0.0.9
|
45
|
-
- - "<"
|
46
|
-
- !ruby/object:Gem::Version
|
47
|
-
version: '1'
|
26
|
+
version: '1.2'
|
48
27
|
- !ruby/object:Gem::Dependency
|
49
28
|
name: prometheus-client
|
50
29
|
requirement: !ruby/object:Gem::Requirement
|
51
30
|
requirements:
|
52
|
-
- -
|
31
|
+
- - '='
|
53
32
|
- !ruby/object:Gem::Version
|
54
|
-
version:
|
33
|
+
version: 0.8.0
|
55
34
|
type: :runtime
|
56
35
|
prerelease: false
|
57
36
|
version_requirements: !ruby/object:Gem::Requirement
|
58
37
|
requirements:
|
59
|
-
- -
|
38
|
+
- - '='
|
60
39
|
- !ruby/object:Gem::Version
|
61
|
-
version:
|
40
|
+
version: 0.8.0
|
62
41
|
- !ruby/object:Gem::Dependency
|
63
42
|
name: sigdump
|
64
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -175,16 +154,16 @@ dependencies:
|
|
175
154
|
name: rake
|
176
155
|
requirement: !ruby/object:Gem::Requirement
|
177
156
|
requirements:
|
178
|
-
- - "
|
157
|
+
- - "~>"
|
179
158
|
- !ruby/object:Gem::Version
|
180
|
-
version: '0'
|
159
|
+
version: '12.0'
|
181
160
|
type: :development
|
182
161
|
prerelease: false
|
183
162
|
version_requirements: !ruby/object:Gem::Requirement
|
184
163
|
requirements:
|
185
|
-
- - "
|
164
|
+
- - "~>"
|
186
165
|
- !ruby/object:Gem::Version
|
187
|
-
version: '0'
|
166
|
+
version: '12.0'
|
188
167
|
- !ruby/object:Gem::Dependency
|
189
168
|
name: redcarpet
|
190
169
|
requirement: !ruby/object:Gem::Requirement
|
@@ -227,20 +206,6 @@ dependencies:
|
|
227
206
|
- - ">="
|
228
207
|
- !ruby/object:Gem::Version
|
229
208
|
version: '0'
|
230
|
-
- !ruby/object:Gem::Dependency
|
231
|
-
name: rubocop-discourse
|
232
|
-
requirement: !ruby/object:Gem::Requirement
|
233
|
-
requirements:
|
234
|
-
- - ">="
|
235
|
-
- !ruby/object:Gem::Version
|
236
|
-
version: '0'
|
237
|
-
type: :development
|
238
|
-
prerelease: false
|
239
|
-
version_requirements: !ruby/object:Gem::Requirement
|
240
|
-
requirements:
|
241
|
-
- - ">="
|
242
|
-
- !ruby/object:Gem::Version
|
243
|
-
version: '0'
|
244
209
|
- !ruby/object:Gem::Dependency
|
245
210
|
name: simplecov
|
246
211
|
requirement: !ruby/object:Gem::Requirement
|
@@ -277,79 +242,30 @@ description: |
|
|
277
242
|
for your services, as well as a collection of helper classes to manage
|
278
243
|
common aspects of a system service.
|
279
244
|
email:
|
280
|
-
-
|
245
|
+
- matt.palmer@discourse.org
|
281
246
|
executables: []
|
282
247
|
extensions: []
|
283
248
|
extra_rdoc_files: []
|
284
249
|
files:
|
285
|
-
- ".editorconfig"
|
286
|
-
- ".git-blame-ignore-revs"
|
287
|
-
- ".github/workflows/ci.yml"
|
288
250
|
- ".gitignore"
|
289
251
|
- ".rubocop.yml"
|
252
|
+
- ".travis.yml"
|
290
253
|
- ".yardopts"
|
291
254
|
- CODE_OF_CONDUCT.md
|
292
255
|
- CONTRIBUTING.md
|
293
256
|
- LICENCE
|
294
257
|
- README.md
|
295
258
|
- lib/service_skeleton.rb
|
259
|
+
- lib/service_skeleton/background_worker.rb
|
296
260
|
- lib/service_skeleton/config.rb
|
297
|
-
- lib/service_skeleton/config_class.rb
|
298
261
|
- lib/service_skeleton/config_variable.rb
|
299
|
-
- lib/service_skeleton/config_variable/boolean.rb
|
300
|
-
- lib/service_skeleton/config_variable/enum.rb
|
301
|
-
- lib/service_skeleton/config_variable/float.rb
|
302
|
-
- lib/service_skeleton/config_variable/integer.rb
|
303
|
-
- lib/service_skeleton/config_variable/kv_list.rb
|
304
|
-
- lib/service_skeleton/config_variable/path_list.rb
|
305
|
-
- lib/service_skeleton/config_variable/string.rb
|
306
|
-
- lib/service_skeleton/config_variable/url.rb
|
307
|
-
- lib/service_skeleton/config_variable/yaml_file.rb
|
308
262
|
- lib/service_skeleton/config_variables.rb
|
309
263
|
- lib/service_skeleton/error.rb
|
310
264
|
- lib/service_skeleton/filtering_logger.rb
|
311
|
-
- lib/service_skeleton/generator.rb
|
312
265
|
- lib/service_skeleton/logging_helpers.rb
|
313
|
-
- lib/service_skeleton/metric_method_name.rb
|
314
266
|
- lib/service_skeleton/metrics_methods.rb
|
315
|
-
- lib/service_skeleton/
|
316
|
-
- lib/service_skeleton/service_name.rb
|
317
|
-
- lib/service_skeleton/signal_manager.rb
|
318
|
-
- lib/service_skeleton/signals_methods.rb
|
319
|
-
- lib/service_skeleton/ultravisor_children.rb
|
320
|
-
- lib/service_skeleton/ultravisor_loggerstash.rb
|
267
|
+
- lib/service_skeleton/signal_handler.rb
|
321
268
|
- service_skeleton.gemspec
|
322
|
-
- ultravisor/.yardopts
|
323
|
-
- ultravisor/Guardfile
|
324
|
-
- ultravisor/README.md
|
325
|
-
- ultravisor/lib/ultravisor.rb
|
326
|
-
- ultravisor/lib/ultravisor/child.rb
|
327
|
-
- ultravisor/lib/ultravisor/child/call.rb
|
328
|
-
- ultravisor/lib/ultravisor/child/call_receiver.rb
|
329
|
-
- ultravisor/lib/ultravisor/child/cast.rb
|
330
|
-
- ultravisor/lib/ultravisor/child/cast_receiver.rb
|
331
|
-
- ultravisor/lib/ultravisor/child/process_cast_call.rb
|
332
|
-
- ultravisor/lib/ultravisor/error.rb
|
333
|
-
- ultravisor/lib/ultravisor/logging_helpers.rb
|
334
|
-
- ultravisor/spec/example_group_methods.rb
|
335
|
-
- ultravisor/spec/example_methods.rb
|
336
|
-
- ultravisor/spec/spec_helper.rb
|
337
|
-
- ultravisor/spec/ultravisor/add_child_spec.rb
|
338
|
-
- ultravisor/spec/ultravisor/child/call_spec.rb
|
339
|
-
- ultravisor/spec/ultravisor/child/cast_spec.rb
|
340
|
-
- ultravisor/spec/ultravisor/child/id_spec.rb
|
341
|
-
- ultravisor/spec/ultravisor/child/new_spec.rb
|
342
|
-
- ultravisor/spec/ultravisor/child/restart_delay_spec.rb
|
343
|
-
- ultravisor/spec/ultravisor/child/restart_spec.rb
|
344
|
-
- ultravisor/spec/ultravisor/child/run_spec.rb
|
345
|
-
- ultravisor/spec/ultravisor/child/shutdown_spec.rb
|
346
|
-
- ultravisor/spec/ultravisor/child/spawn_spec.rb
|
347
|
-
- ultravisor/spec/ultravisor/child/unsafe_instance_spec.rb
|
348
|
-
- ultravisor/spec/ultravisor/child/wait_spec.rb
|
349
|
-
- ultravisor/spec/ultravisor/new_spec.rb
|
350
|
-
- ultravisor/spec/ultravisor/remove_child_spec.rb
|
351
|
-
- ultravisor/spec/ultravisor/run_spec.rb
|
352
|
-
- ultravisor/spec/ultravisor/shutdown_spec.rb
|
353
269
|
homepage: https://github.com/discourse/service_skeleton
|
354
270
|
licenses: []
|
355
271
|
metadata: {}
|
@@ -361,14 +277,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
361
277
|
requirements:
|
362
278
|
- - ">="
|
363
279
|
- !ruby/object:Gem::Version
|
364
|
-
version: 2.
|
280
|
+
version: 2.3.0
|
365
281
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
366
282
|
requirements:
|
367
283
|
- - ">"
|
368
284
|
- !ruby/object:Gem::Version
|
369
285
|
version: 1.3.1
|
370
286
|
requirements: []
|
371
|
-
|
287
|
+
rubyforge_project:
|
288
|
+
rubygems_version: 2.5.2.1
|
372
289
|
signing_key:
|
373
290
|
specification_version: 4
|
374
291
|
summary: The bare bones of a service
|
data/.editorconfig
DELETED
data/.git-blame-ignore-revs
DELETED
data/.github/workflows/ci.yml
DELETED
@@ -1,50 +0,0 @@
|
|
1
|
-
name: Service Skeleton Tests
|
2
|
-
|
3
|
-
on:
|
4
|
-
pull_request:
|
5
|
-
push:
|
6
|
-
branches:
|
7
|
-
- master
|
8
|
-
tags:
|
9
|
-
- v*
|
10
|
-
|
11
|
-
jobs:
|
12
|
-
build:
|
13
|
-
runs-on: ubuntu-latest
|
14
|
-
name: Ruby ${{ matrix.ruby }}
|
15
|
-
strategy:
|
16
|
-
matrix:
|
17
|
-
ruby: ["2.5", "2.6", "2.7"]
|
18
|
-
steps:
|
19
|
-
- uses: actions/checkout@v2
|
20
|
-
- uses: actions/setup-ruby@v1
|
21
|
-
with:
|
22
|
-
ruby-version: ${{ matrix.ruby }}
|
23
|
-
- name: Bundler cache
|
24
|
-
uses: actions/cache@v2
|
25
|
-
with:
|
26
|
-
path: vendor/bundle
|
27
|
-
key: ${{ runner.os }}-${{ matrix.ruby }}-gems-${{ hashFiles('**/Gemfile.lock') }}
|
28
|
-
restore-keys: |
|
29
|
-
${{ runner.os }}-${{ matrix.ruby }}-gems-
|
30
|
-
- name: Setup gems
|
31
|
-
run: |
|
32
|
-
gem install bundler
|
33
|
-
bundle config path vendor/bundle
|
34
|
-
bundle install --jobs 4
|
35
|
-
- name: Rubocop
|
36
|
-
run: bundle exec rubocop
|
37
|
-
- name: Tests
|
38
|
-
run: bundle exec rspec
|
39
|
-
- name: Ultravisor Tests
|
40
|
-
run: bundle exec rspec ultravisor/spec
|
41
|
-
publish:
|
42
|
-
if: contains(github.ref, 'refs/tags/v')
|
43
|
-
needs: build
|
44
|
-
runs-on: ubuntu-latest
|
45
|
-
steps:
|
46
|
-
- uses: actions/checkout@v2
|
47
|
-
- name: Release Gem
|
48
|
-
uses: CvX/publish-rubygems-action@master
|
49
|
-
env:
|
50
|
-
RUBYGEMS_API_KEY: ${{secrets.RUBYGEMS_API_KEY}}
|