Rams MCP · The full engine, now in your coding agent
infisical on GitHub

infisical/infisical

Reviewed against Rams quality heuristics: accessibility, color, typography, spacing, components, motion, UX, and craft.

30 files reviewed·July 25, 2026

View on GitHub

Low

Design risk in this codebase.

6issues
Serious · top 5 shown below

Top fix

Add a confirmation step before granting server admin access

See the fix

Verdict

Six copy-pasted Switch blocks reveal a settings screen built by repetition, not componentization, and the cracks show at exactly the moments that matter most. High-consequence toggles like admin grants and login-method disabling fire instantly with no confirmation, turning a flat UI pattern into a real lockout risk.

Files Rams reviewed

frontend/src/pages/pam/components/policyEditors/index.tsx

frontend/src/pages/admin/AccessManagementPage/components/AddServerAdminModal.tsx

frontend/src/pages/admin/AuthenticationPage/components/AuthenticationPageForm.tsx

frontend/src/pages/admin/CachingPage/components/CachingPageForm.tsx

frontend/src/pages/admin/EncryptionPage/components/EncryptionPageForm.tsx

frontend/src/pages/admin/EnvironmentPage/components/EnvironmentPageForm.tsx

frontend/src/pages/admin/GeneralPage/components/GeneralPageForm.tsx

frontend/src/pages/admin/GeneralPage/components/UsageReportSection.tsx

frontend/src/pages/admin/IntegrationsPage/components/IntegrationsPageForm.tsx

frontend/src/pages/admin/IntegrationsPage/components/MicrosoftTeamsIntegrationForm.tsx

frontend/src/pages/admin/IntegrationsPage/components/SlackIntegrationForm.tsx

frontend/src/pages/admin/ResourceOverviewPage/components/AddOrganizationModal.tsx

frontend/src/pages/admin/ResourceOverviewPage/components/EmailDomainsTable.tsx

frontend/src/pages/admin/ResourceOverviewPage/components/MachineIdentitiesTable.tsx

frontend/src/pages/admin/SignUpPage/components/AdminSignUpForm.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointConnectedServersSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointConnectionSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointDetailsSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointFiltersSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointToolSelectionSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/MCPEndpointUsageStatisticsSection.tsx

frontend/src/pages/ai/MCPEndpointDetailPage/components/PiiFilterConfigModal.tsx

frontend/src/pages/ai/MCPPage/components/MCPActivityLogsTab/MCPActivityLogsDateFilter.tsx

frontend/src/pages/ai/MCPPage/components/MCPActivityLogsTab/MCPActivityLogsFilter.tsx

frontend/src/pages/ai/MCPPage/components/MCPActivityLogsTab/MCPActivityLogsTab.tsx

frontend/src/pages/ai/MCPPage/components/MCPActivityLogsTab/MCPActivityLogsTableRow.tsx

frontend/src/pages/ai/MCPPage/components/MCPEndpointsTab/AddMCPEndpointModal/AddMCPEndpointModal.tsx

frontend/src/pages/ai/MCPPage/components/MCPEndpointsTab/EditMCPEndpointModal.tsx

frontend/src/pages/ai/MCPPage/components/MCPEndpointsTab/MCPEndpointList.tsx

frontend/src/pages/ai/MCPPage/components/MCPEndpointsTab/MCPEndpointRow.tsx

92/100

UX

4 serious
UXSerious

frontend/src/pages/admin/AccessManagementPage/components/AddServerAdminModal.tsx:67

Granting server admin access has no confirmation step before it fires

The "Grant" button submits onSubmit directly, calling grantAdmin.mutateAsync(user.id) with no intermediate confirmation dialog. Elevating a user to server admin is one of the highest-privilege actions in the app, yet it fires on a single click the moment the form validates.

Why it matters

A mis-click or a wrong selection in the user search grants full server admin permissions instantly, with no chance to catch the mistake before it takes effect.

Fix

Require an explicit confirmation step before executing irreversible or high-privilege mutations.

const onSubmit = async ({ user }: FormData) => {
    await grantAdmin.mutateAsync(user.id);

    createNotification({
      type: "success",
      text: "Successfully granted server admin status"
    });
    onClose();
  };
const onSubmit = async ({ user }: FormData) => {
    if (!window.confirm(`Grant server admin access to ${getUserLabel(user)}?`)) return;
    await grantAdmin.mutateAsync(user.id);

    createNotification({
      type: "success",
      text: "Successfully granted server admin status"
    });
    onClose();
  };
UXSerious

frontend/src/pages/admin/AuthenticationPage/components/AuthenticationPageForm.tsx:86

"At least one login method should be enabled" error hides in a toast

In AuthenticationPageForm's onAuthFormSubmit, disabling every login switch produces createNotification({ type: 'error', text: 'At least one login method should be enabled.' }) as a global toast, with no inline error rendered near the Email, Google, Github, Gitlab, SAML, OIDC, or LDAP Switch rows that caused it.

Why it matters

The toast disappears after a few seconds and gives no visual link back to which control needs to change, so the admin has to guess which switch to re-enable.

Fix

Attach validation errors to the specific form field via react-hook-form's setError so the message renders inline where the user is looking.

if (!enabledMethods.length) {
      createNotification({
        type: "error",
        text: "At least one login method should be enabled."
      });
      return;
    }
if (!enabledMethods.length) {
      setError("isEmailEnabled", {
        message: "At least one login method must stay enabled."
      });
      return;
    }
UXSerious

frontend/src/pages/admin/AuthenticationPage/components/AuthenticationPageForm.tsx:234

Disabling a login method locks out relying users with no confirmation

The "Save" button in AuthenticationPageForm submits directly with isDisabled={isSubmitting || !isDirty}, no confirmation step, even though unchecking a switch like GitHub or SAML and saving immediately removes that login path for every org user who depends on it.

Why it matters

An admin who toggles off a login method by mistake locks out all users relying on that provider the instant Save completes, with no warning before the change takes effect.

Fix

Confirm destructive or access-affecting changes before submit when the diff removes an enabled login method.

<Button
        className="mt-2"
        type="submit"
        isLoading={isSubmitting}
        isDisabled={isSubmitting || !isDirty}
      >
        Save
      </Button>
<Button
        className="mt-2"
        type="submit"
        isLoading={isSubmitting}
        isDisabled={isSubmitting || !isDirty}
        onClick={(e) => {
          if (!window.confirm("Disabling a login method may lock out users who rely on it. Continue?")) {
            e.preventDefault();
          }
        }}
      >
        Save
      </Button>
UXSerious

frontend/src/pages/admin/AccessManagementPage/components/AddServerAdminModal.tsx:110

Cancel button defaults to type submit inside the grant-admin form

In AddServerAdminModal's Content form, the "Cancel" button at line 110 has no explicit type attribute. Inside a <form>, buttons default to type='submit', so this button sits alongside the real "Grant" submit button with the same implicit behavior.

Why it matters

A click on "Cancel" can submit the form and grant server admin access instead of closing the modal, the opposite of what the label promises.

Fix

Set explicit type='button' on every in-form action that is not meant to submit.

<Button onClick={() => onClose()} variant="plain" colorSchema="secondary">
  Cancel
</Button>
<Button type="button" onClick={() => onClose()} variant="plain" colorSchema="secondary">
  Cancel
</Button>
98/100

Components

1 serious
ComponentsSerious

frontend/src/pages/admin/AuthenticationPage/components/AuthenticationPageForm.tsx:114

Six copy-pasted Switch blocks mean every fix repeats six times

AuthenticationPageForm repeats the identical Controller + FormControl + Switch structure for isEmailEnabled, isGoogleEnabled, isGithubEnabled, isGitlabEnabled, isSamlEnabled, and isOidcEnabled, differing only in name, id, and label text (starting at line 114 with "Email").

Why it matters

Any future change to error display, spacing, or accessibility on these switches has to be applied six separate times, and missing one creates visible drift between login methods.

Fix

Extract the repeated Controller/Switch pattern into a single parameterized component.

<Controller
          control={control}
          name="isEmailEnabled"
          render={({ field, fieldState: { error } }) => {
            return (
              <FormControl isError={Boolean(error)} errorText={error?.message}>
                <Switch
                  id="email-enabled"
                  onCheckedChange={(value) => field.onChange(value)}
                  isChecked={field.value}
                >
                  <p className="w-24">Email</p>
                </Switch>
              </FormControl>
            );
          }}
        />
const LoginMethodSwitch = ({ control, name, id, label }: LoginMethodSwitchProps) => (
  <Controller
    control={control}
    name={name}
    render={({ field, fieldState: { error } }) => (
      <FormControl isError={Boolean(error)} errorText={error?.message}>
        <Switch id={id} onCheckedChange={field.onChange} isChecked={field.value}>
          <p className="w-24">{label}</p>
        </Switch>
      </FormControl>
    )}
  />
);

<LoginMethodSwitch control={control} name="isEmailEnabled" id="email-enabled" label="Email" />

Accessibility

No issues found

Typography

No issues found

Color

No issues found

Spacing

No issues found

Motion

No issues found

Craft

No issues found

Working well

  • The FilterableSelect wires isLoading from comparing searchUserFilter to debouncedSearchTerm, giving accurate loading feedback during the debounce window.
  • The Invalidate button is correctly disabled via isDisabled={!user.superAdmin || isInvalidating}, preventing duplicate submissions while a cache job runs.
  • The Select is only rendered once `rootKmsDetails` is available (`{!!rootKmsDetails && ...}`), avoiding a flash of an empty control before data loads.
  • Disabling the Save button on `isSubmitting || !isDirty` correctly prevents redundant submits and no-op saves in one condition.

Scored July 25, 2026 with Rams Engine v0.0.3 · Engine changelog
First scored July 9, 2026: 59/100. This rescore on v0.0.3: 88/100.

This page is an automated design review of infisical/infisical’s UI code: 30 files read against 291 versioned rules covering accessibility, color, typography, spacing, components, UX, motion, and craft. The score is out of 100; confirmed criticals cap it — one at 59, two at 49, three or more at 39.

More design scores

Score your own repo.

Free on public repos, no account. The same engine that scored this page reads your UI code and mints a score page like this one.

Public repos only. The full engine reviews the UI code and mints a public score page — we email you the link too. Already-scored repos open instantly.

Or get a design review on every pull requestInstall Rams