Skip to content

chore: Polish Settings, Certificates, and Downloads views against Fuselage#3344

Open
jeanfbrito wants to merge 7 commits into
masterfrom
chore/polish-settings
Open

chore: Polish Settings, Certificates, and Downloads views against Fuselage#3344
jeanfbrito wants to merge 7 commits into
masterfrom
chore/polish-settings

Conversation

@jeanfbrito
Copy link
Copy Markdown
Member

@jeanfbrito jeanfbrito commented May 26, 2026

Summary

Polishes the three full-window panels in the desktop shell (Settings, Certificates, Downloads) so they line up with the Fuselage design system, and captures the design direction in committed PRODUCT.md / DESIGN.md context files.

The visual contract in DESIGN.md was built from the live Fuselage token source (@rocket.chat/fuselage-tokens + PaletteStyleTag), not from the hardcoded fallbacks scattered through the app, so the documented values match what the runtime actually emits across the light, dark, and high-contrast themes.

What changed

Settings

  • GeneralTab's flat list of ~19 features is grouped into 5 labeled sections (Notifications, Performance, Calls & video, Window & appearance, Integrations) via a small reusable Section helper, mirroring the existing DeveloperTab pattern.
  • SettingsView title steps from h1 to h2 with tightened title-to-tabs spacing; Tabs share the content gutter; Scrollable inner uses padding instead of margin. Esc dismisses the view; back IconButton gains an aria-label.

Certificates

  • Extracted a CertificateSection with an h4 title, a hint line, and an empty state. Dropped a stray <Box is='form'>, doubled padding, an off-scale marginBlockStart, and Table sticky (two stacked sticky headers shared one scroll container).
  • <TableRow action> provides the hover affordance; striped removed.

Downloads

  • Title to h2; bg='light' to bg='room' for theme parity with Settings; filter row trimmed to an even gutter; SelectLegacy swapped for the current Select; clear-filters icon corrected from trash to cross with an aria-label and a disabled state when no filters are active.
  • Empty states for first-run and filtered-empty. Esc-to-close + aria-label.
  • DownloadItem: literal widths replaced with flex + min/max so rows reflow; semantic color tokens; per-row actions moved into a ButtonGroup with danger on destructive ones; progress bar hidden for completed downloads.

Shared + cleanup

  • Downloads and Certificates lists share one row affordance: a 1px stroke-extra-light divider + surface-hover hover tint, both theme tokens.
  • Anchor-as-button (<a href='#'>) replaced with the Fuselage Button primitive in both ActionButtons.
  • Swept every color prop onto semantic token names (font-default, font-hint, font-secondary-info, etc.) across the touched views plus ServerInfoContent, ServersView, TopBar.
  • Replaced raw style={{ paddingTop: '4px' }} with paddingBlockStart='x4' in the affected settings features.
  • Body font stack in Shell/styles.tsx switched from system-ui to the Fuselage Inter-first stack. The pre-hydration overlays (loading.css / error.css) intentionally keep system-ui; documented in DESIGN.md.

Design context

  • PRODUCT.md, DESIGN.md, and .impeccable/design.json capture register, users, anti-references, principles, and the Fuselage-verified token contract for future UI work.

Before:
image
After:
image

Before:
image
After:
image

Before:
image
After:
image

Notes for reviewers

  • Verified with npx tsc --noEmit (clean) on every commit; GitNexus upstream impact analysis was LOW on each touched surface.
  • Theme verification (light / dark / high-contrast) in a running build is still pending; the code is token-based so it should follow the active theme, but a visual pass is worth doing before merge.
  • .impeccable/design.json is agent-context tooling output. If the team would rather not track it, it can move to .gitignore and drop from this PR.

Test plan

  • Open Settings; confirm the five sections render and group correctly per platform
  • Open Certificates; confirm hover affordance and empty states; scroll with both tables populated
  • Open Downloads; confirm filters, clear-filters disabled state, empty states, completed-item rows
  • Tab through each view with the keyboard; confirm focus, aria-labels, Esc-to-close
  • Cycle light / dark / high-contrast themes and confirm all three read correctly

Summary by CodeRabbit

  • New Features

    • Escape key to go back; Settings reorganized into labeled sections.
    • New reusable UI sections and certificate sections for clearer layout.
  • Style

    • Downloads UI: compact actions, conditional progress, improved empty states and keyboard support.
    • Visual refinements: typography, color token updates, spacing, global font stack, and subtle top-bar/header color tweaks.
  • Bug Fixes / UX

    • Action controls standardized to button components; improved row/truncation behavior and keyboard handling.
  • Documentation

    • Added comprehensive design system and product documentation.
  • Localization

    • New/updated English strings for downloads, certificates manager, and settings.
  • Chores

    • Desktop config updated with additional URI/MIME associations.

Review Change Stack

Align SettingsView with the desktop design system (DESIGN.md):

- Group GeneralTab's 19 features into 5 sections (Notifications,
  Performance, Calls & video, Window & appearance, Integrations)
  via a reusable Section helper, mirroring the DeveloperTab
  "Logging" header pattern.
- Title row uses fontScale h2 (24/32) with alignItems=center and
  an mie={8} gap to the back IconButton. Step down from h1
  matches the shell-quiet hierarchy in DESIGN.md.
- Title block uses pi/pbs/pbe spacing so the Tabs sit close to
  the title typographically. Tabs wrap in <Box pi={24}> so they
  align with the content gutter instead of running edge-to-edge.
- Scrollable inner switches from m='x24' to pi/pbs/pbe (padding,
  not margin, inside a scroll container).
- Esc key dismisses the SettingsView for keyboard users, with
  tabIndex={-1} on the visible root so it can capture key
  events. Back IconButton gains an aria-label.
- TelephonyServer drops a raw style={{ paddingTop: '4px' }} in
  favor of paddingBlockStart='x4', matching the sibling
  ThemeAppearance feature.
- ClearPermittedScreenCaptureServers loses a leftover
  console.log from its onClick handler.
- en.i18n.json gains settings.back and the five new
  settings.sections.* keys.
Align the Certificates tab with the rest of the SettingsView
redesign and fix the stacked-sticky-header bug.

- Extract a CertificateSection helper that renders an h4 title,
  a c1 hint paragraph, and either an empty-state message or the
  table. Matches the section pattern in GeneralTab / DeveloperTab.
- Drop the bogus <Box is='form'> wrapper (there is no form here)
  and the outer padding={24}, which doubled the SettingsView
  outer pi={24}. Replace marginBlockStart={50} between sections
  with mbs={32} (on the Fuselage 4-multiple scale).
- Drop the Table sticky prop: two stacked sticky-headed tables
  share one Scrollable, so the first header would stick over the
  second table's rows mid-scroll. Headers now flow with content.
- Add empty-state copy for both tables ("No trusted certificates
  yet." / "No certificates have been flagged.") and hint copy
  explaining what each section means.
- CertificateItem drops the decorative key icon and wraps the
  URL in <Box withTruncatedText title={url}> so long URLs
  ellipsize instead of overflowing the column.
- ActionButton replaces <a href='#'> with Fuselage <Button small
  danger>: correct semantics and a11y role for a destructive
  action, no scroll-jump on click.
Bring DownloadsManagerView in line with the SettingsView redesign
and give the Downloads and Certificates lists a shared
row-affordance pattern (hairline divider + hover tint), so users
can tell which row they are about to click.

DownloadsManagerView:
- Title fontScale steps from h1 to h2 with pi/pbs/pbe rhythm
  matching SettingsView. bg switches from 'light' to 'room' so
  the Downloads surface obeys PaletteStyleTag theme preference
  the same way Settings does.
- Filter row trims its 64px outer gutter to pi={24} and replaces
  paddingInline={2} per child with mie={8}, so the four controls
  sit on an even rhythm. The clear-filters affordance moves from
  a destructive 'trash' icon to 'cross', gains an aria-label,
  and disables itself when no filters are active.
- SelectLegacy is swapped for the current Fuselage Select used
  elsewhere in the app.
- Empty-state copy: a first-run "No downloads yet" message and
  a "No downloads match these filters" + Clear-filters button
  when active filters exclude every row.
- Esc dismisses the view; the back IconButton gains an
  aria-label. handleBackButton moves to useCallback to match
  the rest of the codebase.

DownloadItem:
- Fixed literal widths (388 / 344 / 32 / mbe=26) and arbitrary
  pixel values get replaced with flex + minWidth/maxWidth +
  4-multiple spacing so the row reflows on narrower windows.
- Semantic color tokens replace the raw palette refs
  (font-default, font-danger, font-secondary-info).
- The per-row action list moves into a Fuselage ButtonGroup.
  Destructive actions (Cancel, Remove) use the danger variant
  so the hierarchy reads at a glance.
- The progress bar hides for completed downloads (a full bar
  at 100% conveys nothing on a finished item).
- Each row carries a 1px stroke-extra-light top border (skipped
  on :first-of-type) and a hovered surface-hover background via
  @rocket.chat/css-in-js. Padding shifts from mbe={24} to
  symmetric pbs/pbe/pi so the hover highlight reaches edge to
  edge.

ActionButton (Downloads):
- The <a href='#'> anchor is replaced with a Fuselage <Button
  small secondary>: correct semantics, no scroll-jump, and the
  small/secondary pairing reads quietly inside a dense row.

CertificatesManager + CertificateItem:
- The cert table drops the striped prop; on the dark settings
  surface the stripe broke the tonal-step rule. TableRow gains
  the action prop so Fuselage's built-in --action:hover lights
  up the row, matching the Downloads cue.

i18n:
- Adds downloads.back and the four downloads.empty.* keys.
- Renames "Show in Folder" to "Show in folder" (Sentence Case
  Rule).
Strategic and visual design context for /impeccable workflows.
DESIGN.md is the Stitch six-section spec with tokens verified
against the live Fuselage source (packages/fuselage-tokens and
PaletteStyleTag), not against the hardcoded fallbacks scattered
across src/ui.

Key facts the spec captures:

- Three themes ship: light, dark, and high-contrast. The shell
  must verify every color choice in all three. PRODUCT.md
  mandates WCAG 2.2 AA plus government and healthcare extras,
  so high-contrast is not optional.
- Tokens are emitted by PaletteStyleTag as
  --rcx-color-<category>-<role>, never as palette-grade vars
  like --rcx-color-primary-500. The TS palette pipeline maps
  primary -> b, danger -> r, success -> g, warning -> y,
  neutral -> n; palette-grade vars exist only as SCSS fallbacks.
- Primary button background is --rcx-color-button-background-
  primary-default (colors.b500 = #1d74f5), distinct from
  --rcx-color-status-background-info (light tint #d1ebfe).
- Mention count badge is Badge variant='secondary',
  badge-background-level-1 = colors.n700 = #6c737a. Gray, not
  red. The badge is a count, not an alarm.
- surface-room is theme-following (white in light, #1F2329 in
  dark). The hardcoded #2f343d in Shell/styles.tsx and
  SideBar/styles.tsx is a pre-PaletteStyleTag-hydration
  backstop only; do not treat it as a token.

The sidecar at .impeccable/design.json carries tonal ramps per
color, dark-theme hex values, shadow and motion tokens, and
self-contained HTML/CSS snippets for the impeccable live panel.
Components covered: Server Button (selected), Mention Badge,
Warning Badge, Primary Button, Danger Button, Dialog, Sidebar
Rail, and the shared List Row affordance (hairline divider +
hover tint) used by both Downloads and Certificates.
DESIGN.md mandates that color tokens be read through their full
semantic name (font-default, font-hint, font-annotation,
font-secondary-info), never via short aliases (default, hint,
annotation) and never via palette-grade vars (neutral-600).
This commit clears every drift in src/ui.

- color='default' -> color='font-default' across SettingsView,
  DownloadsManagerView, TopBar, ServersView (MarkdownContent,
  DocumentViewer, PdfContent).
- color='hint' -> color='font-hint' across CertificatesManager
  and ServerInfoContent (11 sites).
- color='annotation' -> color='font-annotation' across
  CertificatesManager and ServerInfoContent.
- FileIcon's color='neutral-600' (banned palette-grade ref)
  becomes color='font-secondary-info'.
- AvailableBrowsers and OutlookCalendarSyncInterval drop their
  raw style={{ paddingTop: '4px' }} inline CSS in favor of the
  Fuselage paddingBlockStart='x4' shorthand, matching
  TelephonyServer and ThemeAppearance.
- Shell/styles.tsx replaces body font-family: system-ui with the
  Inter-first stack documented in DESIGN.md.

DESIGN.md gains a Pre-Hydration Exception rule clarifying that
src/public/loading.css and error.css intentionally keep
system-ui and the hardcoded #2f343d background because they
render before React mounts and before PaletteStyleTag emits any
--rcx-color-* variable.
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 26, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 5d6fee91-9c42-4e94-a18c-1eab7408058e

📥 Commits

Reviewing files that changed from the base of the PR and between b677565 and 6ebdc9b.

📒 Files selected for processing (1)
  • electron-builder.json
📜 Recent review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: check (windows-latest)
  • GitHub Check: check (macos-latest)
  • GitHub Check: check (ubuntu-latest)
🔇 Additional comments (1)
electron-builder.json (1)

130-131: LGTM!


Walkthrough

Adds a machine-readable design system and docs; migrates many UI components to semantic design tokens; refactors certificates, downloads, and settings UIs for composition, spacing, and keyboard accessibility; and updates related i18n strings.

Changes

Design System Adoption & Component Refactoring

Layer / File(s) Summary
Design system documentation and config
.impeccable/design.json, DESIGN.md, PRODUCT.md
Adds machine-readable design system definition with semantic color metadata, typography mappings, shadow/motion tokens, and component specs; documents token-driven theming rules and accessibility requirements; and defines product scope, brand personality, and WCAG 2.2 AA inclusion targets.
Certificates manager composition-based refactoring
src/ui/components/CertificatesManager/*, src/i18n/en.i18n.json
Refactors CertificatesManager into composed CertificateSection components; adds CertificateSection and CertificateItem truncation/tooltip behavior; replaces anchor-based ActionButton with Fuselage Button; and adds i18n strings for hints and empty states.
Downloads manager keyboard navigation and empty-state handling
src/ui/components/DownloadsManagerView/*, src/i18n/en.i18n.json
Upgrades filter controls to Select/IconButton, persists filter keys as strings, adds Escape-to-back keyboard handler, computes totalDownloads, differentiates empty-state messaging, refactors DownloadItem layout and action buttons, and standardizes ActionButton to Fuselage Button.
Settings view section-based reorganization and keyboard navigation
src/ui/components/SettingsView/*, src/i18n/en.i18n.json
Adds a Section component and restructures GeneralTab into titled sections; introduces Escape-key handling with memoized callbacks; replaces inline spacing with Fuselage spacing props; and adds i18n labels for back and section headers.
Design token and typography updates
src/ui/components/ServerInfoContent.tsx, src/ui/components/ServersView/*, src/ui/components/TopBar/index.tsx, src/ui/components/Shell/styles.tsx
Migrates legacy color tokens (default, hint, annotation, neutral-600) to semantic tokens (font-default, font-hint, font-annotation, font-secondary-info) across viewers and TopBar; updates global body font-family to an Inter-first stack.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately summarizes the main change: polishing three key views (Settings, Certificates, Downloads) against the Fuselage design system with related documentation additions.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

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


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.

@jeanfbrito
Copy link
Copy Markdown
Member Author

Theming note + verification

Theme handling is owned by Fuselage, not this shell. The desktop app consumes --rcx-color-* tokens emitted by Fuselage's PaletteStyleTag; the light / dark / high-contrast values, their contrast, and WCAG compliance are all defined and maintained in @rocket.chat/fuselage-tokens. This PR's only theming obligation is token discipline: reference semantic tokens, never hardcode a color.

Verified:

  • Token sweep across every touched view is clean: no hardcoded hex outside var(--rcx-color-*), no palette-grade vars (neutral-600 etc.), no short-alias color props, no color literals inside the emotion css blocks.
  • The touched surfaces (Settings, Certificates, Downloads, ServersView) render as descendants of Shell, which mounts PaletteStyleTag, so they inherit the emitted variables in whatever theme is active.
  • Visually confirmed by hand in light, dark, and high-contrast. All three read correctly.

So the earlier "verify all three themes" item is resolved: theme correctness flows from Fuselage, and the shell consumes it cleanly.

Copy link
Copy Markdown
Contributor

@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: 6

🧹 Nitpick comments (1)
.impeccable/design.json (1)

3-3: 💤 Low value

Consider using actual generation timestamp.

The generatedAt timestamp is set to exactly midnight (00:00:00Z), which appears hardcoded. For a machine-readable design configuration, an actual generation timestamp would be more useful for tracking updates and version control.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.impeccable/design.json at line 3, The "generatedAt" value is hardcoded to
"2026-05-26T00:00:00Z"; update the generator so the "generatedAt" field (key
"generatedAt" in .impeccable/design.json) is populated at runtime with the
actual ISO 8601 UTC timestamp (e.g., new Date().toISOString()) when the
design.json is produced; ensure any code that writes this file uses that dynamic
timestamp and that tests/fixtures are adjusted to allow or mock the generatedAt
value.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/ui/components/CertificatesManager/CertificatesManager.tsx`:
- Around line 69-75: The file currently declares multiple React components
(CertificateSection and CertificatesManagerWrapper) which triggers the
react/no-multi-comp lint rule; extract those two child components into their own
component modules (e.g., CertificateSection.tsx and
CertificatesManagerWrapper.tsx) keeping their prop types
(CertificateSectionProps, CertificatesManagerWrapperProps) and any used
MUI/utility imports, export them (named or default), then import them back into
CertificatesManager.tsx and use them so CertificatesManager.tsx contains only
the single top-level component declaration (CertificatesManager). Ensure props
and any handlers passed from CertificatesManager are preserved and update
imports/exports accordingly.

In `@src/ui/components/DownloadsManagerView/DownloadItem.tsx`:
- Around line 15-16: The Prettier formatting errors in DownloadItem.tsx are
caused by unformatted CSS template literals and a JSX prop block; run the
project's Prettier formatter or manually reformat the CSS template (the block
starting with "border-block-start: 1px solid var(--rcx-color-stroke-extra-light,
transparent);") and the JSX props inside the DownloadItem component so they
match the project's Prettier rules (consistent indentation, line breaks, and
trailing commas where configured). Locate the DownloadItem component and its
styled/template CSS and adjust whitespace and line breaks to match Prettier
output (or run npm/yarn prettier --write on the file) to resolve the
eslint/prettier violations.

In `@src/ui/components/DownloadsManagerView/index.tsx`:
- Around line 238-243: Prettier is failing on the JSX prop formatting for the
filter-row Box elements; run the project's Prettier formatter (or your editor's
auto-format) and fix the prop blocks in the DownloadsManagerView component so
they match the repo's Prettier rules (e.g., format the Box props at lines with
"display='flex' alignItems='center' pi={24} pbe={16}" and the other Box blocks
at the mentioned ranges), ensuring consistent line breaks/spacing to satisfy
prettier/prettier checks; specifically reformat the JSX prop lists for the Box
elements in index.tsx so CI no longer flags them.

In `@src/ui/components/ServerInfoContent.tsx`:
- Line 348: The JSX props on the Box element in ServerInfoContent.tsx are all on
one long line; split them across multiple lines to satisfy the max line length
and improve readability—locate the Box usage (Box fontSize='x10'
color='font-annotation' style={textWrapStyle}) inside the ServerInfoContent
component and reformat so each prop (fontSize, color, style) is on its own line,
preserving the same prop names and values (including textWrapStyle) and keeping
the same surrounding JSX structure.

In `@src/ui/components/SettingsView/GeneralTab.tsx`:
- Around line 29-36: The file declares two React components (Section and
GeneralTab) which triggers react/no-multi-comp; replace the Section component
with a non-component helper renderer and update GeneralTab to call it instead:
remove the const Section = (...) JSX component and add a plain function (e.g.,
renderSection(title, isFirst, children)) that returns the same JSX, preserve
SectionProps typing for its parameters, then update every usage of <Section ...>
inside GeneralTab to call renderSection(title, isFirst, children); this keeps
the same output while avoiding a second component declaration in the file.

In `@src/ui/components/Shell/styles.tsx`:
- Around line 37-38: The font-family declaration in
src/ui/components/Shell/styles.tsx is formatted in a way that breaks Prettier
rules; locate the CSS rule containing the font-family declaration and reformat
it to satisfy Prettier (either collapse the font list into a single properly
quoted/comma-separated line or break into Prettier-friendly wrapped lines), then
run Prettier/ESLint to confirm the file passes formatting checks; ensure the
exact token "font-family" in the styles.tsx template literal or styled component
is updated and no trailing commas or stray spacing violate the formatter.

---

Nitpick comments:
In @.impeccable/design.json:
- Line 3: The "generatedAt" value is hardcoded to "2026-05-26T00:00:00Z"; update
the generator so the "generatedAt" field (key "generatedAt" in
.impeccable/design.json) is populated at runtime with the actual ISO 8601 UTC
timestamp (e.g., new Date().toISOString()) when the design.json is produced;
ensure any code that writes this file uses that dynamic timestamp and that
tests/fixtures are adjusted to allow or mock the generatedAt value.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 6d4f5fc7-e08b-4c1d-8a76-fa187008c6d8

📥 Commits

Reviewing files that changed from the base of the PR and between bd8830e and 3ee3d0c.

📒 Files selected for processing (23)
  • .impeccable/design.json
  • DESIGN.md
  • PRODUCT.md
  • src/i18n/en.i18n.json
  • src/ui/components/CertificatesManager/ActionButton.tsx
  • src/ui/components/CertificatesManager/CertificateItem.tsx
  • src/ui/components/CertificatesManager/CertificatesManager.tsx
  • src/ui/components/DownloadsManagerView/ActionButton.tsx
  • src/ui/components/DownloadsManagerView/DownloadItem.tsx
  • src/ui/components/DownloadsManagerView/FileIcon.tsx
  • src/ui/components/DownloadsManagerView/index.tsx
  • src/ui/components/ServerInfoContent.tsx
  • src/ui/components/ServersView/DocumentViewer.tsx
  • src/ui/components/ServersView/MarkdownContent.tsx
  • src/ui/components/ServersView/PdfContent.tsx
  • src/ui/components/SettingsView/GeneralTab.tsx
  • src/ui/components/SettingsView/SettingsView.tsx
  • src/ui/components/SettingsView/features/AvailableBrowsers.tsx
  • src/ui/components/SettingsView/features/ClearPermittedScreenCaptureServers.tsx
  • src/ui/components/SettingsView/features/OutlookCalendarSyncInterval.tsx
  • src/ui/components/SettingsView/features/TelephonyServer.tsx
  • src/ui/components/Shell/styles.tsx
  • src/ui/components/TopBar/index.tsx
💤 Files with no reviewable changes (1)
  • src/ui/components/SettingsView/features/ClearPermittedScreenCaptureServers.tsx
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: check (windows-latest)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (CLAUDE.md)

**/*.{ts,tsx}: Use TypeScript for all new code in this codebase unless explicitly told otherwise
Use Fuselage components from @rocket.chat/fuselage for all UI work — only create custom components when Fuselage doesn't provide the needed functionality
Check Theme.d.ts for valid color tokens when working with Fuselage components
Use optional chaining with fallbacks for platform-specific APIs instead of mocks (e.g., process.getuid?.() ?? 1000) to ensure code works across all platforms without requiring mocks
TypeScript code must use strict mode
Use React functional components with hooks instead of class components
Redux actions must follow the FSA (Flux Standard Action) pattern
Use camelCase for file naming
Use PascalCase for component file names (React components)
Write self-documenting code through clear naming — avoid unnecessary comments

Files:

  • src/ui/components/DownloadsManagerView/FileIcon.tsx
  • src/ui/components/ServersView/DocumentViewer.tsx
  • src/ui/components/Shell/styles.tsx
  • src/ui/components/CertificatesManager/CertificateItem.tsx
  • src/ui/components/DownloadsManagerView/ActionButton.tsx
  • src/ui/components/CertificatesManager/ActionButton.tsx
  • src/ui/components/SettingsView/features/AvailableBrowsers.tsx
  • src/ui/components/ServersView/PdfContent.tsx
  • src/ui/components/TopBar/index.tsx
  • src/ui/components/SettingsView/features/TelephonyServer.tsx
  • src/ui/components/SettingsView/features/OutlookCalendarSyncInterval.tsx
  • src/ui/components/CertificatesManager/CertificatesManager.tsx
  • src/ui/components/SettingsView/GeneralTab.tsx
  • src/ui/components/SettingsView/SettingsView.tsx
  • src/ui/components/ServersView/MarkdownContent.tsx
  • src/ui/components/ServerInfoContent.tsx
  • src/ui/components/DownloadsManagerView/index.tsx
  • src/ui/components/DownloadsManagerView/DownloadItem.tsx
🪛 ast-grep (0.42.3)
src/ui/components/ServersView/MarkdownContent.tsx

[warning] 237-237: Usage of dangerouslySetInnerHTML detected. This bypasses React's built-in XSS protection. Always sanitize HTML content using libraries like DOMPurify before injecting it into the DOM to prevent XSS attacks.
Context: dangerouslySetInnerHTML
Note: [CWE-79] Improper Neutralization of Input During Web Page Generation [REFERENCES]
- https://reactjs.org/docs/dom-elements.html#dangerouslysetinnerhtml
- https://cwe.mitre.org/data/definitions/79.html

(react-unsafe-html-injection)

🪛 ESLint
src/ui/components/Shell/styles.tsx

[error] 37-37: Replace ·Inter,·-apple-system,·BlinkMacSystemFont, with ⏎············Inter,⏎············-apple-system,⏎············BlinkMacSystemFont,⏎···········

(prettier/prettier)


[error] 38-38: Replace ·Oxygen,·Ubuntu,·Cantarell,·'Helvetica·Neue', with ⏎············Oxygen,⏎············Ubuntu,⏎············Cantarell,⏎············'Helvetica·Neue',⏎···········

(prettier/prettier)

src/ui/components/CertificatesManager/CertificatesManager.tsx

[error] 69-75: Declare only one React component per file

(react/no-multi-comp)


[error] 77-105: Declare only one React component per file

(react/no-multi-comp)

src/ui/components/SettingsView/GeneralTab.tsx

[error] 38-78: Declare only one React component per file

(react/no-multi-comp)

src/ui/components/ServerInfoContent.tsx

[error] 348-348: Replace ·fontSize='x10'·color='font-annotation'·style={textWrapStyle} with ⏎····················fontSize='x10'⏎····················color='font-annotation'⏎····················style={textWrapStyle}⏎··················

(prettier/prettier)

src/ui/components/DownloadsManagerView/index.tsx

[error] 238-243: Replace ⏎········display='flex'⏎········alignItems='center'⏎········pi={24}⏎········pbe={16}⏎······ with ·display='flex'·alignItems='center'·pi={24}·pbe={16}

(prettier/prettier)


[error] 244-250: Replace ⏎··········flexGrow={3}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x160'⏎··········mie={8}⏎········ with ·flexGrow={3}·flexShrink={1}·flexBasis={0}·minWidth='x160'·mie={8}

(prettier/prettier)


[error] 258-264: Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x140'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x140'·mie={8}

(prettier/prettier)


[error] 272-278: Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x120'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x120'·mie={8}

(prettier/prettier)


[error] 286-292: Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x120'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x120'·mie={8}

(prettier/prettier)

src/ui/components/DownloadsManagerView/DownloadItem.tsx

[error] 15-16: Delete ⏎···

(prettier/prettier)


[error] 208-212: Replace ⏎················color='font-secondary-info'⏎················fontScale='c1'⏎················withTruncatedText⏎·············· with ·color='font-secondary-info'·fontScale='c1'·withTruncatedText

(prettier/prettier)

🪛 GitHub Check: check (ubuntu-latest)
src/ui/components/CertificatesManager/CertificatesManager.tsx

[failure] 77-77:
Declare only one React component per file


[failure] 69-69:
Declare only one React component per file

src/ui/components/ServerInfoContent.tsx

[failure] 348-348:
Replace ·fontSize='x10'·color='font-annotation'·style={textWrapStyle} with ⏎····················fontSize='x10'⏎····················color='font-annotation'⏎····················style={textWrapStyle}⏎··················

src/ui/components/DownloadsManagerView/index.tsx

[failure] 286-286:
Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x120'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x120'·mie={8}


[failure] 272-272:
Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x120'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x120'·mie={8}


[failure] 258-258:
Replace ⏎··········flexGrow={2}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x140'⏎··········mie={8}⏎········ with ·flexGrow={2}·flexShrink={1}·flexBasis={0}·minWidth='x140'·mie={8}


[failure] 244-244:
Replace ⏎··········flexGrow={3}⏎··········flexShrink={1}⏎··········flexBasis={0}⏎··········minWidth='x160'⏎··········mie={8}⏎········ with ·flexGrow={3}·flexShrink={1}·flexBasis={0}·minWidth='x160'·mie={8}


[failure] 238-238:
Replace ⏎········display='flex'⏎········alignItems='center'⏎········pi={24}⏎········pbe={16}⏎······ with ·display='flex'·alignItems='center'·pi={24}·pbe={16}

src/ui/components/DownloadsManagerView/DownloadItem.tsx

[failure] 15-15:
Delete ⏎···


[failure] 208-208:
Replace ⏎················color='font-secondary-info'⏎················fontScale='c1'⏎················withTruncatedText⏎·············· with ·color='font-secondary-info'·fontScale='c1'·withTruncatedText

🪛 LanguageTool
DESIGN.md

[grammar] ~179-~179: Ensure spelling is correct
Context: ...ients, no decorative iconography in the titlebar, no busy toolbar). It is not generic Sa...

(QB_NEW_EN_ORTHOGRAPHY_ERROR_IDS_1)


[style] ~179-~179: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...aphy in the titlebar, no busy toolbar). It is not generic SaaS marketing (no hero ...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[grammar] ~185-~185: Use a hyphen to join words.
Context: ...rfaces step by exactly one tint. - Inter primary, system stack fallback (`-apple-...

(QB_NEW_EN_HYPHEN)


[style] ~400-~400: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...rning'` (orange) for not-logged-in. - Do verify every color choice in light, d...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~401-~401: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...h-contrast** themes before merging. - Do use sentence case in source strings; ...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~402-~402: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...at the component layer when needed. - Do apply the shared row affordance (`<Ta...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~403-~403: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...ox rows) to every new list surface. - Do use Fuselage Box withTruncatedText ...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~404-~404: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ... URLs, file names, and identifiers. - Do use pi/pbs/pbe Fuselage spacing sho...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~409-~409: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ... dark purple, no playful microcopy. - Don't revive old Skype or legacy Teams c...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~410-~410: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...ecorative iconography in titlebars. - Don't use generic SaaS marketing pattern...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~411-~411: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...ds, no gradient accents on numbers. - Don't pursue Linear-empty minimalism at ...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~412-~412: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...ism at the cost of sidebar density. - Don't use border-left or `border-right...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~413-~413: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...al 4-pixel server selection stripe. - Don't use background-clip: text gradie...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~414-~414: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...ckground-clip: text` gradient text. - Don't introduce glassmorphism as a styli...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~421-~421: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...* wrap shell content in card grids. - Don't use modals as the first thought fo...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~422-~422: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...as the first thought for new flows. - Don't rename, recolor, or re-style Fusel...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)


[style] ~423-~423: Three successive sentences begin with the same word. Consider rewording the sentence or use a thesaurus to find a synonym.
Context: ...Dropdown, IconButton` primitives. - Don't confuse Badge variants: unread is ...

(ENGLISH_WORD_REPEAT_BEGINNING_RULE)

PRODUCT.md

[grammar] ~36-~36: Ensure spelling is correct
Context: ...OS traffic lights and vibrancy, Windows titlebar buttons and Mica, Linux menubar fallbac...

(QB_NEW_EN_ORTHOGRAPHY_ERROR_IDS_1)


[grammar] ~36-~36: Ensure spelling is correct
Context: ...indows titlebar buttons and Mica, Linux menubar fallbacks. The desktop edge over the br...

(QB_NEW_EN_ORTHOGRAPHY_ERROR_IDS_1)

🔇 Additional comments (19)
src/ui/components/CertificatesManager/ActionButton.tsx (1)

1-8: LGTM!

src/ui/components/CertificatesManager/CertificateItem.tsx (1)

1-1: LGTM!

Also applies to: 20-24

src/i18n/en.i18n.json (1)

185-191: LGTM!

Also applies to: 228-228, 235-241, 250-250, 255-259

src/ui/components/DownloadsManagerView/ActionButton.tsx (1)

1-8: LGTM!

src/ui/components/DownloadsManagerView/FileIcon.tsx (1)

29-29: LGTM!

src/ui/components/SettingsView/SettingsView.tsx (1)

41-55: LGTM!

Also applies to: 58-124

src/ui/components/SettingsView/features/AvailableBrowsers.tsx (1)

87-87: LGTM!

src/ui/components/SettingsView/features/OutlookCalendarSyncInterval.tsx (1)

62-62: LGTM!

src/ui/components/SettingsView/features/TelephonyServer.tsx (1)

66-66: LGTM!

.impeccable/design.json (1)

4-324: LGTM!

DESIGN.md (1)

1-427: LGTM!

PRODUCT.md (1)

1-53: LGTM!

src/ui/components/ServerInfoContent.tsx (2)

127-150: LGTM!


184-303: LGTM!

src/ui/components/ServersView/DocumentViewer.tsx (1)

35-35: LGTM!

src/ui/components/ServersView/MarkdownContent.tsx (1)

208-237: LGTM!

src/ui/components/ServersView/PdfContent.tsx (1)

81-81: LGTM!

src/ui/components/TopBar/index.tsx (1)

28-28: LGTM!

src/ui/components/Shell/styles.tsx (1)

37-38: ⚡ Quick win

Verify that the Inter font is actually loaded (font scan didn’t complete)

font-family now prioritizes Inter, but the suggested verification run didn’t successfully execute its searches (ripgrep reported unrecognized file type: tsx), so it doesn’t establish whether @font-face, Inter-related CSS imports, or Fuselage-provided font styles/woff2 assets exist. Re-run the check using -g '*.ts' -g '*.tsx' -g '*.css' -g '*.scss' globs (instead of --type=tsx) and confirm there are @font-face/Inter imports or woff2/font asset references from the app entrypoints/Fuselage styles.

Comment thread src/ui/components/CertificatesManager/CertificatesManager.tsx Outdated
Comment thread src/ui/components/DownloadsManagerView/DownloadItem.tsx Outdated
Comment thread src/ui/components/DownloadsManagerView/index.tsx Outdated
Comment thread src/ui/components/ServerInfoContent.tsx Outdated
Comment thread src/ui/components/SettingsView/GeneralTab.tsx Outdated
Comment thread src/ui/components/Shell/styles.tsx Outdated
@jeanfbrito jeanfbrito changed the title Polish Settings, Certificates, and Downloads views against Fuselage chore: Polish Settings, Certificates, and Downloads views against Fuselage May 26, 2026
CodeRabbit/CI flagged two lint rules on the polish branch:

- react/no-multi-comp: GeneralTab.tsx and CertificatesManager.tsx
  each declared more than one React component. Extract the helpers
  into their own files (SettingsView/Section.tsx,
  CertificatesManager/CertificateSection.tsx) and inline the
  trivial wrapper Box, so each file declares a single component.
- prettier/prettier: re-ran the formatter over the CSS template
  literal in DownloadItem.tsx and the JSX prop blocks in
  DownloadsManagerView/index.tsx, ServerInfoContent.tsx, and
  Shell/styles.tsx.

No behavior, token, or copy changes. yarn lint and tsc --noEmit
both clean.
electron-builder 26.0.3 rejects MimeType as a direct property of
linux.desktop ("unknown property 'MimeType'"), failing the Linux
build step in CI. MimeType is a desktop-entry key, so it belongs
inside linux.desktop.entry alongside Name, Comment, GenericName,
and Categories. The scheme handlers (rocketchat, callto, tel) are
preserved verbatim.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant