Skip to content

Commit

Permalink
Load metrics for job statuses asynchronously (#1286)
Browse files Browse the repository at this point in the history
* Load metrics for job statuses asynchronously

* Extract state names to method; add basic request tests

---------

Co-authored-by: Ben Sheldon [he/him] <[email protected]>
  • Loading branch information
binarygit and bensheldon authored Mar 18, 2024
1 parent 35461ea commit 20fd1f8
Show file tree
Hide file tree
Showing 7 changed files with 66 additions and 4 deletions.
10 changes: 10 additions & 0 deletions app/controllers/good_job/metrics_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,20 @@ def primary_nav
}
end

def job_status
@filter = JobsFilter.new(params)

render json: @filter.states.transform_values { |count| number_with_delimiter(count) }
end

private

def number_to_human(count)
helpers.number_to_human(count, **helpers.translate_hash("good_job.number.human.decimal_units"))
end

def number_with_delimiter(count)
helpers.number_with_delimiter(count, **helpers.translate_hash('good_job.number.format'))
end
end
end
4 changes: 4 additions & 0 deletions app/filters/good_job/base_filter.rb
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@ def states
raise NotImplementedError
end

def state_names
raise NotImplementedError
end

def to_params(override = {})
{
job_class: params[:job_class],
Expand Down
4 changes: 4 additions & 0 deletions app/filters/good_job/jobs_filter.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@

module GoodJob
class JobsFilter < BaseFilter
def state_names
%w[scheduled retried queued running succeeded discarded]
end

def states
@_states ||= begin
query = filtered_query(params.except(:state))
Expand Down
8 changes: 4 additions & 4 deletions app/views/good_job/shared/_filter.erb
Original file line number Diff line number Diff line change
Expand Up @@ -47,16 +47,16 @@
</div>
<% end %>

<ul data-live-poll-region="filter-tabs" class="nav nav-tabs my-3">
<ul data-controller="async-values" data-async-values-url-value="<%= metrics_job_status_path %>" data-live-poll-region="filter-tabs" class="nav nav-tabs my-3">
<li class="nav-item">
<%= link_to t(".all"), filter.to_params(state: nil), class: "nav-link #{"active" unless params[:state].present?}" %>
</li>

<% filter.states.each do |name, count| %>
<% filter.state_names.each do |name| %>
<li class="nav-item">
<%= link_to filter.to_params(state: name), class: "nav-link #{"active" if params[:state] == name}" do %>
<%= t(name, scope: 'good_job.status', count: count) %>
<span class="badge bg-primary rounded-pill <%= "bg-secondary" if count == 0 %>"><%= number_with_delimiter(count, t('good_job.number.format')) %></span>
<%= t(name, scope: 'good_job.status') %>
<span data-async-values-target="value", data-async-values-key="<%= name %>" data-async-values-zero-class="bg-secondary" class="badge bg-primary rounded-pill d-none"></span>
<% end %>
</li>
<% end %>
Expand Down
1 change: 1 addition & 0 deletions config/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
end
end
get 'jobs/metrics/primary_nav', to: 'metrics#primary_nav', as: :metrics_primary_nav
get 'jobs/metrics/job_status', to: 'metrics#job_status', as: :metrics_job_status

resources :batches, only: %i[index show]

Expand Down
6 changes: 6 additions & 0 deletions spec/app/filters/good_job/jobs_filter_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,12 @@
end
end

describe '#state_names' do
it 'matches states' do
expect(filter.state_names).to match_array(filter.states.keys)
end
end

describe '#states' do
it 'is a valid result' do
expect(filter.states).to eq({
Expand Down
37 changes: 37 additions & 0 deletions spec/requests/good_job/metrics_controller_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# frozen_string_literal: true

require 'rails_helper'

describe GoodJob::MetricsController do
describe 'GET #primary_nav' do
it 'returns the primary navigation metrics' do
get good_job.metrics_primary_nav_path
expect(response).to have_http_status(:ok)
expect(response.body).to eq(
{
jobs_count: '0',
batches_count: '0',
cron_entries_count: '1',
processes_count: '0',
}.to_json
)
end
end

describe 'GET #job_status' do
it 'returns the primary navigation metrics' do
get good_job.metrics_job_status_path
expect(response).to have_http_status(:ok)
expect(response.body).to eq(
{
"scheduled" => "0",
"retried" => "0",
"queued" => "0",
"running" => "0",
"succeeded" => "0",
"discarded" => "0",
}.to_json
)
end
end
end

0 comments on commit 20fd1f8

Please sign in to comment.