Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Deal with server not ready gracefully #68

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 23 additions & 1 deletion lib/puma/metrics/app.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@

module Puma
module Metrics
MetricsNotAvailableError = Class.new(StandardError)

class App
def initialize(launcher)
@launcher = launcher
Expand All @@ -20,16 +22,36 @@ def call(_env)
{ 'Content-Type' => 'text/plain' },
[Prometheus::Client::Formats::Text.marshal(Prometheus::Client.registry)]
]
rescue MetricsNotAvailableError => e
[503, { 'Content-Type' => 'text/plain' }, ["#{e.message}\n"]]
end

def retrieve_and_parse_stats!
puma_stats = @launcher.stats
puma_stats = fetch_stats
if puma_stats.is_a?(Hash) # Modern Puma outputs stats as a Symbol-keyed Hash
@parser.parse(puma_stats)
else
@parser.parse(JSON.parse(puma_stats, symbolize_names: true))
end
end

private

def fetch_stats
@launcher.stats
rescue NoMethodError
# Puma plugins are started in the background along with the server, so
# there's a chance that a request will arrive to the server started by
# this plugin before the main one has been registered in the launcher.
#
# If that happens, fetching the stats fails because `@server` is nil,
# causing a NoMethodError.
#
# Ideally this code should detect the case using the launcher public
# interface, but no methods expose the information that is required for
# that.
raise MetricsNotAvailableError, 'Puma is booting up. Stats are not yet ready.'
end
end
end
end