Skip to content

feat: add per-inbox signature management#226

Merged
gabrieljablonski merged 3 commits intomainfrom
gabrieljablonski/feat-signature-per-inbox
Feb 26, 2026
Merged

feat: add per-inbox signature management#226
gabrieljablonski merged 3 commits intomainfrom
gabrieljablonski/feat-signature-per-inbox

Conversation

@gabrieljablonski
Copy link
Member

@gabrieljablonski gabrieljablonski commented Feb 26, 2026

  • Introduced InboxSignature model to manage signatures specific to each inbox.
  • Added API endpoints for fetching, creating, updating, and deleting inbox signatures.
  • Updated UI components to support inbox-specific signatures, including overrides for signature position and separator.
  • Implemented a new composable useInboxSignatures for managing inbox signatures in the frontend.
  • Enhanced existing components to utilize inbox signatures, including the reply box and message signature settings.
  • Added tests for the new inbox signatures functionality, ensuring proper behavior of the API and model validations.
  • Updated translations for new UI elements related to inbox signatures.

Pull Request Template

Description

Please include a summary of the change and issue(s) fixed. Also, mention relevant motivation, context, and any dependencies that this change requires.
Fixes # (issue)

Type of change

Please delete options that are not relevant.

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality not to work as expected)
  • This change requires a documentation update

How Has This Been Tested?

Please describe the tests that you ran to verify your changes. Provide instructions so we can reproduce. Please also list any relevant details for your test configuration.

Checklist:

  • My code follows the style guidelines of this project
  • I have performed a self-review of my code
  • I have commented on my code, particularly in hard-to-understand areas
  • I have made corresponding changes to the documentation
  • My changes generate no new warnings
  • I have added tests that prove my fix is effective or that my feature works
  • New and existing unit tests pass locally with my changes
  • Any dependent changes have been merged and published in downstream modules

This change is Reviewable

Summary by CodeRabbit

  • New Features
    • Per-inbox message signatures: set custom content, position (top/bottom), and separator for each inbox.
    • Composer & reply UI now apply inbox-specific signatures and honor per-inbox overrides.
    • Settings UI: inbox selector, reset-to-default control, and save/delete flows for inbox signatures.
  • Localization
    • Added tooltip and settings text for signature placement and reset actions.

- Introduced `InboxSignature` model to manage signatures specific to each inbox.
- Added API endpoints for fetching, creating, updating, and deleting inbox signatures.
- Updated UI components to support inbox-specific signatures, including overrides for signature position and separator.
- Implemented a new composable `useInboxSignatures` for managing inbox signatures in the frontend.
- Enhanced existing components to utilize inbox signatures, including the reply box and message signature settings.
- Added tests for the new inbox signatures functionality, ensuring proper behavior of the API and model validations.
- Updated translations for new UI elements related to inbox signatures.
@gabrieljablonski gabrieljablonski self-assigned this Feb 26, 2026
Copilot AI review requested due to automatic review settings February 26, 2026 19:04
@coderabbitai
Copy link

coderabbitai bot commented Feb 26, 2026

Important

Review skipped

Auto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Introduces per-inbox message signatures: new InboxSignature model, API endpoints and views, frontend composable and API client, editor/component wiring to fetch/apply inbox-scoped signatures, settings UI to manage inbox overrides, migrations, and tests.

Changes

Cohort / File(s) Summary
Backend API & Models
app/controllers/api/v1/profile/inbox_signatures_controller.rb, app/models/inbox_signature.rb, app/models/inbox.rb, app/models/user.rb
New Profile InboxSignatures controller (index/show/update/destroy), InboxSignature model with validations, and has_many associations on Inbox and User (dependent: :destroy_async).
API Views & Routes
app/views/api/v1/profile/inbox_signatures/*, config/routes.rb
Jbuilder partials and views for inbox_signature resources; new profile-scoped routes for inbox_signatures (param: :inbox_id).
Database
db/migrate/20260226173647_create_inbox_signatures.rb, db/migrate/20260226194714_add_inbox_id_index_to_inbox_signatures.rb, db/schema.rb
Creates inbox_signatures table with user_id, inbox_id, message_signature, signature_position (default top), signature_separator (default blank); unique index on (user_id,inbox_id) and added inbox_id index.
Frontend Composable & API
app/javascript/dashboard/composables/useInboxSignatures.js, app/javascript/dashboard/api/inboxSignatures.js
New composable managing inbox-signature state (fetch/upsert/delete/getters) and API client exposing getAll/get/upsert/delete.
Editor & Message Components
app/javascript/dashboard/components/widgets/WootWriter/Editor.vue, app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue, app/javascript/dashboard/components-next/NewConversation/helpers/composeConversationHelper.js
Editor accepts signature position/separator overrides; ReplyBox and compose helper now use inbox-scoped signature and settings instead of only global UI settings.
Conversation Composition
app/javascript/dashboard/components-next/NewConversation/ComposeConversation.vue, app/javascript/dashboard/components-next/NewConversation/components/ComposeNewConversationForm.vue
ComposeConversation fetches inbox signatures; form accepts signatureSettings prop and includes it in new message payload.
Settings & Signature Management
app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue, app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue
Settings UI wired to fetch/manage inbox signatures; MessageSignature adds inbox selector, updateInboxSignature/deleteInboxSignature flows, and reset-to-default behavior.
Backend Service
lib/captain/reply_suggestion_service.rb
reply suggestion service uses a resolved_signature helper to prefer inbox-specific signature for agent prompts.
Localization
app/javascript/dashboard/i18n/locale/en/conversation.json, app/javascript/dashboard/i18n/locale/en/settings.json, app/javascript/dashboard/i18n/locale/pt_BR/conversation.json, app/javascript/dashboard/i18n/locale/pt_BR/settings.json
Added tooltip and settings strings for signature position labels and inbox selector (en & pt_BR).
Tests & Factories
spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb, spec/models/inbox_signature_spec.rb, spec/factories/inbox_signatures.rb, app/javascript/dashboard/composables/spec/useInboxSignatures.spec.js
Comprehensive controller, model, factory, and composable unit tests covering CRUD, validations, caching, and fallback behavior.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant ReplyBox as ReplyBox (Component)
    participant Composable as useInboxSignatures (Composable)
    participant API as InboxSignatures API Client
    participant Backend as Backend (API)

    User->>ReplyBox: mounts / selects inbox
    ReplyBox->>Composable: fetchInboxSignatures()
    Composable->>API: getAll(accountId)
    API->>Backend: GET /api/v1/profile/inbox_signatures
    Backend-->>API: inbox signatures list
    API-->>Composable: response
    Composable->>Composable: build map by inbox_id

    User->>ReplyBox: request signature for inbox
    ReplyBox->>Composable: getSignatureForInbox(inboxId)
    Composable-->>ReplyBox: inbox-specific signature or global fallback
    ReplyBox->>ReplyBox: render Editor with overrides / append signature
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~30 minutes

Possibly related PRs

  • #183: related changes to signature rendering and preview in Editor.vue and ReplyBox.vue.
  • #78: related updates to appendSignature helper and signature rendering behavior.

Suggested labels

enhancement

🐰
Per-inbox signatures hop into place,
Each message finds its own space,
Overrides here, defaults still near,
A little rabbit signs with cheer! 🥕

🚥 Pre-merge checks | ✅ 2 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 6.67% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The PR title 'feat: add per-inbox signature management' accurately summarizes the main change—introducing per-inbox signature management functionality across the backend and frontend.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch gabrieljablonski/feat-signature-per-inbox

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@gabrieljablonski
Copy link
Member Author

@coderabbitai review

@coderabbitai
Copy link

coderabbitai bot commented Feb 26, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (5)
db/schema.rb (1)

860-869: Consider adding an index on inbox_id for query performance.

The composite unique index on [user_id, inbox_id] only optimizes queries that filter by user_id first. Queries filtering by inbox_id alone (e.g., when destroying an inbox and its associated signatures via dependent: :destroy_async) won't benefit from this index.

Looking at similar patterns like inbox_members (Line 857), an individual index on inbox_id is included.

Suggested migration to add index
add_index :inbox_signatures, :inbox_id

Based on learnings: "Always validate presence and uniqueness in Rails models, and add proper database indexes."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@db/schema.rb` around lines 860 - 869, Add a single-column index on inbox_id
for the inbox_signatures table to speed queries that filter by inbox_id (e.g.,
dependent: :destroy_async); create a migration that adds an index on :inbox_id
for inbox_signatures (ensure it does not duplicate the existing unique composite
index index_inbox_signatures_on_user_id_and_inbox_id) and run migrations to
apply it.
spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb (1)

82-128: Consider adding validation error tests.

The upsert tests cover happy paths well. Consider adding a test for validation failures (e.g., invalid signature_position value like 'invalid') to ensure the API returns appropriate error responses.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb` around
lines 82 - 128, Add a negative spec that sends invalid params (e.g.,
signature_position: 'invalid') to the PUT
/api/v1/profile/inbox_signatures/:inbox_id endpoint and assert the controller
returns a 422 (or appropriate error status) and a JSON error payload; locate the
test alongside the existing upsert examples in
spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb, reuse the
same request pattern (put ..., params: signature_params, headers:
agent.create_new_auth_token, as: :json), and verify that InboxSignature count
does not change and that the response.parsed_body contains the model validation
errors for signature_position coming from the InboxSignature validations or
Api::V1::Profile::InboxSignaturesController.
app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue (1)

50-53: Consider awaiting fetchInboxSignatures or handling potential race conditions.

The fetchInboxSignatures() call is fire-and-forget during setup. While this is acceptable for preloading, if the user interacts with inbox signatures before the fetch completes, there could be stale state issues. Consider whether this timing is acceptable for the UX.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue` around
lines 50 - 53, fetchInboxSignatures() is called fire-and-forget which can cause
race conditions if the user interacts with inbox signatures before the fetch
completes; update the setup logic to await fetchInboxSignatures() (or capture
and act on its returned Promise) so the component state is populated before user
actions, or add/loading state gating around the UI and ensure
upsertInboxSignature and deleteInboxSignature check for pending/loaded state;
specifically modify the initialization where useInboxSignatures() is used to
either await fetchInboxSignatures() or set a "loadingSignatures" flag that the
template and upsertInboxSignature/deleteInboxSignature respect.
app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue (1)

316-316: Minor: Consider using Tailwind utility class instead of custom h-[10rem].

The h-[10rem] uses Tailwind's arbitrary value syntax which works, but consider using a standard Tailwind height class (e.g., h-40 = 10rem) for consistency.

♻️ Suggested change
     <WootMessageEditor
       id="message-signature-input"
       v-model="signature"
-      class="message-editor h-[10rem] !px-3"
+      class="message-editor h-40 !px-3"
       is-format-mode
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue`
at line 316, The class on the message editor uses an arbitrary Tailwind value
"h-[10rem]"—replace it with the equivalent standard utility "h-40" for
consistency; update the element that currently has class "message-editor
h-[10rem] !px-3" in MessageSignature.vue to use "message-editor h-40 !px-3".
app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue (1)

101-129: Consider removing unused inboxSignaturesFetched from setup return.

inboxSignaturesFetched is destructured and returned from setup but is never used elsewhere in the component. Removing it will keep the code clean and reduce unnecessary clutter.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue` around
lines 101 - 129, The variable inboxSignaturesFetched is unused; remove it to
clean up the setup function by deleting the hasFetched: inboxSignaturesFetched
alias from the useInboxSignatures() destructuring and removing
inboxSignaturesFetched from the returned object, and verify no other references
to inboxSignaturesFetched remain (adjust any remaining logic to use hasFetched
or fetch status from useInboxSignatures() directly if needed).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@app/controllers/api/v1/profile/inbox_signatures_controller.rb`:
- Around line 5-12: The index action currently trusts params[:account_id] and
uses Account.find(...) which allows users to access other accounts' signatures;
update the logic in index to authorize the requested account before using its
inbox_ids — e.g. find the account scoped to the current user or use your
authorization policy (authorize Account) to ensure the user belongs to that
account, then use that account's inbox_ids for `@user.inbox_signatures`; if the
account is not accessible, fall back to `@user.inbox_signatures` or return a
forbidden response.
- Around line 18-26: In update action, before creating a new InboxSignature via
`@user.inbox_signatures.create`! (when `@inbox_signature` is nil), verify the
current user is a member of the target inbox (params[:inbox_id]) using the
existing membership check (e.g., InboxMember.exists?(user: `@user`, inbox_id:
params[:inbox_id]) or the controller's authorize/membership helper); if the user
is not a member, halt and respond with forbidden/unauthorized (raise
Pundit::NotAuthorizedError or render head :forbidden) instead of creating the
signature; keep the membership check path for both update and create branches so
`@inbox_signature.update`! still requires membership.

In `@db/migrate/20260226173647_create_inbox_signatures.rb`:
- Around line 4-5: The migration CreateInboxSignatures currently adds
t.references :user and t.references :inbox without DB-level foreign keys; update
the migration so these references include foreign_key constraints (or add
explicit add_foreign_key calls for user_id and inbox_id) to enforce referential
integrity and prevent orphaned inbox_signatures rows when users or inboxes are
deleted; modify the t.references lines in the CreateInboxSignatures migration or
append add_foreign_key :inbox_signatures, :users and add_foreign_key
:inbox_signatures, :inboxes accordingly.

---

Nitpick comments:
In `@app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue`:
- Around line 101-129: The variable inboxSignaturesFetched is unused; remove it
to clean up the setup function by deleting the hasFetched:
inboxSignaturesFetched alias from the useInboxSignatures() destructuring and
removing inboxSignaturesFetched from the returned object, and verify no other
references to inboxSignaturesFetched remain (adjust any remaining logic to use
hasFetched or fetch status from useInboxSignatures() directly if needed).

In `@app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue`:
- Around line 50-53: fetchInboxSignatures() is called fire-and-forget which can
cause race conditions if the user interacts with inbox signatures before the
fetch completes; update the setup logic to await fetchInboxSignatures() (or
capture and act on its returned Promise) so the component state is populated
before user actions, or add/loading state gating around the UI and ensure
upsertInboxSignature and deleteInboxSignature check for pending/loaded state;
specifically modify the initialization where useInboxSignatures() is used to
either await fetchInboxSignatures() or set a "loadingSignatures" flag that the
template and upsertInboxSignature/deleteInboxSignature respect.

In
`@app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue`:
- Line 316: The class on the message editor uses an arbitrary Tailwind value
"h-[10rem]"—replace it with the equivalent standard utility "h-40" for
consistency; update the element that currently has class "message-editor
h-[10rem] !px-3" in MessageSignature.vue to use "message-editor h-40 !px-3".

In `@db/schema.rb`:
- Around line 860-869: Add a single-column index on inbox_id for the
inbox_signatures table to speed queries that filter by inbox_id (e.g.,
dependent: :destroy_async); create a migration that adds an index on :inbox_id
for inbox_signatures (ensure it does not duplicate the existing unique composite
index index_inbox_signatures_on_user_id_and_inbox_id) and run migrations to
apply it.

In `@spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb`:
- Around line 82-128: Add a negative spec that sends invalid params (e.g.,
signature_position: 'invalid') to the PUT
/api/v1/profile/inbox_signatures/:inbox_id endpoint and assert the controller
returns a 422 (or appropriate error status) and a JSON error payload; locate the
test alongside the existing upsert examples in
spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb, reuse the
same request pattern (put ..., params: signature_params, headers:
agent.create_new_auth_token, as: :json), and verify that InboxSignature count
does not change and that the response.parsed_body contains the model validation
errors for signature_position coming from the InboxSignature validations or
Api::V1::Profile::InboxSignaturesController.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 21007bd and fa2698c.

📒 Files selected for processing (29)
  • app/controllers/api/v1/profile/inbox_signatures_controller.rb
  • app/javascript/dashboard/api/inboxSignatures.js
  • app/javascript/dashboard/components-next/NewConversation/ComposeConversation.vue
  • app/javascript/dashboard/components-next/NewConversation/components/ComposeNewConversationForm.vue
  • app/javascript/dashboard/components-next/NewConversation/helpers/composeConversationHelper.js
  • app/javascript/dashboard/components/widgets/WootWriter/Editor.vue
  • app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue
  • app/javascript/dashboard/composables/spec/useInboxSignatures.spec.js
  • app/javascript/dashboard/composables/useInboxSignatures.js
  • app/javascript/dashboard/i18n/locale/en/conversation.json
  • app/javascript/dashboard/i18n/locale/en/settings.json
  • app/javascript/dashboard/i18n/locale/pt_BR/conversation.json
  • app/javascript/dashboard/i18n/locale/pt_BR/settings.json
  • app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue
  • app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue
  • app/models/inbox.rb
  • app/models/inbox_signature.rb
  • app/models/user.rb
  • app/views/api/v1/profile/inbox_signatures/_inbox_signature.json.jbuilder
  • app/views/api/v1/profile/inbox_signatures/index.json.jbuilder
  • app/views/api/v1/profile/inbox_signatures/show.json.jbuilder
  • app/views/api/v1/profile/inbox_signatures/update.json.jbuilder
  • config/routes.rb
  • db/migrate/20260226173647_create_inbox_signatures.rb
  • db/schema.rb
  • lib/captain/reply_suggestion_service.rb
  • spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb
  • spec/factories/inbox_signatures.rb
  • spec/models/inbox_signature_spec.rb

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This pull request introduces a comprehensive per-inbox signature management feature that allows users to configure unique email/message signatures for each inbox they manage, with fallback to a global default signature. The feature is well-implemented across both backend (Ruby on Rails) and frontend (Vue.js) with appropriate test coverage.

Changes:

  • Backend: Added InboxSignature model with database migration, API endpoints, and business logic integration
  • Frontend: Implemented UI components for managing inbox-specific signatures with a composable pattern for state management
  • Translations: Added complete English and Portuguese (pt-BR) translations for all new UI elements

Reviewed changes

Copilot reviewed 29 out of 29 changed files in this pull request and generated 8 comments.

Show a summary per file
File Description
db/migrate/20260226173647_create_inbox_signatures.rb Migration to create inbox_signatures table with unique constraint on user_id and inbox_id
db/schema.rb Updated schema to reflect new inbox_signatures table
app/models/inbox_signature.rb Model with validations for signature content, position, and separator
app/models/user.rb Added has_many association to inbox_signatures
app/models/inbox.rb Added has_many association to inbox_signatures
app/controllers/api/v1/profile/inbox_signatures_controller.rb RESTful API endpoints for managing inbox signatures
app/views/api/v1/profile/inbox_signatures/*.json.jbuilder JSON view templates for API responses
config/routes.rb Added routes for inbox signatures API
lib/captain/reply_suggestion_service.rb Integrated inbox-specific signatures into AI reply suggestions
app/javascript/dashboard/api/inboxSignatures.js API client for inbox signatures endpoints
app/javascript/dashboard/composables/useInboxSignatures.js Vue composable for managing inbox signatures state
app/javascript/dashboard/composables/spec/useInboxSignatures.spec.js Comprehensive unit tests for the composable
app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue Enhanced UI component with inbox selector and signature management
app/javascript/dashboard/routes/dashboard/settings/profile/Index.vue Integration of inbox signature handlers
app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue Updated to use inbox-specific signatures
app/javascript/dashboard/components/widgets/WootWriter/Editor.vue Added support for signature position/separator overrides with tooltips
app/javascript/dashboard/components-next/NewConversation/*.vue Updated compose conversation components to support inbox signatures
app/javascript/dashboard/i18n/locale/en/*.json English translations for new UI elements
app/javascript/dashboard/i18n/locale/pt_BR/*.json Portuguese translations for new UI elements
spec/models/inbox_signature_spec.rb Model tests for validations and associations
spec/factories/inbox_signatures.rb Factory for creating test inbox signatures
spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb API endpoint tests covering CRUD operations

@gabrieljablonski
Copy link
Member Author

@coderabbitai review

@coderabbitai
Copy link

coderabbitai bot commented Feb 26, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@app/controllers/api/v1/profile/inbox_signatures_controller.rb`:
- Around line 56-61: The authorization check in validate_account_access!
currently calls head :unauthorized but does not halt execution, so the
controller action (e.g., index) can continue; update validate_account_access!
(and mirror the same fix used for validate_inbox_access) to immediately return
after sending the unauthorized response — for example, change the unauthorized
branch to use return head :unauthorized or add an explicit return after head
:unauthorized so the action stops executing when the account check fails.
- Around line 49-54: The authorization check in validate_inbox_access uses head
:unauthorized but does not halt execution; update the validate_inbox_access
method so that when InboxMember.exists?(user_id: `@user.id`, inbox_id: inbox_id)
is false you call head :unauthorized and return to stop the action from
continuing. Locate the validate_inbox_access method and append an explicit
return after head :unauthorized (e.g., head :unauthorized and return) to ensure
the controller action is not executed for unauthorized requests.

In
`@app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue`:
- Around line 234-243: The label uses for="inboxSelector" but the SingleSelect
component (v-model="selectedInbox") has no matching id, breaking label-control
association; update the SingleSelect instance to include an id="inboxSelector"
prop (or pass the id via the component's prop name if it uses a different prop
like inputId) so the label is explicitly associated with the control, or
alternatively add an aria-labelledby/aria-describedby that references the
label—ensure the identifier exactly matches "inboxSelector" and adjust the
SingleSelect prop name if the component expects a different prop.
- Around line 162-164: fetchInboxSignatures() is called async but the component
never refreshes the selected inbox form when that fetch completes; ensure the
selected inbox signature/state is reloaded after the fetch resolves by making
fetchInboxSignatures() return a Promise (or await it) and then calling the
existing selected-inbox loader (e.g., the method that populates selectedInbox or
the reactive state used for the form) to rehydrate the form values so you don't
fallback to global values and accidentally overwrite overrides; update the call
site in MessageSignature.vue (where fetchInboxSignatures() is invoked on mount
and/or on inbox change) to await the fetch and then invoke the routine that sets
selectedInbox/selectedInboxSignature so the correct override values are applied.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between fa2698c and 4e45eb5.

📒 Files selected for processing (8)
  • app/controllers/api/v1/profile/inbox_signatures_controller.rb
  • app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue
  • app/javascript/dashboard/routes/dashboard/settings/profile/MessageSignature.vue
  • app/models/inbox_signature.rb
  • db/migrate/20260226194714_add_inbox_id_index_to_inbox_signatures.rb
  • db/schema.rb
  • spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb
  • spec/models/inbox_signature_spec.rb
🚧 Files skipped from review as they are similar to previous changes (5)
  • app/javascript/dashboard/components/widgets/conversation/ReplyBox.vue
  • spec/models/inbox_signature_spec.rb
  • spec/controllers/api/v1/profile/inbox_signatures_controller_spec.rb
  • db/schema.rb
  • app/models/inbox_signature.rb

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 30 out of 30 changed files in this pull request and generated 4 comments.

@gabrieljablonski gabrieljablonski merged commit 56c5609 into main Feb 26, 2026
@gabrieljablonski gabrieljablonski deleted the gabrieljablonski/feat-signature-per-inbox branch February 26, 2026 22:53
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants