Skip to content
Merged
Show file tree
Hide file tree
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
10 changes: 9 additions & 1 deletion app/controllers/sponsors_controller.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
class SponsorsController < ApplicationController
def index
@sponsor_levels = Sponsor.active.group_by(&:level)
# v1: bump when the sponsors view or partials change, otherwise a deploy
# keeps serving the cached body until the next sponsor save.
key = "sponsors/index/v1/#{Sponsor.active.maximum(:updated_at)&.to_fs(:usec)}"
body = Rails.cache.fetch(key) do
@sponsor_levels = Sponsor.active.group_by(&:level)
render_to_string(layout: false)
end
# body is markup rendered by this app's own template, not user input
render html: body.html_safe # rubocop:disable Rails/OutputSafety
end
end
43 changes: 43 additions & 0 deletions spec/requests/sponsors_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
# frozen_string_literal: true

require 'rails_helper'

RSpec.describe 'Sponsors' do
let!(:sponsor) { Fabricate.create(:sponsor, name: 'Acme Corp') }

around do |example|
original_cache = Rails.cache
Rails.cache = ActiveSupport::Cache::MemoryStore.new
example.run
Rails.cache = original_cache
end

it 'renders the sponsors page' do
get '/sponsors'

expect(response).to have_http_status(:ok)
expect(response.body).to include('Acme Corp')
end

it 'serves the cached body when no sponsor has been updated' do
get '/sponsors'

# update_columns bypasses callbacks, so updated_at (and the cache key) stays unchanged
sponsor.update_columns(name: 'Renamed Corp')

get '/sponsors'

expect(response.body).to include('Acme Corp')
expect(response.body).not_to include('Renamed Corp')
end

it 're-renders when a sponsor is updated' do
get '/sponsors'

sponsor.update!(name: 'Renamed Corp')

get '/sponsors'

expect(response.body).to include('Renamed Corp')
end
end
Loading