Skip to content

feat(management): add enforceSSOExclusions to tenant create and update - #775

Open
hagaikali wants to merge 3 commits into
descope:mainfrom
hagaikali:feat/tenant-enforce-sso-exclusions
Open

feat(management): add enforceSSOExclusions to tenant create and update#775
hagaikali wants to merge 3 commits into
descope:mainfrom
hagaikali:feat/tenant-enforce-sso-exclusions

Conversation

@hagaikali

Copy link
Copy Markdown

The /v1/mgmt/tenant/create and /v1/mgmt/tenant/update endpoints accept enforceSSOExclusions and the Go SDK sends it on every write, but the Node SDK had no way to supply it. Since tenant update is a full replace, any Node SDK tenant write silently cleared an enforceSSOExclusions list set from the console or another SDK.

Also adds enforceSSOExclusions and roleInheritance to the Tenant read type; both are returned by GET /v1/mgmt/tenant but were missing, which made roleInheritance write-only and unpreservable in a read-modify-write.

Related Issues

No Issue submitted for it.
Noticed during day-to-day working and submitted a PR.

Description

management.tenant.create, createWithId, and update had no way to send
enforceSSOExclusions, even though the endpoints they POST to accept it. Because tenant
update is a full replace, this additionally made every Node SDK tenant write silently
erase an exclusions list configured from the console or another SDK.

This appends enforceSSOExclusions?: string[] as the last parameter of all three
methods and sends it in the request body. With this change, the Node SDK's tenant
create/update request surface matches the Go SDK's field for field.

Must

  • Tests — extended the create, createWithId, and update blocks in
    lib/management/tenant.test.ts to pass the new argument and assert it in the expected
    POST body. The existing parent-tenant test variants were intentionally left without the
    new argument, so they continue to cover the omitted case. Full suite: 451/451 passing,
    coverage above the configured thresholds (statements 97.89%, functions 98.41%,
    lines 98.91% against a 97% gate).
  • Documentation (if applicable) — README tenant create and update examples now show
    enforceSSOExclusions, plus an explicit warning that fields omitted from update are
    cleared.

The /v1/mgmt/tenant/create and /v1/mgmt/tenant/update endpoints accept
enforceSSOExclusions and the Go SDK sends it on every write, but the Node SDK
had no way to supply it. Since tenant update is a full replace, any Node SDK
tenant write silently cleared an enforceSSOExclusions list set from the console
or another SDK.

Also adds enforceSSOExclusions and roleInheritance to the Tenant read type;
both are returned by GET /v1/mgmt/tenant but were missing, which made
roleInheritance write-only and unpreservable in a read-modify-write.
@shuni-bot

shuni-bot Bot commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

🐕 Review complete — View session on Shuni Portal 🐾

@shuni-bot

shuni-bot Bot commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

🐕 Suggested Reviewers

The review assignment balances breadth of coverage across core implementation, testing, and documentation, leveraging contributors with deep and focused experience on tenant management for an efficient and comprehensive review process.

Reviewer Reason
dorsha Dorsha has the most commits, covering multiple files such as README.md, tenant.test.ts, and tenant.ts, indicating broad familiarity with the codebase and thorough understanding of the management modules.
aviadl Aviadl has several commits across key files, providing insight into both the documentation and core functionality, making them well-suited for review.
talaharoni Talaharoni's contributions focus on README.md and types.ts, offering valuable perspective on type definitions and documentation which are crucial for correctness and clarity.
ruvenzx Ruvenzx has worked on tenant.test.ts and tenant.ts, giving them specific experience with tenant management logic and testing, relevant for assessing new feature integration.
itaihanski Itaihanski's commits also cover tenant-related files, suggesting familiarity with tenant management flows and potential impact points for the new features.

Suggested by Shuni based on git history and PR context. Names are not @-mentioned to avoid notifying anyone — request a review from whoever fits best.

@hagaikali

Copy link
Copy Markdown
Author

@dorsha @itaihanski
Requesting review, tenant mgmt related.

@shuni-bot shuni-bot Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🐕 Shuni's Review

Threads an optional enforceSSOExclusions?: string[] through tenant create/createWithId/update and adds enforceSSOExclusions + roleInheritance to the read-side Tenant type.

The code is clean — I checked every positional slot in all three signatures against the README examples and the test call sites, and they line up exactly. Appending the param last keeps existing callers source-compatible. All findings below are in the README.

Sniffed out 4 issues:

  • 1 🟡 MEDIUM: enforceSSOExclusions label says "user IDs" but the example passes an email
  • 3 🟢 LOW: stale createWithId example, overbroad omit-warning, hardcoded enforceSSO: true in copy-paste examples

See inline comments. Good bones! Woof!

Comment thread README.md Outdated
false, // disabled
'', // parent tenant ID
'none', // roleInheritance
['admin@domain.com'], // enforceSSOExclusions - user IDs excluded from SSO enforcement

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟡 MEDIUM: The label says user IDs, but the value is a login ID (admin@domain.com). This README treats those as distinct elsewhere (e.g. the batch-delete example explicitly calls for Descope user IDs like U2abc...).

Since the SDK does no client-side validation, whichever one is wrong produces a request that succeeds but silently doesn't match the intended user — the admin stays SSO-enforced with no error surfaced. Worth confirming against the API and making the label and the value agree (same on line 644).

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

handled

Comment thread README.md Outdated
);

// You can optionally set your own ID when creating a tenant
await descopeClient.management.tenant.createWithId('my-custom-id', 'My Tenant', ['domain.com'], {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟢 LOW: createWithId takes the same enforceSSO/disabled/parent/roleInheritance/enforceSSOExclusions args, but this example was left at 4 args while create and update were expanded.

Reads like the new field isn't available on this path, which would push users toward create-then-update — exactly the full-replace call the note two lines below warns about.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

handled

Comment thread README.md Outdated
});

// Update will override all fields as is. Use carefully.
// Any field you omit is cleared on the tenant, so read the tenant first and pass

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟢 LOW: "Any field you omit is cleared ... read the tenant first and pass back the values you want to keep" is broader than update actually is.

update has no parent parameter and never sends defaultRoles, and the Tenant read type has no parent field — so those two can't be "passed back" and aren't at risk. Scoping the sentence to update's own parameters avoids implying a read-modify-write is needed to protect them.

Comment thread README.md
'My Tenant',
['domain.com', 'another-domain.com'],
{ customAttributeName: 'val' },
true, // enforceSSO

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟢 LOW: This example hardcodes enforceSSO: true on the call the note above describes as a full replace. true is the coherent value for demonstrating exclusions, so I wouldn't flip it — but the existing warning only covers omitted fields, not the values the snippet hands you. Someone copy-pasting this to rename a tenant turns SSO enforcement on. A short // existing value — read it back before copying style caution would close that gap (same on line 621).

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

handled

Use the README's user-ID placeholder instead of an email for
enforceSSOExclusions, expand the createWithId example to show the same
optional arguments, scope the full-replace warning to the parameters update
actually takes, and note that the sample values are illustrative rather than
defaults.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant