g5_prom_rails 0.1.1 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +6 -14
- data/lib/g5_prom_rails/engine.rb +1 -3
- data/lib/g5_prom_rails/metrics.rb +2 -10
- data/lib/g5_prom_rails/sidekiq_application_metrics.rb +4 -4
- data/lib/g5_prom_rails/sidekiq_timing_middleware.rb +1 -2
- data/lib/g5_prom_rails/version.rb +1 -1
- data/lib/g5_prom_rails.rb +0 -1
- 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: 26f2e4fc24881fa6fc383f69ffa57108a6194e02
|
4
|
+
data.tar.gz: fb1e5fd89456cc43d0bcf00c44cda9af8c188e01
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f411c57b452898f94939900701f030d3d53e0bbe32ad412dfd0f36560d80e6f079f0a7df2029191225eb79c5df90eb3fe3d06f3e5a29692479e339fd154e208f
|
7
|
+
data.tar.gz: 252b576492228b9fd7bf0456bb41d1664fafd4f477d450c1f0a7e0a3daf978ee884c578ca5430c4e966c15d075a73a5eb351dd5cc7fc7ec059172b9283a4c574
|
data/README.md
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
# G5 Prom Rails
|
2
2
|
|
3
|
-
|
3
|
+
A Rails engine that provides very basic help in integrating Prometheus into your Rails app. It brings in Prometheus Exporter middleware, initializes a metrics registry, and can add metrics for common use-cases and Rails gems.
|
4
4
|
|
5
5
|
## Installation
|
6
6
|
|
@@ -17,10 +17,12 @@ $ bundle
|
|
17
17
|
|
18
18
|
## Usage
|
19
19
|
|
20
|
-
The engine brings in the `prometheus-client` ruby gem. It is well-documented, and
|
20
|
+
The engine brings in the `prometheus-client` ruby gem. It is well-documented, and G5PromRails doesn't insulate you from how that gem works. You should [read its documentation](https://github.com/prometheus/client_ruby) to understand what metric types are available to you and how to update them. Registries and metrics endpoints are configured for you.
|
21
21
|
|
22
22
|
This gem is designed to work when Prometheus scrapes both individual instances of Rails (horizontally scaled processes) and the application as a whole. Application-level metrics are those that are shared between every Rails process, like database model counts or background job queue sizes. Per-process metrics are instrumented events that hit individual processes, like a particular controller action being called. Prometheus deals with aggregating events that happen in multiple disconnected processes, like load balanced Rails web servers.
|
23
23
|
|
24
|
+
It's also important that Prometheus is set up to relabel your metrics based on the application being scraped from. I'm assuming if you can scrape every instance of a load-balanced web application, you're using service discovery in some form and this kind of relabeling is possible.
|
25
|
+
|
24
26
|
## Configuration
|
25
27
|
|
26
28
|
There are a few configuration points for the engine, which you should specify in an initializer. Here's an example of a simple recommended setup:
|
@@ -87,14 +89,6 @@ There are a couple of general Prometheus tips things to keep in mind.
|
|
87
89
|
* Read [the official Prometheus guidelines on metric naming](https://prometheus.io/docs/practices/naming/). It's short and extremely helpful.
|
88
90
|
* Did you see the big warning at the end of the naming guidelines? Labels in Prometheus are extremely powerful; I encourage you to use them, but don't abuse them. A new time series database is created for every combination of label values. Feel free to use a label that could have dozens of possible values, for instance in your blog post counter to differentiate drafts from published articles. Do *not* use `author_id` as a label to count posts by author. *Especially* do not use multiple labels that could have many possible values, because the effect on the total number of time series databases is multiplicative.
|
89
91
|
|
90
|
-
## App Name
|
91
|
-
|
92
|
-
As you will soon learn, G5PromRails can provide you with some automatic metrics. Most of them are scoped to your application's name. It will attempt to infer the application's name from the Rails Application class's (`config/application.rb`) dasherized parent module name. If that doesn't work for you, it can be manually defined with:
|
93
|
-
|
94
|
-
```ruby
|
95
|
-
G5PromRails.app_name = "my-app-name"
|
96
|
-
```
|
97
|
-
|
98
92
|
## Sidekiq
|
99
93
|
|
100
94
|
Prometheus's strategy is to scrape metrics. If you take a moment to think about it, we have a problem: how do you scrape in-memory metrics from a Sidekiq worker? That process doesn't start a web server.
|
@@ -115,8 +109,6 @@ Metrics include:
|
|
115
109
|
* *`sidekiq_queued`* Gauge for current queue length. The label `queue` is applied to allow per-queue analysis.
|
116
110
|
* *`sidekiq_job_seconds`*,*`sidekiq_job_seconds_sum`*,*`sidekiq_job_seconds_count`* Histogram for job execution time. The label `job_name` is applied, and will be identical to the Ruby class name of the job (e.g. `MyImportantWorker`). To understand how to use this data, look at [the official documentation](https://prometheus.io/docs/practices/histograms/). See particularly the section about aggregation.
|
117
111
|
|
118
|
-
Each metric also has the `app` label applied with the name of your application.
|
119
|
-
|
120
112
|
## Helpers
|
121
113
|
|
122
114
|
There are some common instrumentation tasks that this gem can help you with.
|
@@ -129,9 +121,9 @@ When you'd like to instrument the count of certain ActiveRecord models, in an in
|
|
129
121
|
G5PromRails.count_models(Post, Comment)
|
130
122
|
```
|
131
123
|
|
132
|
-
Will result in a gauge metric named `model_rows` with a `model` label set to the tableized name of your model
|
124
|
+
Will result in a gauge metric named `model_rows` with a `model` label set to the tableized name of your model. In PromQL this will look like:
|
133
125
|
```promql
|
134
|
-
model_rows{model="posts"
|
126
|
+
model_rows{model="posts"}
|
135
127
|
```
|
136
128
|
|
137
129
|
This metric is left un-namespaced because it gives you the ability to compare these values across applications, while still allowing them to be limited to a single app via PromQL. The values will automatically be refreshed when the application-level metrics endpoint is hit.
|
data/lib/g5_prom_rails/engine.rb
CHANGED
@@ -13,8 +13,7 @@ module G5PromRails
|
|
13
13
|
end
|
14
14
|
|
15
15
|
initializer "g5_prom_rails.configure_global" do |app|
|
16
|
-
|
17
|
-
G5PromRails::Metrics = MetricsContainer.new(app_name)
|
16
|
+
G5PromRails::Metrics = MetricsContainer.new
|
18
17
|
|
19
18
|
if G5PromRails.initialize_per_application.present?
|
20
19
|
G5PromRails::Metrics.per_application.instance_eval(
|
@@ -79,7 +78,6 @@ module G5PromRails
|
|
79
78
|
config.server_middleware do |chain|
|
80
79
|
chain.add(
|
81
80
|
G5PromRails::SidekiqTimingMiddleware,
|
82
|
-
app: G5PromRails::Metrics.app,
|
83
81
|
metric: timing_metric
|
84
82
|
)
|
85
83
|
end
|
@@ -7,11 +7,9 @@ class G5PromRails::MetricsContainer
|
|
7
7
|
|
8
8
|
MODEL_COUNT_NAME = :model_rows
|
9
9
|
|
10
|
-
attr_reader :app
|
11
10
|
attr_reader :per_process, :per_application
|
12
11
|
|
13
|
-
def initialize
|
14
|
-
@app = app
|
12
|
+
def initialize
|
15
13
|
@per_process = Prometheus::Client::Registry.new
|
16
14
|
@per_application = Prometheus::Client::Registry.new
|
17
15
|
@model_count_gauge = @per_application.gauge(MODEL_COUNT_NAME, "model row counts")
|
@@ -21,15 +19,9 @@ class G5PromRails::MetricsContainer
|
|
21
19
|
def update_model_count_gauge(*models)
|
22
20
|
models.each do |model|
|
23
21
|
@model_count_gauge.set(
|
24
|
-
{
|
22
|
+
{ model: model.name.tableize },
|
25
23
|
model.count
|
26
24
|
)
|
27
25
|
end
|
28
26
|
end
|
29
|
-
|
30
|
-
protected
|
31
|
-
|
32
|
-
def app_hash(h = {})
|
33
|
-
{ app: app }.merge(h)
|
34
|
-
end
|
35
27
|
end
|
@@ -27,12 +27,12 @@ module G5PromRails::SidekiqApplicationMetrics
|
|
27
27
|
|
28
28
|
def update_sidekiq_statistics
|
29
29
|
stats = Sidekiq::Stats.new
|
30
|
-
@processed_counter.set(
|
31
|
-
@failed_counter.set(
|
32
|
-
@retry_gauge.set(
|
30
|
+
@processed_counter.set({}, stats.processed)
|
31
|
+
@failed_counter.set({}, stats.failed)
|
32
|
+
@retry_gauge.set({}, stats.retry_size)
|
33
33
|
|
34
34
|
Sidekiq::Stats::Queues.new.lengths.each do |queue, length|
|
35
|
-
@queues_gauge.set(
|
35
|
+
@queues_gauge.set({ queue: queue }, length)
|
36
36
|
end
|
37
37
|
end
|
38
38
|
end
|
@@ -24,13 +24,12 @@ class G5PromRails::SidekiqTimingMiddleware
|
|
24
24
|
end
|
25
25
|
|
26
26
|
def initialize(options = nil)
|
27
|
-
@app = options[:app]
|
28
27
|
@metric = options[:metric]
|
29
28
|
end
|
30
29
|
|
31
30
|
def call(worker, msg, queue)
|
32
31
|
@metric.observe(
|
33
|
-
{
|
32
|
+
{ job_class: worker.class.name },
|
34
33
|
Benchmark.realtime { yield }
|
35
34
|
)
|
36
35
|
end
|
data/lib/g5_prom_rails.rb
CHANGED