@stigmer/react 3.30.0 → 3.31.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (33) hide show
  1. package/oauth-app/OAuthAppDetailPanel.d.ts +5 -1
  2. package/oauth-app/OAuthAppDetailPanel.d.ts.map +1 -1
  3. package/oauth-app/OAuthAppDetailPanel.js +10 -5
  4. package/oauth-app/OAuthAppDetailPanel.js.map +1 -1
  5. package/oauth-app/OAuthAppListPanel.d.ts +11 -3
  6. package/oauth-app/OAuthAppListPanel.d.ts.map +1 -1
  7. package/oauth-app/OAuthAppListPanel.js +4 -4
  8. package/oauth-app/OAuthAppListPanel.js.map +1 -1
  9. package/oauth-app/copy.d.ts +15 -0
  10. package/oauth-app/copy.d.ts.map +1 -0
  11. package/oauth-app/copy.js +15 -0
  12. package/oauth-app/copy.js.map +1 -0
  13. package/oauth-app/useDeleteOAuthApp.d.ts +4 -3
  14. package/oauth-app/useDeleteOAuthApp.d.ts.map +1 -1
  15. package/oauth-app/useDeleteOAuthApp.js +4 -3
  16. package/oauth-app/useDeleteOAuthApp.js.map +1 -1
  17. package/oauth-app/useOAuthAppList.d.ts +6 -4
  18. package/oauth-app/useOAuthAppList.d.ts.map +1 -1
  19. package/oauth-app/useOAuthAppList.js +6 -4
  20. package/oauth-app/useOAuthAppList.js.map +1 -1
  21. package/package.json +5 -5
  22. package/settings/OAuthAppsSection.d.ts +9 -1
  23. package/settings/OAuthAppsSection.d.ts.map +1 -1
  24. package/settings/OAuthAppsSection.js +17 -3
  25. package/settings/OAuthAppsSection.js.map +1 -1
  26. package/src/oauth-app/OAuthAppDetailPanel.tsx +39 -24
  27. package/src/oauth-app/OAuthAppListPanel.tsx +12 -3
  28. package/src/oauth-app/__tests__/OAuthAppDetailPanel.test.tsx +57 -9
  29. package/src/oauth-app/copy.ts +16 -0
  30. package/src/oauth-app/useDeleteOAuthApp.ts +4 -3
  31. package/src/oauth-app/useOAuthAppList.ts +6 -4
  32. package/src/settings/OAuthAppsSection.tsx +21 -3
  33. package/src/settings/__tests__/OAuthAppsSection.test.tsx +133 -0
@@ -16,7 +16,11 @@ export interface OAuthAppDetailPanelProps {
16
16
  * View and edit panel for an existing OAuth app.
17
17
  *
18
18
  * In **view mode**, displays all OAuth configuration fields in a
19
- * structured label/value layout with "Edit" and "Delete" buttons.
19
+ * structured label/value layout, with an "Edit" button for a caller who
20
+ * may edit the app (`can_edit`) and a "Delete" button for one who may
21
+ * delete it (`can_delete`). Both belong to the app's creator alone: the
22
+ * organization's admins may view an app they did not create, never change
23
+ * it.
20
24
  *
21
25
  * In **edit mode**, fields become editable inputs. The client secret
22
26
  * field shows a placeholder — leave it empty to keep the existing
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppDetailPanel.d.ts","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppDetailPanel.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAclF,6CAA6C;AAC7C,MAAM,WAAW,wBAAwB;IACvC,kDAAkD;IAClD,QAAQ,CAAC,QAAQ,EAAE,QAAQ,CAAC;IAC5B,+DAA+D;IAC/D,QAAQ,CAAC,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,QAAQ,KAAK,IAAI,CAAC;IAC7C,wDAAwD;IACxD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;IAChC,kDAAkD;IAClD,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IAC7B,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,QAAQ,EACR,SAAS,EACT,SAAS,EACT,MAAM,EACN,SAAS,GACV,EAAE,wBAAwB,2CA+a1B"}
1
+ {"version":3,"file":"OAuthAppDetailPanel.d.ts","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppDetailPanel.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAelF,6CAA6C;AAC7C,MAAM,WAAW,wBAAwB;IACvC,kDAAkD;IAClD,QAAQ,CAAC,QAAQ,EAAE,QAAQ,CAAC;IAC5B,+DAA+D;IAC/D,QAAQ,CAAC,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,QAAQ,KAAK,IAAI,CAAC;IAC7C,wDAAwD;IACxD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;IAChC,kDAAkD;IAClD,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IAC7B,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,QAAQ,EACR,SAAS,EACT,SAAS,EACT,MAAM,EACN,SAAS,GACV,EAAE,wBAAwB,2CAyb1B"}
@@ -7,12 +7,17 @@ import { TokenEndpointAuthMethod, VendorApprovalStatus, } from "@stigmer/protos/
7
7
  import { timestampDate } from "@bufbuild/protobuf/wkt";
8
8
  import { useUpdateOAuthApp } from "./useUpdateOAuthApp.js";
9
9
  import { useDeleteOAuthApp } from "./useDeleteOAuthApp.js";
10
+ import { PermissionGate } from "../iam-policy/PermissionGate.js";
10
11
  import { SpinnerIcon } from "../internal/SpinnerIcon.js";
11
12
  /**
12
13
  * View and edit panel for an existing OAuth app.
13
14
  *
14
15
  * In **view mode**, displays all OAuth configuration fields in a
15
- * structured label/value layout with "Edit" and "Delete" buttons.
16
+ * structured label/value layout, with an "Edit" button for a caller who
17
+ * may edit the app (`can_edit`) and a "Delete" button for one who may
18
+ * delete it (`can_delete`). Both belong to the app's creator alone: the
19
+ * organization's admins may view an app they did not create, never change
20
+ * it.
16
21
  *
17
22
  * In **edit mode**, fields become editable inputs. The client secret
18
23
  * field shows a placeholder — leave it empty to keep the existing
@@ -139,10 +144,10 @@ export function OAuthAppDetailPanel({ oauthApp, onUpdated, onDeleted, onBack, cl
139
144
  !isUpdating;
140
145
  const createdAt = oauthApp.status?.audit?.specAudit?.createdAt;
141
146
  const updatedAt = oauthApp.status?.audit?.specAudit?.updatedAt;
142
- return (_jsxs("div", { className: cn("stg:space-y-4", className), children: [_jsxs("div", { className: "stg:flex stg:items-start stg:justify-between stg:gap-3", children: [_jsxs("div", { className: "stg:min-w-0", children: [onBack && (_jsxs("button", { type: "button", onClick: onBack, className: "stg:text-muted-foreground stg:hover:text-foreground stg:mb-1 stg:flex stg:items-center stg:gap-1 stg:text-xs stg:transition-colors", children: [_jsx(ArrowLeftIcon, {}), "Back to list"] })), _jsx("h3", { className: "stg:text-foreground stg:truncate stg:text-sm stg:font-semibold", children: spec?.provider || meta?.name || "OAuth App" }), meta?.slug && (_jsx("span", { className: "stg:text-muted-foreground stg:font-mono stg:text-xs", children: meta.slug }))] }), mode === "view" && (_jsxs("div", { className: "stg:flex stg:items-center stg:gap-1", children: [_jsx("button", { type: "button", onClick: enterEdit, className: cn("stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium", "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover", "stg:transition-colors"), children: "Edit" }), _jsx("button", { type: "button", onClick: () => {
143
- clearDeleteError();
144
- setConfirmingDelete(true);
145
- }, className: cn("stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium", "stg:text-destructive-muted stg:hover:text-destructive stg:hover:bg-destructive-subtle", "stg:transition-colors"), children: "Delete" })] }))] }), confirmingDelete && (_jsxs("div", { className: "stg:rounded-md stg:border stg:border-destructive/30 stg:bg-destructive-subtle stg:p-3", role: "alert", children: [_jsx("p", { className: "stg:text-foreground stg:mb-2 stg:text-xs stg:font-medium", children: "Delete this OAuth app?" }), _jsx("p", { className: "stg:text-muted-foreground stg:mb-3 stg:text-[0.65rem]", children: "This action is permanent. Any MCP server overrides referencing this app will lose their binding." }), deleteError && (_jsx("p", { className: "stg:text-destructive stg:mb-2 stg:text-[0.65rem]", role: "alert", children: getUserMessage(deleteError) })), _jsxs("div", { className: "stg:flex stg:items-center stg:gap-2", children: [_jsxs("button", { type: "button", onClick: handleDelete, disabled: isDeleting, className: cn("stg:inline-flex stg:items-center stg:gap-1.5 stg:rounded-md stg:px-3 stg:py-1.5 stg:text-xs stg:font-medium", "stg:bg-destructive stg:text-destructive-foreground stg:hover:bg-destructive-hover", "stg:disabled:pointer-events-none stg:disabled:opacity-40"), children: [isDeleting && _jsx(SpinnerIcon, { size: 12 }), "Delete permanently"] }), _jsx("button", { type: "button", onClick: () => {
147
+ return (_jsxs("div", { className: cn("stg:space-y-4", className), children: [_jsxs("div", { className: "stg:flex stg:items-start stg:justify-between stg:gap-3", children: [_jsxs("div", { className: "stg:min-w-0", children: [onBack && (_jsxs("button", { type: "button", onClick: onBack, className: "stg:text-muted-foreground stg:hover:text-foreground stg:mb-1 stg:flex stg:items-center stg:gap-1 stg:text-xs stg:transition-colors", children: [_jsx(ArrowLeftIcon, {}), "Back to list"] })), _jsx("h3", { className: "stg:text-foreground stg:truncate stg:text-sm stg:font-semibold", children: spec?.provider || meta?.name || "OAuth App" }), meta?.slug && (_jsx("span", { className: "stg:text-muted-foreground stg:font-mono stg:text-xs", children: meta.slug }))] }), mode === "view" && (_jsxs("div", { className: "stg:flex stg:items-center stg:gap-1", children: [_jsx(PermissionGate, { resource: { kind: "oauth_app", id: meta?.id ?? "" }, relation: "can_edit", children: _jsx("button", { type: "button", onClick: enterEdit, className: cn("stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium", "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover", "stg:transition-colors"), children: "Edit" }) }), _jsx(PermissionGate, { resource: { kind: "oauth_app", id: meta?.id ?? "" }, relation: "can_delete", children: _jsx("button", { type: "button", onClick: () => {
148
+ clearDeleteError();
149
+ setConfirmingDelete(true);
150
+ }, className: cn("stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium", "stg:text-destructive-muted stg:hover:text-destructive stg:hover:bg-destructive-subtle", "stg:transition-colors"), children: "Delete" }) })] }))] }), confirmingDelete && (_jsxs("div", { className: "stg:rounded-md stg:border stg:border-destructive/30 stg:bg-destructive-subtle stg:p-3", role: "alert", children: [_jsx("p", { className: "stg:text-foreground stg:mb-2 stg:text-xs stg:font-medium", children: "Delete this OAuth app?" }), _jsx("p", { className: "stg:text-muted-foreground stg:mb-3 stg:text-[0.65rem]", children: "This action is permanent. Any MCP server overrides referencing this app will lose their binding." }), deleteError && (_jsx("p", { className: "stg:text-destructive stg:mb-2 stg:text-[0.65rem]", role: "alert", children: getUserMessage(deleteError) })), _jsxs("div", { className: "stg:flex stg:items-center stg:gap-2", children: [_jsxs("button", { type: "button", onClick: handleDelete, disabled: isDeleting, className: cn("stg:inline-flex stg:items-center stg:gap-1.5 stg:rounded-md stg:px-3 stg:py-1.5 stg:text-xs stg:font-medium", "stg:bg-destructive stg:text-destructive-foreground stg:hover:bg-destructive-hover", "stg:disabled:pointer-events-none stg:disabled:opacity-40"), children: [isDeleting && _jsx(SpinnerIcon, { size: 12 }), "Delete permanently"] }), _jsx("button", { type: "button", onClick: () => {
146
151
  setConfirmingDelete(false);
147
152
  clearDeleteError();
148
153
  }, disabled: isDeleting, className: cn("stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs", "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover", "stg:disabled:pointer-events-none stg:disabled:opacity-50"), children: "Cancel" })] })] })), mode === "view" ? (_jsx(ViewMode, { spec: spec, createdAt: createdAt, updatedAt: updatedAt })) : (_jsxs("form", { onSubmit: handleSave, className: "stg:space-y-3", children: [_jsx(FieldInput, { id: `${baseId}-provider`, label: "Provider", value: provider, onChange: setProvider, placeholder: "e.g. Slack", disabled: isUpdating, required: true }), _jsx(FieldInput, { id: `${baseId}-client-id`, label: "Client ID", value: clientId, onChange: setClientId, placeholder: "OAuth client identifier", disabled: isUpdating, required: true }), _jsx(FieldInput, { id: `${baseId}-client-secret`, label: "Client secret", value: clientSecret, onChange: setClientSecret, placeholder: "Leave empty to keep existing secret", type: "password", hint: "Only enter a value to replace the existing secret", disabled: isUpdating }), _jsx(FieldInput, { id: `${baseId}-auth-url`, label: "Authorization URL", value: authorizationUrl, onChange: setAuthorizationUrl, placeholder: "https://vendor.com/oauth/authorize", disabled: isUpdating, required: true }), _jsx(FieldInput, { id: `${baseId}-token-url`, label: "Token URL", value: tokenUrl, onChange: setTokenUrl, placeholder: "https://vendor.com/oauth/token", disabled: isUpdating, required: true }), _jsx(FieldInput, { id: `${baseId}-scopes`, label: "Scopes", value: scopes, onChange: setScopes, placeholder: "read, write, admin", hint: "Comma-separated OAuth scopes", disabled: isUpdating }), _jsx(FieldInput, { id: `${baseId}-userinfo-url`, label: "Userinfo URL", value: userinfoUrl, onChange: setUserinfoUrl, placeholder: "https://vendor.com/userinfo", hint: "OIDC endpoint for fetching user profile data (optional)", disabled: isUpdating }), _jsx(FieldInput, { id: `${baseId}-scope-param`, label: "Scope parameter name", value: scopeParameterName, onChange: setScopeParameterName, placeholder: "scope", hint: 'Defaults to "scope". Some vendors use a non-standard name.', disabled: isUpdating }), _jsxs("div", { className: "stg:space-y-1", children: [_jsx("label", { htmlFor: `${baseId}-token-auth-method`, className: "stg:text-xs stg:font-medium stg:text-foreground", children: "Token endpoint auth method" }), _jsxs("select", { id: `${baseId}-token-auth-method`, value: tokenEndpointAuthMethod, onChange: (e) => setTokenEndpointAuthMethod(e.target.value), disabled: isUpdating, className: cn("stg:w-full stg:rounded-md stg:border stg:border-input stg:bg-background stg:px-2.5 stg:py-1.5 stg:text-xs stg:text-foreground", "stg:focus-visible:outline-none stg:focus-visible:ring-1 stg:focus-visible:ring-ring", "stg:disabled:pointer-events-none stg:disabled:opacity-50"), children: [_jsx("option", { value: "unspecified", children: "Unspecified (treated as HTTP Basic)" }), _jsx("option", { value: "client_secret_basic", children: "client_secret_basic (HTTP Basic header)" }), _jsx("option", { value: "client_secret_post", children: "client_secret_post (form body)" })] })] }), _jsxs("div", { className: "stg:space-y-1", children: [_jsx("label", { htmlFor: `${baseId}-approval-status`, className: "stg:text-xs stg:font-medium stg:text-foreground", children: "Vendor approval status" }), _jsxs("select", { id: `${baseId}-approval-status`, value: vendorApprovalStatus, onChange: (e) => setVendorApprovalStatus(e.target.value), disabled: isUpdating, className: cn("stg:w-full stg:rounded-md stg:border stg:border-input stg:bg-background stg:px-2.5 stg:py-1.5 stg:text-xs stg:text-foreground", "stg:focus-visible:outline-none stg:focus-visible:ring-1 stg:focus-visible:ring-ring", "stg:disabled:pointer-events-none stg:disabled:opacity-50"), children: [_jsx("option", { value: "unspecified", children: "Unspecified (treated as approved)" }), _jsx("option", { value: "pending", children: "Pending" }), _jsx("option", { value: "approved", children: "Approved" }), _jsx("option", { value: "rejected", children: "Rejected" })] })] }), _jsx(FieldInput, { id: `${baseId}-approval-docs`, label: "Vendor approval docs URL", value: vendorApprovalDocsUrl, onChange: setVendorApprovalDocsUrl, placeholder: "https://docs.example.com/byoa", hint: "Help link shown when vendor approval is pending", disabled: isUpdating }), updateError && (_jsx("p", { className: "stg:text-destructive stg:text-[0.65rem]", role: "alert", children: getUserMessage(updateError) })), _jsxs("div", { className: "stg:flex stg:items-center stg:gap-2 stg:pt-1", children: [_jsxs("button", { type: "submit", disabled: !canSave, className: cn("stg:inline-flex stg:items-center stg:gap-1.5 stg:rounded-md stg:px-3 stg:py-1.5 stg:text-xs stg:font-medium", "stg:bg-primary stg:text-primary-foreground stg:hover:bg-primary-hover", "stg:disabled:pointer-events-none stg:disabled:opacity-40"), children: [isUpdating && _jsx(SpinnerIcon, { size: 12 }), "Save changes"] }), _jsx("button", { type: "button", onClick: cancelEdit, disabled: isUpdating, className: cn("stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs", "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover", "stg:disabled:pointer-events-none stg:disabled:opacity-50"), children: "Cancel" })] })] }))] }));
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppDetailPanel.js","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppDetailPanel.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"OAuthAppDetailPanel.js","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppDetailPanel.tsx"],"names":[],"mappings":"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"}
@@ -1,3 +1,4 @@
1
+ import type { ReactNode } from "react";
1
2
  import type { OAuthApp } from "@stigmer/protos/ai/stigmer/iam/oauthapp/v1/api_pb";
2
3
  /** Props for {@link OAuthAppListPanel}. */
3
4
  export interface OAuthAppListPanelProps {
@@ -11,12 +12,19 @@ export interface OAuthAppListPanelProps {
11
12
  readonly onEdit?: (app: OAuthApp) => void;
12
13
  /** Re-expose refetch so parents can trigger a list refresh. */
13
14
  readonly onRefetchRef?: (refetch: () => void) => void;
15
+ /**
16
+ * Shown when the list is empty. Defaults to "No OAuth apps configured
17
+ * yet." The list holds only the apps the caller may view (each app's
18
+ * creator and the organization's admins), so a host that knows the
19
+ * caller may not manage OAuth apps should say who does instead.
20
+ */
21
+ readonly emptyState?: ReactNode;
14
22
  /** Additional CSS class names for the root container. */
15
23
  readonly className?: string;
16
24
  }
17
25
  /**
18
- * Displays a list of {@link OAuthApp} resources owned by an
19
- * organization.
26
+ * Displays the {@link OAuthApp} resources of an organization that the
27
+ * caller may view.
20
28
  *
21
29
  * Each row shows the provider name, client ID (non-secret), and
22
30
  * creation date. When `onEdit` is provided, rows include a pencil
@@ -39,5 +47,5 @@ export interface OAuthAppListPanelProps {
39
47
  * />
40
48
  * ```
41
49
  */
42
- export declare function OAuthAppListPanel({ org, onEdit, onRefetchRef, className, }: OAuthAppListPanelProps): import("react/jsx-runtime").JSX.Element;
50
+ export declare function OAuthAppListPanel({ org, onEdit, onRefetchRef, emptyState, className, }: OAuthAppListPanelProps): import("react/jsx-runtime").JSX.Element;
43
51
  //# sourceMappingURL=OAuthAppListPanel.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppListPanel.d.ts","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppListPanel.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAQlF,2CAA2C;AAC3C,MAAM,WAAW,sBAAsB;IACrC,gDAAgD;IAChD,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB;;;;OAIG;IACH,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,GAAG,EAAE,QAAQ,KAAK,IAAI,CAAC;IAC1C,+DAA+D;IAC/D,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,IAAI,KAAK,IAAI,CAAC;IACtD,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,iBAAiB,CAAC,EAChC,GAAG,EACH,MAAM,EACN,YAAY,EACZ,SAAS,GACV,EAAE,sBAAsB,2CA4DxB"}
1
+ {"version":3,"file":"OAuthAppListPanel.d.ts","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppListPanel.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAIvC,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAQlF,2CAA2C;AAC3C,MAAM,WAAW,sBAAsB;IACrC,gDAAgD;IAChD,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB;;;;OAIG;IACH,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,GAAG,EAAE,QAAQ,KAAK,IAAI,CAAC;IAC1C,+DAA+D;IAC/D,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,IAAI,KAAK,IAAI,CAAC;IACtD;;;;;OAKG;IACH,QAAQ,CAAC,UAAU,CAAC,EAAE,SAAS,CAAC;IAChC,yDAAyD;IACzD,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,iBAAiB,CAAC,EAChC,GAAG,EACH,MAAM,EACN,YAAY,EACZ,UAA4C,EAC5C,SAAS,GACV,EAAE,sBAAsB,2CA4DxB"}
@@ -6,8 +6,8 @@ import { timestampDate } from "@bufbuild/protobuf/wkt";
6
6
  import { Tooltip, TooltipContent, TooltipTrigger } from "../internal/tooltip.js";
7
7
  import { useOAuthAppList } from "./useOAuthAppList.js";
8
8
  /**
9
- * Displays a list of {@link OAuthApp} resources owned by an
10
- * organization.
9
+ * Displays the {@link OAuthApp} resources of an organization that the
10
+ * caller may view.
11
11
  *
12
12
  * Each row shows the provider name, client ID (non-secret), and
13
13
  * creation date. When `onEdit` is provided, rows include a pencil
@@ -30,7 +30,7 @@ import { useOAuthAppList } from "./useOAuthAppList.js";
30
30
  * />
31
31
  * ```
32
32
  */
33
- export function OAuthAppListPanel({ org, onEdit, onRefetchRef, className, }) {
33
+ export function OAuthAppListPanel({ org, onEdit, onRefetchRef, emptyState = "No OAuth apps configured yet.", className, }) {
34
34
  const { oauthApps, isLoading, error, refetch } = useOAuthAppList(org);
35
35
  if (onRefetchRef) {
36
36
  onRefetchRef(refetch);
@@ -42,7 +42,7 @@ export function OAuthAppListPanel({ org, onEdit, onRefetchRef, className, }) {
42
42
  return (_jsx("p", { className: cn("stg:text-destructive stg:text-xs", className), role: "alert", children: getUserMessage(error) }));
43
43
  }
44
44
  if (oauthApps.length === 0) {
45
- return (_jsx("p", { className: cn("stg:text-muted-foreground stg:py-4 stg:text-center stg:text-xs", className), children: "No OAuth apps configured yet." }));
45
+ return (_jsx("p", { className: cn("stg:text-muted-foreground stg:py-4 stg:text-center stg:text-xs", className), children: emptyState }));
46
46
  }
47
47
  return (_jsx("div", { className: cn("stg:space-y-2", className), role: "list", "aria-label": "OAuth apps", children: oauthApps.map((app) => (_jsx(OAuthAppRow, { oauthApp: app, onEdit: onEdit ? () => onEdit(app) : undefined }, app.metadata?.id ?? ""))) }));
48
48
  }
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppListPanel.js","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppListPanel.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"OAuthAppListPanel.js","sourceRoot":"","sources":["../../src/oauth-app/OAuthAppListPanel.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * OAuth-app copy shared by more than one surface, so the settings section
3
+ * and anything else that lists an organization's OAuth apps say the same
4
+ * thing.
5
+ *
6
+ * OAuth apps are administrative infrastructure: an app carries its
7
+ * organization's vendor credentials and endpoints, so its creator and the
8
+ * organization's admins see it and other members may not see it at all
9
+ * (stigmer/stigmer#1257). An empty list is therefore not evidence that none
10
+ * is configured, so a caller who may not create OAuth apps is told who
11
+ * manages them instead of being told that nothing exists.
12
+ */
13
+ /** Shown in place of the empty state to a caller who may not create OAuth apps. */
14
+ export declare const OAUTH_APPS_MANAGED_BY_ADMINS = "OAuth apps are managed by your organization's admins.";
15
+ //# sourceMappingURL=copy.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"copy.d.ts","sourceRoot":"","sources":["../../src/oauth-app/copy.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,mFAAmF;AACnF,eAAO,MAAM,4BAA4B,0DACgB,CAAC"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * OAuth-app copy shared by more than one surface, so the settings section
3
+ * and anything else that lists an organization's OAuth apps say the same
4
+ * thing.
5
+ *
6
+ * OAuth apps are administrative infrastructure: an app carries its
7
+ * organization's vendor credentials and endpoints, so its creator and the
8
+ * organization's admins see it and other members may not see it at all
9
+ * (stigmer/stigmer#1257). An empty list is therefore not evidence that none
10
+ * is configured, so a caller who may not create OAuth apps is told who
11
+ * manages them instead of being told that nothing exists.
12
+ */
13
+ /** Shown in place of the empty state to a caller who may not create OAuth apps. */
14
+ export const OAUTH_APPS_MANAGED_BY_ADMINS = "OAuth apps are managed by your organization's admins.";
15
+ //# sourceMappingURL=copy.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"copy.js","sourceRoot":"","sources":["../../src/oauth-app/copy.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,mFAAmF;AACnF,MAAM,CAAC,MAAM,4BAA4B,GACvC,uDAAuD,CAAC"}
@@ -15,9 +15,10 @@ export interface UseDeleteOAuthAppReturn {
15
15
  * state.
16
16
  *
17
17
  * Deletes an OAuth app by its resource ID. Returns the deleted
18
- * {@link OAuthApp} on success so callers can confirm which app was
19
- * removed. The deletion is permanent — any MCP server overrides
20
- * referencing this app will lose their binding.
18
+ * {@link OAuthApp} on success, its client secret redacted like every
19
+ * read, so callers can confirm which app was removed. The deletion is
20
+ * permanent, and the server refuses it while an MCP server's
21
+ * `oauth_app_ref` still resolves to the app.
21
22
  *
22
23
  * @example
23
24
  * ```tsx
@@ -1 +1 @@
1
- {"version":3,"file":"useDeleteOAuthApp.d.ts","sourceRoot":"","sources":["../../src/oauth-app/useDeleteOAuthApp.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAIlF,iDAAiD;AACjD,MAAM,WAAW,uBAAuB;IACtC,2GAA2G;IAC3G,QAAQ,CAAC,SAAS,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC;IACtD,oDAAoD;IACpD,QAAQ,CAAC,UAAU,EAAE,OAAO,CAAC;IAC7B,iEAAiE;IACjE,QAAQ,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IAC7B,+BAA+B;IAC/B,QAAQ,CAAC,UAAU,EAAE,MAAM,IAAI,CAAC;CACjC;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,iBAAiB,IAAI,uBAAuB,CAyB3D"}
1
+ {"version":3,"file":"useDeleteOAuthApp.d.ts","sourceRoot":"","sources":["../../src/oauth-app/useDeleteOAuthApp.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAIlF,iDAAiD;AACjD,MAAM,WAAW,uBAAuB;IACtC,2GAA2G;IAC3G,QAAQ,CAAC,SAAS,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC;IACtD,oDAAoD;IACpD,QAAQ,CAAC,UAAU,EAAE,OAAO,CAAC;IAC7B,iEAAiE;IACjE,QAAQ,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IAC7B,+BAA+B;IAC/B,QAAQ,CAAC,UAAU,EAAE,MAAM,IAAI,CAAC;CACjC;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,iBAAiB,IAAI,uBAAuB,CAyB3D"}
@@ -7,9 +7,10 @@ import { toError } from "../internal/toError.js";
7
7
  * state.
8
8
  *
9
9
  * Deletes an OAuth app by its resource ID. Returns the deleted
10
- * {@link OAuthApp} on success so callers can confirm which app was
11
- * removed. The deletion is permanent — any MCP server overrides
12
- * referencing this app will lose their binding.
10
+ * {@link OAuthApp} on success, its client secret redacted like every
11
+ * read, so callers can confirm which app was removed. The deletion is
12
+ * permanent, and the server refuses it while an MCP server's
13
+ * `oauth_app_ref` still resolves to the app.
13
14
  *
14
15
  * @example
15
16
  * ```tsx
@@ -1 +1 @@
1
- {"version":3,"file":"useDeleteOAuthApp.js","sourceRoot":"","sources":["../../src/oauth-app/useDeleteOAuthApp.ts"],"names":[],"mappings":"AAAA,YAAY,CAAC;AAEb,OAAO,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAE9C,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,OAAO,EAAE,MAAM,wBAAwB,CAAC;AAcjD;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,UAAU,iBAAiB;IAC/B,MAAM,OAAO,GAAG,UAAU,EAAE,CAAC;IAC7B,MAAM,CAAC,UAAU,EAAE,aAAa,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IACpD,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,GAAG,QAAQ,CAAe,IAAI,CAAC,CAAC;IAEvD,MAAM,UAAU,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,CAAC;IAEzD,MAAM,SAAS,GAAG,WAAW,CAC3B,KAAK,EAAE,EAAU,EAAqB,EAAE;QACtC,aAAa,CAAC,IAAI,CAAC,CAAC;QACpB,QAAQ,CAAC,IAAI,CAAC,CAAC;QAEf,IAAI,CAAC;YACH,OAAO,MAAM,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,UAAU,EAAE,EAAE,EAAE,CAAC,CAAC;QAC3D,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC;YACvB,MAAM,GAAG,CAAC;QACZ,CAAC;gBAAS,CAAC;YACT,aAAa,CAAC,KAAK,CAAC,CAAC;QACvB,CAAC;IACH,CAAC,EACD,CAAC,OAAO,CAAC,CACV,CAAC;IAEF,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,KAAK,EAAE,UAAU,EAAE,CAAC;AACtD,CAAC"}
1
+ {"version":3,"file":"useDeleteOAuthApp.js","sourceRoot":"","sources":["../../src/oauth-app/useDeleteOAuthApp.ts"],"names":[],"mappings":"AAAA,YAAY,CAAC;AAEb,OAAO,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAE9C,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,OAAO,EAAE,MAAM,wBAAwB,CAAC;AAcjD;;;;;;;;;;;;;;;;;GAiBG;AACH,MAAM,UAAU,iBAAiB;IAC/B,MAAM,OAAO,GAAG,UAAU,EAAE,CAAC;IAC7B,MAAM,CAAC,UAAU,EAAE,aAAa,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IACpD,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,GAAG,QAAQ,CAAe,IAAI,CAAC,CAAC;IAEvD,MAAM,UAAU,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,CAAC;IAEzD,MAAM,SAAS,GAAG,WAAW,CAC3B,KAAK,EAAE,EAAU,EAAqB,EAAE;QACtC,aAAa,CAAC,IAAI,CAAC,CAAC;QACpB,QAAQ,CAAC,IAAI,CAAC,CAAC;QAEf,IAAI,CAAC;YACH,OAAO,MAAM,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,UAAU,EAAE,EAAE,EAAE,CAAC,CAAC;QAC3D,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC;YACvB,MAAM,GAAG,CAAC;QACZ,CAAC;gBAAS,CAAC;YACT,aAAa,CAAC,KAAK,CAAC,CAAC;QACvB,CAAC;IACH,CAAC,EACD,CAAC,OAAO,CAAC,CACV,CAAC;IAEF,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,KAAK,EAAE,UAAU,EAAE,CAAC;AACtD,CAAC"}
@@ -13,11 +13,13 @@ export interface UseOAuthAppListReturn {
13
13
  readonly refetch: () => void;
14
14
  }
15
15
  /**
16
- * Data hook that fetches all {@link OAuthApp} entries for an organization.
16
+ * Data hook that fetches the {@link OAuthApp} entries of an organization
17
+ * that the caller may view.
17
18
  *
18
- * Returns every OAuthApp whose `metadata.org` matches the input. In
19
- * practice these are the BYOA OAuth apps created through the "Bring
20
- * your own app" flow on MCP server detail pages.
19
+ * Returns the organization's OAuthApps that a `get` would return to the
20
+ * caller: each app's creator and the organization's admins see it, other
21
+ * members and viewers see none. In practice these are the BYOA OAuth apps
22
+ * created through the "Bring your own app" flow on MCP server detail pages.
21
23
  *
22
24
  * Pass `null` for `org` to skip fetching (stable no-op). Useful when
23
25
  * the active organization has not been resolved yet.
@@ -1 +1 @@
1
- {"version":3,"file":"useOAuthAppList.d.ts","sourceRoot":"","sources":["../../src/oauth-app/useOAuthAppList.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAIlF,+CAA+C;AAC/C,MAAM,WAAW,qBAAqB;IACpC,6EAA6E;IAC7E,QAAQ,CAAC,SAAS,EAAE,SAAS,QAAQ,EAAE,CAAC;IACxC,gEAAgE;IAChE,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAC;IAC5B,8EAA8E;IAC9E,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAC;IAC/B,kEAAkE;IAClE,QAAQ,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IAC7B,iEAAiE;IACjE,QAAQ,CAAC,OAAO,EAAE,MAAM,IAAI,CAAC;CAC9B;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,eAAe,CAC7B,GAAG,EAAE,MAAM,GAAG,IAAI,GACjB,qBAAqB,CAevB"}
1
+ {"version":3,"file":"useOAuthAppList.d.ts","sourceRoot":"","sources":["../../src/oauth-app/useOAuthAppList.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,mDAAmD,CAAC;AAIlF,+CAA+C;AAC/C,MAAM,WAAW,qBAAqB;IACpC,6EAA6E;IAC7E,QAAQ,CAAC,SAAS,EAAE,SAAS,QAAQ,EAAE,CAAC;IACxC,gEAAgE;IAChE,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAC;IAC5B,8EAA8E;IAC9E,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAC;IAC/B,kEAAkE;IAClE,QAAQ,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IAC7B,iEAAiE;IACjE,QAAQ,CAAC,OAAO,EAAE,MAAM,IAAI,CAAC;CAC9B;AAED;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAgB,eAAe,CAC7B,GAAG,EAAE,MAAM,GAAG,IAAI,GACjB,qBAAqB,CAevB"}
@@ -4,11 +4,13 @@ import { ListOAuthAppsByOrgInputSchema } from "@stigmer/protos/ai/stigmer/iam/oa
4
4
  import { useStigmer } from "../hooks.js";
5
5
  import { useFetch } from "../internal/useFetch.js";
6
6
  /**
7
- * Data hook that fetches all {@link OAuthApp} entries for an organization.
7
+ * Data hook that fetches the {@link OAuthApp} entries of an organization
8
+ * that the caller may view.
8
9
  *
9
- * Returns every OAuthApp whose `metadata.org` matches the input. In
10
- * practice these are the BYOA OAuth apps created through the "Bring
11
- * your own app" flow on MCP server detail pages.
10
+ * Returns the organization's OAuthApps that a `get` would return to the
11
+ * caller: each app's creator and the organization's admins see it, other
12
+ * members and viewers see none. In practice these are the BYOA OAuth apps
13
+ * created through the "Bring your own app" flow on MCP server detail pages.
12
14
  *
13
15
  * Pass `null` for `org` to skip fetching (stable no-op). Useful when
14
16
  * the active organization has not been resolved yet.
@@ -1 +1 @@
1
- {"version":3,"file":"useOAuthAppList.js","sourceRoot":"","sources":["../../src/oauth-app/useOAuthAppList.ts"],"names":[],"mappings":"AAAA,YAAY,CAAC;AAEb,OAAO,EAAE,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAC5C,OAAO,EAAE,6BAA6B,EAAE,MAAM,kDAAkD,CAAC;AAEjG,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,yBAAyB,CAAC;AAgBnD;;;;;;;;;;;;;;;;;GAiBG;AACH,MAAM,UAAU,eAAe,CAC7B,GAAkB;IAElB,MAAM,OAAO,GAAG,UAAU,EAAE,CAAC;IAE7B,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,SAAS,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,QAAQ,CAC3E,GAAG;QACD,CAAC,CAAC,GAAG,EAAE,CACH,OAAO,CAAC,QAAQ;aACb,SAAS,CAAC,MAAM,CAAC,6BAA6B,EAAE,EAAE,GAAG,EAAE,CAAC,CAAC;aACzD,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC;QAClC,CAAC,CAAC,IAAI,EACR,CAAC,GAAG,EAAE,OAAO,CAAC,EACd,EAAgB,CACjB,CAAC;IAEF,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;AAChE,CAAC"}
1
+ {"version":3,"file":"useOAuthAppList.js","sourceRoot":"","sources":["../../src/oauth-app/useOAuthAppList.ts"],"names":[],"mappings":"AAAA,YAAY,CAAC;AAEb,OAAO,EAAE,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAC5C,OAAO,EAAE,6BAA6B,EAAE,MAAM,kDAAkD,CAAC;AAEjG,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,yBAAyB,CAAC;AAgBnD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,UAAU,eAAe,CAC7B,GAAkB;IAElB,MAAM,OAAO,GAAG,UAAU,EAAE,CAAC;IAE7B,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,SAAS,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,QAAQ,CAC3E,GAAG;QACD,CAAC,CAAC,GAAG,EAAE,CACH,OAAO,CAAC,QAAQ;aACb,SAAS,CAAC,MAAM,CAAC,6BAA6B,EAAE,EAAE,GAAG,EAAE,CAAC,CAAC;aACzD,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC;QAClC,CAAC,CAAC,IAAI,EACR,CAAC,GAAG,EAAE,OAAO,CAAC,EACd,EAAgB,CACjB,CAAC;IAEF,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;AAChE,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@stigmer/react",
3
- "version": "3.30.0",
3
+ "version": "3.31.0",
4
4
  "description": "React provider and client hook for the Stigmer platform SDK",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",
@@ -37,8 +37,8 @@
37
37
  "dependencies": {
38
38
  "@bufbuild/protovalidate": "^1.1.1",
39
39
  "@dagrejs/dagre": "^1.1.4",
40
- "@stigmer/plugin-package": "3.30.0",
41
- "@stigmer/theme": "3.30.0",
40
+ "@stigmer/plugin-package": "3.31.0",
41
+ "@stigmer/theme": "3.31.0",
42
42
  "diff": "^8.0.3",
43
43
  "fflate": "^0.8.2",
44
44
  "hast-util-to-jsx-runtime": "^2.3.6",
@@ -61,8 +61,8 @@
61
61
  "@codemirror/state": "^6.0.0",
62
62
  "@codemirror/view": "^6.0.0",
63
63
  "@lezer/highlight": "^1.0.0",
64
- "@stigmer/protos": "3.30.0",
65
- "@stigmer/sdk": "3.30.0",
64
+ "@stigmer/protos": "3.31.0",
65
+ "@stigmer/sdk": "3.31.0",
66
66
  "@tanstack/react-table": "^8.20.0",
67
67
  "@xyflow/react": "^12.0.0",
68
68
  "elkjs": "^0.9.0",
@@ -1,3 +1,11 @@
1
- /** Settings section for organization OAuth app credentials. */
1
+ /**
2
+ * Settings section for organization OAuth app credentials.
3
+ *
4
+ * "New OAuth app" is offered once the server confirms the caller holds
5
+ * `can_create_oauth_app` on the organization. The list shows only the apps
6
+ * the caller may view (each app's creator and the organization's admins),
7
+ * so a caller who may not create OAuth apps is told that the
8
+ * organization's admins manage them rather than that none is configured.
9
+ */
2
10
  export declare function OAuthAppsSection(): import("react/jsx-runtime").JSX.Element;
3
11
  //# sourceMappingURL=OAuthAppsSection.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppsSection.d.ts","sourceRoot":"","sources":["../../src/settings/OAuthAppsSection.tsx"],"names":[],"mappings":"AAgBA,+DAA+D;AAC/D,wBAAgB,gBAAgB,4CAmF/B"}
1
+ {"version":3,"file":"OAuthAppsSection.d.ts","sourceRoot":"","sources":["../../src/settings/OAuthAppsSection.tsx"],"names":[],"mappings":"AAkBA;;;;;;;;GAQG;AACH,wBAAgB,gBAAgB,4CA2F/B"}
@@ -4,14 +4,28 @@ import { useCallback, useId, useRef, useState } from "react";
4
4
  import { OAuthAppListPanel } from "../oauth-app/OAuthAppListPanel.js";
5
5
  import { CreateOAuthAppForm } from "../oauth-app/CreateOAuthAppForm.js";
6
6
  import { OAuthAppDetailPanel } from "../oauth-app/OAuthAppDetailPanel.js";
7
+ import { OAUTH_APPS_MANAGED_BY_ADMINS } from "../oauth-app/copy.js";
7
8
  import { useResourceAvailable, ApiResourceKind } from "../deployment-mode.js";
9
+ import { useCheckPermission } from "../iam-policy/useCheckPermission.js";
8
10
  import { CloudFeatureNotice } from "../internal/CloudFeatureNotice.js";
9
- import { useActiveOrgSlug } from "../organization/OrgProvider.js";
10
- /** Settings section for organization OAuth app credentials. */
11
+ import { useActiveOrgId, useActiveOrgSlug } from "../organization/OrgProvider.js";
12
+ /**
13
+ * Settings section for organization OAuth app credentials.
14
+ *
15
+ * "New OAuth app" is offered once the server confirms the caller holds
16
+ * `can_create_oauth_app` on the organization. The list shows only the apps
17
+ * the caller may view (each app's creator and the organization's admins),
18
+ * so a caller who may not create OAuth apps is told that the
19
+ * organization's admins manage them rather than that none is configured.
20
+ */
11
21
  export function OAuthAppsSection() {
12
22
  const headingId = useId();
13
23
  const org = useActiveOrgSlug();
24
+ const orgId = useActiveOrgId();
14
25
  const oauthAppsAvailable = useResourceAvailable(ApiResourceKind.oauth_app);
26
+ const createCheck = useCheckPermission(oauthAppsAvailable && orgId ? { kind: "organization", id: orgId } : null, "can_create_oauth_app");
27
+ const canCreate = !createCheck.isLoading && createCheck.allowed;
28
+ const deniedCreate = !createCheck.isLoading && !createCheck.allowed;
15
29
  const [flow, setFlow] = useState({ phase: "idle" });
16
30
  const listRefetchRef = useRef(null);
17
31
  const handleRefetchRef = useCallback((refetch) => {
@@ -29,6 +43,6 @@ export function OAuthAppsSection() {
29
43
  listRefetchRef.current?.();
30
44
  setFlow({ phase: "idle" });
31
45
  }, []);
32
- return (_jsxs("section", { "aria-labelledby": headingId, children: [_jsxs("div", { className: "stg:mb-3 stg:flex stg:items-center stg:justify-between", children: [_jsx("h2", { id: headingId, className: "stg:text-foreground stg:text-sm stg:font-semibold", children: "OAuth Apps" }), oauthAppsAvailable && org && flow.phase === "idle" && (_jsx("button", { type: "button", onClick: () => setFlow({ phase: "creating" }), className: "stg:text-primary stg:hover:text-foreground stg:text-xs stg:font-medium stg:transition-colors", children: "+ New OAuth app" }))] }), _jsx("p", { className: "stg:text-muted-foreground stg:mb-4 stg:text-xs", children: "OAuth app credentials configured for your organization. Create new apps here or bring your own from an MCP server's detail page." }), !oauthAppsAvailable ? (_jsx(CloudFeatureNotice, { children: "OAuth apps are not available in local mode. Bring-your-own-app OAuth requires the cloud platform." })) : flow.phase === "creating" ? (_jsx("div", { className: "stg:border-border stg:bg-card stg:rounded-lg stg:border stg:p-4", children: _jsx(CreateOAuthAppForm, { org: org, onCreated: handleCreated, onCancel: () => setFlow({ phase: "idle" }) }) })) : flow.phase === "editing" ? (_jsx("div", { className: "stg:border-border stg:bg-card stg:rounded-lg stg:border stg:p-4", children: _jsx(OAuthAppDetailPanel, { oauthApp: flow.oauthApp, onUpdated: handleUpdated, onDeleted: handleDeleted, onBack: () => setFlow({ phase: "idle" }) }) })) : (_jsx(OAuthAppListPanel, { org: org, onEdit: (app) => setFlow({ phase: "editing", oauthApp: app }), onRefetchRef: handleRefetchRef }))] }));
46
+ return (_jsxs("section", { "aria-labelledby": headingId, children: [_jsxs("div", { className: "stg:mb-3 stg:flex stg:items-center stg:justify-between", children: [_jsx("h2", { id: headingId, className: "stg:text-foreground stg:text-sm stg:font-semibold", children: "OAuth Apps" }), oauthAppsAvailable && org && canCreate && flow.phase === "idle" && (_jsx("button", { type: "button", onClick: () => setFlow({ phase: "creating" }), className: "stg:text-primary stg:hover:text-foreground stg:text-xs stg:font-medium stg:transition-colors", children: "+ New OAuth app" }))] }), _jsx("p", { className: "stg:text-muted-foreground stg:mb-4 stg:text-xs", children: "OAuth app credentials configured for your organization. Create new apps here or bring your own from an MCP server's detail page." }), !oauthAppsAvailable ? (_jsx(CloudFeatureNotice, { children: "OAuth apps are not available in local mode. Bring-your-own-app OAuth requires the cloud platform." })) : flow.phase === "creating" ? (_jsx("div", { className: "stg:border-border stg:bg-card stg:rounded-lg stg:border stg:p-4", children: _jsx(CreateOAuthAppForm, { org: org, onCreated: handleCreated, onCancel: () => setFlow({ phase: "idle" }) }) })) : flow.phase === "editing" ? (_jsx("div", { className: "stg:border-border stg:bg-card stg:rounded-lg stg:border stg:p-4", children: _jsx(OAuthAppDetailPanel, { oauthApp: flow.oauthApp, onUpdated: handleUpdated, onDeleted: handleDeleted, onBack: () => setFlow({ phase: "idle" }) }) })) : (_jsx(OAuthAppListPanel, { org: org, onEdit: (app) => setFlow({ phase: "editing", oauthApp: app }), onRefetchRef: handleRefetchRef, emptyState: deniedCreate ? OAUTH_APPS_MANAGED_BY_ADMINS : undefined }))] }));
33
47
  }
34
48
  //# sourceMappingURL=OAuthAppsSection.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"OAuthAppsSection.js","sourceRoot":"","sources":["../../src/settings/OAuthAppsSection.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"OAuthAppsSection.js","sourceRoot":"","sources":["../../src/settings/OAuthAppsSection.tsx"],"names":[],"mappings":"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"}
@@ -11,6 +11,7 @@ import {
11
11
  import { timestampDate, type Timestamp } from "@bufbuild/protobuf/wkt";
12
12
  import { useUpdateOAuthApp } from "./useUpdateOAuthApp.js";
13
13
  import { useDeleteOAuthApp } from "./useDeleteOAuthApp.js";
14
+ import { PermissionGate } from "../iam-policy/PermissionGate.js";
14
15
  import { SpinnerIcon } from "../internal/SpinnerIcon.js";
15
16
 
16
17
  // ---------------------------------------------------------------------------
@@ -35,7 +36,11 @@ export interface OAuthAppDetailPanelProps {
35
36
  * View and edit panel for an existing OAuth app.
36
37
  *
37
38
  * In **view mode**, displays all OAuth configuration fields in a
38
- * structured label/value layout with "Edit" and "Delete" buttons.
39
+ * structured label/value layout, with an "Edit" button for a caller who
40
+ * may edit the app (`can_edit`) and a "Delete" button for one who may
41
+ * delete it (`can_delete`). Both belong to the app's creator alone: the
42
+ * organization's admins may view an app they did not create, never change
43
+ * it.
39
44
  *
40
45
  * In **edit mode**, fields become editable inputs. The client secret
41
46
  * field shows a placeholder — leave it empty to keep the existing
@@ -223,31 +228,41 @@ export function OAuthAppDetailPanel({
223
228
 
224
229
  {mode === "view" && (
225
230
  <div className="stg:flex stg:items-center stg:gap-1">
226
- <button
227
- type="button"
228
- onClick={enterEdit}
229
- className={cn(
230
- "stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium",
231
- "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover",
232
- "stg:transition-colors",
233
- )}
231
+ <PermissionGate
232
+ resource={{ kind: "oauth_app", id: meta?.id ?? "" }}
233
+ relation="can_edit"
234
234
  >
235
- Edit
236
- </button>
237
- <button
238
- type="button"
239
- onClick={() => {
240
- clearDeleteError();
241
- setConfirmingDelete(true);
242
- }}
243
- className={cn(
244
- "stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium",
245
- "stg:text-destructive-muted stg:hover:text-destructive stg:hover:bg-destructive-subtle",
246
- "stg:transition-colors",
247
- )}
235
+ <button
236
+ type="button"
237
+ onClick={enterEdit}
238
+ className={cn(
239
+ "stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium",
240
+ "stg:text-muted-foreground stg:hover:text-foreground stg:hover:bg-accent-hover",
241
+ "stg:transition-colors",
242
+ )}
243
+ >
244
+ Edit
245
+ </button>
246
+ </PermissionGate>
247
+ <PermissionGate
248
+ resource={{ kind: "oauth_app", id: meta?.id ?? "" }}
249
+ relation="can_delete"
248
250
  >
249
- Delete
250
- </button>
251
+ <button
252
+ type="button"
253
+ onClick={() => {
254
+ clearDeleteError();
255
+ setConfirmingDelete(true);
256
+ }}
257
+ className={cn(
258
+ "stg:shrink-0 stg:rounded-md stg:px-2.5 stg:py-1.5 stg:text-xs stg:font-medium",
259
+ "stg:text-destructive-muted stg:hover:text-destructive stg:hover:bg-destructive-subtle",
260
+ "stg:transition-colors",
261
+ )}
262
+ >
263
+ Delete
264
+ </button>
265
+ </PermissionGate>
251
266
  </div>
252
267
  )}
253
268
  </div>
@@ -1,5 +1,6 @@
1
1
  "use client";
2
2
 
3
+ import type { ReactNode } from "react";
3
4
  import { cn } from "@stigmer/theme";
4
5
  import { getUserMessage } from "@stigmer/sdk";
5
6
  import { timestampDate } from "@bufbuild/protobuf/wkt";
@@ -23,13 +24,20 @@ export interface OAuthAppListPanelProps {
23
24
  readonly onEdit?: (app: OAuthApp) => void;
24
25
  /** Re-expose refetch so parents can trigger a list refresh. */
25
26
  readonly onRefetchRef?: (refetch: () => void) => void;
27
+ /**
28
+ * Shown when the list is empty. Defaults to "No OAuth apps configured
29
+ * yet." The list holds only the apps the caller may view (each app's
30
+ * creator and the organization's admins), so a host that knows the
31
+ * caller may not manage OAuth apps should say who does instead.
32
+ */
33
+ readonly emptyState?: ReactNode;
26
34
  /** Additional CSS class names for the root container. */
27
35
  readonly className?: string;
28
36
  }
29
37
 
30
38
  /**
31
- * Displays a list of {@link OAuthApp} resources owned by an
32
- * organization.
39
+ * Displays the {@link OAuthApp} resources of an organization that the
40
+ * caller may view.
33
41
  *
34
42
  * Each row shows the provider name, client ID (non-secret), and
35
43
  * creation date. When `onEdit` is provided, rows include a pencil
@@ -56,6 +64,7 @@ export function OAuthAppListPanel({
56
64
  org,
57
65
  onEdit,
58
66
  onRefetchRef,
67
+ emptyState = "No OAuth apps configured yet.",
59
68
  className,
60
69
  }: OAuthAppListPanelProps) {
61
70
  const { oauthApps, isLoading, error, refetch } = useOAuthAppList(org);
@@ -97,7 +106,7 @@ export function OAuthAppListPanel({
97
106
  className,
98
107
  )}
99
108
  >
100
- No OAuth apps configured yet.
109
+ {emptyState}
101
110
  </p>
102
111
  );
103
112
  }
@@ -6,17 +6,24 @@ import {
6
6
  type OAuthApp,
7
7
  } from "@stigmer/protos/ai/stigmer/iam/oauthapp/v1/api_pb";
8
8
  import { TokenEndpointAuthMethod } from "@stigmer/protos/ai/stigmer/iam/oauthapp/v1/spec_pb";
9
+ import type { CheckMyPermissionInput } from "@stigmer/protos/ai/stigmer/iam/iampolicy/v1/io_pb";
9
10
  import type { OAuthAppInput } from "@stigmer/sdk";
10
11
  import { StigmerContext } from "../../context";
11
12
  import { OAuthAppDetailPanel } from "../OAuthAppDetailPanel";
12
13
 
13
14
  /**
14
- * Regression suite for the full-spec-replace wipe bug: the panel must
15
- * spread `toOAuthAppUpdateInput` and override only what it edits, so a
16
- * spec field the form does not know about survives the save. The secret
17
- * has its own contract: an empty secret input sends the fetched value —
18
- * the server's redaction marker — which the update pipeline treats as
19
- * "keep the stored secret" (oss#395 pins the marker/ciphertext boundary).
15
+ * Pins two things about the detail panel:
16
+ *
17
+ * - the full-spec-replace wipe bug: the panel must spread
18
+ * `toOAuthAppUpdateInput` and override only what it edits, so a spec
19
+ * field the form does not know about survives the save. The secret has
20
+ * its own contract: an empty secret input sends the fetched value — the
21
+ * server's redaction marker — which the update pipeline treats as "keep
22
+ * the stored secret" (oss#395 pins the marker/ciphertext boundary);
23
+ * - Edit is offered only with `can_edit` and Delete only with
24
+ * `can_delete` on the app, so an organization admin who may view an app
25
+ * they did not create is never handed a control the server would
26
+ * refuse (both belong to the creator; stigmer/stigmer#1257).
20
27
  */
21
28
 
22
29
  const REDACTED = "***REDACTED***";
@@ -39,9 +46,15 @@ const APP: OAuthApp = create(OAuthAppSchema, {
39
46
  },
40
47
  });
41
48
 
42
- function renderPanel(update: ReturnType<typeof vi.fn>) {
49
+ function renderPanel(
50
+ update: ReturnType<typeof vi.fn>,
51
+ checkMyPermission: ReturnType<typeof vi.fn> = vi.fn(async () => ({
52
+ isAuthorized: true,
53
+ })),
54
+ ) {
43
55
  const client = {
44
56
  oauthapp: { update },
57
+ iamPolicy: { checkMyPermission },
45
58
  } as never;
46
59
  return render(
47
60
  <StigmerContext.Provider value={client}>
@@ -57,7 +70,7 @@ describe("OAuthAppDetailPanel save payload", () => {
57
70
  const update = vi.fn(async (_input: OAuthAppInput) => APP);
58
71
  renderPanel(update);
59
72
 
60
- fireEvent.click(screen.getByRole("button", { name: "Edit" }));
73
+ fireEvent.click(await screen.findByRole("button", { name: "Edit" }));
61
74
  const provider = await screen.findByLabelText("Provider");
62
75
  fireEvent.change(provider, { target: { value: "github-enterprise" } });
63
76
  fireEvent.click(screen.getByRole("button", { name: "Save changes" }));
@@ -83,7 +96,7 @@ describe("OAuthAppDetailPanel save payload", () => {
83
96
  const update = vi.fn(async (_input: OAuthAppInput) => APP);
84
97
  renderPanel(update);
85
98
 
86
- fireEvent.click(screen.getByRole("button", { name: "Edit" }));
99
+ fireEvent.click(await screen.findByRole("button", { name: "Edit" }));
87
100
  const secret = await screen.findByLabelText("Client secret");
88
101
  fireEvent.change(secret, { target: { value: "new-secret" } });
89
102
  fireEvent.click(screen.getByRole("button", { name: "Save changes" }));
@@ -92,3 +105,38 @@ describe("OAuthAppDetailPanel save payload", () => {
92
105
  expect(update.mock.calls[0]![0].clientSecret).toBe("new-secret");
93
106
  });
94
107
  });
108
+
109
+ describe("OAuthAppDetailPanel edit and delete gates", () => {
110
+ it("offers Edit only with can_edit and Delete only with can_delete on the app", async () => {
111
+ const checkMyPermission = vi.fn(async (input: CheckMyPermissionInput) => ({
112
+ isAuthorized: input.relation === "can_delete",
113
+ }));
114
+ renderPanel(vi.fn(), checkMyPermission);
115
+
116
+ await screen.findByRole("button", { name: "Delete" });
117
+ expect(screen.queryByRole("button", { name: "Edit" })).toBeNull();
118
+ const asked = checkMyPermission.mock.calls.map(
119
+ ([input]) =>
120
+ `${input.resource?.kind}:${input.resource?.id}:${input.relation}`,
121
+ );
122
+ expect(asked.sort()).toEqual([
123
+ "oauth_app:oa-1:can_delete",
124
+ "oauth_app:oa-1:can_edit",
125
+ ]);
126
+ });
127
+
128
+ it("an admin who did not create the app reads it with neither control", async () => {
129
+ const checkMyPermission = vi.fn(async (_input: CheckMyPermissionInput) => ({
130
+ isAuthorized: false,
131
+ }));
132
+ renderPanel(vi.fn(), checkMyPermission);
133
+
134
+ await waitFor(() => expect(checkMyPermission).toHaveBeenCalledTimes(2));
135
+ // The configuration stays readable; only the change affordances are withheld.
136
+ expect(screen.getByRole("heading", { name: "github" })).toBeTruthy();
137
+ await waitFor(() =>
138
+ expect(screen.queryByRole("button", { name: "Edit" })).toBeNull(),
139
+ );
140
+ expect(screen.queryByRole("button", { name: "Delete" })).toBeNull();
141
+ });
142
+ });
@@ -0,0 +1,16 @@
1
+ /**
2
+ * OAuth-app copy shared by more than one surface, so the settings section
3
+ * and anything else that lists an organization's OAuth apps say the same
4
+ * thing.
5
+ *
6
+ * OAuth apps are administrative infrastructure: an app carries its
7
+ * organization's vendor credentials and endpoints, so its creator and the
8
+ * organization's admins see it and other members may not see it at all
9
+ * (stigmer/stigmer#1257). An empty list is therefore not evidence that none
10
+ * is configured, so a caller who may not create OAuth apps is told who
11
+ * manages them instead of being told that nothing exists.
12
+ */
13
+
14
+ /** Shown in place of the empty state to a caller who may not create OAuth apps. */
15
+ export const OAUTH_APPS_MANAGED_BY_ADMINS =
16
+ "OAuth apps are managed by your organization's admins.";
@@ -22,9 +22,10 @@ export interface UseDeleteOAuthAppReturn {
22
22
  * state.
23
23
  *
24
24
  * Deletes an OAuth app by its resource ID. Returns the deleted
25
- * {@link OAuthApp} on success so callers can confirm which app was
26
- * removed. The deletion is permanent — any MCP server overrides
27
- * referencing this app will lose their binding.
25
+ * {@link OAuthApp} on success, its client secret redacted like every
26
+ * read, so callers can confirm which app was removed. The deletion is
27
+ * permanent, and the server refuses it while an MCP server's
28
+ * `oauth_app_ref` still resolves to the app.
28
29
  *
29
30
  * @example
30
31
  * ```tsx
@@ -21,11 +21,13 @@ export interface UseOAuthAppListReturn {
21
21
  }
22
22
 
23
23
  /**
24
- * Data hook that fetches all {@link OAuthApp} entries for an organization.
24
+ * Data hook that fetches the {@link OAuthApp} entries of an organization
25
+ * that the caller may view.
25
26
  *
26
- * Returns every OAuthApp whose `metadata.org` matches the input. In
27
- * practice these are the BYOA OAuth apps created through the "Bring
28
- * your own app" flow on MCP server detail pages.
27
+ * Returns the organization's OAuthApps that a `get` would return to the
28
+ * caller: each app's creator and the organization's admins see it, other
29
+ * members and viewers see none. In practice these are the BYOA OAuth apps
30
+ * created through the "Bring your own app" flow on MCP server detail pages.
29
31
  *
30
32
  * Pass `null` for `org` to skip fetching (stable no-op). Useful when
31
33
  * the active organization has not been resolved yet.
@@ -5,20 +5,37 @@ import type { OAuthApp } from "@stigmer/protos/ai/stigmer/iam/oauthapp/v1/api_pb
5
5
  import { OAuthAppListPanel } from "../oauth-app/OAuthAppListPanel.js";
6
6
  import { CreateOAuthAppForm } from "../oauth-app/CreateOAuthAppForm.js";
7
7
  import { OAuthAppDetailPanel } from "../oauth-app/OAuthAppDetailPanel.js";
8
+ import { OAUTH_APPS_MANAGED_BY_ADMINS } from "../oauth-app/copy.js";
8
9
  import { useResourceAvailable, ApiResourceKind } from "../deployment-mode.js";
10
+ import { useCheckPermission } from "../iam-policy/useCheckPermission.js";
9
11
  import { CloudFeatureNotice } from "../internal/CloudFeatureNotice.js";
10
- import { useActiveOrgSlug } from "../organization/OrgProvider.js";
12
+ import { useActiveOrgId, useActiveOrgSlug } from "../organization/OrgProvider.js";
11
13
 
12
14
  type FlowState =
13
15
  | { phase: "idle" }
14
16
  | { phase: "creating" }
15
17
  | { phase: "editing"; oauthApp: OAuthApp };
16
18
 
17
- /** Settings section for organization OAuth app credentials. */
19
+ /**
20
+ * Settings section for organization OAuth app credentials.
21
+ *
22
+ * "New OAuth app" is offered once the server confirms the caller holds
23
+ * `can_create_oauth_app` on the organization. The list shows only the apps
24
+ * the caller may view (each app's creator and the organization's admins),
25
+ * so a caller who may not create OAuth apps is told that the
26
+ * organization's admins manage them rather than that none is configured.
27
+ */
18
28
  export function OAuthAppsSection() {
19
29
  const headingId = useId();
20
30
  const org = useActiveOrgSlug();
31
+ const orgId = useActiveOrgId();
21
32
  const oauthAppsAvailable = useResourceAvailable(ApiResourceKind.oauth_app);
33
+ const createCheck = useCheckPermission(
34
+ oauthAppsAvailable && orgId ? { kind: "organization", id: orgId } : null,
35
+ "can_create_oauth_app",
36
+ );
37
+ const canCreate = !createCheck.isLoading && createCheck.allowed;
38
+ const deniedCreate = !createCheck.isLoading && !createCheck.allowed;
22
39
 
23
40
  const [flow, setFlow] = useState<FlowState>({ phase: "idle" });
24
41
  const listRefetchRef = useRef<(() => void) | null>(null);
@@ -52,7 +69,7 @@ export function OAuthAppsSection() {
52
69
  OAuth Apps
53
70
  </h2>
54
71
 
55
- {oauthAppsAvailable && org && flow.phase === "idle" && (
72
+ {oauthAppsAvailable && org && canCreate && flow.phase === "idle" && (
56
73
  <button
57
74
  type="button"
58
75
  onClick={() => setFlow({ phase: "creating" })}
@@ -94,6 +111,7 @@ export function OAuthAppsSection() {
94
111
  org={org}
95
112
  onEdit={(app) => setFlow({ phase: "editing", oauthApp: app })}
96
113
  onRefetchRef={handleRefetchRef}
114
+ emptyState={deniedCreate ? OAUTH_APPS_MANAGED_BY_ADMINS : undefined}
97
115
  />
98
116
  )}
99
117
  </section>
@@ -0,0 +1,133 @@
1
+ /**
2
+ * Pins what OAuthAppsSection offers a caller by the server's verdicts.
3
+ * OAuth apps are administrative: an app carries its organization's vendor
4
+ * credentials, the model shows it to its creator and the organization's
5
+ * admins only, and the list holds only the apps the caller may view
6
+ * (stigmer/stigmer#1257), so the section must neither offer what the server
7
+ * refuses nor call an empty list "nothing configured" to someone who simply
8
+ * may not see it.
9
+ *
10
+ * - the list asks for the active organization's apps by its slug;
11
+ * - "New OAuth app" is offered only with `can_create_oauth_app` on the
12
+ * organization, checked on the organization's id;
13
+ * - an empty list reads "No OAuth apps configured yet." to a caller who
14
+ * may create one, and names the organization's admins to a caller the
15
+ * server has refused.
16
+ *
17
+ * The data hook and the permission check are stubbed; the list panel is
18
+ * real. The detail panel's Edit and Delete gates are pinned beside it
19
+ * (oauth-app/__tests__/OAuthAppDetailPanel.test.tsx).
20
+ */
21
+ import { describe, it, expect, vi, afterEach } from "vitest";
22
+ import { cleanup, render, screen } from "@testing-library/react";
23
+ import { create } from "@bufbuild/protobuf";
24
+ import {
25
+ OAuthAppSchema,
26
+ type OAuthApp,
27
+ } from "@stigmer/protos/ai/stigmer/iam/oauthapp/v1/api_pb";
28
+ import type { DeploymentMode } from "@stigmer/sdk";
29
+ import { DeploymentModeContext } from "../../deployment-mode";
30
+
31
+ const stubs = vi.hoisted(() => ({
32
+ listedOrg: undefined as string | null | undefined,
33
+ apps: [] as OAuthApp[],
34
+ allowed: new Set<string>(),
35
+ checked: [] as Array<[string, string, string]>,
36
+ }));
37
+
38
+ vi.mock("../../organization/OrgProvider.js", () => ({
39
+ useActiveOrgSlug: () => "acme",
40
+ useActiveOrgId: () => "org_acme",
41
+ }));
42
+ vi.mock("../../oauth-app/useOAuthAppList.js", () => ({
43
+ useOAuthAppList: (org: string | null) => {
44
+ stubs.listedOrg = org;
45
+ return {
46
+ oauthApps: stubs.apps,
47
+ isLoading: false,
48
+ isRefetching: false,
49
+ error: null,
50
+ refetch: () => {},
51
+ };
52
+ },
53
+ }));
54
+ vi.mock("../../iam-policy/useCheckPermission.js", () => ({
55
+ useCheckPermission: (
56
+ resource: { kind: string; id: string } | null,
57
+ relation: string,
58
+ ) => {
59
+ if (resource !== null) {
60
+ stubs.checked.push([resource.kind, resource.id, relation]);
61
+ }
62
+ return {
63
+ allowed: resource === null ? true : stubs.allowed.has(relation),
64
+ isLoading: false,
65
+ error: null,
66
+ };
67
+ },
68
+ }));
69
+
70
+ import { OAuthAppsSection } from "../OAuthAppsSection";
71
+
72
+ const SLACK = create(OAuthAppSchema, {
73
+ metadata: {
74
+ id: "oapp_slack",
75
+ name: "Slack OAuth",
76
+ slug: "slack-oauth",
77
+ org: "acme",
78
+ },
79
+ spec: { provider: "slack", clientId: "slack-client-1" },
80
+ });
81
+
82
+ function renderSection(mode: DeploymentMode = "cloud") {
83
+ return render(
84
+ <DeploymentModeContext.Provider value={mode}>
85
+ <OAuthAppsSection />
86
+ </DeploymentModeContext.Provider>,
87
+ );
88
+ }
89
+
90
+ afterEach(() => {
91
+ cleanup();
92
+ stubs.listedOrg = undefined;
93
+ stubs.apps = [];
94
+ stubs.allowed = new Set();
95
+ stubs.checked = [];
96
+ });
97
+
98
+ describe("OAuthAppsSection", () => {
99
+ it("lists the active organization's apps the caller may view", () => {
100
+ stubs.apps = [SLACK];
101
+ renderSection();
102
+ expect(stubs.listedOrg).toBe("acme");
103
+ expect(screen.getByText("slack-client-1")).toBeTruthy();
104
+ });
105
+
106
+ it("offers New OAuth app only with can_create_oauth_app on the organization", () => {
107
+ renderSection();
108
+ expect(screen.queryByRole("button", { name: /New OAuth app/ })).toBeNull();
109
+ expect(stubs.checked).toContainEqual([
110
+ "organization",
111
+ "org_acme",
112
+ "can_create_oauth_app",
113
+ ]);
114
+
115
+ cleanup();
116
+ stubs.allowed = new Set(["can_create_oauth_app"]);
117
+ renderSection();
118
+ expect(screen.getByRole("button", { name: /New OAuth app/ })).toBeTruthy();
119
+ });
120
+
121
+ it("names the organization's admins, not an empty configuration, to a caller who may not create OAuth apps", () => {
122
+ renderSection();
123
+ expect(
124
+ screen.getByText("OAuth apps are managed by your organization's admins."),
125
+ ).toBeTruthy();
126
+ expect(screen.queryByText("No OAuth apps configured yet.")).toBeNull();
127
+
128
+ cleanup();
129
+ stubs.allowed = new Set(["can_create_oauth_app"]);
130
+ renderSection();
131
+ expect(screen.getByText("No OAuth apps configured yet.")).toBeTruthy();
132
+ });
133
+ });