@descope/node-sdk
Advanced tools
Comparing version 0.0.0-next-502d6795-20230212 to 0.0.0-next-5099c5a3-20241213
@@ -1,2 +0,2 @@ | ||
"use strict";var e=require("tslib"),t=require("@descope/core-js-sdk"),s=require("jose"),a=require("node-fetch");function n(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}var o=n(t),r=n(a);const i=t=>async(...s)=>{var a,n,o;const r=await t(...s);if(!r.data)return r;let i=r.data,{refreshJwt:l}=i,d=e.__rest(i,["refreshJwt"]);const p=[];var m;return l?p.push(`${"DSR"}=${l}; Domain=${(null==(m=d)?void 0:m.cookieDomain)||""}; Max-Age=${(null==m?void 0:m.cookieMaxAge)||""}; Path=${(null==m?void 0:m.cookiePath)||"/"}; HttpOnly; SameSite=Strict`):(null===(a=r.response)||void 0===a?void 0:a.headers.get("set-cookie"))&&(l=((e,t)=>{const s=null==e?void 0:e.match(RegExp(`(?:^|;\\s*)${t}=([^;]*)`));return s?s[1]:null})(null===(n=r.response)||void 0===n?void 0:n.headers.get("set-cookie"),"DSR"),p.push(null===(o=r.response)||void 0===o?void 0:o.headers.get("set-cookie"))),Object.assign(Object.assign({},r),{data:Object.assign(Object.assign({},r.data),{refreshJwt:l,cookies:p})})};function l(e,t,s){var a,n;const o=s?null===(n=null===(a=e.token.tenants)||void 0===a?void 0:a[s])||void 0===n?void 0:n[t]:e.token[t];return Array.isArray(o)?o:[]}var d={create:"/v1/mgmt/user/create",update:"/v1/mgmt/user/update",delete:"/v1/mgmt/user/delete",load:"/v1/mgmt/user",search:"/v1/mgmt/user/search",updateStatus:"/v1/mgmt/user/update/status",updateEmail:"/v1/mgmt/user/update/email",updatePhone:"/v1/mgmt/user/update/phone",updateDisplayName:"/v1/mgmt/user/update/name",addRole:"/v1/mgmt/user/update/role/add",removeRole:"/v1/mgmt/user/update/role/remove",addTenant:"/v1/mgmt/user/update/tenant/add",removeTenant:"/v1/mgmt/user/update/tenant/remove"},p={create:"/v1/mgmt/accesskey/create",load:"/v1/mgmt/accesskey",search:"/v1/mgmt/accesskey/search",update:"/v1/mgmt/accesskey/update",deactivate:"/v1/mgmt/accesskey/deactivate",activate:"/v1/mgmt/accesskey/activate",delete:"/v1/mgmt/accesskey/delete"},m={create:"/v1/mgmt/tenant/create",update:"/v1/mgmt/tenant/update",delete:"/v1/mgmt/tenant/delete",loadAll:"/v1/mgmt/tenant/all"},c={configure:"/v1/mgmt/sso/settings",metadata:"/v1/mgmt/sso/metadata",mapping:"/v1/mgmt/sso/mapping"},u={update:"/v1/mgmt/jwt/update"},g={create:"/v1/mgmt/permission/create",update:"/v1/mgmt/permission/update",delete:"/v1/mgmt/permission/delete",loadAll:"/v1/mgmt/permission/all"},h={create:"/v1/mgmt/role/create",update:"/v1/mgmt/role/update",delete:"/v1/mgmt/role/delete",loadAll:"/v1/mgmt/role/all"},v={loadAllGroups:"/v1/mgmt/group/all",loadAllGroupsForMember:"/v1/mgmt/group/member/all",loadAllGroupMembers:"/v1/mgmt/group/members"};const f=(e,s)=>({create:(a,n,o,r,i,l)=>t.transformResponse(e.httpClient.post(d.create,{loginId:a,email:n,phone:o,displayName:r,roleNames:i,userTenants:l},{token:s}),(e=>e.user)),update:(a,n,o,r,i,l)=>t.transformResponse(e.httpClient.post(d.update,{loginId:a,email:n,phone:o,displayName:r,roleNames:i,userTenants:l},{token:s}),(e=>e.user)),delete:a=>t.transformResponse(e.httpClient.post(d.delete,{loginId:a},{token:s})),load:a=>t.transformResponse(e.httpClient.get(d.load,{queryParams:{loginId:a},token:s}),(e=>e.user)),loadByUserId:a=>t.transformResponse(e.httpClient.get(d.load,{queryParams:{userId:a},token:s}),(e=>e.user)),searchAll:(a,n,o)=>t.transformResponse(e.httpClient.post(d.search,{tenantIds:a,roleNames:n,limit:o},{token:s}),(e=>e.users)),activate:a=>t.transformResponse(e.httpClient.post(d.updateStatus,{loginId:a,status:"enabled"},{token:s}),(e=>e.user)),deactivate:a=>t.transformResponse(e.httpClient.post(d.updateStatus,{loginId:a,status:"disabled"},{token:s}),(e=>e.user)),updateEmail:(a,n,o)=>t.transformResponse(e.httpClient.post(d.updateEmail,{loginId:a,email:n,verified:o},{token:s}),(e=>e.user)),updatePhone:(a,n,o)=>t.transformResponse(e.httpClient.post(d.updatePhone,{loginId:a,phone:n,verified:o},{token:s}),(e=>e.user)),updateDisplayName:(a,n)=>t.transformResponse(e.httpClient.post(d.updateDisplayName,{loginId:a,displayName:n},{token:s}),(e=>e.user)),addRoles:(a,n)=>t.transformResponse(e.httpClient.post(d.addRole,{loginId:a,roleNames:n},{token:s}),(e=>e.user)),removeRoles:(a,n)=>t.transformResponse(e.httpClient.post(d.removeRole,{loginId:a,roleNames:n},{token:s}),(e=>e.user)),addTenant:(a,n)=>t.transformResponse(e.httpClient.post(d.addTenant,{loginId:a,tenantId:n},{token:s}),(e=>e.user)),removeTenant:(a,n)=>t.transformResponse(e.httpClient.post(d.removeTenant,{loginId:a,tenantId:n},{token:s}),(e=>e.user)),addTenantRoles:(a,n,o)=>t.transformResponse(e.httpClient.post(d.addRole,{loginId:a,tenantId:n,roleNames:o},{token:s}),(e=>e.user)),removeTenantRoles:(a,n,o)=>t.transformResponse(e.httpClient.post(d.removeRole,{loginId:a,tenantId:n,roleNames:o},{token:s}),(e=>e.user))}),k=(e,s)=>({create:(a,n)=>t.transformResponse(e.httpClient.post(m.create,{name:a,selfProvisioningDomains:n},{token:s})),createWithId:(a,n,o)=>t.transformResponse(e.httpClient.post(m.create,{id:a,name:n,selfProvisioningDomains:o},{token:s})),update:(a,n,o)=>t.transformResponse(e.httpClient.post(m.update,{id:a,name:n,selfProvisioningDomains:o},{token:s})),delete:a=>t.transformResponse(e.httpClient.post(m.delete,{id:a},{token:s})),loadAll:()=>t.transformResponse(e.httpClient.get(m.loadAll,{token:s}),(e=>e.tenants))}),y=(e,s)=>({update:(a,n)=>t.transformResponse(e.httpClient.post(u.update,{jwt:a,customClaims:n},{token:s}))}),R=(e,s)=>({create:(a,n)=>t.transformResponse(e.httpClient.post(g.create,{name:a,description:n},{token:s})),update:(a,n,o)=>t.transformResponse(e.httpClient.post(g.update,{name:a,newName:n,description:o},{token:s})),delete:a=>t.transformResponse(e.httpClient.post(g.delete,{name:a},{token:s})),loadAll:()=>t.transformResponse(e.httpClient.get(g.loadAll,{token:s}),(e=>e.permissions))}),C=(e,s)=>({create:(a,n,o)=>t.transformResponse(e.httpClient.post(h.create,{name:a,description:n,permissionNames:o},{token:s})),update:(a,n,o,r)=>t.transformResponse(e.httpClient.post(h.update,{name:a,newName:n,description:o,permissionNames:r},{token:s})),delete:a=>t.transformResponse(e.httpClient.post(h.delete,{name:a},{token:s})),loadAll:()=>t.transformResponse(e.httpClient.get(h.loadAll,{token:s}),(e=>e.roles))}),w=(e,s)=>({loadAllGroups:a=>t.transformResponse(e.httpClient.post(v.loadAllGroups,{tenantId:a},{token:s})),loadAllGroupsForMember:(a,n,o)=>t.transformResponse(e.httpClient.post(v.loadAllGroupsForMember,{tenantId:a,loginIds:o,userIds:n},{token:s})),loadAllGroupMembers:(a,n)=>t.transformResponse(e.httpClient.post(v.loadAllGroupMembers,{tenantId:a,groupId:n},{token:s}))}),b=(e,s)=>({configureSettings:(a,n,o,r,i)=>t.transformResponse(e.httpClient.post(c.configure,{tenantId:a,idpURL:n,entityId:r,idpCert:o,redirectURL:i},{token:s})),configureMetadata:(a,n)=>t.transformResponse(e.httpClient.post(c.metadata,{tenantId:a,idpMetadataURL:n},{token:s})),configureMapping:(a,n,o)=>t.transformResponse(e.httpClient.post(c.mapping,{tenantId:a,roleMapping:n,attributeMapping:o},{token:s}))}),I=(e,s)=>({create:(a,n,o,r)=>t.transformResponse(e.httpClient.post(p.create,{name:a,expireTime:n,roleNames:o,keyTenants:r},{token:s})),load:a=>t.transformResponse(e.httpClient.get(p.load,{queryParams:{id:a},token:s}),(e=>e.key)),searchAll:a=>t.transformResponse(e.httpClient.post(p.search,{tenantIds:a},{token:s}),(e=>e.keys)),update:(a,n)=>t.transformResponse(e.httpClient.post(p.update,{id:a,name:n},{token:s}),(e=>e.key)),deactivate:a=>t.transformResponse(e.httpClient.post(p.deactivate,{id:a},{token:s})),activate:a=>t.transformResponse(e.httpClient.post(p.activate,{id:a},{token:s})),delete:a=>t.transformResponse(e.httpClient.post(p.delete,{id:a},{token:s}))});globalThis.fetch=r.default,globalThis.Headers=a.Headers,globalThis.Request=a.Request,globalThis.Response=a.Response;const A=a=>{var n,{managementKey:r}=a,d=e.__rest(a,["managementKey"]);const p=o.default(Object.assign(Object.assign({},d),{baseHeaders:Object.assign(Object.assign({},d.baseHeaders),{"x-descope-sdk-name":"nodejs","x-descope-sdk-node-version":(null===(n=null===process||void 0===process?void 0:process.versions)||void 0===n?void 0:n.node)||"","x-descope-sdk-version":"0.0.0-next-502d6795-20230212"})})),{projectId:m,logger:c}=d,u={},g=((e,t)=>({user:f(e,t),accessKey:I(e,t),tenant:k(e,t),sso:b(e,t),jwt:y(e,t),permission:R(e,t),role:C(e,t),group:w(e,t)}))(p,r),h=Object.assign(Object.assign({},p),{management:g,async getKey(e){if(!(null==e?void 0:e.kid))throw Error("header.kid must not be empty");if(u[e.kid])return u[e.kid];if(Object.assign(u,await(async()=>{const e=(await p.httpClient.get(`v2/keys/${m}`).then((e=>e.json()))).keys;return Array.isArray(e)?(await Promise.all(e.map((async e=>[e.kid,await s.importJWK(e)])))).reduce(((e,[t,s])=>t?Object.assign(Object.assign({},e),{[t.toString()]:s}):e),{}):{}})()),!u[e.kid])throw Error("failed to fetch matching key");return u[e.kid]},async validateJwt(e){var t;const a=(await s.jwtVerify(e,h.getKey,{clockTolerance:5})).payload;if(a&&(a.iss=null===(t=a.iss)||void 0===t?void 0:t.split("/").pop(),a.iss!==m))throw new s.errors.JWTClaimValidationFailed('unexpected "iss" claim value',"iss","check_failed");return{jwt:e,token:a}},async validateSession(e){if(!e)throw Error("session token is required for validation");try{return await h.validateJwt(e)}catch(e){throw null==c||c.error("session validation failed",e),Error("session validation failed")}},async refreshSession(e){var t,s;if(!e)throw Error("refresh token is required to refresh a session");try{await h.validateJwt(e);const a=await h.refresh(e);if(a.ok){return await h.validateJwt(null===(t=a.data)||void 0===t?void 0:t.sessionJwt)}throw Error(null===(s=a.error)||void 0===s?void 0:s.errorMessage)}catch(e){throw null==c||c.error("refresh token validation failed",e),Error("refresh token validation failed")}},async validateAndRefreshSession(e,t){if(!e&&!t)throw Error("both session and refresh tokens are empty");try{return await h.validateSession(e)}catch(e){null==c||c.log("session validation failed - trying to refresh it")}return h.refreshSession(t)},async exchangeAccessKey(e){if(!e)throw Error("access key must not be empty");let t;try{t=await h.accessKey.exchange(e)}catch(e){throw null==c||c.error("failed to exchange access key",e),Error("could not exchange access key")}const{sessionJwt:s}=t.data;if(!s)throw null==c||c.error("failed to parse exchange access key response"),Error("could not exchange access key");try{return await h.validateJwt(s)}catch(e){throw null==c||c.error("failed to parse jwt from access key",e),Error("could not exchange access key")}},validatePermissions:(e,t)=>h.validateTenantPermissions(e,null,t),validateTenantPermissions(e,t,s){const a=l(e,"permissions",t);return s.every((e=>a.includes(e)))},validateRoles:(e,t)=>h.validateTenantRoles(e,null,t),validateTenantRoles(e,t,s){const a=l(e,"roles",t);return s.every((e=>a.includes(e)))}});return t.wrapWith(h,["otp.verify.email","otp.verify.sms","otp.verify.whatsapp","magicLink.verify","enchantedLink.signUp","enchantedLink.signIn","oauth.exchange","saml.exchange","totp.verify","webauthn.signIn.finish","webauthn.signUp.finish","refresh"],i)};A.RefreshTokenCookieName="DSR",A.SessionTokenCookieName="DS",module.exports=A; | ||
"use strict";Object.defineProperty(exports,"__esModule",{value:!0});var e=require("tslib"),t=require("@descope/core-js-sdk"),s=require("jose"),n=require("cross-fetch");function o(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}var a=o(t);var r;null!==(r=globalThis.Headers)&&void 0!==r||(globalThis.Headers=n.Headers);const i=(...e)=>(e.forEach((e=>{var t,s;e&&"object"==typeof e&&(null!==(t=(s=e).highWaterMark)&&void 0!==t||(s.highWaterMark=31457280))})),n.fetch(...e)),p=t=>async(...s)=>{var n,o,a;const r=await t(...s);if(!r.data)return r;let i=r.data,{refreshJwt:p}=i,l=e.__rest(i,["refreshJwt"]);const m=[];var d;return p?m.push(`${"DSR"}=${p}; Domain=${(null==(d=l)?void 0:d.cookieDomain)||""}; Max-Age=${(null==d?void 0:d.cookieMaxAge)||""}; Path=${(null==d?void 0:d.cookiePath)||"/"}; HttpOnly; SameSite=Strict`):(null===(n=r.response)||void 0===n?void 0:n.headers.get("set-cookie"))&&(p=((e,t)=>{const s=null==e?void 0:e.match(RegExp(`(?:^|;\\s*)${t}=([^;]*)`));return s?s[1]:null})(null===(o=r.response)||void 0===o?void 0:o.headers.get("set-cookie"),"DSR"),m.push(null===(a=r.response)||void 0===a?void 0:a.headers.get("set-cookie"))),Object.assign(Object.assign({},r),{data:Object.assign(Object.assign({},r.data),{refreshJwt:p,cookies:m})})};function l(e,t,s){var n,o;const a=s?null===(o=null===(n=e.token.tenants)||void 0===n?void 0:n[s])||void 0===o?void 0:o[t]:e.token[t];return Array.isArray(a)?a:[]}function m(e,t){var s;return!!(null===(s=e.token.tenants)||void 0===s?void 0:s[t])}var d={create:"/v1/mgmt/user/create",createTestUser:"/v1/mgmt/user/create/test",createBatch:"/v1/mgmt/user/create/batch",update:"/v1/mgmt/user/update",patch:"/v1/mgmt/user/patch",delete:"/v1/mgmt/user/delete",deleteAllTestUsers:"/v1/mgmt/user/test/delete/all",load:"/v1/mgmt/user",logout:"/v1/mgmt/user/logout",search:"/v2/mgmt/user/search",searchTestUsers:"/v2/mgmt/user/search/test",getProviderToken:"/v1/mgmt/user/provider/token",updateStatus:"/v1/mgmt/user/update/status",updateLoginId:"/v1/mgmt/user/update/loginid",updateEmail:"/v1/mgmt/user/update/email",updatePhone:"/v1/mgmt/user/update/phone",updateDisplayName:"/v1/mgmt/user/update/name",updatePicture:"/v1/mgmt/user/update/picture",updateCustomAttribute:"/v1/mgmt/user/update/customAttribute",setRole:"/v1/mgmt/user/update/role/set",addRole:"/v2/mgmt/user/update/role/add",removeRole:"/v1/mgmt/user/update/role/remove",setSSOApps:"/v1/mgmt/user/update/ssoapp/set",addSSOApps:"/v1/mgmt/user/update/ssoapp/add",removeSSOApps:"/v1/mgmt/user/update/ssoapp/remove",addTenant:"/v1/mgmt/user/update/tenant/add",removeTenant:"/v1/mgmt/user/update/tenant/remove",setPassword:"/v1/mgmt/user/password/set",setTemporaryPassword:"/v1/mgmt/user/password/set/temporary",setActivePassword:"/v1/mgmt/user/password/set/active",expirePassword:"/v1/mgmt/user/password/expire",removeAllPasskeys:"/v1/mgmt/user/passkeys/delete",generateOTPForTest:"/v1/mgmt/tests/generate/otp",generateMagicLinkForTest:"/v1/mgmt/tests/generate/magiclink",generateEnchantedLinkForTest:"/v1/mgmt/tests/generate/enchantedlink",generateEmbeddedLink:"/v1/mgmt/user/signin/embeddedlink",history:"/v1/mgmt/user/history"},c={updateName:"/v1/mgmt/project/update/name",updateTags:"/v1/mgmt/project/update/tags",clone:"/v1/mgmt/project/clone",projectsList:"/v1/mgmt/projects/list",exportSnapshot:"/v1/mgmt/project/snapshot/export",importSnapshot:"/v1/mgmt/project/snapshot/import",validateSnapshot:"/v1/mgmt/project/snapshot/validate"},g={create:"/v1/mgmt/accesskey/create",load:"/v1/mgmt/accesskey",search:"/v1/mgmt/accesskey/search",update:"/v1/mgmt/accesskey/update",deactivate:"/v1/mgmt/accesskey/deactivate",activate:"/v1/mgmt/accesskey/activate",delete:"/v1/mgmt/accesskey/delete"},u={create:"/v1/mgmt/tenant/create",update:"/v1/mgmt/tenant/update",delete:"/v1/mgmt/tenant/delete",load:"/v1/mgmt/tenant",settings:"/v1/mgmt/tenant/settings",loadAll:"/v1/mgmt/tenant/all",searchAll:"/v1/mgmt/tenant/search",generateSSOConfigurationLink:"/v1/mgmt/tenant/adminlinks/sso/generate"},h={oidcCreate:"/v1/mgmt/sso/idp/app/oidc/create",samlCreate:"/v1/mgmt/sso/idp/app/saml/create",oidcUpdate:"/v1/mgmt/sso/idp/app/oidc/update",samlUpdate:"/v1/mgmt/sso/idp/app/saml/update",delete:"/v1/mgmt/sso/idp/app/delete",load:"/v1/mgmt/sso/idp/app/load",loadAll:"/v1/mgmt/sso/idp/apps/load"},v={settings:"/v1/mgmt/sso/settings",metadata:"/v1/mgmt/sso/metadata",mapping:"/v1/mgmt/sso/mapping",settingsv2:"/v2/mgmt/sso/settings",oidc:{configure:"/v1/mgmt/sso/oidc"},saml:{configure:"/v1/mgmt/sso/saml",metadata:"/v1/mgmt/sso/saml/metadata"}},f={update:"/v1/mgmt/jwt/update",impersonate:"/v1/mgmt/impersonate"},k={settings:"/v1/mgmt/password/settings"},R={create:"/v1/mgmt/permission/create",update:"/v1/mgmt/permission/update",delete:"/v1/mgmt/permission/delete",loadAll:"/v1/mgmt/permission/all"},C={create:"/v1/mgmt/role/create",update:"/v1/mgmt/role/update",delete:"/v1/mgmt/role/delete",loadAll:"/v1/mgmt/role/all",search:"/v1/mgmt/role/search"},y={list:"/v1/mgmt/flow/list",delete:"/v1/mgmt/flow/delete",export:"/v1/mgmt/flow/export",import:"/v1/mgmt/flow/import"},I={export:"/v1/mgmt/theme/export",import:"/v1/mgmt/theme/import"},b={loadAllGroups:"/v1/mgmt/group/all",loadAllGroupsForMember:"/v1/mgmt/group/member/all",loadAllGroupMembers:"/v1/mgmt/group/members"},w={search:"/v1/mgmt/audit/search",createEvent:"/v1/mgmt/audit/event"},A={schemaSave:"/v1/mgmt/authz/schema/save",schemaDelete:"/v1/mgmt/authz/schema/delete",schemaLoad:"/v1/mgmt/authz/schema/load",nsSave:"/v1/mgmt/authz/ns/save",nsDelete:"/v1/mgmt/authz/ns/delete",rdSave:"/v1/mgmt/authz/rd/save",rdDelete:"/v1/mgmt/authz/rd/delete",reCreate:"/v1/mgmt/authz/re/create",reDelete:"/v1/mgmt/authz/re/delete",reDeleteResources:"/v1/mgmt/authz/re/deleteresources",hasRelations:"/v1/mgmt/authz/re/has",who:"/v1/mgmt/authz/re/who",resource:"/v1/mgmt/authz/re/resource",targets:"/v1/mgmt/authz/re/targets",targetAll:"/v1/mgmt/authz/re/targetall",getModified:"/v1/mgmt/authz/getmodified"},S={schema:"/v1/mgmt/fga/schema",relations:"/v1/mgmt/fga/relations",deleteRelations:"/v1/mgmt/fga/relations/delete",check:"/v1/mgmt/fga/check"};const N=(e,s)=>({create:function(n,o,a,r,i,p,l,m,c,g,u,h,v,f){const k="string"==typeof o?{loginId:n,email:o,phone:a,displayName:r,givenName:u,middleName:h,familyName:v,roleNames:i,userTenants:p,customAttributes:l,picture:m,verifiedEmail:c,verifiedPhone:g,additionalLoginIds:f}:Object.assign(Object.assign({loginId:n},o),{roleNames:null==o?void 0:o.roles,roles:void 0});return t.transformResponse(e.httpClient.post(d.create,k,{token:s}),(e=>e.user))},createTestUser:function(n,o,a,r,i,p,l,m,c,g,u,h,v,f){const k="string"==typeof o?{loginId:n,email:o,phone:a,displayName:r,givenName:u,middleName:h,familyName:v,roleNames:i,userTenants:p,customAttributes:l,picture:m,verifiedEmail:c,verifiedPhone:g,additionalLoginIds:f,test:!0}:Object.assign(Object.assign({loginId:n},o),{roleNames:null==o?void 0:o.roles,roles:void 0,test:!0});return t.transformResponse(e.httpClient.post(d.createTestUser,k,{token:s}),(e=>e.user))},invite:function(n,o,a,r,i,p,l,m,c,g,u,h,v,f,k,R,C,y){const I="string"==typeof o?{loginId:n,email:o,phone:a,displayName:r,givenName:f,middleName:k,familyName:R,roleNames:i,userTenants:p,invite:!0,customAttributes:l,picture:m,verifiedEmail:c,verifiedPhone:g,inviteUrl:u,sendMail:h,sendSMS:v,additionalLoginIds:C,templateId:y}:Object.assign(Object.assign({loginId:n},o),{roleNames:null==o?void 0:o.roles,roles:void 0,invite:!0});return t.transformResponse(e.httpClient.post(d.create,I,{token:s}),(e=>e.user))},inviteBatch:(n,o,a,r,i,p)=>t.transformResponse(e.httpClient.post(d.createBatch,{users:n.map((e=>{const t=Object.assign(Object.assign({},e),{roleNames:e.roles});return delete t.roles,t})),invite:!0,inviteUrl:o,sendMail:a,sendSMS:r,templateOptions:i,templateId:p},{token:s}),(e=>e)),update:function(n,o,a,r,i,p,l,m,c,g,u,h,v,f){const k="string"==typeof o?{loginId:n,email:o,phone:a,displayName:r,givenName:u,middleName:h,familyName:v,roleNames:i,userTenants:p,customAttributes:l,picture:m,verifiedEmail:c,verifiedPhone:g,additionalLoginIds:f}:Object.assign(Object.assign({loginId:n},o),{roleNames:null==o?void 0:o.roles,roles:void 0});return t.transformResponse(e.httpClient.post(d.update,k,{token:s}),(e=>e.user))},patch:function(n,o){const a={loginId:n};return void 0!==o.email&&(a.email=o.email),void 0!==o.phone&&(a.phone=o.phone),void 0!==o.displayName&&(a.displayName=o.displayName),void 0!==o.givenName&&(a.givenName=o.givenName),void 0!==o.middleName&&(a.middleName=o.middleName),void 0!==o.familyName&&(a.familyName=o.familyName),void 0!==o.roles&&(a.roleNames=o.roles),void 0!==o.userTenants&&(a.userTenants=o.userTenants),void 0!==o.customAttributes&&(a.customAttributes=o.customAttributes),void 0!==o.picture&&(a.picture=o.picture),void 0!==o.verifiedEmail&&(a.verifiedEmail=o.verifiedEmail),void 0!==o.verifiedPhone&&(a.verifiedPhone=o.verifiedPhone),void 0!==o.ssoAppIds&&(a.ssoAppIds=o.ssoAppIds),t.transformResponse(e.httpClient.patch(d.patch,a,{token:s}),(e=>e.user))},delete:n=>t.transformResponse(e.httpClient.post(d.delete,{loginId:n},{token:s})),deleteByUserId:n=>t.transformResponse(e.httpClient.post(d.delete,{userId:n},{token:s})),deleteAllTestUsers:()=>t.transformResponse(e.httpClient.delete(d.deleteAllTestUsers,{token:s})),load:n=>t.transformResponse(e.httpClient.get(d.load,{queryParams:{loginId:n},token:s}),(e=>e.user)),loadByUserId:n=>t.transformResponse(e.httpClient.get(d.load,{queryParams:{userId:n},token:s}),(e=>e.user)),logoutUser:n=>t.transformResponse(e.httpClient.post(d.logout,{loginId:n},{token:s})),logoutUserByUserId:n=>t.transformResponse(e.httpClient.post(d.logout,{userId:n},{token:s})),searchAll:(n,o,a,r,i,p,l,m,c,g)=>t.transformResponse(e.httpClient.post(d.search,{tenantIds:n,roleNames:o,limit:a,page:r,testUsersOnly:i,withTestUser:p,customAttributes:l,statuses:m,emails:c,phones:g},{token:s}),(e=>e.users)),searchTestUsers:n=>t.transformResponse(e.httpClient.post(d.searchTestUsers,Object.assign(Object.assign({},n),{withTestUser:!0,testUsersOnly:!0,roleNames:n.roles,roles:void 0}),{token:s}),(e=>e.users)),search:n=>t.transformResponse(e.httpClient.post(d.search,Object.assign(Object.assign({},n),{roleNames:n.roles,roles:void 0}),{token:s}),(e=>e.users)),getProviderToken:(n,o,a)=>t.transformResponse(e.httpClient.get(d.getProviderToken,{queryParams:{loginId:n,provider:o,withRefreshToken:(null==a?void 0:a.withRefreshToken)?"true":"false",forceRefresh:(null==a?void 0:a.forceRefresh)?"true":"false"},token:s}),(e=>e)),activate:n=>t.transformResponse(e.httpClient.post(d.updateStatus,{loginId:n,status:"enabled"},{token:s}),(e=>e.user)),deactivate:n=>t.transformResponse(e.httpClient.post(d.updateStatus,{loginId:n,status:"disabled"},{token:s}),(e=>e.user)),updateLoginId:(n,o)=>t.transformResponse(e.httpClient.post(d.updateLoginId,{loginId:n,newLoginId:o},{token:s}),(e=>e.user)),updateEmail:(n,o,a)=>t.transformResponse(e.httpClient.post(d.updateEmail,{loginId:n,email:o,verified:a},{token:s}),(e=>e.user)),updatePhone:(n,o,a)=>t.transformResponse(e.httpClient.post(d.updatePhone,{loginId:n,phone:o,verified:a},{token:s}),(e=>e.user)),updateDisplayName:(n,o,a,r,i)=>t.transformResponse(e.httpClient.post(d.updateDisplayName,{loginId:n,displayName:o,givenName:a,middleName:r,familyName:i},{token:s}),(e=>e.user)),updatePicture:(n,o)=>t.transformResponse(e.httpClient.post(d.updatePicture,{loginId:n,picture:o},{token:s}),(e=>e.user)),updateCustomAttribute:(n,o,a)=>t.transformResponse(e.httpClient.post(d.updateCustomAttribute,{loginId:n,attributeKey:o,attributeValue:a},{token:s}),(e=>e.user)),setRoles:(n,o)=>t.transformResponse(e.httpClient.post(d.setRole,{loginId:n,roleNames:o},{token:s}),(e=>e.user)),addRoles:(n,o)=>t.transformResponse(e.httpClient.post(d.addRole,{loginId:n,roleNames:o},{token:s}),(e=>e.user)),removeRoles:(n,o)=>t.transformResponse(e.httpClient.post(d.removeRole,{loginId:n,roleNames:o},{token:s}),(e=>e.user)),addTenant:(n,o)=>t.transformResponse(e.httpClient.post(d.addTenant,{loginId:n,tenantId:o},{token:s}),(e=>e.user)),removeTenant:(n,o)=>t.transformResponse(e.httpClient.post(d.removeTenant,{loginId:n,tenantId:o},{token:s}),(e=>e.user)),setTenantRoles:(n,o,a)=>t.transformResponse(e.httpClient.post(d.setRole,{loginId:n,tenantId:o,roleNames:a},{token:s}),(e=>e.user)),addTenantRoles:(n,o,a)=>t.transformResponse(e.httpClient.post(d.addRole,{loginId:n,tenantId:o,roleNames:a},{token:s}),(e=>e.user)),removeTenantRoles:(n,o,a)=>t.transformResponse(e.httpClient.post(d.removeRole,{loginId:n,tenantId:o,roleNames:a},{token:s}),(e=>e.user)),addSSOapps:(n,o)=>t.transformResponse(e.httpClient.post(d.addSSOApps,{loginId:n,ssoAppIds:o},{token:s}),(e=>e.user)),setSSOapps:(n,o)=>t.transformResponse(e.httpClient.post(d.setSSOApps,{loginId:n,ssoAppIds:o},{token:s}),(e=>e.user)),removeSSOapps:(n,o)=>t.transformResponse(e.httpClient.post(d.removeSSOApps,{loginId:n,ssoAppIds:o},{token:s}),(e=>e.user)),generateOTPForTestUser:(n,o,a)=>t.transformResponse(e.httpClient.post(d.generateOTPForTest,{deliveryMethod:n,loginId:o,loginOptions:a},{token:s}),(e=>e)),generateMagicLinkForTestUser:(n,o,a,r)=>t.transformResponse(e.httpClient.post(d.generateMagicLinkForTest,{deliveryMethod:n,loginId:o,URI:a,loginOptions:r},{token:s}),(e=>e)),generateEnchantedLinkForTestUser:(n,o,a)=>t.transformResponse(e.httpClient.post(d.generateEnchantedLinkForTest,{loginId:n,URI:o,loginOptions:a},{token:s}),(e=>e)),generateEmbeddedLink:(n,o)=>t.transformResponse(e.httpClient.post(d.generateEmbeddedLink,{loginId:n,customClaims:o},{token:s}),(e=>e)),setTemporaryPassword:(n,o)=>t.transformResponse(e.httpClient.post(d.setTemporaryPassword,{loginId:n,password:o},{token:s}),(e=>e)),setActivePassword:(n,o)=>t.transformResponse(e.httpClient.post(d.setActivePassword,{loginId:n,password:o},{token:s}),(e=>e)),setPassword:(n,o)=>t.transformResponse(e.httpClient.post(d.setPassword,{loginId:n,password:o},{token:s}),(e=>e)),expirePassword:n=>t.transformResponse(e.httpClient.post(d.expirePassword,{loginId:n},{token:s}),(e=>e)),removeAllPasskeys:n=>t.transformResponse(e.httpClient.post(d.removeAllPasskeys,{loginId:n},{token:s}),(e=>e)),history:n=>t.transformResponse(e.httpClient.post(d.history,n,{token:s}),(e=>e))}),O=(e,s)=>({updateName:n=>t.transformResponse(e.httpClient.post(c.updateName,{name:n},{token:s})),updateTags:n=>t.transformResponse(e.httpClient.post(c.updateTags,{tags:n},{token:s})),clone:(n,o,a)=>t.transformResponse(e.httpClient.post(c.clone,{name:n,environment:o,tags:a},{token:s})),listProjects:async()=>t.transformResponse(e.httpClient.post(c.projectsList,{},{token:s}),(e=>e.projects.map((({id:e,name:t,environment:s,tags:n})=>({id:e,name:t,environment:s,tags:n}))))),exportSnapshot:()=>t.transformResponse(e.httpClient.post(c.exportSnapshot,{},{token:s})),importSnapshot:n=>t.transformResponse(e.httpClient.post(c.importSnapshot,n,{token:s})),validateSnapshot:n=>t.transformResponse(e.httpClient.post(c.validateSnapshot,n,{token:s})),export:()=>t.transformResponse(e.httpClient.post(c.exportSnapshot,{},{token:s}),(e=>e.files)),import:n=>t.transformResponse(e.httpClient.post(c.importSnapshot,{files:n},{token:s}))}),j=(e,s)=>({create:(n,o,a)=>t.transformResponse(e.httpClient.post(u.create,{name:n,selfProvisioningDomains:o,customAttributes:a},{token:s})),createWithId:(n,o,a,r)=>t.transformResponse(e.httpClient.post(u.create,{id:n,name:o,selfProvisioningDomains:a,customAttributes:r},{token:s})),update:(n,o,a,r)=>t.transformResponse(e.httpClient.post(u.update,{id:n,name:o,selfProvisioningDomains:a,customAttributes:r},{token:s})),delete:(n,o)=>t.transformResponse(e.httpClient.post(u.delete,{id:n,cascade:o},{token:s})),load:n=>t.transformResponse(e.httpClient.get(u.load,{queryParams:{id:n},token:s}),(e=>e)),loadAll:()=>t.transformResponse(e.httpClient.get(u.loadAll,{token:s}),(e=>e.tenants)),searchAll:(n,o,a,r)=>t.transformResponse(e.httpClient.post(u.searchAll,{tenantIds:n,tenantNames:o,tenantSelfProvisioningDomains:a,customAttributes:r},{token:s}),(e=>e.tenants)),getSettings:n=>t.transformResponse(e.httpClient.get(u.settings,{queryParams:{id:n},token:s}),(e=>e)),configureSettings:(n,o)=>t.transformResponse(e.httpClient.post(u.settings,Object.assign(Object.assign({},o),{tenantId:n}),{token:s})),generateSSOConfigurationLink:(n,o)=>t.transformResponse(e.httpClient.post(u.generateSSOConfigurationLink,{tenantId:n,expireTime:o},{token:s}),(e=>e))}),T=(e,s)=>({update:(n,o)=>t.transformResponse(e.httpClient.post(f.update,{jwt:n,customClaims:o},{token:s})),impersonate:(n,o,a)=>t.transformResponse(e.httpClient.post(f.impersonate,{impersonatorId:n,loginId:o,validateConsent:a},{token:s}))}),P=(e,s)=>({create:(n,o)=>t.transformResponse(e.httpClient.post(R.create,{name:n,description:o},{token:s})),update:(n,o,a)=>t.transformResponse(e.httpClient.post(R.update,{name:n,newName:o,description:a},{token:s})),delete:n=>t.transformResponse(e.httpClient.post(R.delete,{name:n},{token:s})),loadAll:()=>t.transformResponse(e.httpClient.get(R.loadAll,{token:s}),(e=>e.permissions))}),E=(e,s)=>({create:(n,o,a,r)=>t.transformResponse(e.httpClient.post(C.create,{name:n,description:o,permissionNames:a,tenantId:r},{token:s})),update:(n,o,a,r,i)=>t.transformResponse(e.httpClient.post(C.update,{name:n,newName:o,description:a,permissionNames:r,tenantId:i},{token:s})),delete:(n,o)=>t.transformResponse(e.httpClient.post(C.delete,{name:n,tenantId:o},{token:s})),loadAll:()=>t.transformResponse(e.httpClient.get(C.loadAll,{token:s}),(e=>e.roles)),search:n=>t.transformResponse(e.httpClient.post(C.search,n,{token:s}),(e=>e.roles))}),M=(e,s)=>({loadAllGroups:n=>t.transformResponse(e.httpClient.post(b.loadAllGroups,{tenantId:n},{token:s})),loadAllGroupsForMember:(n,o,a)=>t.transformResponse(e.httpClient.post(b.loadAllGroupsForMember,{tenantId:n,loginIds:a,userIds:o},{token:s})),loadAllGroupMembers:(n,o)=>t.transformResponse(e.httpClient.post(b.loadAllGroupMembers,{tenantId:n,groupId:o},{token:s}))}),x=(e,s)=>({getSettings:n=>t.transformResponse(e.httpClient.get(v.settings,{queryParams:{tenantId:n},token:s}),(e=>e)),deleteSettings:n=>t.transformResponse(e.httpClient.delete(v.settings,{queryParams:{tenantId:n},token:s})),configureSettings:(n,o,a,r,i,p)=>t.transformResponse(e.httpClient.post(v.settings,{tenantId:n,idpURL:o,entityId:r,idpCert:a,redirectURL:i,domains:p},{token:s})),configureMetadata:(n,o,a,r)=>t.transformResponse(e.httpClient.post(v.metadata,{tenantId:n,idpMetadataURL:o,redirectURL:a,domains:r},{token:s})),configureMapping:(n,o,a)=>t.transformResponse(e.httpClient.post(v.mapping,{tenantId:n,roleMappings:o,attributeMapping:a},{token:s})),configureOIDCSettings:(n,o,a)=>{const r=Object.assign(Object.assign({},o),{userAttrMapping:o.attributeMapping});return delete r.attributeMapping,t.transformResponse(e.httpClient.post(v.oidc.configure,{tenantId:n,settings:r,domains:a},{token:s}))},configureSAMLSettings:(n,o,a,r)=>t.transformResponse(e.httpClient.post(v.saml.configure,{tenantId:n,settings:o,redirectUrl:a,domains:r},{token:s})),configureSAMLByMetadata:(n,o,a,r)=>t.transformResponse(e.httpClient.post(v.saml.metadata,{tenantId:n,settings:o,redirectUrl:a,domains:r},{token:s})),loadSettings:n=>t.transformResponse(e.httpClient.get(v.settingsv2,{queryParams:{tenantId:n},token:s}),(e=>{var t,s;const n=e;return n.oidc&&(n.oidc=Object.assign(Object.assign({},n.oidc),{attributeMapping:n.oidc.userAttrMapping}),delete n.oidc.userAttrMapping),(null===(t=n.saml)||void 0===t?void 0:t.groupsMapping)&&(n.saml.groupsMapping=null===(s=n.saml)||void 0===s?void 0:s.groupsMapping.map((e=>{const t=e;return t.roleName=t.role.name,delete t.role,t}))),n}))}),U=(e,s)=>({create:(n,o,a,r,i,p,l,m)=>t.transformResponse(e.httpClient.post(g.create,{name:n,expireTime:o,roleNames:a,keyTenants:r,userId:i,customClaims:p,description:l,permittedIps:m},{token:s})),load:n=>t.transformResponse(e.httpClient.get(g.load,{queryParams:{id:n},token:s}),(e=>e.key)),searchAll:n=>t.transformResponse(e.httpClient.post(g.search,{tenantIds:n},{token:s}),(e=>e.keys)),update:(n,o,a)=>t.transformResponse(e.httpClient.post(g.update,{id:n,name:o,description:a},{token:s}),(e=>e.key)),deactivate:n=>t.transformResponse(e.httpClient.post(g.deactivate,{id:n},{token:s})),activate:n=>t.transformResponse(e.httpClient.post(g.activate,{id:n},{token:s})),delete:n=>t.transformResponse(e.httpClient.post(g.delete,{id:n},{token:s}))}),L=(e,s)=>({list:()=>t.transformResponse(e.httpClient.post(y.list,{},{token:s})),delete:n=>t.transformResponse(e.httpClient.post(y.delete,{ids:n},{token:s})),export:n=>t.transformResponse(e.httpClient.post(y.export,{flowId:n},{token:s})),import:(n,o,a)=>t.transformResponse(e.httpClient.post(y.import,{flowId:n,flow:o,screens:a},{token:s}))}),D=(e,s)=>({export:()=>t.transformResponse(e.httpClient.post(I.export,{},{token:s})),import:n=>t.transformResponse(e.httpClient.post(I.import,{theme:n},{token:s}))}),q=(e,s)=>({search:n=>{const o=Object.assign(Object.assign({},n),{externalIds:n.loginIds});return delete o.loginIds,t.transformResponse(e.httpClient.post(w.search,o,{token:s}),(e=>null==e?void 0:e.audits.map((e=>{const t=Object.assign(Object.assign({},e),{occurred:parseFloat(e.occurred),loginIds:e.externalIds});return delete t.externalIds,t}))))},createEvent:n=>{const o=Object.assign({},n);return t.transformResponse(e.httpClient.post(w.createEvent,o,{token:s}))}}),F=(e,s)=>({saveSchema:(n,o)=>t.transformResponse(e.httpClient.post(A.schemaSave,{schema:n,upgrade:o},{token:s})),deleteSchema:()=>t.transformResponse(e.httpClient.post(A.schemaDelete,{},{token:s})),loadSchema:()=>t.transformResponse(e.httpClient.post(A.schemaLoad,{},{token:s}),(e=>e.schema)),saveNamespace:(n,o,a)=>t.transformResponse(e.httpClient.post(A.nsSave,{namespace:n,oldName:o,schemaName:a},{token:s})),deleteNamespace:(n,o)=>t.transformResponse(e.httpClient.post(A.nsDelete,{name:n,schemaName:o},{token:s})),saveRelationDefinition:(n,o,a,r)=>t.transformResponse(e.httpClient.post(A.rdSave,{relationDefinition:n,namespace:o,oldName:a,schemaName:r},{token:s})),deleteRelationDefinition:(n,o,a)=>t.transformResponse(e.httpClient.post(A.rdDelete,{name:n,namespace:o,schemaName:a},{token:s})),createRelations:n=>t.transformResponse(e.httpClient.post(A.reCreate,{relations:n},{token:s})),deleteRelations:n=>t.transformResponse(e.httpClient.post(A.reDelete,{relations:n},{token:s})),deleteRelationsForResources:n=>t.transformResponse(e.httpClient.post(A.reDeleteResources,{resources:n},{token:s})),hasRelations:n=>t.transformResponse(e.httpClient.post(A.hasRelations,{relationQueries:n},{token:s}),(e=>e.relationQueries)),whoCanAccess:(n,o,a)=>t.transformResponse(e.httpClient.post(A.who,{resource:n,relationDefinition:o,namespace:a},{token:s}),(e=>e.targets)),resourceRelations:n=>t.transformResponse(e.httpClient.post(A.resource,{resource:n},{token:s}),(e=>e.relations)),targetsRelations:n=>t.transformResponse(e.httpClient.post(A.targets,{targets:n},{token:s}),(e=>e.relations)),whatCanTargetAccess:n=>t.transformResponse(e.httpClient.post(A.targetAll,{target:n},{token:s}),(e=>e.relations)),getModified:n=>t.transformResponse(e.httpClient.post(A.getModified,{since:n?n.getTime():0},{token:s}),(e=>e))}),z=(e,s)=>({createOidcApplication:n=>{var o;return t.transformResponse(e.httpClient.post(h.oidcCreate,Object.assign(Object.assign({},n),{enabled:null===(o=n.enabled)||void 0===o||o}),{token:s}))},createSamlApplication:n=>{var o;return t.transformResponse(e.httpClient.post(h.samlCreate,Object.assign(Object.assign({},n),{enabled:null===(o=n.enabled)||void 0===o||o}),{token:s}))},updateOidcApplication:n=>t.transformResponse(e.httpClient.post(h.oidcUpdate,Object.assign({},n),{token:s})),updateSamlApplication:n=>t.transformResponse(e.httpClient.post(h.samlUpdate,Object.assign({},n),{token:s})),delete:n=>t.transformResponse(e.httpClient.post(h.delete,{id:n},{token:s})),load:n=>t.transformResponse(e.httpClient.get(h.load,{queryParams:{id:n},token:s}),(e=>e)),loadAll:()=>t.transformResponse(e.httpClient.get(h.loadAll,{token:s}),(e=>e.apps))}),J=(e,s)=>({getSettings:n=>t.transformResponse(e.httpClient.get(k.settings,{queryParams:{tenantId:n},token:s}),(e=>e)),configureSettings:(n,o)=>t.transformResponse(e.httpClient.post(k.settings,Object.assign(Object.assign({},o),{tenantId:n}),{token:s}))}),$=(e,s)=>({saveSchema:n=>t.transformResponse(e.httpClient.post(S.schema,n,{token:s})),deleteSchema:()=>t.transformResponse(e.httpClient.post(A.schemaDelete,{},{token:s})),createRelations:n=>t.transformResponse(e.httpClient.post(S.relations,{tuples:n},{token:s})),deleteRelations:n=>t.transformResponse(e.httpClient.post(S.deleteRelations,{tuples:n},{token:s})),check:n=>t.transformResponse(e.httpClient.post(S.check,{tuples:n},{token:s}),(e=>e.tuples))});var K=Object.freeze({__proto__:null,default:{badRequest:"E011001",missingArguments:"E011002",invalidRequest:"E011003",invalidArguments:"E011004",wrongOTPCode:"E061102",tooManyOTPAttempts:"E061103",enchantedLinkPending:"E062503",userNotFound:"E062108"}});const _=n=>{var o,{managementKey:r,publicKey:d}=n,c=e.__rest(n,["managementKey","publicKey"]);const g=a.default(Object.assign(Object.assign({fetch:i},c),{baseHeaders:Object.assign(Object.assign({},c.baseHeaders),{"x-descope-sdk-name":"nodejs","x-descope-sdk-node-version":(null===(o=null===process||void 0===process?void 0:process.versions)||void 0===o?void 0:o.node)||"","x-descope-sdk-version":"0.0.0-next-5099c5a3-20241213"})})),{projectId:u,logger:h}=c,v={},f=((e,t)=>({user:N(e,t),project:O(e,t),accessKey:U(e,t),tenant:j(e,t),ssoApplication:z(e,t),sso:x(e,t),jwt:T(e,t),permission:P(e,t),password:J(e,t),role:E(e,t),group:M(e,t),flow:L(e,t),theme:D(e,t),audit:q(e,t),authz:F(e,t),fga:$(e,t)}))(g,r),k=Object.assign(Object.assign({},g),{refresh:async e=>g.refresh(e),management:f,async getKey(e){if(!(null==e?void 0:e.kid))throw Error("header.kid must not be empty");if(v[e.kid])return v[e.kid];if(Object.assign(v,await(async()=>{if(d)try{const e=JSON.parse(d),t=await s.importJWK(e);return{[e.kid]:t}}catch(e){throw null==h||h.error("Failed to parse the provided public key",e),new Error(`Failed to parse public key. Error: ${e}`)}const e=(await g.httpClient.get(`v2/keys/${u}`).then((e=>e.json()))).keys;return Array.isArray(e)?(await Promise.all(e.map((async e=>[e.kid,await s.importJWK(e)])))).reduce(((e,[t,s])=>t?Object.assign(Object.assign({},e),{[t.toString()]:s}):e),{}):{}})()),!v[e.kid])throw Error("failed to fetch matching key");return v[e.kid]},async validateJwt(e){var t;const n=(await s.jwtVerify(e,k.getKey,{clockTolerance:5})).payload;if(n&&(n.iss=null===(t=n.iss)||void 0===t?void 0:t.split("/").pop(),n.iss!==u))throw new s.errors.JWTClaimValidationFailed('unexpected "iss" claim value',"iss","check_failed");return{jwt:e,token:n}},async validateSession(e){if(!e)throw Error("session token is required for validation");try{return await k.validateJwt(e)}catch(e){throw null==h||h.error("session validation failed",e),Error(`session validation failed. Error: ${e}`)}},async refreshSession(e){var t,s;if(!e)throw Error("refresh token is required to refresh a session");try{await k.validateJwt(e);const n=await k.refresh(e);if(n.ok){return await k.validateJwt(null===(t=n.data)||void 0===t?void 0:t.sessionJwt)}throw Error(null===(s=n.error)||void 0===s?void 0:s.errorMessage)}catch(e){throw null==h||h.error("refresh token validation failed",e),Error(`refresh token validation failed, Error: ${e}`)}},async validateAndRefreshSession(e,t){if(!e&&!t)throw Error("both session and refresh tokens are empty");try{return await k.validateSession(e)}catch(e){null==h||h.log(`session validation failed with error ${e} - trying to refresh it`)}return k.refreshSession(t)},async exchangeAccessKey(e,t){if(!e)throw Error("access key must not be empty");let s;try{s=await k.accessKey.exchange(e,t)}catch(e){throw null==h||h.error("failed to exchange access key",e),Error(`could not exchange access key - Failed to exchange. Error: ${e}`)}const{sessionJwt:n}=s.data;if(!n)throw null==h||h.error("failed to parse exchange access key response"),Error("could not exchange access key");try{return await k.validateJwt(n)}catch(e){throw null==h||h.error("failed to parse jwt from access key",e),Error(`could not exchange access key - failed to validate jwt. Error: ${e}`)}},validatePermissions:(e,t)=>k.validateTenantPermissions(e,"",t),getMatchedPermissions:(e,t)=>k.getMatchedTenantPermissions(e,"",t),validateTenantPermissions(e,t,s){if(t&&!m(e,t))return!1;const n=l(e,"permissions",t);return s.every((e=>n.includes(e)))},getMatchedTenantPermissions(e,t,s){if(t&&!m(e,t))return[];const n=l(e,"permissions",t);return s.filter((e=>n.includes(e)))},validateRoles:(e,t)=>k.validateTenantRoles(e,"",t),getMatchedRoles:(e,t)=>k.getMatchedTenantRoles(e,"",t),validateTenantRoles(e,t,s){if(t&&!m(e,t))return!1;const n=l(e,"roles",t);return s.every((e=>n.includes(e)))},getMatchedTenantRoles(e,t,s){if(t&&!m(e,t))return[];const n=l(e,"roles",t);return s.filter((e=>n.includes(e)))}});return t.wrapWith(k,["otp.verify.email","otp.verify.sms","otp.verify.voice","otp.verify.whatsapp","magicLink.verify","enchantedLink.signUp","enchantedLink.signIn","oauth.exchange","saml.exchange","totp.verify","webauthn.signIn.finish","webauthn.signUp.finish","refresh"],p)};_.RefreshTokenCookieName="DSR",_.SessionTokenCookieName="DS",exports.default=_,exports.descopeErrors=K; | ||
//# sourceMappingURL=index.cjs.js.map |
@@ -1,2 +0,2 @@ | ||
import{__rest as e}from"tslib";import t,{transformResponse as a,wrapWith as s}from"@descope/core-js-sdk";import{jwtVerify as o,errors as n,importJWK as r}from"jose";import i,{Headers as l,Request as d,Response as p}from"node-fetch";const m=t=>async(...a)=>{var s,o,n;const r=await t(...a);if(!r.data)return r;let i=r.data,{refreshJwt:l}=i,d=e(i,["refreshJwt"]);const p=[];var m;return l?p.push(`${"DSR"}=${l}; Domain=${(null==(m=d)?void 0:m.cookieDomain)||""}; Max-Age=${(null==m?void 0:m.cookieMaxAge)||""}; Path=${(null==m?void 0:m.cookiePath)||"/"}; HttpOnly; SameSite=Strict`):(null===(s=r.response)||void 0===s?void 0:s.headers.get("set-cookie"))&&(l=((e,t)=>{const a=null==e?void 0:e.match(RegExp(`(?:^|;\\s*)${t}=([^;]*)`));return a?a[1]:null})(null===(o=r.response)||void 0===o?void 0:o.headers.get("set-cookie"),"DSR"),p.push(null===(n=r.response)||void 0===n?void 0:n.headers.get("set-cookie"))),Object.assign(Object.assign({},r),{data:Object.assign(Object.assign({},r.data),{refreshJwt:l,cookies:p})})};function c(e,t,a){var s,o;const n=a?null===(o=null===(s=e.token.tenants)||void 0===s?void 0:s[a])||void 0===o?void 0:o[t]:e.token[t];return Array.isArray(n)?n:[]}var u={create:"/v1/mgmt/user/create",update:"/v1/mgmt/user/update",delete:"/v1/mgmt/user/delete",load:"/v1/mgmt/user",search:"/v1/mgmt/user/search",updateStatus:"/v1/mgmt/user/update/status",updateEmail:"/v1/mgmt/user/update/email",updatePhone:"/v1/mgmt/user/update/phone",updateDisplayName:"/v1/mgmt/user/update/name",addRole:"/v1/mgmt/user/update/role/add",removeRole:"/v1/mgmt/user/update/role/remove",addTenant:"/v1/mgmt/user/update/tenant/add",removeTenant:"/v1/mgmt/user/update/tenant/remove"},g={create:"/v1/mgmt/accesskey/create",load:"/v1/mgmt/accesskey",search:"/v1/mgmt/accesskey/search",update:"/v1/mgmt/accesskey/update",deactivate:"/v1/mgmt/accesskey/deactivate",activate:"/v1/mgmt/accesskey/activate",delete:"/v1/mgmt/accesskey/delete"},h={create:"/v1/mgmt/tenant/create",update:"/v1/mgmt/tenant/update",delete:"/v1/mgmt/tenant/delete",loadAll:"/v1/mgmt/tenant/all"},v={configure:"/v1/mgmt/sso/settings",metadata:"/v1/mgmt/sso/metadata",mapping:"/v1/mgmt/sso/mapping"},k={update:"/v1/mgmt/jwt/update"},y={create:"/v1/mgmt/permission/create",update:"/v1/mgmt/permission/update",delete:"/v1/mgmt/permission/delete",loadAll:"/v1/mgmt/permission/all"},f={create:"/v1/mgmt/role/create",update:"/v1/mgmt/role/update",delete:"/v1/mgmt/role/delete",loadAll:"/v1/mgmt/role/all"},C={loadAllGroups:"/v1/mgmt/group/all",loadAllGroupsForMember:"/v1/mgmt/group/member/all",loadAllGroupMembers:"/v1/mgmt/group/members"};const w=(e,t)=>({create:(s,o,n,r,i,l)=>a(e.httpClient.post(u.create,{loginId:s,email:o,phone:n,displayName:r,roleNames:i,userTenants:l},{token:t}),(e=>e.user)),update:(s,o,n,r,i,l)=>a(e.httpClient.post(u.update,{loginId:s,email:o,phone:n,displayName:r,roleNames:i,userTenants:l},{token:t}),(e=>e.user)),delete:s=>a(e.httpClient.post(u.delete,{loginId:s},{token:t})),load:s=>a(e.httpClient.get(u.load,{queryParams:{loginId:s},token:t}),(e=>e.user)),loadByUserId:s=>a(e.httpClient.get(u.load,{queryParams:{userId:s},token:t}),(e=>e.user)),searchAll:(s,o,n)=>a(e.httpClient.post(u.search,{tenantIds:s,roleNames:o,limit:n},{token:t}),(e=>e.users)),activate:s=>a(e.httpClient.post(u.updateStatus,{loginId:s,status:"enabled"},{token:t}),(e=>e.user)),deactivate:s=>a(e.httpClient.post(u.updateStatus,{loginId:s,status:"disabled"},{token:t}),(e=>e.user)),updateEmail:(s,o,n)=>a(e.httpClient.post(u.updateEmail,{loginId:s,email:o,verified:n},{token:t}),(e=>e.user)),updatePhone:(s,o,n)=>a(e.httpClient.post(u.updatePhone,{loginId:s,phone:o,verified:n},{token:t}),(e=>e.user)),updateDisplayName:(s,o)=>a(e.httpClient.post(u.updateDisplayName,{loginId:s,displayName:o},{token:t}),(e=>e.user)),addRoles:(s,o)=>a(e.httpClient.post(u.addRole,{loginId:s,roleNames:o},{token:t}),(e=>e.user)),removeRoles:(s,o)=>a(e.httpClient.post(u.removeRole,{loginId:s,roleNames:o},{token:t}),(e=>e.user)),addTenant:(s,o)=>a(e.httpClient.post(u.addTenant,{loginId:s,tenantId:o},{token:t}),(e=>e.user)),removeTenant:(s,o)=>a(e.httpClient.post(u.removeTenant,{loginId:s,tenantId:o},{token:t}),(e=>e.user)),addTenantRoles:(s,o,n)=>a(e.httpClient.post(u.addRole,{loginId:s,tenantId:o,roleNames:n},{token:t}),(e=>e.user)),removeTenantRoles:(s,o,n)=>a(e.httpClient.post(u.removeRole,{loginId:s,tenantId:o,roleNames:n},{token:t}),(e=>e.user))}),I=(e,t)=>({create:(s,o)=>a(e.httpClient.post(h.create,{name:s,selfProvisioningDomains:o},{token:t})),createWithId:(s,o,n)=>a(e.httpClient.post(h.create,{id:s,name:o,selfProvisioningDomains:n},{token:t})),update:(s,o,n)=>a(e.httpClient.post(h.update,{id:s,name:o,selfProvisioningDomains:n},{token:t})),delete:s=>a(e.httpClient.post(h.delete,{id:s},{token:t})),loadAll:()=>a(e.httpClient.get(h.loadAll,{token:t}),(e=>e.tenants))}),b=(e,t)=>({update:(s,o)=>a(e.httpClient.post(k.update,{jwt:s,customClaims:o},{token:t}))}),A=(e,t)=>({create:(s,o)=>a(e.httpClient.post(y.create,{name:s,description:o},{token:t})),update:(s,o,n)=>a(e.httpClient.post(y.update,{name:s,newName:o,description:n},{token:t})),delete:s=>a(e.httpClient.post(y.delete,{name:s},{token:t})),loadAll:()=>a(e.httpClient.get(y.loadAll,{token:t}),(e=>e.permissions))}),R=(e,t)=>({create:(s,o,n)=>a(e.httpClient.post(f.create,{name:s,description:o,permissionNames:n},{token:t})),update:(s,o,n,r)=>a(e.httpClient.post(f.update,{name:s,newName:o,description:n,permissionNames:r},{token:t})),delete:s=>a(e.httpClient.post(f.delete,{name:s},{token:t})),loadAll:()=>a(e.httpClient.get(f.loadAll,{token:t}),(e=>e.roles))}),T=(e,t)=>({loadAllGroups:s=>a(e.httpClient.post(C.loadAllGroups,{tenantId:s},{token:t})),loadAllGroupsForMember:(s,o,n)=>a(e.httpClient.post(C.loadAllGroupsForMember,{tenantId:s,loginIds:n,userIds:o},{token:t})),loadAllGroupMembers:(s,o)=>a(e.httpClient.post(C.loadAllGroupMembers,{tenantId:s,groupId:o},{token:t}))}),j=(e,t)=>({configureSettings:(s,o,n,r,i)=>a(e.httpClient.post(v.configure,{tenantId:s,idpURL:o,entityId:r,idpCert:n,redirectURL:i},{token:t})),configureMetadata:(s,o)=>a(e.httpClient.post(v.metadata,{tenantId:s,idpMetadataURL:o},{token:t})),configureMapping:(s,o,n)=>a(e.httpClient.post(v.mapping,{tenantId:s,roleMapping:o,attributeMapping:n},{token:t}))}),N=(e,t)=>({create:(s,o,n,r)=>a(e.httpClient.post(g.create,{name:s,expireTime:o,roleNames:n,keyTenants:r},{token:t})),load:s=>a(e.httpClient.get(g.load,{queryParams:{id:s},token:t}),(e=>e.key)),searchAll:s=>a(e.httpClient.post(g.search,{tenantIds:s},{token:t}),(e=>e.keys)),update:(s,o)=>a(e.httpClient.post(g.update,{id:s,name:o},{token:t}),(e=>e.key)),deactivate:s=>a(e.httpClient.post(g.deactivate,{id:s},{token:t})),activate:s=>a(e.httpClient.post(g.activate,{id:s},{token:t})),delete:s=>a(e.httpClient.post(g.delete,{id:s},{token:t}))});globalThis.fetch=i,globalThis.Headers=l,globalThis.Request=d,globalThis.Response=p;const x=a=>{var i,{managementKey:l}=a,d=e(a,["managementKey"]);const p=t(Object.assign(Object.assign({},d),{baseHeaders:Object.assign(Object.assign({},d.baseHeaders),{"x-descope-sdk-name":"nodejs","x-descope-sdk-node-version":(null===(i=null===process||void 0===process?void 0:process.versions)||void 0===i?void 0:i.node)||"","x-descope-sdk-version":"0.0.0-next-502d6795-20230212"})})),{projectId:u,logger:g}=d,h={},v=((e,t)=>({user:w(e,t),accessKey:N(e,t),tenant:I(e,t),sso:j(e,t),jwt:b(e,t),permission:A(e,t),role:R(e,t),group:T(e,t)}))(p,l),k=Object.assign(Object.assign({},p),{management:v,async getKey(e){if(!(null==e?void 0:e.kid))throw Error("header.kid must not be empty");if(h[e.kid])return h[e.kid];if(Object.assign(h,await(async()=>{const e=(await p.httpClient.get(`v2/keys/${u}`).then((e=>e.json()))).keys;return Array.isArray(e)?(await Promise.all(e.map((async e=>[e.kid,await r(e)])))).reduce(((e,[t,a])=>t?Object.assign(Object.assign({},e),{[t.toString()]:a}):e),{}):{}})()),!h[e.kid])throw Error("failed to fetch matching key");return h[e.kid]},async validateJwt(e){var t;const a=(await o(e,k.getKey,{clockTolerance:5})).payload;if(a&&(a.iss=null===(t=a.iss)||void 0===t?void 0:t.split("/").pop(),a.iss!==u))throw new n.JWTClaimValidationFailed('unexpected "iss" claim value',"iss","check_failed");return{jwt:e,token:a}},async validateSession(e){if(!e)throw Error("session token is required for validation");try{return await k.validateJwt(e)}catch(e){throw null==g||g.error("session validation failed",e),Error("session validation failed")}},async refreshSession(e){var t,a;if(!e)throw Error("refresh token is required to refresh a session");try{await k.validateJwt(e);const s=await k.refresh(e);if(s.ok){return await k.validateJwt(null===(t=s.data)||void 0===t?void 0:t.sessionJwt)}throw Error(null===(a=s.error)||void 0===a?void 0:a.errorMessage)}catch(e){throw null==g||g.error("refresh token validation failed",e),Error("refresh token validation failed")}},async validateAndRefreshSession(e,t){if(!e&&!t)throw Error("both session and refresh tokens are empty");try{return await k.validateSession(e)}catch(e){null==g||g.log("session validation failed - trying to refresh it")}return k.refreshSession(t)},async exchangeAccessKey(e){if(!e)throw Error("access key must not be empty");let t;try{t=await k.accessKey.exchange(e)}catch(e){throw null==g||g.error("failed to exchange access key",e),Error("could not exchange access key")}const{sessionJwt:a}=t.data;if(!a)throw null==g||g.error("failed to parse exchange access key response"),Error("could not exchange access key");try{return await k.validateJwt(a)}catch(e){throw null==g||g.error("failed to parse jwt from access key",e),Error("could not exchange access key")}},validatePermissions:(e,t)=>k.validateTenantPermissions(e,null,t),validateTenantPermissions(e,t,a){const s=c(e,"permissions",t);return a.every((e=>s.includes(e)))},validateRoles:(e,t)=>k.validateTenantRoles(e,null,t),validateTenantRoles(e,t,a){const s=c(e,"roles",t);return a.every((e=>s.includes(e)))}});return s(k,["otp.verify.email","otp.verify.sms","otp.verify.whatsapp","magicLink.verify","enchantedLink.signUp","enchantedLink.signIn","oauth.exchange","saml.exchange","totp.verify","webauthn.signIn.finish","webauthn.signUp.finish","refresh"],m)};x.RefreshTokenCookieName="DSR",x.SessionTokenCookieName="DS";export{x as default}; | ||
import{__rest as e}from"tslib";import t,{transformResponse as s,wrapWith as a}from"@descope/core-js-sdk";import{jwtVerify as o,errors as n,importJWK as i}from"jose";import{Headers as r,fetch as l}from"cross-fetch";var d;null!==(d=globalThis.Headers)&&void 0!==d||(globalThis.Headers=r);const p=(...e)=>(e.forEach((e=>{var t,s;e&&"object"==typeof e&&(null!==(t=(s=e).highWaterMark)&&void 0!==t||(s.highWaterMark=31457280))})),l(...e)),m=t=>async(...s)=>{var a,o,n;const i=await t(...s);if(!i.data)return i;let r=i.data,{refreshJwt:l}=r,d=e(r,["refreshJwt"]);const p=[];var m;return l?p.push(`${"DSR"}=${l}; Domain=${(null==(m=d)?void 0:m.cookieDomain)||""}; Max-Age=${(null==m?void 0:m.cookieMaxAge)||""}; Path=${(null==m?void 0:m.cookiePath)||"/"}; HttpOnly; SameSite=Strict`):(null===(a=i.response)||void 0===a?void 0:a.headers.get("set-cookie"))&&(l=((e,t)=>{const s=null==e?void 0:e.match(RegExp(`(?:^|;\\s*)${t}=([^;]*)`));return s?s[1]:null})(null===(o=i.response)||void 0===o?void 0:o.headers.get("set-cookie"),"DSR"),p.push(null===(n=i.response)||void 0===n?void 0:n.headers.get("set-cookie"))),Object.assign(Object.assign({},i),{data:Object.assign(Object.assign({},i.data),{refreshJwt:l,cookies:p})})};function c(e,t,s){var a,o;const n=s?null===(o=null===(a=e.token.tenants)||void 0===a?void 0:a[s])||void 0===o?void 0:o[t]:e.token[t];return Array.isArray(n)?n:[]}function g(e,t){var s;return!!(null===(s=e.token.tenants)||void 0===s?void 0:s[t])}var u={create:"/v1/mgmt/user/create",createTestUser:"/v1/mgmt/user/create/test",createBatch:"/v1/mgmt/user/create/batch",update:"/v1/mgmt/user/update",patch:"/v1/mgmt/user/patch",delete:"/v1/mgmt/user/delete",deleteAllTestUsers:"/v1/mgmt/user/test/delete/all",load:"/v1/mgmt/user",logout:"/v1/mgmt/user/logout",search:"/v2/mgmt/user/search",searchTestUsers:"/v2/mgmt/user/search/test",getProviderToken:"/v1/mgmt/user/provider/token",updateStatus:"/v1/mgmt/user/update/status",updateLoginId:"/v1/mgmt/user/update/loginid",updateEmail:"/v1/mgmt/user/update/email",updatePhone:"/v1/mgmt/user/update/phone",updateDisplayName:"/v1/mgmt/user/update/name",updatePicture:"/v1/mgmt/user/update/picture",updateCustomAttribute:"/v1/mgmt/user/update/customAttribute",setRole:"/v1/mgmt/user/update/role/set",addRole:"/v2/mgmt/user/update/role/add",removeRole:"/v1/mgmt/user/update/role/remove",setSSOApps:"/v1/mgmt/user/update/ssoapp/set",addSSOApps:"/v1/mgmt/user/update/ssoapp/add",removeSSOApps:"/v1/mgmt/user/update/ssoapp/remove",addTenant:"/v1/mgmt/user/update/tenant/add",removeTenant:"/v1/mgmt/user/update/tenant/remove",setPassword:"/v1/mgmt/user/password/set",setTemporaryPassword:"/v1/mgmt/user/password/set/temporary",setActivePassword:"/v1/mgmt/user/password/set/active",expirePassword:"/v1/mgmt/user/password/expire",removeAllPasskeys:"/v1/mgmt/user/passkeys/delete",generateOTPForTest:"/v1/mgmt/tests/generate/otp",generateMagicLinkForTest:"/v1/mgmt/tests/generate/magiclink",generateEnchantedLinkForTest:"/v1/mgmt/tests/generate/enchantedlink",generateEmbeddedLink:"/v1/mgmt/user/signin/embeddedlink",history:"/v1/mgmt/user/history"},h={updateName:"/v1/mgmt/project/update/name",updateTags:"/v1/mgmt/project/update/tags",clone:"/v1/mgmt/project/clone",projectsList:"/v1/mgmt/projects/list",exportSnapshot:"/v1/mgmt/project/snapshot/export",importSnapshot:"/v1/mgmt/project/snapshot/import",validateSnapshot:"/v1/mgmt/project/snapshot/validate"},v={create:"/v1/mgmt/accesskey/create",load:"/v1/mgmt/accesskey",search:"/v1/mgmt/accesskey/search",update:"/v1/mgmt/accesskey/update",deactivate:"/v1/mgmt/accesskey/deactivate",activate:"/v1/mgmt/accesskey/activate",delete:"/v1/mgmt/accesskey/delete"},k={create:"/v1/mgmt/tenant/create",update:"/v1/mgmt/tenant/update",delete:"/v1/mgmt/tenant/delete",load:"/v1/mgmt/tenant",settings:"/v1/mgmt/tenant/settings",loadAll:"/v1/mgmt/tenant/all",searchAll:"/v1/mgmt/tenant/search",generateSSOConfigurationLink:"/v1/mgmt/tenant/adminlinks/sso/generate"},C={oidcCreate:"/v1/mgmt/sso/idp/app/oidc/create",samlCreate:"/v1/mgmt/sso/idp/app/saml/create",oidcUpdate:"/v1/mgmt/sso/idp/app/oidc/update",samlUpdate:"/v1/mgmt/sso/idp/app/saml/update",delete:"/v1/mgmt/sso/idp/app/delete",load:"/v1/mgmt/sso/idp/app/load",loadAll:"/v1/mgmt/sso/idp/apps/load"},f={settings:"/v1/mgmt/sso/settings",metadata:"/v1/mgmt/sso/metadata",mapping:"/v1/mgmt/sso/mapping",settingsv2:"/v2/mgmt/sso/settings",oidc:{configure:"/v1/mgmt/sso/oidc"},saml:{configure:"/v1/mgmt/sso/saml",metadata:"/v1/mgmt/sso/saml/metadata"}},y={update:"/v1/mgmt/jwt/update",impersonate:"/v1/mgmt/impersonate"},I={settings:"/v1/mgmt/password/settings"},b={create:"/v1/mgmt/permission/create",update:"/v1/mgmt/permission/update",delete:"/v1/mgmt/permission/delete",loadAll:"/v1/mgmt/permission/all"},w={create:"/v1/mgmt/role/create",update:"/v1/mgmt/role/update",delete:"/v1/mgmt/role/delete",loadAll:"/v1/mgmt/role/all",search:"/v1/mgmt/role/search"},A={list:"/v1/mgmt/flow/list",delete:"/v1/mgmt/flow/delete",export:"/v1/mgmt/flow/export",import:"/v1/mgmt/flow/import"},S={export:"/v1/mgmt/theme/export",import:"/v1/mgmt/theme/import"},N={loadAllGroups:"/v1/mgmt/group/all",loadAllGroupsForMember:"/v1/mgmt/group/member/all",loadAllGroupMembers:"/v1/mgmt/group/members"},O={search:"/v1/mgmt/audit/search",createEvent:"/v1/mgmt/audit/event"},j={schemaSave:"/v1/mgmt/authz/schema/save",schemaDelete:"/v1/mgmt/authz/schema/delete",schemaLoad:"/v1/mgmt/authz/schema/load",nsSave:"/v1/mgmt/authz/ns/save",nsDelete:"/v1/mgmt/authz/ns/delete",rdSave:"/v1/mgmt/authz/rd/save",rdDelete:"/v1/mgmt/authz/rd/delete",reCreate:"/v1/mgmt/authz/re/create",reDelete:"/v1/mgmt/authz/re/delete",reDeleteResources:"/v1/mgmt/authz/re/deleteresources",hasRelations:"/v1/mgmt/authz/re/has",who:"/v1/mgmt/authz/re/who",resource:"/v1/mgmt/authz/re/resource",targets:"/v1/mgmt/authz/re/targets",targetAll:"/v1/mgmt/authz/re/targetall",getModified:"/v1/mgmt/authz/getmodified"},T={schema:"/v1/mgmt/fga/schema",relations:"/v1/mgmt/fga/relations",deleteRelations:"/v1/mgmt/fga/relations/delete",check:"/v1/mgmt/fga/check"};const P=(e,t)=>({create:function(a,o,n,i,r,l,d,p,m,c,g,h,v,k){const C="string"==typeof o?{loginId:a,email:o,phone:n,displayName:i,givenName:g,middleName:h,familyName:v,roleNames:r,userTenants:l,customAttributes:d,picture:p,verifiedEmail:m,verifiedPhone:c,additionalLoginIds:k}:Object.assign(Object.assign({loginId:a},o),{roleNames:null==o?void 0:o.roles,roles:void 0});return s(e.httpClient.post(u.create,C,{token:t}),(e=>e.user))},createTestUser:function(a,o,n,i,r,l,d,p,m,c,g,h,v,k){const C="string"==typeof o?{loginId:a,email:o,phone:n,displayName:i,givenName:g,middleName:h,familyName:v,roleNames:r,userTenants:l,customAttributes:d,picture:p,verifiedEmail:m,verifiedPhone:c,additionalLoginIds:k,test:!0}:Object.assign(Object.assign({loginId:a},o),{roleNames:null==o?void 0:o.roles,roles:void 0,test:!0});return s(e.httpClient.post(u.createTestUser,C,{token:t}),(e=>e.user))},invite:function(a,o,n,i,r,l,d,p,m,c,g,h,v,k,C,f,y,I){const b="string"==typeof o?{loginId:a,email:o,phone:n,displayName:i,givenName:k,middleName:C,familyName:f,roleNames:r,userTenants:l,invite:!0,customAttributes:d,picture:p,verifiedEmail:m,verifiedPhone:c,inviteUrl:g,sendMail:h,sendSMS:v,additionalLoginIds:y,templateId:I}:Object.assign(Object.assign({loginId:a},o),{roleNames:null==o?void 0:o.roles,roles:void 0,invite:!0});return s(e.httpClient.post(u.create,b,{token:t}),(e=>e.user))},inviteBatch:(a,o,n,i,r,l)=>s(e.httpClient.post(u.createBatch,{users:a.map((e=>{const t=Object.assign(Object.assign({},e),{roleNames:e.roles});return delete t.roles,t})),invite:!0,inviteUrl:o,sendMail:n,sendSMS:i,templateOptions:r,templateId:l},{token:t}),(e=>e)),update:function(a,o,n,i,r,l,d,p,m,c,g,h,v,k){const C="string"==typeof o?{loginId:a,email:o,phone:n,displayName:i,givenName:g,middleName:h,familyName:v,roleNames:r,userTenants:l,customAttributes:d,picture:p,verifiedEmail:m,verifiedPhone:c,additionalLoginIds:k}:Object.assign(Object.assign({loginId:a},o),{roleNames:null==o?void 0:o.roles,roles:void 0});return s(e.httpClient.post(u.update,C,{token:t}),(e=>e.user))},patch:function(a,o){const n={loginId:a};return void 0!==o.email&&(n.email=o.email),void 0!==o.phone&&(n.phone=o.phone),void 0!==o.displayName&&(n.displayName=o.displayName),void 0!==o.givenName&&(n.givenName=o.givenName),void 0!==o.middleName&&(n.middleName=o.middleName),void 0!==o.familyName&&(n.familyName=o.familyName),void 0!==o.roles&&(n.roleNames=o.roles),void 0!==o.userTenants&&(n.userTenants=o.userTenants),void 0!==o.customAttributes&&(n.customAttributes=o.customAttributes),void 0!==o.picture&&(n.picture=o.picture),void 0!==o.verifiedEmail&&(n.verifiedEmail=o.verifiedEmail),void 0!==o.verifiedPhone&&(n.verifiedPhone=o.verifiedPhone),void 0!==o.ssoAppIds&&(n.ssoAppIds=o.ssoAppIds),s(e.httpClient.patch(u.patch,n,{token:t}),(e=>e.user))},delete:a=>s(e.httpClient.post(u.delete,{loginId:a},{token:t})),deleteByUserId:a=>s(e.httpClient.post(u.delete,{userId:a},{token:t})),deleteAllTestUsers:()=>s(e.httpClient.delete(u.deleteAllTestUsers,{token:t})),load:a=>s(e.httpClient.get(u.load,{queryParams:{loginId:a},token:t}),(e=>e.user)),loadByUserId:a=>s(e.httpClient.get(u.load,{queryParams:{userId:a},token:t}),(e=>e.user)),logoutUser:a=>s(e.httpClient.post(u.logout,{loginId:a},{token:t})),logoutUserByUserId:a=>s(e.httpClient.post(u.logout,{userId:a},{token:t})),searchAll:(a,o,n,i,r,l,d,p,m,c)=>s(e.httpClient.post(u.search,{tenantIds:a,roleNames:o,limit:n,page:i,testUsersOnly:r,withTestUser:l,customAttributes:d,statuses:p,emails:m,phones:c},{token:t}),(e=>e.users)),searchTestUsers:a=>s(e.httpClient.post(u.searchTestUsers,Object.assign(Object.assign({},a),{withTestUser:!0,testUsersOnly:!0,roleNames:a.roles,roles:void 0}),{token:t}),(e=>e.users)),search:a=>s(e.httpClient.post(u.search,Object.assign(Object.assign({},a),{roleNames:a.roles,roles:void 0}),{token:t}),(e=>e.users)),getProviderToken:(a,o,n)=>s(e.httpClient.get(u.getProviderToken,{queryParams:{loginId:a,provider:o,withRefreshToken:(null==n?void 0:n.withRefreshToken)?"true":"false",forceRefresh:(null==n?void 0:n.forceRefresh)?"true":"false"},token:t}),(e=>e)),activate:a=>s(e.httpClient.post(u.updateStatus,{loginId:a,status:"enabled"},{token:t}),(e=>e.user)),deactivate:a=>s(e.httpClient.post(u.updateStatus,{loginId:a,status:"disabled"},{token:t}),(e=>e.user)),updateLoginId:(a,o)=>s(e.httpClient.post(u.updateLoginId,{loginId:a,newLoginId:o},{token:t}),(e=>e.user)),updateEmail:(a,o,n)=>s(e.httpClient.post(u.updateEmail,{loginId:a,email:o,verified:n},{token:t}),(e=>e.user)),updatePhone:(a,o,n)=>s(e.httpClient.post(u.updatePhone,{loginId:a,phone:o,verified:n},{token:t}),(e=>e.user)),updateDisplayName:(a,o,n,i,r)=>s(e.httpClient.post(u.updateDisplayName,{loginId:a,displayName:o,givenName:n,middleName:i,familyName:r},{token:t}),(e=>e.user)),updatePicture:(a,o)=>s(e.httpClient.post(u.updatePicture,{loginId:a,picture:o},{token:t}),(e=>e.user)),updateCustomAttribute:(a,o,n)=>s(e.httpClient.post(u.updateCustomAttribute,{loginId:a,attributeKey:o,attributeValue:n},{token:t}),(e=>e.user)),setRoles:(a,o)=>s(e.httpClient.post(u.setRole,{loginId:a,roleNames:o},{token:t}),(e=>e.user)),addRoles:(a,o)=>s(e.httpClient.post(u.addRole,{loginId:a,roleNames:o},{token:t}),(e=>e.user)),removeRoles:(a,o)=>s(e.httpClient.post(u.removeRole,{loginId:a,roleNames:o},{token:t}),(e=>e.user)),addTenant:(a,o)=>s(e.httpClient.post(u.addTenant,{loginId:a,tenantId:o},{token:t}),(e=>e.user)),removeTenant:(a,o)=>s(e.httpClient.post(u.removeTenant,{loginId:a,tenantId:o},{token:t}),(e=>e.user)),setTenantRoles:(a,o,n)=>s(e.httpClient.post(u.setRole,{loginId:a,tenantId:o,roleNames:n},{token:t}),(e=>e.user)),addTenantRoles:(a,o,n)=>s(e.httpClient.post(u.addRole,{loginId:a,tenantId:o,roleNames:n},{token:t}),(e=>e.user)),removeTenantRoles:(a,o,n)=>s(e.httpClient.post(u.removeRole,{loginId:a,tenantId:o,roleNames:n},{token:t}),(e=>e.user)),addSSOapps:(a,o)=>s(e.httpClient.post(u.addSSOApps,{loginId:a,ssoAppIds:o},{token:t}),(e=>e.user)),setSSOapps:(a,o)=>s(e.httpClient.post(u.setSSOApps,{loginId:a,ssoAppIds:o},{token:t}),(e=>e.user)),removeSSOapps:(a,o)=>s(e.httpClient.post(u.removeSSOApps,{loginId:a,ssoAppIds:o},{token:t}),(e=>e.user)),generateOTPForTestUser:(a,o,n)=>s(e.httpClient.post(u.generateOTPForTest,{deliveryMethod:a,loginId:o,loginOptions:n},{token:t}),(e=>e)),generateMagicLinkForTestUser:(a,o,n,i)=>s(e.httpClient.post(u.generateMagicLinkForTest,{deliveryMethod:a,loginId:o,URI:n,loginOptions:i},{token:t}),(e=>e)),generateEnchantedLinkForTestUser:(a,o,n)=>s(e.httpClient.post(u.generateEnchantedLinkForTest,{loginId:a,URI:o,loginOptions:n},{token:t}),(e=>e)),generateEmbeddedLink:(a,o)=>s(e.httpClient.post(u.generateEmbeddedLink,{loginId:a,customClaims:o},{token:t}),(e=>e)),setTemporaryPassword:(a,o)=>s(e.httpClient.post(u.setTemporaryPassword,{loginId:a,password:o},{token:t}),(e=>e)),setActivePassword:(a,o)=>s(e.httpClient.post(u.setActivePassword,{loginId:a,password:o},{token:t}),(e=>e)),setPassword:(a,o)=>s(e.httpClient.post(u.setPassword,{loginId:a,password:o},{token:t}),(e=>e)),expirePassword:a=>s(e.httpClient.post(u.expirePassword,{loginId:a},{token:t}),(e=>e)),removeAllPasskeys:a=>s(e.httpClient.post(u.removeAllPasskeys,{loginId:a},{token:t}),(e=>e)),history:a=>s(e.httpClient.post(u.history,a,{token:t}),(e=>e))}),R=(e,t)=>({updateName:a=>s(e.httpClient.post(h.updateName,{name:a},{token:t})),updateTags:a=>s(e.httpClient.post(h.updateTags,{tags:a},{token:t})),clone:(a,o,n)=>s(e.httpClient.post(h.clone,{name:a,environment:o,tags:n},{token:t})),listProjects:async()=>s(e.httpClient.post(h.projectsList,{},{token:t}),(e=>e.projects.map((({id:e,name:t,environment:s,tags:a})=>({id:e,name:t,environment:s,tags:a}))))),exportSnapshot:()=>s(e.httpClient.post(h.exportSnapshot,{},{token:t})),importSnapshot:a=>s(e.httpClient.post(h.importSnapshot,a,{token:t})),validateSnapshot:a=>s(e.httpClient.post(h.validateSnapshot,a,{token:t})),export:()=>s(e.httpClient.post(h.exportSnapshot,{},{token:t}),(e=>e.files)),import:a=>s(e.httpClient.post(h.importSnapshot,{files:a},{token:t}))}),E=(e,t)=>({create:(a,o,n)=>s(e.httpClient.post(k.create,{name:a,selfProvisioningDomains:o,customAttributes:n},{token:t})),createWithId:(a,o,n,i)=>s(e.httpClient.post(k.create,{id:a,name:o,selfProvisioningDomains:n,customAttributes:i},{token:t})),update:(a,o,n,i)=>s(e.httpClient.post(k.update,{id:a,name:o,selfProvisioningDomains:n,customAttributes:i},{token:t})),delete:(a,o)=>s(e.httpClient.post(k.delete,{id:a,cascade:o},{token:t})),load:a=>s(e.httpClient.get(k.load,{queryParams:{id:a},token:t}),(e=>e)),loadAll:()=>s(e.httpClient.get(k.loadAll,{token:t}),(e=>e.tenants)),searchAll:(a,o,n,i)=>s(e.httpClient.post(k.searchAll,{tenantIds:a,tenantNames:o,tenantSelfProvisioningDomains:n,customAttributes:i},{token:t}),(e=>e.tenants)),getSettings:a=>s(e.httpClient.get(k.settings,{queryParams:{id:a},token:t}),(e=>e)),configureSettings:(a,o)=>s(e.httpClient.post(k.settings,Object.assign(Object.assign({},o),{tenantId:a}),{token:t})),generateSSOConfigurationLink:(a,o)=>s(e.httpClient.post(k.generateSSOConfigurationLink,{tenantId:a,expireTime:o},{token:t}),(e=>e))}),M=(e,t)=>({update:(a,o)=>s(e.httpClient.post(y.update,{jwt:a,customClaims:o},{token:t})),impersonate:(a,o,n)=>s(e.httpClient.post(y.impersonate,{impersonatorId:a,loginId:o,validateConsent:n},{token:t}))}),x=(e,t)=>({create:(a,o)=>s(e.httpClient.post(b.create,{name:a,description:o},{token:t})),update:(a,o,n)=>s(e.httpClient.post(b.update,{name:a,newName:o,description:n},{token:t})),delete:a=>s(e.httpClient.post(b.delete,{name:a},{token:t})),loadAll:()=>s(e.httpClient.get(b.loadAll,{token:t}),(e=>e.permissions))}),U=(e,t)=>({create:(a,o,n,i)=>s(e.httpClient.post(w.create,{name:a,description:o,permissionNames:n,tenantId:i},{token:t})),update:(a,o,n,i,r)=>s(e.httpClient.post(w.update,{name:a,newName:o,description:n,permissionNames:i,tenantId:r},{token:t})),delete:(a,o)=>s(e.httpClient.post(w.delete,{name:a,tenantId:o},{token:t})),loadAll:()=>s(e.httpClient.get(w.loadAll,{token:t}),(e=>e.roles)),search:a=>s(e.httpClient.post(w.search,a,{token:t}),(e=>e.roles))}),L=(e,t)=>({loadAllGroups:a=>s(e.httpClient.post(N.loadAllGroups,{tenantId:a},{token:t})),loadAllGroupsForMember:(a,o,n)=>s(e.httpClient.post(N.loadAllGroupsForMember,{tenantId:a,loginIds:n,userIds:o},{token:t})),loadAllGroupMembers:(a,o)=>s(e.httpClient.post(N.loadAllGroupMembers,{tenantId:a,groupId:o},{token:t}))}),D=(e,t)=>({getSettings:a=>s(e.httpClient.get(f.settings,{queryParams:{tenantId:a},token:t}),(e=>e)),deleteSettings:a=>s(e.httpClient.delete(f.settings,{queryParams:{tenantId:a},token:t})),configureSettings:(a,o,n,i,r,l)=>s(e.httpClient.post(f.settings,{tenantId:a,idpURL:o,entityId:i,idpCert:n,redirectURL:r,domains:l},{token:t})),configureMetadata:(a,o,n,i)=>s(e.httpClient.post(f.metadata,{tenantId:a,idpMetadataURL:o,redirectURL:n,domains:i},{token:t})),configureMapping:(a,o,n)=>s(e.httpClient.post(f.mapping,{tenantId:a,roleMappings:o,attributeMapping:n},{token:t})),configureOIDCSettings:(a,o,n)=>{const i=Object.assign(Object.assign({},o),{userAttrMapping:o.attributeMapping});return delete i.attributeMapping,s(e.httpClient.post(f.oidc.configure,{tenantId:a,settings:i,domains:n},{token:t}))},configureSAMLSettings:(a,o,n,i)=>s(e.httpClient.post(f.saml.configure,{tenantId:a,settings:o,redirectUrl:n,domains:i},{token:t})),configureSAMLByMetadata:(a,o,n,i)=>s(e.httpClient.post(f.saml.metadata,{tenantId:a,settings:o,redirectUrl:n,domains:i},{token:t})),loadSettings:a=>s(e.httpClient.get(f.settingsv2,{queryParams:{tenantId:a},token:t}),(e=>{var t,s;const a=e;return a.oidc&&(a.oidc=Object.assign(Object.assign({},a.oidc),{attributeMapping:a.oidc.userAttrMapping}),delete a.oidc.userAttrMapping),(null===(t=a.saml)||void 0===t?void 0:t.groupsMapping)&&(a.saml.groupsMapping=null===(s=a.saml)||void 0===s?void 0:s.groupsMapping.map((e=>{const t=e;return t.roleName=t.role.name,delete t.role,t}))),a}))}),F=(e,t)=>({create:(a,o,n,i,r,l,d,p)=>s(e.httpClient.post(v.create,{name:a,expireTime:o,roleNames:n,keyTenants:i,userId:r,customClaims:l,description:d,permittedIps:p},{token:t})),load:a=>s(e.httpClient.get(v.load,{queryParams:{id:a},token:t}),(e=>e.key)),searchAll:a=>s(e.httpClient.post(v.search,{tenantIds:a},{token:t}),(e=>e.keys)),update:(a,o,n)=>s(e.httpClient.post(v.update,{id:a,name:o,description:n},{token:t}),(e=>e.key)),deactivate:a=>s(e.httpClient.post(v.deactivate,{id:a},{token:t})),activate:a=>s(e.httpClient.post(v.activate,{id:a},{token:t})),delete:a=>s(e.httpClient.post(v.delete,{id:a},{token:t}))}),z=(e,t)=>({list:()=>s(e.httpClient.post(A.list,{},{token:t})),delete:a=>s(e.httpClient.post(A.delete,{ids:a},{token:t})),export:a=>s(e.httpClient.post(A.export,{flowId:a},{token:t})),import:(a,o,n)=>s(e.httpClient.post(A.import,{flowId:a,flow:o,screens:n},{token:t}))}),q=(e,t)=>({export:()=>s(e.httpClient.post(S.export,{},{token:t})),import:a=>s(e.httpClient.post(S.import,{theme:a},{token:t}))}),$=(e,t)=>({search:a=>{const o=Object.assign(Object.assign({},a),{externalIds:a.loginIds});return delete o.loginIds,s(e.httpClient.post(O.search,o,{token:t}),(e=>null==e?void 0:e.audits.map((e=>{const t=Object.assign(Object.assign({},e),{occurred:parseFloat(e.occurred),loginIds:e.externalIds});return delete t.externalIds,t}))))},createEvent:a=>{const o=Object.assign({},a);return s(e.httpClient.post(O.createEvent,o,{token:t}))}}),J=(e,t)=>({saveSchema:(a,o)=>s(e.httpClient.post(j.schemaSave,{schema:a,upgrade:o},{token:t})),deleteSchema:()=>s(e.httpClient.post(j.schemaDelete,{},{token:t})),loadSchema:()=>s(e.httpClient.post(j.schemaLoad,{},{token:t}),(e=>e.schema)),saveNamespace:(a,o,n)=>s(e.httpClient.post(j.nsSave,{namespace:a,oldName:o,schemaName:n},{token:t})),deleteNamespace:(a,o)=>s(e.httpClient.post(j.nsDelete,{name:a,schemaName:o},{token:t})),saveRelationDefinition:(a,o,n,i)=>s(e.httpClient.post(j.rdSave,{relationDefinition:a,namespace:o,oldName:n,schemaName:i},{token:t})),deleteRelationDefinition:(a,o,n)=>s(e.httpClient.post(j.rdDelete,{name:a,namespace:o,schemaName:n},{token:t})),createRelations:a=>s(e.httpClient.post(j.reCreate,{relations:a},{token:t})),deleteRelations:a=>s(e.httpClient.post(j.reDelete,{relations:a},{token:t})),deleteRelationsForResources:a=>s(e.httpClient.post(j.reDeleteResources,{resources:a},{token:t})),hasRelations:a=>s(e.httpClient.post(j.hasRelations,{relationQueries:a},{token:t}),(e=>e.relationQueries)),whoCanAccess:(a,o,n)=>s(e.httpClient.post(j.who,{resource:a,relationDefinition:o,namespace:n},{token:t}),(e=>e.targets)),resourceRelations:a=>s(e.httpClient.post(j.resource,{resource:a},{token:t}),(e=>e.relations)),targetsRelations:a=>s(e.httpClient.post(j.targets,{targets:a},{token:t}),(e=>e.relations)),whatCanTargetAccess:a=>s(e.httpClient.post(j.targetAll,{target:a},{token:t}),(e=>e.relations)),getModified:a=>s(e.httpClient.post(j.getModified,{since:a?a.getTime():0},{token:t}),(e=>e))}),K=(e,t)=>({createOidcApplication:a=>{var o;return s(e.httpClient.post(C.oidcCreate,Object.assign(Object.assign({},a),{enabled:null===(o=a.enabled)||void 0===o||o}),{token:t}))},createSamlApplication:a=>{var o;return s(e.httpClient.post(C.samlCreate,Object.assign(Object.assign({},a),{enabled:null===(o=a.enabled)||void 0===o||o}),{token:t}))},updateOidcApplication:a=>s(e.httpClient.post(C.oidcUpdate,Object.assign({},a),{token:t})),updateSamlApplication:a=>s(e.httpClient.post(C.samlUpdate,Object.assign({},a),{token:t})),delete:a=>s(e.httpClient.post(C.delete,{id:a},{token:t})),load:a=>s(e.httpClient.get(C.load,{queryParams:{id:a},token:t}),(e=>e)),loadAll:()=>s(e.httpClient.get(C.loadAll,{token:t}),(e=>e.apps))}),G=(e,t)=>({getSettings:a=>s(e.httpClient.get(I.settings,{queryParams:{tenantId:a},token:t}),(e=>e)),configureSettings:(a,o)=>s(e.httpClient.post(I.settings,Object.assign(Object.assign({},o),{tenantId:a}),{token:t}))}),B=(e,t)=>({saveSchema:a=>s(e.httpClient.post(T.schema,a,{token:t})),deleteSchema:()=>s(e.httpClient.post(j.schemaDelete,{},{token:t})),createRelations:a=>s(e.httpClient.post(T.relations,{tuples:a},{token:t})),deleteRelations:a=>s(e.httpClient.post(T.deleteRelations,{tuples:a},{token:t})),check:a=>s(e.httpClient.post(T.check,{tuples:a},{token:t}),(e=>e.tuples))});var H=Object.freeze({__proto__:null,default:{badRequest:"E011001",missingArguments:"E011002",invalidRequest:"E011003",invalidArguments:"E011004",wrongOTPCode:"E061102",tooManyOTPAttempts:"E061103",enchantedLinkPending:"E062503",userNotFound:"E062108"}});const _=s=>{var r,{managementKey:l,publicKey:d}=s,u=e(s,["managementKey","publicKey"]);const h=t(Object.assign(Object.assign({fetch:p},u),{baseHeaders:Object.assign(Object.assign({},u.baseHeaders),{"x-descope-sdk-name":"nodejs","x-descope-sdk-node-version":(null===(r=null===process||void 0===process?void 0:process.versions)||void 0===r?void 0:r.node)||"","x-descope-sdk-version":"0.0.0-next-5099c5a3-20241213"})})),{projectId:v,logger:k}=u,C={},f=((e,t)=>({user:P(e,t),project:R(e,t),accessKey:F(e,t),tenant:E(e,t),ssoApplication:K(e,t),sso:D(e,t),jwt:M(e,t),permission:x(e,t),password:G(e,t),role:U(e,t),group:L(e,t),flow:z(e,t),theme:q(e,t),audit:$(e,t),authz:J(e,t),fga:B(e,t)}))(h,l),y=Object.assign(Object.assign({},h),{refresh:async e=>h.refresh(e),management:f,async getKey(e){if(!(null==e?void 0:e.kid))throw Error("header.kid must not be empty");if(C[e.kid])return C[e.kid];if(Object.assign(C,await(async()=>{if(d)try{const e=JSON.parse(d),t=await i(e);return{[e.kid]:t}}catch(e){throw null==k||k.error("Failed to parse the provided public key",e),new Error(`Failed to parse public key. Error: ${e}`)}const e=(await h.httpClient.get(`v2/keys/${v}`).then((e=>e.json()))).keys;return Array.isArray(e)?(await Promise.all(e.map((async e=>[e.kid,await i(e)])))).reduce(((e,[t,s])=>t?Object.assign(Object.assign({},e),{[t.toString()]:s}):e),{}):{}})()),!C[e.kid])throw Error("failed to fetch matching key");return C[e.kid]},async validateJwt(e){var t;const s=(await o(e,y.getKey,{clockTolerance:5})).payload;if(s&&(s.iss=null===(t=s.iss)||void 0===t?void 0:t.split("/").pop(),s.iss!==v))throw new n.JWTClaimValidationFailed('unexpected "iss" claim value',"iss","check_failed");return{jwt:e,token:s}},async validateSession(e){if(!e)throw Error("session token is required for validation");try{return await y.validateJwt(e)}catch(e){throw null==k||k.error("session validation failed",e),Error(`session validation failed. Error: ${e}`)}},async refreshSession(e){var t,s;if(!e)throw Error("refresh token is required to refresh a session");try{await y.validateJwt(e);const a=await y.refresh(e);if(a.ok){return await y.validateJwt(null===(t=a.data)||void 0===t?void 0:t.sessionJwt)}throw Error(null===(s=a.error)||void 0===s?void 0:s.errorMessage)}catch(e){throw null==k||k.error("refresh token validation failed",e),Error(`refresh token validation failed, Error: ${e}`)}},async validateAndRefreshSession(e,t){if(!e&&!t)throw Error("both session and refresh tokens are empty");try{return await y.validateSession(e)}catch(e){null==k||k.log(`session validation failed with error ${e} - trying to refresh it`)}return y.refreshSession(t)},async exchangeAccessKey(e,t){if(!e)throw Error("access key must not be empty");let s;try{s=await y.accessKey.exchange(e,t)}catch(e){throw null==k||k.error("failed to exchange access key",e),Error(`could not exchange access key - Failed to exchange. Error: ${e}`)}const{sessionJwt:a}=s.data;if(!a)throw null==k||k.error("failed to parse exchange access key response"),Error("could not exchange access key");try{return await y.validateJwt(a)}catch(e){throw null==k||k.error("failed to parse jwt from access key",e),Error(`could not exchange access key - failed to validate jwt. Error: ${e}`)}},validatePermissions:(e,t)=>y.validateTenantPermissions(e,"",t),getMatchedPermissions:(e,t)=>y.getMatchedTenantPermissions(e,"",t),validateTenantPermissions(e,t,s){if(t&&!g(e,t))return!1;const a=c(e,"permissions",t);return s.every((e=>a.includes(e)))},getMatchedTenantPermissions(e,t,s){if(t&&!g(e,t))return[];const a=c(e,"permissions",t);return s.filter((e=>a.includes(e)))},validateRoles:(e,t)=>y.validateTenantRoles(e,"",t),getMatchedRoles:(e,t)=>y.getMatchedTenantRoles(e,"",t),validateTenantRoles(e,t,s){if(t&&!g(e,t))return!1;const a=c(e,"roles",t);return s.every((e=>a.includes(e)))},getMatchedTenantRoles(e,t,s){if(t&&!g(e,t))return[];const a=c(e,"roles",t);return s.filter((e=>a.includes(e)))}});return a(y,["otp.verify.email","otp.verify.sms","otp.verify.voice","otp.verify.whatsapp","magicLink.verify","enchantedLink.signUp","enchantedLink.signIn","oauth.exchange","saml.exchange","totp.verify","webauthn.signIn.finish","webauthn.signUp.finish","refresh"],m)};_.RefreshTokenCookieName="DSR",_.SessionTokenCookieName="DS";export{_ as default,H as descopeErrors}; | ||
//# sourceMappingURL=index.esm.js.map |
{ | ||
"name": "@descope/node-sdk", | ||
"version": "0.0.0-next-502d6795-20230212", | ||
"version": "0.0.0-next-5099c5a3-20241213", | ||
"description": "Node.js library used to integrate with Descope", | ||
@@ -10,4 +10,10 @@ "typings": "./dist/index.d.ts", | ||
"exports": { | ||
"require": "./dist/cjs/index.cjs.js", | ||
"import": "./dist/index.esm.js" | ||
"require": { | ||
"types": "./dist/index.d.ts", | ||
"default": "./dist/cjs/index.cjs.js" | ||
}, | ||
"import": { | ||
"types": "./dist/index.d.ts", | ||
"default": "./dist/index.esm.js" | ||
} | ||
}, | ||
@@ -53,12 +59,11 @@ "type": "module", | ||
"devDependencies": { | ||
"@rollup/plugin-commonjs": "^22.0.0", | ||
"@rollup/plugin-commonjs": "^28.0.0", | ||
"@rollup/plugin-json": "^4.1.0", | ||
"@rollup/plugin-node-resolve": "^13.3.0", | ||
"@rollup/plugin-replace": "^4.0.0", | ||
"@rollup/plugin-replace": "^6.0.0", | ||
"@rollup/plugin-typescript": "^8.3.0", | ||
"@size-limit/preset-small-lib": "^8.0.0", | ||
"@size-limit/preset-small-lib": "^11.0.0", | ||
"@types/jest": "^29.0.0", | ||
"@types/jsonwebtoken": "^9.0.0", | ||
"@types/node": "^15.14.9", | ||
"@types/node-fetch": "^2.6.1", | ||
"@types/node": "^22.0.0", | ||
"@typescript-eslint/eslint-plugin": "^5.25.0", | ||
@@ -69,7 +74,7 @@ "@typescript-eslint/parser": "^5.27.0", | ||
"eslint-config-airbnb-typescript": "^17.0.0", | ||
"eslint-config-prettier": "^8.5.0", | ||
"eslint-config-prettier": "^9.0.0", | ||
"eslint-import-resolver-typescript": "^3.0.0", | ||
"eslint-plugin-import": "^2.26.0", | ||
"eslint-plugin-jest": "^26.4.6", | ||
"eslint-plugin-jest-dom": "^4.0.2", | ||
"eslint-plugin-jest": "^27.0.0", | ||
"eslint-plugin-jest-dom": "^5.0.0", | ||
"eslint-plugin-jest-formatting": "^3.1.0", | ||
@@ -81,8 +86,8 @@ "eslint-plugin-no-only-tests": "^3.0.0", | ||
"jest": "^29.0.0", | ||
"jsdoc": "^3.6.10", | ||
"lint-staged": "^13.0.3", | ||
"jsdoc": "^4.0.0", | ||
"lint-staged": "^15.0.0", | ||
"nock": "^13.2.4", | ||
"prettier": "^2.7.1", | ||
"prettier": "^2.8.8", | ||
"pretty-quick": "^3.1.3", | ||
"rollup": "^2.62.0", | ||
"rollup": "^2.79.2", | ||
"rollup-plugin-auto-external": "^2.0.0", | ||
@@ -93,3 +98,3 @@ "rollup-plugin-browsersync": "^1.3.3", | ||
"rollup-plugin-dts": "^4.2.2", | ||
"rollup-plugin-esbuild": "^4.9.1", | ||
"rollup-plugin-esbuild": "^6.0.0", | ||
"rollup-plugin-inject-process-env": "^1.3.1", | ||
@@ -103,9 +108,7 @@ "rollup-plugin-livereload": "^2.0.5", | ||
"dependencies": { | ||
"@descope/core-js-sdk": "0.0.41-alpha.55", | ||
"jose": "4.11.2", | ||
"node-fetch": "2.6.8" | ||
}, | ||
"peerDependencies": { | ||
"tslib": ">=1.14.1" | ||
"@descope/core-js-sdk": "2.31.0", | ||
"cross-fetch": "^4.0.0", | ||
"jose": "5.2.2", | ||
"tslib": "^2.0.0" | ||
} | ||
} |
772
README.md
@@ -18,7 +18,10 @@ # Descope SDK for Node.js | ||
## Setup | ||
## Authentication Functions | ||
A Descope `Project ID` is required to initialize the SDK. Find it on the | ||
[project page in the Descope Console](https://app.descope.com/settings/project). | ||
### Setup | ||
Before you can use authentication functions listed below, you must initialize `descopeClient` to use all of the built-in SDK functions. | ||
You'll need your Descope `Project ID` to create this, and you can find it on the [project page](https://app.descope.com/settings/project) in the Descope Console. | ||
```typescript | ||
@@ -30,9 +33,89 @@ import DescopeClient from '@descope/node-sdk'; | ||
## Usage | ||
Once you've created a `descopeClient`, you can use that to work with the following functions: | ||
Here are some examples how to manage and authenticate users: | ||
1. [OTP Authentication](#otp-authentication) | ||
2. [Magic Link](#magic-link) | ||
3. [Enchanted Link](#enchanted-link) | ||
4. [OAuth](#oauth) | ||
5. [SSO/SAML](#ssosaml) | ||
6. [TOTP Authentication](#totp-authentication) | ||
7. [Passwords](#passwords) | ||
8. [Session Validation](#session-validation) | ||
9. [Roles & Permission Validation](#roles--permission-validation) | ||
10. [Logging Out](#logging-out) | ||
## Management Functions | ||
### Setup | ||
Before you can use management functions listed below, you must initialize `descopeClient`. | ||
If you wish to also use management functions, you will need to initialize a new version of your `descopeClient`, but this time with a `ManagementKey` as well as your `Project ID`. Create a management key in the [Descope Console](https://app.descope.com/settings/company/managementkeys). | ||
```typescript | ||
import DescopeClient from '@descope/node-sdk'; | ||
const descopeClient = DescopeClient({ | ||
projectId: 'my-project-ID', | ||
managementKey: 'management-key', | ||
}); | ||
``` | ||
Then, you can use that to work with the following functions: | ||
1. [Manage Tenants](#manage-tenants) | ||
2. [Manage Users](#manage-users) | ||
3. [Manage Access Keys](#manage-access-keys) | ||
4. [Manage SSO Setting](#manage-sso-setting) | ||
5. [Manage Permissions](#manage-permissions) | ||
6. [Manage Roles](#manage-roles) | ||
7. [Query SSO Groups](#query-sso-groups) | ||
8. [Manage Flows](#manage-flows) | ||
9. [Manage JWTs](#manage-jwts) | ||
10. [Impersonate](#impersonate) | ||
11. [Embedded Links](#embedded-links) | ||
12. [Audit](#audit) | ||
13. [Manage FGA (Fine-grained Authorization)](#manage-fga-fine-grained-authorization) | ||
14. [Manage Project](#manage-project) | ||
15. [Manage SSO applications](#manage-sso-applications) | ||
If you wish to run any of our code samples and play with them, check out our [Code Examples](#code-examples) section. | ||
If you're performing end-to-end testing, check out the [Utils for your end to end (e2e) tests and integration tests](#utils-for-your-end-to-end-e2e-tests-and-integration-tests) section. You will need to use the `descopeClient` you created under the setup of [Management Functions](#management-functions). | ||
--- | ||
## Error Handling | ||
Every `async` operation may fail. In case it does, there will be information regarding what happened on the response object. | ||
A typical case of error handling might look something like: | ||
```ts | ||
import { SdkResponse, descopeErrors } from '@descope/node-sdk'; | ||
// ... | ||
try { | ||
const resp = await sdk.otp.signIn.email(loginId); | ||
if (resp.error) { | ||
switch (resp.error.errorCode) { | ||
case descopeErrors.userNotFound: | ||
// Handle specifically | ||
break; | ||
default: | ||
// Handle generally | ||
// `resp.error` will contain `errorCode`, `errorDescription` and sometimes `errorMessage` to | ||
// help understand what went wrong. See SdkResponse for more information. | ||
} | ||
} | ||
} catch (e) { | ||
// Handle technical error | ||
} | ||
``` | ||
--- | ||
### OTP Authentication | ||
Send a user a one-time password (OTP) using your preferred delivery method (_email / SMS_). An email address or phone number must be provided accordingly. | ||
Send a user a one-time password (OTP) using your preferred delivery method (_Email / SMS / Voice call / WhatsApp_). An email address or phone number must be provided accordingly. | ||
@@ -224,2 +307,68 @@ The user can either `sign up`, `sign in` or `sign up or in` | ||
### Passwords | ||
The user can also authenticate with a password, though it's recommended to | ||
prefer passwordless authentication methods if possible. Sign up requires the | ||
caller to provide a valid password that meets all the requirements configured | ||
for the [password authentication method](https://app.descope.com/settings/authentication/password) in the Descope console. | ||
```js | ||
// Every user must have a loginId. All other user information is optional | ||
const loginId = 'desmond@descope.com'; | ||
const password = 'qYlvi65KaX'; | ||
const user = { | ||
name: 'Desmond Copeland', | ||
email: loginId, | ||
}; | ||
const jwtResponse = await descopeClient.password.signUp(loginId, password, user); | ||
// jwtResponse.data.sessionJwt; | ||
// jwtResponse.data.refreshJwt; | ||
``` | ||
The user can later sign in using the same loginId and password. | ||
```js | ||
const jwtResponse = await descopeClient.password.signIn(loginId, password); | ||
// jwtResponse.data.sessionJwt; | ||
// jwtResponse.data.refreshJwt; | ||
``` | ||
The session and refresh JWTs should be returned to the caller, and passed with every request in the session. Read more on [session validation](#session-validation) | ||
In case the user needs to update their password, one of two methods are available: Resetting their password or replacing their password | ||
**Changing Passwords** | ||
_NOTE: sendReset will only work if the user has a validated email address. Otherwise password reset prompts cannot be sent._ | ||
In the [password authentication method](https://app.descope.com/settings/authentication/password) in the Descope console, it is possible to define which alternative authentication method can be used in order to authenticate the user, in order to reset and update their password. | ||
```js | ||
// Start the reset process by sending a password reset prompt. In this example we'll assume | ||
// that magic link is configured as the reset method. The optional redirect URL is used in the | ||
// same way as in regular magic link authentication. | ||
const loginId = 'desmond@descope.com'; | ||
const redirectURL = 'https://myapp.com/password-reset'; | ||
const passwordResetResponse = await descopeClient.password.sendReset(loginId, redirectURL); | ||
``` | ||
The magic link, in this case, must then be verified like any other magic link (see the [magic link section](#magic-link) for more details). However, after verifying the user, it is expected | ||
to allow them to provide a new password instead of the old one. Since the user is now authenticated, this is possible via: | ||
```js | ||
// The refresh token is required to make sure the user is authenticated. | ||
await descopeClient.password.update(loginId, newPassword, token); | ||
``` | ||
`update()` can always be called when the user is authenticated and has a valid session. | ||
Alternatively, it is also possible to replace an existing active password with a new one. | ||
```js | ||
// Replaces the user's current password with a new one | ||
const jwtResponse = await descopeClient.password.replace(loginId, oldPassword, newPassword); | ||
// jwtResponse.data.sessionJwt; | ||
// jwtResponse.data.refreshJwt; | ||
``` | ||
### Session Validation | ||
@@ -273,3 +422,3 @@ | ||
res.status(401).json({ | ||
error: new Error('Unauthorized!'), | ||
error: 'Unauthorized!', | ||
}); | ||
@@ -290,7 +439,5 @@ } | ||
// You can validate specific permissions | ||
const validTenantPermissions = await descopeClient.validateTenantPermissions( | ||
authInfo, | ||
'my-tenant-ID', | ||
['Permission to validate'], | ||
); | ||
const validTenantPermissions = descopeClient.validateTenantPermissions(authInfo, 'my-tenant-ID', [ | ||
'Permission to validate', | ||
]); | ||
if (!validTenantPermissions) { | ||
@@ -301,3 +448,3 @@ // Deny access | ||
// Or validate roles directly | ||
const validTenantRoles = await descopeClient.validateTenantRoles(authInfo, 'my-tenant-ID', [ | ||
const validTenantRoles = descopeClient.validateTenantRoles(authInfo, 'my-tenant-ID', [ | ||
'Role to validate', | ||
@@ -308,2 +455,14 @@ ]); | ||
} | ||
// Or get the matched roles/permissions | ||
const matchedTenantRoles = descopeClient.getMatchedTenantRoles(authInfo, 'my-tenant-ID', [ | ||
'Role to validate', | ||
'Another role to validate', | ||
]); | ||
const matchedTenantPermissions = descopeClient.getMatchedTenantPermissions( | ||
authInfo, | ||
'my-tenant-ID', | ||
['Permission to validate', 'Another permission to validate'], | ||
); | ||
``` | ||
@@ -315,5 +474,3 @@ | ||
// You can validate specific permissions | ||
const validPermissions = await descopeClient.validatePermissions(authInfo, [ | ||
'Permission to validate', | ||
]); | ||
const validPermissions = descopeClient.validatePermissions(authInfo, ['Permission to validate']); | ||
if (!validPermissions) { | ||
@@ -324,6 +481,17 @@ // Deny access | ||
// Or validate roles directly | ||
const validRoles = await descopeClient.validateRoles(authInfo, ['Role to validate']); | ||
const validRoles = descopeClient.validateRoles(authInfo, ['Role to validate']); | ||
if (!validRoles) { | ||
// Deny access | ||
} | ||
// Or get the matched roles/permissions | ||
const matchedRoles = descopeClient.getMatchedRoles(authInfo, [ | ||
'Role to validate', | ||
'Another role to validate', | ||
]); | ||
const matchedPermissions = descopeClient.getMatchedPermissions(authInfo, [ | ||
'Permission to validate', | ||
'Another permission to validate', | ||
]); | ||
``` | ||
@@ -347,6 +515,6 @@ | ||
## Management API | ||
## Management Functions | ||
It is very common for some form of management or automation to be required. These can be performed | ||
using the management API. Please note that these actions are more sensitive as they are administrative | ||
using the management functions. Please note that these actions are more sensitive as they are administrative | ||
in nature. Please use responsibly. | ||
@@ -370,3 +538,3 @@ | ||
You can create, update, delete or load tenants: | ||
You can create, update, delete or load tenants, as well as read and update tenant settings: | ||
@@ -376,16 +544,26 @@ ```typescript | ||
// Users logging in to this tenant | ||
await descopeClient.management.tenant.create('My Tenant', ['domain.com']); | ||
await descopeClient.management.tenant.create('My Tenant', ['domain.com'], { | ||
customAttributeName: 'val', | ||
}); | ||
// You can optionally set your own ID when creating a tenant | ||
await descopeClient.management.tenant.createWithId('my-custom-id', 'My Tenant', ['domain.com']); | ||
await descopeClient.management.tenant.createWithId('my-custom-id', 'My Tenant', ['domain.com'], { | ||
customAttributeName: 'val', | ||
}); | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.tenant.update('my-custom-id', 'My Tenant', [ | ||
'domain.com', | ||
'another-domain.com', | ||
]); | ||
await descopeClient.management.tenant.update( | ||
'my-custom-id', | ||
'My Tenant', | ||
['domain.com', 'another-domain.com'], | ||
{ customAttributeName: 'val' }, | ||
); | ||
// Tenant deletion cannot be undone. Use carefully. | ||
await descopeClient.management.tenant.delete('my-custom-id'); | ||
// Pass true to cascade value, in case you want to delete all users/keys associated only with this tenant | ||
await descopeClient.management.tenant.delete('my-custom-id', false); | ||
// Load tenant by id | ||
const tenant = await descopeClient.management.tenant.load('my-custom-id'); | ||
// Load all tenants | ||
@@ -396,4 +574,113 @@ const tenantsRes = await descopeClient.management.tenant.loadAll(); | ||
}); | ||
// Search all tenants according to various parameters | ||
const searchRes = await descopeClient.management.tenant.searchAll(['id']); | ||
searchRes.data.forEach((tenant) => { | ||
// do something | ||
}); | ||
// Load tenant settings by id | ||
const tenantSettings = await descopeClient.management.tenant.getSettings('my-tenant-id'); | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.tenant.configureSettings('my-tenant-id', { | ||
domains: ['domain1.com'], | ||
selfProvisioningDomains: ['domain1.com'], | ||
sessionSettingsEnabled: true, | ||
refreshTokenExpiration: 12, | ||
refreshTokenExpirationUnit: 'days', | ||
sessionTokenExpiration: 10, | ||
sessionTokenExpirationUnit: 'minutes', | ||
enableInactivity: true, | ||
JITDisabled: false, | ||
InactivityTime: 10, | ||
InactivityTimeUnit: 'minutes', | ||
}); | ||
// Generate tenant admin self service link for SSO configuration (valid for 24 hours) | ||
const res = await descopeClient.management.tenant.generateSSOConfigurationLink( | ||
'my-tenant-id', | ||
60 * 60 * 24, | ||
); | ||
console.log(res.adminSSOConfigurationLink); | ||
``` | ||
### Manage Password | ||
You can read and update any tenant password settings and policy: | ||
```typescript | ||
// Load tenant password settings by id | ||
const passwordSettings = await descopeClient.management.password.getSettings('my-tenant-id'); | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.password.configureSettings('my-tenant-id', { | ||
enabled: true, | ||
minLength: 8, | ||
expiration: true, | ||
expirationWeeks: 4, | ||
lock: true, | ||
lockAttempts: 5, | ||
reuse: true, | ||
reuseAmount: 6, | ||
lowercase: true, | ||
uppercase: false, | ||
number: true, | ||
nonAlphaNumeric: false, | ||
}); | ||
``` | ||
### Manage SSO applications | ||
You can create, update, delete or load SSO applications: | ||
```typescript | ||
// Create OIDC sso application | ||
await descopeClient.management.ssoApplication.createOidcApplication({ | ||
name: 'My OIDC app name', | ||
loginPageUrl: 'http://dummy.com/login', | ||
}); | ||
// Create SAML sso application | ||
await descopeClient.management.ssoApplication.createSamlApplication({ | ||
name: 'My SAML app name', | ||
loginPageUrl: 'http://dummy.com/login', | ||
useMetadataInfo: true, | ||
metadataUrl: 'http://dummy.com/metadata', | ||
}); | ||
// Update OIDC sso application. | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.ssoApplication.updateOidcApplication({ | ||
id: 'my-app-id', | ||
name: 'My OIDC app name', | ||
loginPageUrl: 'http://dummy.com/login', | ||
}); | ||
// Update SAML sso application. | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.ssoApplication.updateSamlApplication({ | ||
id: 'my-app-id', | ||
name: 'My SAML app name', | ||
loginPageUrl: 'http://dummy.com/login', | ||
enabled: true, | ||
useMetadataInfo: false, | ||
entityId: 'entity1234', | ||
aceUrl: 'http://dummy.com/acs', | ||
certificate: 'certificate', | ||
}); | ||
// Tenant deletion cannot be undone. Use carefully. | ||
await descopeClient.management.ssoApplication.delete('my-app-id'); | ||
// Load sso application by id | ||
const app = await descopeClient.management.ssoApplication.load('my-app-id'); | ||
// Load all sso applications | ||
const appsRes = await descopeClient.management.ssoApplication.loadAll(); | ||
appsRes.data.forEach((app) => { | ||
// do something | ||
}); | ||
``` | ||
### Manage Users | ||
@@ -407,23 +694,55 @@ | ||
// on a per-tenant basis. | ||
await descopeClient.management.user.create( | ||
'desmond@descope.com', | ||
'desmond@descope.com', | ||
null, | ||
'Desmond Copeland', | ||
null, | ||
[{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
await descopeClient.management.user.create('desmond@descope.com', { | ||
email: 'desmond@descope.com', | ||
displayName: 'Desmond Copeland', | ||
userTenants: [{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
}); | ||
// Alternatively, a user can be created and invited via an email / text message. | ||
// Make sure to configure the invite URL in the Descope console prior to using this function, | ||
// and that an email address / phone number is provided in the information. | ||
await descopeClient.management.user.invite('desmond@descope.com', { | ||
email: 'desmond@descope.com', | ||
displayName: 'Desmond Copeland', | ||
userTenants: [{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
// You can inject custom data into the template. | ||
// Note that you first need to configure custom template in Descope Console | ||
// For example: configure {{options_k1}} in the custom template, and pass { k1: 'v1' } as templateOptions | ||
templateOptions: { k1: 'v1', k2: 'v2' }, | ||
}); | ||
// You can invite batch of users via an email / text message. | ||
// Make sure to configure the invite URL in the Descope console prior to using this function, | ||
// and that an email address / phone number is provided in the information. You can also set | ||
// a cleartext password or import a prehashed one from another service. | ||
await descopeClient.management.user.inviteBatch( | ||
[ | ||
{ | ||
loginId: 'desmond@descope.com', | ||
email: 'desmond@descope.com', | ||
phone: '+123456789123', | ||
displayName: 'Desmond Copeland', | ||
userTenants: [{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
hashedPassword: { | ||
bcrypt: { | ||
hash: '$2a$...', | ||
}, | ||
}, | ||
}, | ||
], | ||
'<invite_url>', | ||
true, | ||
false, | ||
); | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.user.update( | ||
'desmond@descope.com', | ||
'desmond@descope.com', | ||
null, | ||
'Desmond Copeland', | ||
null, | ||
[{ tenantId: 'tenant-ID1', roleNames: ['role-name1', 'role-name2'] }], | ||
); | ||
await descopeClient.management.user.update('desmond@descope.com', { | ||
email: 'desmond@descope.com', | ||
displayName: 'Desmond Copeland', | ||
userTenants: [{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
}); | ||
// Update explicit data for a user rather than overriding all fields | ||
await descopeClient.management.user.updatePhone('desmond@descope.com', '+18005551234', true); | ||
await descopeClient.management.user.updateLoginId('desmond@descope.com', 'bane@descope.com'); | ||
await descopeClient.management.user.removeTenantRoles( | ||
@@ -435,2 +754,6 @@ 'desmond@descope.com', | ||
// Update explicit user's data using patch (will override only provided fields) | ||
const options: PatchUserOptions = { displayName: 'Desmond Copeland Jr.' }; | ||
await descopeClient.management.user.patch('desmond@descope.com', options); | ||
// User deletion cannot be undone. Use carefully. | ||
@@ -446,8 +769,87 @@ await descopeClient.management.user.delete('desmond@descope.com'); | ||
// Search all users, optionally according to tenant and/or role filter | ||
const usersRes = await descopeClient.management.user.searchAll(['tenant-ID']); | ||
// Results can be paginated using the limit and page parameters | ||
const usersRes = await descopeClient.management.user.search({ tenantIds: ['tenant-ID'] }); | ||
usersRes.data.forEach((user) => { | ||
// do something | ||
}); | ||
await descopeClient.management.user.logoutUser('my-custom-id'); | ||
await descopeClient.management.user.logoutUserByUserId('<user-ID>'); | ||
// Get users' authentication history | ||
const userIds = ['user-id-1', 'user-id-2']; | ||
const usersHistoryRes = await descopeClient.management.user.history(userIds); | ||
usersHistoryRes.forEach((userHistory) => { | ||
// do something | ||
}); | ||
``` | ||
#### Set or Expire User Password | ||
You can set a new active password for a user that they can sign in with. | ||
You can also set a temporary password that they user will be forced to change on the next login. | ||
For a user that already has an active password, you can expire their current password, effectively requiring them to change it on the next login. | ||
```typescript | ||
// Set a user's temporary password | ||
await descopeClient.management.user.setTemporaryPassword('<login-ID>', '<some-password>'); | ||
// Set a user's password | ||
await descopeClient.management.user.setActivePassword('<login-ID>', '<some-password>'); | ||
// Or alternatively, expire a user password | ||
await descopeClient.management.user.expirePassword('<login-ID>'); | ||
``` | ||
### Manage Project | ||
You can update project name and tags, as well as clone the current project to a new one: | ||
```typescript | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.project.updateName('new-project-name'); | ||
// Set will override all fields as is. Use carefully. | ||
await descopeClient.management.project.updateTags(['tag1!', 'new']); | ||
// Clone the current project to a new one | ||
// Note that this action is supported only with a pro license or above. | ||
const cloneRes = await descopeClient.management.project.clone('new-project-name'); | ||
``` | ||
With using a company management key you can get a list of all the projects in the company: | ||
```typescript | ||
const projects = await descopeClient.management.project.listProjects(); | ||
``` | ||
You can manage your project's settings and configurations by exporting a snapshot: | ||
```typescript | ||
// Exports the current state of the project | ||
const exportRes = await descopeClient.management.project.exportSnapshot(); | ||
``` | ||
You can also import previously exported snapshots into the same project or a different one: | ||
```typescript | ||
const validateReq = { | ||
files: exportRes.files, | ||
}; | ||
// Validate that an exported snapshot can be imported into the current project | ||
const validateRes = await descopeClient.management.project.import(files); | ||
if (!validateRes.ok) { | ||
// validation failed, check failures and missingSecrets to fix this | ||
} | ||
// Import the previously exported snapshot into the current project | ||
const importReq = { | ||
files: exportRes.files, | ||
}; | ||
await descopeClient.management.project.importSnapshot(files); | ||
``` | ||
### Manage Access Keys | ||
@@ -461,2 +863,6 @@ | ||
// on a per-tenant basis. | ||
// If userId is supplied, then authorization will be ignored, and the access key will be bound to the user's authorization. | ||
// If customClaims is supplied, then those claims will be present in the JWT returned by calls to ExchangeAccessKey. | ||
// If description is supplied, then the access key will hold a descriptive text. | ||
// If permittedIps is supplied, then the access key can only be used from that list of IP addresses or CIDR ranges. | ||
await descopeClient.management.accessKey.create( | ||
@@ -479,3 +885,3 @@ 'key-name', | ||
// Update will override all fields as is. Use carefully. | ||
await descopeClient.management.accessKey.update('key-id', 'new-key-name'); | ||
await descopeClient.management.accessKey.update('key-id', 'new-key-name', 'new-description'); | ||
@@ -497,2 +903,5 @@ // Access keys can be deactivated to prevent usage. This can be undone using "activate". | ||
```typescript | ||
// You can get SSO settings for a specific tenant ID | ||
const ssoSettings = await descopeClient.management.sso.loadSettings("tenant-id") | ||
// You can configure SSO settings manually by setting the required fields directly | ||
@@ -503,8 +912,15 @@ const tenantId = 'tenant-id' // Which tenant this configuration is for | ||
const idpCert = '<your-cert-here>' | ||
const redirectURL = 'https://my-app.com/handle-saml' // Global redirect URL for SSO/SAML | ||
await descopeClient.management.sso.configureSettings(tenantID, idpURL, entityID, idpCert, redirectURL) | ||
const redirectURL = 'https://my-app.com/handle-sso' // Global redirect URL for SSO/SAML | ||
const domains = ['tenant-users.com'] // Users authentication with this domain will be logged in to this tenant | ||
await descopeClient.management.sso.configureSAMLSettings(tenantID, {idpURL, entityID, idpCert}, redirectURL, domains) | ||
// Alternatively, configure using an SSO metadata URL | ||
await descopeClient.management.sso.configureMetadata(tenantID, 'https://idp.com/my-idp-metadata') | ||
await descopeClient.management.sso.configureSAMLByMetadata(tenantID, {idpMetadataUrl: 'https://idp.com/my-idp-metadata'}, redirectURL, domains) | ||
// In case SSO is configured to work with OIDC use the following | ||
const name = 'some-name'; | ||
const clientId = 'client id of OIDC'; | ||
const clientSecret = 'client secret'; | ||
await descopeClient.management.sso.configureOIDCSettings(tenantID, {name, clientId, clientSecret, redirectUrl}, domains) | ||
// Map IDP groups to Descope roles, or map user attributes. | ||
@@ -514,3 +930,3 @@ // This function overrides any previous mapping (even when empty). Use carefully. | ||
tenantId, | ||
{ groups: ['IDP_ADMIN'], role: 'Tenant Admin'} | ||
[{ groups: ['IDP_ADMIN'], roleName: 'Tenant Admin'}] | ||
{ name: 'IDP_NAME', phoneNumber: 'IDP_PHONE'}, | ||
@@ -528,2 +944,5 @@ ) | ||
// You can delete SSO settings for a specific tenant ID | ||
await descopeClient.management.sso.deleteSettings("tenant-id") | ||
### Manage Permissions | ||
@@ -560,6 +979,8 @@ | ||
// You can optionally set a description and associated permission for a roles. | ||
// The optional `tenantId` will scope this role for a specific tenant. If left empty, the role will be available to all tenants. | ||
const name = 'My Role'; | ||
const tenantId = '<tenant id>'; | ||
let description = 'Optional description to briefly explain what this role allows.'; | ||
const permissionNames = ['My Updated Permission']; | ||
descopeClient.management.role.create(name, description, permissionNames); | ||
descopeClient.management.role.create(name, description, permissionNames, tenantId); | ||
@@ -570,6 +991,6 @@ // Update will override all fields as is. Use carefully. | ||
permissionNames.push('Another Permission'); | ||
descopeClient.management.role.update(name, newName, description, permissionNames); | ||
descopeClient.management.role.update(name, newName, description, permissionNames, tenantId); | ||
// Role deletion cannot be undone. Use carefully. | ||
descopeClient.management.role.delete(newName); | ||
descopeClient.management.role.delete(newName, tenantId); | ||
@@ -581,2 +1002,11 @@ // Load all roles | ||
}); | ||
// Search roles | ||
const rolesRes = await descopeClient.management.role.search({ | ||
tenantIds: ['t1', 't2'], | ||
roleNames: ['role1'], | ||
}); | ||
rolesRes.data.forEach((role) => { | ||
// do something | ||
}); | ||
``` | ||
@@ -613,2 +1043,41 @@ | ||
### Manage Flows | ||
You can list your flows and also import and export flows and screens, or the project theme: | ||
```typescript | ||
// List all project flows | ||
const res = await descopeClient.management.flow.list(); | ||
console.log('found total flows', res.total); | ||
res.flows.forEach((flowMetadata) => { | ||
// do something | ||
}); | ||
// Delete flows by ids | ||
await descopeClient.management.flow.delete(['flow-1', 'flow-2']); | ||
// Export the flow and it's matching screens based on the given id | ||
const res = await descopeClient.management.flow.export('sign-up'); | ||
console.log('found flow', res.data.flow); | ||
res.data.screens.forEach((screen) => { | ||
// do something | ||
}); | ||
// Import the given flow and screens as the given id | ||
const { flow, screens } = res.data; | ||
const updatedRes = descopeClient.management.flow.import('sign-up', flow, screens); | ||
console.log('updated flow', updatedRes.data.flow); | ||
updatedRes.data.screens.forEach((screen) => { | ||
// do something | ||
}); | ||
// Export the current theme of the project | ||
const res = descopeClient.management.theme.export(); | ||
console.log(res.data.theme); | ||
// Import the given theme to the project | ||
const updatedRes = descopeClient.management.theme.import(theme); | ||
console.log(updatedRes.data.theme); | ||
``` | ||
### Manage JWTs | ||
@@ -625,5 +1094,183 @@ | ||
### Impersonate | ||
You can impersonate to another user | ||
The impersonator user must have the `impersonation` permission in order for this request to work. | ||
The response would be a refresh JWT of the impersonated user | ||
```typescript | ||
const updatedJWTRes = await descopeClient.management.jwt.impersonate( | ||
'impersonator-id', | ||
'login-id', | ||
true, | ||
); | ||
``` | ||
Note 1: The generate code/link functions, work only for test users, will not work for regular users. | ||
Note 2: In case of testing sign-in / sign-up operations with test users, need to make sure to generate the code prior calling the sign-in / sign-up operations. | ||
### Embedded Links | ||
Embedded links can be created to directly receive a verifiable token without sending it. | ||
This token can then be verified using the magic link 'verify' function, either directly or through a flow. | ||
```typescript | ||
const { token } = await descopeClient.management.user.generateEmbeddedLink('desmond@descope.com', { | ||
key1: 'value1', | ||
}); | ||
``` | ||
### Audit | ||
You can perform an audit search for either specific values or full-text across the fields. Audit search is limited to the last 30 days. | ||
```typescript | ||
// Full text search on the last 10 days | ||
const audits = await descopeClient.management.audit.search({ | ||
from: Date.now() - 10 * 24 * 60 * 60 * 1000, | ||
text: 'some-text', | ||
}); | ||
console.log(audits); | ||
// Search successful logins in the last 30 days | ||
const audits = await descopeClient.management.audit.search({ actions: ['LoginSucceed'] }); | ||
console.log(audits); | ||
``` | ||
You can also create audit event with data | ||
```typescript | ||
await descopeClient.management.audit.createEvent({ | ||
action: 'pencil.created', | ||
type: 'info', // info/warn/error | ||
actorId: 'UXXX', | ||
tenantId: 'tenant-id', | ||
data: { | ||
some: 'data', | ||
}, | ||
}); | ||
``` | ||
### Manage FGA (Fine-grained Authorization) | ||
Descope supports full relation based access control (ReBAC) using a zanzibar like schema and operations. | ||
A schema is comprised of types (entities like documents, folders, orgs, etc.) and each type has relation definitions and permission to define relations to other types. | ||
A simple example for a file system like schema would be: | ||
```yaml | ||
model AuthZ 1.0 | ||
type user | ||
type org | ||
relation member: user | ||
relation parent: org | ||
type folder | ||
relation parent: folder | ||
relation owner: user | org#member | ||
relation editor: user | ||
relation viewer: user | ||
permission can_create: owner | parent.owner | ||
permission can_edit: editor | can_create | ||
permission can_view: viewer | can_edit | ||
type doc | ||
relation parent: folder | ||
relation owner: user | org#member | ||
relation editor: user | ||
relation viewer: user | ||
permission can_create: owner | parent.owner | ||
permission can_edit: editor | can_create | ||
permission can_view: viewer | can_edit | ||
``` | ||
Descope SDK allows you to fully manage the schema and relations as well as perform simple (and not so simple) checks regarding the existence of relations. | ||
```typescript | ||
const descopeClient = require('@descope/node-sdk'); | ||
// Save schema | ||
await descopeClient.management.fga.saveSchema(schema); | ||
// Create a relation between a resource and user | ||
await descopeClient.management.fga.createRelations([ | ||
{ | ||
resource: 'some-doc', | ||
resourceType: 'doc', | ||
relation: 'owner', | ||
target: 'u1', | ||
targetType: 'user', | ||
}, | ||
]); | ||
// Check if target has a relevant relation | ||
// The answer should be true because an owner can also view | ||
const relations = await descopeClient.management.fga.check([ | ||
{ | ||
resource: 'some-doc', | ||
resourceType: 'doc', | ||
relation: 'can_view', | ||
target: 'u1', | ||
targetType: 'user', | ||
}, | ||
]); | ||
``` | ||
### Utils for your end to end (e2e) tests and integration tests | ||
To ease your e2e tests, we exposed dedicated management methods, | ||
that way, you don't need to use 3rd party messaging services in order to receive sign-in/up Email, SMS, Voice call or WhatsApp, and avoid the need of parsing the code and token from them. | ||
```typescript | ||
// User for test can be created, this user will be able to generate code/link without | ||
// the need of 3rd party messaging services. | ||
// Test user must have a loginId, other fields are optional. | ||
// Roles should be set directly if no tenants exist, otherwise set | ||
// on a per-tenant basis. | ||
await descopeClient.management.user.createTestUser('desmond@descope.com', { | ||
email: 'desmond@descope.com', | ||
displayName: 'Desmond Copeland', | ||
userTenants: [{ tenantId: 'tenant-ID1', roleNames: ['role-name1'] }], | ||
}); | ||
// Search all test users according to various parameters | ||
const searchRes = await descopeClient.management.user.searchTestUsers(['id']); | ||
searchRes.data.forEach((user) => { | ||
// do something | ||
}); | ||
// Now test user got created, and this user will be available until you delete it, | ||
// you can use any management operation for test user CRUD. | ||
// You can also delete all test users. | ||
await descopeClient.management.user.deleteAllTestUsers(); | ||
// OTP code can be generated for test user, for example: | ||
const { code } = await descopeClient.management.user.generateOTPForTestUser( | ||
'sms', // you can use also 'email', 'whatsapp', 'voice' | ||
'desmond@descope.com', | ||
); | ||
// Now you can verify the code is valid (using descopeClient.auth.*.verify for example) | ||
// LoginOptions can be provided to set custom claims to the generated jwt. | ||
// Same as OTP, magic link can be generated for test user, for example: | ||
const { link } = await descopeClient.management.user.generateMagicLinkForTestUser( | ||
'email', | ||
'desmond@descope.com', | ||
'', | ||
); | ||
// Enchanted link can be generated for test user, for example: | ||
const { link, pendingRef } = await descopeClient.management.user.generateEnchantedLinkForTestUser( | ||
'desmond@descope.com', | ||
'', | ||
); | ||
``` | ||
## Code Examples | ||
You can find various usage examples in the [examples folder](https://github.com/descope/node-sdk/blob/main/examples). | ||
You can find various usage examples in the [examples folder](/examples). | ||
@@ -667,2 +1314,23 @@ ### Setup | ||
## Providing Custom Public Key | ||
By default, the SDK will download the public key from Descope's servers. You can also provide your own public key. This is useful when the server you are running the SDK on does not have access to the internet. | ||
You can find your public key in the `https://api.descope.com/v2/keys/<project-id>` endpoint. For further information, please see the [Descope Documentation and API reference page](https://docs.descope.com/api/openapi/sessiongetkeys/operation/GetKeysV2). | ||
To provide your own public key, you can do so by providing the `publicKey` option when initializing the SDK: | ||
```typescript | ||
import DescopeClient from '@descope/node-sdk'; | ||
const descopeClient = DescopeClient({ | ||
projectId: 'my-project-ID', | ||
publicKey: '{"alg":"RS256", ... }', | ||
}); | ||
// The public key will be used when validating jwt | ||
const sessionJWt = '<session-jwt>'; | ||
await descopeClient.validateJwt(sessionJWt); | ||
``` | ||
## Learn More | ||
@@ -669,0 +1337,0 @@ |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
459577
43
1862
1319
1
+ Addedcross-fetch@^4.0.0
+ Addedtslib@^2.0.0
+ Added@descope/core-js-sdk@2.31.0(transitive)
+ Addedcross-fetch@4.1.0(transitive)
+ Addedjose@5.2.2(transitive)
+ Addedjwt-decode@4.0.0(transitive)
+ Addednode-fetch@2.7.0(transitive)
- Removednode-fetch@2.6.8
- Removed@descope/core-js-sdk@0.0.41-alpha.55(transitive)
- Removedjose@4.11.2(transitive)
- Removedjwt-decode@3.1.2(transitive)
- Removedlodash.get@4.4.2(transitive)
- Removednode-fetch@2.6.8(transitive)
Updated@descope/core-js-sdk@2.31.0
Updatedjose@5.2.2