From 0ed0af44efda9cb1ceed5479b977a1e964b572b3 Mon Sep 17 00:00:00 2001 From: Sam Ruby Date: Sun, 20 Sep 2026 11:19:14 -0400 Subject: [PATCH] Mint the tampered sgid without extending a Room MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The invalid-sgid test made one live Room attachable — `rooms(:pets).tap { |r| r.extend ActionText::Attachable }` — only to call `attachable_sgid` on it. That method is `to_sgid(expires_in: nil, for: ActionText::Attachable::LOCATOR_NAME).to_s`, so the test can mint the same sgid directly and drop the per-instance extend; the assertion (a signature that does not verify resolves to MissingAttachable) is unchanged, and so are the bytes it tampers with. --- Gemfile.lock | 1 + test/models/action_text_attachment_test.rb | 8 ++++---- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/Gemfile.lock b/Gemfile.lock index 5c2a234..731f245 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -174,6 +174,7 @@ GEM erubi (1.13.1) faker (3.5.2) i18n (>= 1.8.11, < 2) + ffi (1.17.2) ffi (1.17.2-aarch64-linux-gnu) ffi (1.17.2-arm64-darwin) ffi (1.17.2-x86_64-darwin) diff --git a/test/models/action_text_attachment_test.rb b/test/models/action_text_attachment_test.rb index bb3483d..f1fb7c4 100644 --- a/test/models/action_text_attachment_test.rb +++ b/test/models/action_text_attachment_test.rb @@ -24,10 +24,10 @@ class ActionTextAttachmentTest < ActiveSupport::TestCase end test "lookup invalid sgid for an attachable requiring a valid sgid" do - # Make room instance attachable for testing purposes - room = rooms(:pets).tap { |r| r.extend ActionText::Attachable } - - message, signature = rooms(:pets).attachable_sgid.split("--") + # A Room is not attachable; mint the sgid an attachable would carry + # (`ActionText::Attachable#attachable_sgid` is exactly this call) so + # the lookup is exercised on a signature that does not verify. + message, signature = rooms(:pets).to_sgid(expires_in: nil, for: ActionText::Attachable::LOCATOR_NAME).to_s.split("--") html = %Q() node = ActionText::Fragment.wrap(html).find_all(ActionText::Attachment.tag_name).first