mirror of
https://github.com/basecamp/once-campfire.git
synced 2026-10-10 00:30:13 +09:00
af4f94c4bd
Every message rewrote the row of every disconnected member of the room, including the ones who were unread already and stay unread. Open rooms take in the whole account, so in steady state that is every member on every message: 325 WAL pages per post at 10,000 members, against 16 when only the members who had read the room are written. Directs keep touching all their members: a direct's sidebar row is cached by its membership and carries the room's recency, so it has to be refreshed on every message. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017dFSDHrgrLoBELwjV3Qunq
88 lines
2.9 KiB
Ruby
88 lines
2.9 KiB
Ruby
require "test_helper"
|
|
|
|
class Users::SidebarsControllerTest < ActionDispatch::IntegrationTest
|
|
setup do
|
|
sign_in :david
|
|
end
|
|
|
|
test "show" do
|
|
get user_sidebar_url
|
|
|
|
users(:david).rooms.opens.each do |room|
|
|
assert_match /#{room.name}/, @response.body
|
|
end
|
|
end
|
|
|
|
test "unread directs" do
|
|
rooms(:david_and_jason).messages.create! client_message_id: 999, body: "Hello", creator: users(:jason)
|
|
|
|
get user_sidebar_url
|
|
assert_select ".unread", count: users(:david).memberships.select { |m| m.room.direct? && m.unread? }.count
|
|
end
|
|
|
|
|
|
test "unread other" do
|
|
rooms(:watercooler).messages.create! client_message_id: 999, body: "Hello", creator: users(:jason)
|
|
|
|
get user_sidebar_url
|
|
assert_select ".unread", count: users(:david).memberships.reject { |m| m.room.direct? || !m.unread? }.count
|
|
end
|
|
|
|
test "a cached direct that is already unread still sorts by its latest message" do
|
|
room = rooms(:david_and_jason)
|
|
|
|
with_memory_cache do
|
|
travel_to 1.hour.ago do
|
|
room.messages.create! client_message_id: 998, body: "First", creator: users(:jason)
|
|
end
|
|
get user_sidebar_url
|
|
assert memberships(:david_david_and_jason).reload.unread?
|
|
|
|
room.messages.create! client_message_id: 999, body: "Second", creator: users(:jason)
|
|
get user_sidebar_url
|
|
|
|
assert_select "##{dom_id(room, :list)}[data-sorted-list-number=?]", room.reload.updated_at.to_fs(:epoch)
|
|
end
|
|
end
|
|
|
|
test "directs are ordered by room recency, not name" do
|
|
older = rooms(:david_and_jason)
|
|
newer = rooms(:david_and_kevin)
|
|
older.update_column :updated_at, 2.days.ago
|
|
newer.update_column :updated_at, 1.minute.ago
|
|
|
|
get user_sidebar_url
|
|
|
|
assert_operator @response.body.index(dom_id(newer, :list)), :<, @response.body.index(dom_id(older, :list))
|
|
end
|
|
|
|
test "shared rooms stay ordered by name" do
|
|
get user_sidebar_url
|
|
|
|
shared_ids = users(:david).rooms.without_directs.sort_by { |room| room.name.downcase }.map { |room| dom_id(room, :list) }
|
|
positions = shared_ids.map { |id| @response.body.index(id) }
|
|
|
|
assert positions.all?
|
|
assert_equal positions.sort, positions
|
|
end
|
|
|
|
private
|
|
def with_memory_cache
|
|
old_cache = Rails.cache
|
|
old_collection_cache = ActionView::PartialRenderer.collection_cache
|
|
old_controller_cache = Users::SidebarsController.cache_store
|
|
old_caching = Users::SidebarsController.perform_caching
|
|
|
|
Rails.cache = ActiveSupport::Cache::MemoryStore.new
|
|
ActionView::PartialRenderer.collection_cache = Rails.cache
|
|
Users::SidebarsController.cache_store = Rails.cache
|
|
Users::SidebarsController.perform_caching = true
|
|
yield
|
|
ensure
|
|
Rails.cache = old_cache
|
|
ActionView::PartialRenderer.collection_cache = old_collection_cache
|
|
Users::SidebarsController.cache_store = old_controller_cache
|
|
Users::SidebarsController.perform_caching = old_caching
|
|
end
|
|
end
|