@stackframe/stack 2.5.18 → 2.5.20

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (60) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/dist/components/credential-sign-in.js +1 -3
  3. package/dist/components/credential-sign-in.js.map +1 -1
  4. package/dist/components/elements/sidebar-layout.d.mts +20 -0
  5. package/dist/components/elements/sidebar-layout.d.ts +20 -0
  6. package/dist/components/elements/sidebar-layout.js +111 -0
  7. package/dist/components/elements/sidebar-layout.js.map +1 -0
  8. package/dist/components/elements/user-avatar.d.mts +5 -12
  9. package/dist/components/elements/user-avatar.d.ts +5 -12
  10. package/dist/components/elements/user-avatar.js.map +1 -1
  11. package/dist/components/selected-team-switcher.js +36 -23
  12. package/dist/components/selected-team-switcher.js.map +1 -1
  13. package/dist/components/team-icon.d.mts +18 -0
  14. package/dist/components/team-icon.d.ts +18 -0
  15. package/dist/components/team-icon.js +50 -0
  16. package/dist/components/team-icon.js.map +1 -0
  17. package/dist/components-page/account-settings.d.mts +2 -1
  18. package/dist/components-page/account-settings.d.ts +2 -1
  19. package/dist/components-page/account-settings.js +405 -220
  20. package/dist/components-page/account-settings.js.map +1 -1
  21. package/dist/components-page/stack-handler.js +3 -5
  22. package/dist/components-page/stack-handler.js.map +1 -1
  23. package/dist/components-page/team-creation.d.mts +7 -0
  24. package/dist/components-page/team-creation.d.ts +7 -0
  25. package/dist/components-page/team-creation.js +92 -0
  26. package/dist/components-page/team-creation.js.map +1 -0
  27. package/dist/esm/components/credential-sign-in.js +1 -3
  28. package/dist/esm/components/credential-sign-in.js.map +1 -1
  29. package/dist/esm/components/elements/sidebar-layout.js +87 -0
  30. package/dist/esm/components/elements/sidebar-layout.js.map +1 -0
  31. package/dist/esm/components/elements/user-avatar.js.map +1 -1
  32. package/dist/esm/components/selected-team-switcher.js +40 -15
  33. package/dist/esm/components/selected-team-switcher.js.map +1 -1
  34. package/dist/esm/components/team-icon.js +15 -0
  35. package/dist/esm/components/team-icon.js.map +1 -0
  36. package/dist/esm/components-page/account-settings.js +399 -215
  37. package/dist/esm/components-page/account-settings.js.map +1 -1
  38. package/dist/esm/components-page/stack-handler.js +3 -5
  39. package/dist/esm/components-page/stack-handler.js.map +1 -1
  40. package/dist/esm/components-page/team-creation.js +68 -0
  41. package/dist/esm/components-page/team-creation.js.map +1 -0
  42. package/dist/esm/generated/global-css.js +1 -1
  43. package/dist/esm/generated/global-css.js.map +1 -1
  44. package/dist/esm/lib/auth.js +4 -0
  45. package/dist/esm/lib/auth.js.map +1 -1
  46. package/dist/esm/lib/stack-app.js +184 -34
  47. package/dist/esm/lib/stack-app.js.map +1 -1
  48. package/dist/generated/global-css.d.mts +1 -1
  49. package/dist/generated/global-css.d.ts +1 -1
  50. package/dist/generated/global-css.js +1 -1
  51. package/dist/generated/global-css.js.map +1 -1
  52. package/dist/index.d.mts +1 -1
  53. package/dist/index.d.ts +1 -1
  54. package/dist/lib/auth.js +4 -0
  55. package/dist/lib/auth.js.map +1 -1
  56. package/dist/lib/stack-app.d.mts +39 -5
  57. package/dist/lib/stack-app.d.ts +39 -5
  58. package/dist/lib/stack-app.js +184 -34
  59. package/dist/lib/stack-app.js.map +1 -1
  60. package/package.json +7 -6
@@ -239,6 +239,9 @@ type UserExtra = {
239
239
  hasPermission(scope: Team, permissionId: string): Promise<boolean>;
240
240
  setSelectedTeam(team: Team | null): Promise<void>;
241
241
  createTeam(data: TeamCreateOptions): Promise<Team>;
242
+ leaveTeam(team: Team): Promise<void>;
243
+ getTeamProfile(team: Team): Promise<EditableTeamMemberProfile>;
244
+ useTeamProfile(team: Team): EditableTeamMemberProfile;
242
245
  } & AsyncStoreProperty<"team", [id: string], Team | null, false> & AsyncStoreProperty<"teams", [], Team[], true> & AsyncStoreProperty<"permission", [scope: Team, permissionId: string, options?: {
243
246
  recursive?: boolean;
244
247
  }], TeamPermission | null, false> & AsyncStoreProperty<"permissions", [scope: Team, options?: {
@@ -318,6 +321,7 @@ type AdminProject = {
318
321
  readonly isProductionMode: boolean;
319
322
  readonly config: AdminProjectConfig;
320
323
  update(this: AdminProject, update: AdminProjectUpdateOptions): Promise<void>;
324
+ delete(this: AdminProject): Promise<void>;
321
325
  getProductionModeErrors(this: AdminProject): Promise<ProductionModeError[]>;
322
326
  useProductionModeErrors(this: AdminProject): ProductionModeError[];
323
327
  } & Project;
@@ -337,15 +341,18 @@ type ProjectConfig = {
337
341
  readonly signUpEnabled: boolean;
338
342
  readonly credentialEnabled: boolean;
339
343
  readonly magicLinkEnabled: boolean;
344
+ readonly clientTeamCreationEnabled: boolean;
340
345
  readonly oauthProviders: OAuthProviderConfig[];
341
346
  };
342
347
  type OAuthProviderConfig = {
343
348
  readonly id: string;
344
349
  };
345
350
  type AdminProjectConfig = {
351
+ readonly id: string;
346
352
  readonly signUpEnabled: boolean;
347
353
  readonly credentialEnabled: boolean;
348
354
  readonly magicLinkEnabled: boolean;
355
+ readonly clientTeamCreationEnabled: boolean;
349
356
  readonly allowLocalhost: boolean;
350
357
  readonly oauthProviders: AdminOAuthProviderConfig[];
351
358
  readonly emailConfig?: AdminEmailConfig;
@@ -353,7 +360,7 @@ type AdminProjectConfig = {
353
360
  readonly createTeamOnSignUp: boolean;
354
361
  readonly teamCreatorDefaultPermissions: AdminTeamPermission[];
355
362
  readonly teamMemberDefaultPermissions: AdminTeamPermission[];
356
- } & OAuthProviderConfig;
363
+ };
357
364
  type AdminEmailConfig = ({
358
365
  type: "standard";
359
366
  senderName: string;
@@ -389,6 +396,7 @@ type AdminProjectConfigUpdateOptions = {
389
396
  signUpEnabled?: boolean;
390
397
  credentialEnabled?: boolean;
391
398
  magicLinkEnabled?: boolean;
399
+ clientTeamCreationEnabled?: boolean;
392
400
  allowLocalhost?: boolean;
393
401
  createTeamOnSignUp?: boolean;
394
402
  emailConfig?: AdminEmailConfig;
@@ -433,6 +441,21 @@ type ApiKeyCreateOptions = {
433
441
  hasSecretServerKey: boolean;
434
442
  hasSuperSecretAdminKey: boolean;
435
443
  };
444
+ type TeamMemberProfile = {
445
+ displayName: string | null;
446
+ profileImageUrl: string | null;
447
+ };
448
+ type TeamMemberProfileUpdateOptions = {
449
+ displayName?: string;
450
+ profileImageUrl?: string | null;
451
+ };
452
+ type EditableTeamMemberProfile = TeamMemberProfile & {
453
+ update(update: TeamMemberProfileUpdateOptions): Promise<void>;
454
+ };
455
+ type TeamUser = {
456
+ id: string;
457
+ teamProfile: TeamMemberProfile;
458
+ };
436
459
  type Team = {
437
460
  id: string;
438
461
  displayName: string;
@@ -440,14 +463,25 @@ type Team = {
440
463
  inviteUser(options: {
441
464
  email: string;
442
465
  }): Promise<Result<undefined, KnownErrors["TeamPermissionRequired"]>>;
466
+ listUsers(): Promise<TeamUser[]>;
467
+ useUsers(): TeamUser[];
468
+ update(update: TeamUpdateOptions): Promise<void>;
469
+ };
470
+ type TeamUpdateOptions = {
471
+ displayName?: string;
472
+ profileImageUrl?: string | null;
443
473
  };
444
474
  type TeamCreateOptions = {
445
475
  displayName: string;
446
476
  profileImageUrl?: string;
447
477
  };
478
+ type ServerTeamMemberProfile = TeamMemberProfile;
479
+ type ServerTeamUser = ServerUser & {
480
+ teamProfile: ServerTeamMemberProfile;
481
+ };
448
482
  type ServerTeam = {
449
483
  createdAt: Date;
450
- listUsers(): Promise<ServerUser[]>;
484
+ listUsers(): Promise<ServerTeamUser[]>;
451
485
  useUsers(): ServerUser[];
452
486
  update(update: ServerTeamUpdateOptions): Promise<void>;
453
487
  delete(): Promise<void>;
@@ -510,7 +544,7 @@ type StackClientApp<HasTokenStore extends boolean = boolean, ProjectId extends s
510
544
  signInWithCredential(options: {
511
545
  email: string;
512
546
  password: string;
513
- }): Promise<KnownErrors["EmailPasswordMismatch"] | void>;
547
+ }): Promise<KnownErrors["EmailPasswordMismatch"] | KnownErrors["InvalidTotpCode"] | void>;
514
548
  signUpWithCredential(options: {
515
549
  email: string;
516
550
  password: string;
@@ -529,7 +563,7 @@ type StackClientApp<HasTokenStore extends boolean = boolean, ProjectId extends s
529
563
  teamDisplayName: string;
530
564
  }, KnownErrors["VerificationCodeError"]>>;
531
565
  verifyEmail(code: string): Promise<KnownErrors["VerificationCodeError"] | void>;
532
- signInWithMagicLink(code: string): Promise<KnownErrors["VerificationCodeError"] | void>;
566
+ signInWithMagicLink(code: string): Promise<KnownErrors["VerificationCodeError"] | KnownErrors["InvalidTotpCode"] | void>;
533
567
  redirectToOAuthCallback(): Promise<void>;
534
568
  useUser(options: GetUserOptions<HasTokenStore> & {
535
569
  or: 'redirect';
@@ -616,4 +650,4 @@ type AsyncStoreProperty<Name extends string, Args extends any[], Value, IsMultip
616
650
  [key in `use${Capitalize<Name>}`]: (...args: Args) => Value;
617
651
  };
618
652
 
619
- export { type AdminDomainConfig, type AdminEmailConfig, type AdminOAuthProviderConfig, type AdminOwnedProject, type AdminProject, type AdminProjectConfig, type AdminProjectConfigUpdateOptions, type AdminProjectCreateOptions, type AdminProjectUpdateOptions, type AdminTeamPermission, type AdminTeamPermissionDefinition, type AdminTeamPermissionDefinitionCreateOptions, type AdminTeamPermissionDefinitionUpdateOptions, type ApiKey, type ApiKeyBase, type ApiKeyBaseCrudRead, type ApiKeyCreateOptions, type ApiKeyFirstView, type Connection, type CurrentInternalServerUser, type CurrentInternalUser, type CurrentServerUser, type CurrentUser, type GetUserOptions, type HandlerUrls, type OAuthConnection, type OAuthProviderConfig, type OAuthScopesOnSignIn, type Project, type ProjectConfig, type ServerTeam, type ServerTeamCreateOptions, type ServerTeamUpdateOptions, type ServerUser, StackAdminApp, type StackAdminAppConstructorOptions, StackClientApp, type StackClientAppConstructorOptions, type StackClientAppJson, StackServerApp, type StackServerAppConstructorOptions, type Team, type TeamCreateOptions, type TeamPermission, type TokenStoreInit, type User, serverTeamPermissionDefinitionCreateOptionsToCrud, serverTeamPermissionDefinitionUpdateOptionsToCrud, stackAppInternalsSymbol };
653
+ export { type AdminDomainConfig, type AdminEmailConfig, type AdminOAuthProviderConfig, type AdminOwnedProject, type AdminProject, type AdminProjectConfig, type AdminProjectConfigUpdateOptions, type AdminProjectCreateOptions, type AdminProjectUpdateOptions, type AdminTeamPermission, type AdminTeamPermissionDefinition, type AdminTeamPermissionDefinitionCreateOptions, type AdminTeamPermissionDefinitionUpdateOptions, type ApiKey, type ApiKeyBase, type ApiKeyBaseCrudRead, type ApiKeyCreateOptions, type ApiKeyFirstView, type Connection, type CurrentInternalServerUser, type CurrentInternalUser, type CurrentServerUser, type CurrentUser, type EditableTeamMemberProfile, type GetUserOptions, type HandlerUrls, type OAuthConnection, type OAuthProviderConfig, type OAuthScopesOnSignIn, type Project, type ProjectConfig, type ServerTeam, type ServerTeamCreateOptions, type ServerTeamMemberProfile, type ServerTeamUpdateOptions, type ServerTeamUser, type ServerUser, StackAdminApp, type StackAdminAppConstructorOptions, StackClientApp, type StackClientAppConstructorOptions, type StackClientAppJson, StackServerApp, type StackServerAppConstructorOptions, type Team, type TeamCreateOptions, type TeamMemberProfile, type TeamPermission, type TeamUpdateOptions, type TeamUser, type TokenStoreInit, type User, serverTeamPermissionDefinitionCreateOptionsToCrud, serverTeamPermissionDefinitionUpdateOptionsToCrud, stackAppInternalsSymbol };
@@ -239,6 +239,9 @@ type UserExtra = {
239
239
  hasPermission(scope: Team, permissionId: string): Promise<boolean>;
240
240
  setSelectedTeam(team: Team | null): Promise<void>;
241
241
  createTeam(data: TeamCreateOptions): Promise<Team>;
242
+ leaveTeam(team: Team): Promise<void>;
243
+ getTeamProfile(team: Team): Promise<EditableTeamMemberProfile>;
244
+ useTeamProfile(team: Team): EditableTeamMemberProfile;
242
245
  } & AsyncStoreProperty<"team", [id: string], Team | null, false> & AsyncStoreProperty<"teams", [], Team[], true> & AsyncStoreProperty<"permission", [scope: Team, permissionId: string, options?: {
243
246
  recursive?: boolean;
244
247
  }], TeamPermission | null, false> & AsyncStoreProperty<"permissions", [scope: Team, options?: {
@@ -318,6 +321,7 @@ type AdminProject = {
318
321
  readonly isProductionMode: boolean;
319
322
  readonly config: AdminProjectConfig;
320
323
  update(this: AdminProject, update: AdminProjectUpdateOptions): Promise<void>;
324
+ delete(this: AdminProject): Promise<void>;
321
325
  getProductionModeErrors(this: AdminProject): Promise<ProductionModeError[]>;
322
326
  useProductionModeErrors(this: AdminProject): ProductionModeError[];
323
327
  } & Project;
@@ -337,15 +341,18 @@ type ProjectConfig = {
337
341
  readonly signUpEnabled: boolean;
338
342
  readonly credentialEnabled: boolean;
339
343
  readonly magicLinkEnabled: boolean;
344
+ readonly clientTeamCreationEnabled: boolean;
340
345
  readonly oauthProviders: OAuthProviderConfig[];
341
346
  };
342
347
  type OAuthProviderConfig = {
343
348
  readonly id: string;
344
349
  };
345
350
  type AdminProjectConfig = {
351
+ readonly id: string;
346
352
  readonly signUpEnabled: boolean;
347
353
  readonly credentialEnabled: boolean;
348
354
  readonly magicLinkEnabled: boolean;
355
+ readonly clientTeamCreationEnabled: boolean;
349
356
  readonly allowLocalhost: boolean;
350
357
  readonly oauthProviders: AdminOAuthProviderConfig[];
351
358
  readonly emailConfig?: AdminEmailConfig;
@@ -353,7 +360,7 @@ type AdminProjectConfig = {
353
360
  readonly createTeamOnSignUp: boolean;
354
361
  readonly teamCreatorDefaultPermissions: AdminTeamPermission[];
355
362
  readonly teamMemberDefaultPermissions: AdminTeamPermission[];
356
- } & OAuthProviderConfig;
363
+ };
357
364
  type AdminEmailConfig = ({
358
365
  type: "standard";
359
366
  senderName: string;
@@ -389,6 +396,7 @@ type AdminProjectConfigUpdateOptions = {
389
396
  signUpEnabled?: boolean;
390
397
  credentialEnabled?: boolean;
391
398
  magicLinkEnabled?: boolean;
399
+ clientTeamCreationEnabled?: boolean;
392
400
  allowLocalhost?: boolean;
393
401
  createTeamOnSignUp?: boolean;
394
402
  emailConfig?: AdminEmailConfig;
@@ -433,6 +441,21 @@ type ApiKeyCreateOptions = {
433
441
  hasSecretServerKey: boolean;
434
442
  hasSuperSecretAdminKey: boolean;
435
443
  };
444
+ type TeamMemberProfile = {
445
+ displayName: string | null;
446
+ profileImageUrl: string | null;
447
+ };
448
+ type TeamMemberProfileUpdateOptions = {
449
+ displayName?: string;
450
+ profileImageUrl?: string | null;
451
+ };
452
+ type EditableTeamMemberProfile = TeamMemberProfile & {
453
+ update(update: TeamMemberProfileUpdateOptions): Promise<void>;
454
+ };
455
+ type TeamUser = {
456
+ id: string;
457
+ teamProfile: TeamMemberProfile;
458
+ };
436
459
  type Team = {
437
460
  id: string;
438
461
  displayName: string;
@@ -440,14 +463,25 @@ type Team = {
440
463
  inviteUser(options: {
441
464
  email: string;
442
465
  }): Promise<Result<undefined, KnownErrors["TeamPermissionRequired"]>>;
466
+ listUsers(): Promise<TeamUser[]>;
467
+ useUsers(): TeamUser[];
468
+ update(update: TeamUpdateOptions): Promise<void>;
469
+ };
470
+ type TeamUpdateOptions = {
471
+ displayName?: string;
472
+ profileImageUrl?: string | null;
443
473
  };
444
474
  type TeamCreateOptions = {
445
475
  displayName: string;
446
476
  profileImageUrl?: string;
447
477
  };
478
+ type ServerTeamMemberProfile = TeamMemberProfile;
479
+ type ServerTeamUser = ServerUser & {
480
+ teamProfile: ServerTeamMemberProfile;
481
+ };
448
482
  type ServerTeam = {
449
483
  createdAt: Date;
450
- listUsers(): Promise<ServerUser[]>;
484
+ listUsers(): Promise<ServerTeamUser[]>;
451
485
  useUsers(): ServerUser[];
452
486
  update(update: ServerTeamUpdateOptions): Promise<void>;
453
487
  delete(): Promise<void>;
@@ -510,7 +544,7 @@ type StackClientApp<HasTokenStore extends boolean = boolean, ProjectId extends s
510
544
  signInWithCredential(options: {
511
545
  email: string;
512
546
  password: string;
513
- }): Promise<KnownErrors["EmailPasswordMismatch"] | void>;
547
+ }): Promise<KnownErrors["EmailPasswordMismatch"] | KnownErrors["InvalidTotpCode"] | void>;
514
548
  signUpWithCredential(options: {
515
549
  email: string;
516
550
  password: string;
@@ -529,7 +563,7 @@ type StackClientApp<HasTokenStore extends boolean = boolean, ProjectId extends s
529
563
  teamDisplayName: string;
530
564
  }, KnownErrors["VerificationCodeError"]>>;
531
565
  verifyEmail(code: string): Promise<KnownErrors["VerificationCodeError"] | void>;
532
- signInWithMagicLink(code: string): Promise<KnownErrors["VerificationCodeError"] | void>;
566
+ signInWithMagicLink(code: string): Promise<KnownErrors["VerificationCodeError"] | KnownErrors["InvalidTotpCode"] | void>;
533
567
  redirectToOAuthCallback(): Promise<void>;
534
568
  useUser(options: GetUserOptions<HasTokenStore> & {
535
569
  or: 'redirect';
@@ -616,4 +650,4 @@ type AsyncStoreProperty<Name extends string, Args extends any[], Value, IsMultip
616
650
  [key in `use${Capitalize<Name>}`]: (...args: Args) => Value;
617
651
  };
618
652
 
619
- export { type AdminDomainConfig, type AdminEmailConfig, type AdminOAuthProviderConfig, type AdminOwnedProject, type AdminProject, type AdminProjectConfig, type AdminProjectConfigUpdateOptions, type AdminProjectCreateOptions, type AdminProjectUpdateOptions, type AdminTeamPermission, type AdminTeamPermissionDefinition, type AdminTeamPermissionDefinitionCreateOptions, type AdminTeamPermissionDefinitionUpdateOptions, type ApiKey, type ApiKeyBase, type ApiKeyBaseCrudRead, type ApiKeyCreateOptions, type ApiKeyFirstView, type Connection, type CurrentInternalServerUser, type CurrentInternalUser, type CurrentServerUser, type CurrentUser, type GetUserOptions, type HandlerUrls, type OAuthConnection, type OAuthProviderConfig, type OAuthScopesOnSignIn, type Project, type ProjectConfig, type ServerTeam, type ServerTeamCreateOptions, type ServerTeamUpdateOptions, type ServerUser, StackAdminApp, type StackAdminAppConstructorOptions, StackClientApp, type StackClientAppConstructorOptions, type StackClientAppJson, StackServerApp, type StackServerAppConstructorOptions, type Team, type TeamCreateOptions, type TeamPermission, type TokenStoreInit, type User, serverTeamPermissionDefinitionCreateOptionsToCrud, serverTeamPermissionDefinitionUpdateOptionsToCrud, stackAppInternalsSymbol };
653
+ export { type AdminDomainConfig, type AdminEmailConfig, type AdminOAuthProviderConfig, type AdminOwnedProject, type AdminProject, type AdminProjectConfig, type AdminProjectConfigUpdateOptions, type AdminProjectCreateOptions, type AdminProjectUpdateOptions, type AdminTeamPermission, type AdminTeamPermissionDefinition, type AdminTeamPermissionDefinitionCreateOptions, type AdminTeamPermissionDefinitionUpdateOptions, type ApiKey, type ApiKeyBase, type ApiKeyBaseCrudRead, type ApiKeyCreateOptions, type ApiKeyFirstView, type Connection, type CurrentInternalServerUser, type CurrentInternalUser, type CurrentServerUser, type CurrentUser, type EditableTeamMemberProfile, type GetUserOptions, type HandlerUrls, type OAuthConnection, type OAuthProviderConfig, type OAuthScopesOnSignIn, type Project, type ProjectConfig, type ServerTeam, type ServerTeamCreateOptions, type ServerTeamMemberProfile, type ServerTeamUpdateOptions, type ServerTeamUser, type ServerUser, StackAdminApp, type StackAdminAppConstructorOptions, StackClientApp, type StackClientAppConstructorOptions, type StackClientAppJson, StackServerApp, type StackServerAppConstructorOptions, type Team, type TeamCreateOptions, type TeamMemberProfile, type TeamPermission, type TeamUpdateOptions, type TeamUser, type TokenStoreInit, type User, serverTeamPermissionDefinitionCreateOptionsToCrud, serverTeamPermissionDefinitionUpdateOptionsToCrud, stackAppInternalsSymbol };
@@ -63,7 +63,7 @@ var import_url = require("../utils/url");
63
63
  var import_auth = require("./auth");
64
64
  var import_cookie = require("./cookie");
65
65
  var NextNavigation = (0, import_compile_time.scrambleDuringCompileTime)(NextNavigationUnscrambled);
66
- var clientVersion = "js @stackframe/stack@2.5.18";
66
+ var clientVersion = "js @stackframe/stack@2.5.20";
67
67
  function getUrls(partial) {
68
68
  const handler = partial.handler ?? "/handler";
69
69
  const home = partial.home ?? "/";
@@ -216,6 +216,16 @@ var _StackClientAppImpl = class __StackClientAppImpl {
216
216
  });
217
217
  }
218
218
  );
219
+ this._teamMemberProfilesCache = createCacheBySession(
220
+ async (session, [teamId]) => {
221
+ return await this._interface.listTeamMemberProfiles({ teamId }, session);
222
+ }
223
+ );
224
+ this._currentUserTeamProfileCache = createCacheBySession(
225
+ async (session, [teamId]) => {
226
+ return await this._interface.getTeamMemberProfile({ teamId, userId: "me" }, session);
227
+ }
228
+ );
219
229
  this._memoryTokenStore = createEmptyTokenStore();
220
230
  this._requestTokenStores = /* @__PURE__ */ new WeakMap();
221
231
  this._storedCookieTokenStore = null;
@@ -497,6 +507,9 @@ var _StackClientAppImpl = class __StackClientAppImpl {
497
507
  return import_react2.default.useSyncExternalStore(subscribe, getSnapshot, getSnapshot);
498
508
  }
499
509
  async _signInToAccountWithTokens(tokens) {
510
+ if (!("accessToken" in tokens) || !("refreshToken" in tokens)) {
511
+ throw new import_errors.StackAssertionError("Invalid tokens object; can't sign in with this", { tokens });
512
+ }
500
513
  const tokenStore = this._getOrCreateTokenStore();
501
514
  tokenStore.set(tokens);
502
515
  }
@@ -524,6 +537,7 @@ var _StackClientAppImpl = class __StackClientAppImpl {
524
537
  signUpEnabled: crud.config.sign_up_enabled,
525
538
  credentialEnabled: crud.config.credential_enabled,
526
539
  magicLinkEnabled: crud.config.magic_link_enabled,
540
+ clientTeamCreationEnabled: crud.config.client_team_creation_enabled,
527
541
  oauthProviders: crud.config.enabled_oauth_providers.map((p) => ({
528
542
  id: p.id
529
543
  }))
@@ -535,6 +549,15 @@ var _StackClientAppImpl = class __StackClientAppImpl {
535
549
  id: crud.id
536
550
  };
537
551
  }
552
+ _clientTeamUserFromCrud(crud) {
553
+ return {
554
+ id: crud.user_id,
555
+ teamProfile: {
556
+ displayName: crud.display_name,
557
+ profileImageUrl: crud.profile_image_url
558
+ }
559
+ };
560
+ }
538
561
  _clientTeamFromCrud(crud) {
539
562
  const app = this;
540
563
  return {
@@ -548,6 +571,18 @@ var _StackClientAppImpl = class __StackClientAppImpl {
548
571
  session: app._getSession(),
549
572
  callbackUrl: (0, import_url.constructRedirectUrl)(app.urls.teamInvitation)
550
573
  });
574
+ },
575
+ async listUsers() {
576
+ const result = await app._teamMemberProfilesCache.getOrWait([app._getSession(), crud.id], "write-only");
577
+ return result.map((crud2) => app._clientTeamUserFromCrud(crud2));
578
+ },
579
+ useUsers() {
580
+ const result = useAsyncCache(app._teamMemberProfilesCache, [app._getSession(), crud.id], "team.useUsers()");
581
+ return result.map((crud2) => app._clientTeamUserFromCrud(crud2));
582
+ },
583
+ async update(data) {
584
+ await app._interface.updateTeam({ data: teamUpdateOptionsToCrud(data), teamId: crud.id }, app._getSession());
585
+ await app._currentUserTeamsCache.refresh([app._getSession()]);
551
586
  }
552
587
  };
553
588
  }
@@ -600,6 +635,24 @@ var _StackClientAppImpl = class __StackClientAppImpl {
600
635
  }
601
636
  };
602
637
  }
638
+ _editableTeamProfileFromCrud(crud) {
639
+ const app = this;
640
+ return {
641
+ displayName: crud.display_name,
642
+ profileImageUrl: crud.profile_image_url,
643
+ async update(update) {
644
+ await app._interface.updateTeamMemberProfile({
645
+ teamId: crud.team_id,
646
+ userId: crud.user_id,
647
+ profile: {
648
+ display_name: update.displayName,
649
+ profile_image_url: update.profileImageUrl
650
+ }
651
+ }, app._getSession());
652
+ await app._currentUserTeamProfileCache.refresh([app._getSession(), crud.team_id]);
653
+ }
654
+ };
655
+ }
603
656
  _createUserExtra(crud, session) {
604
657
  const app = this;
605
658
  async function getConnectedAccount(id, options) {
@@ -645,6 +698,9 @@ var _StackClientAppImpl = class __StackClientAppImpl {
645
698
  await app._currentUserTeamsCache.refresh([session]);
646
699
  return app._clientTeamFromCrud(crud2);
647
700
  },
701
+ async leaveTeam(team) {
702
+ await app._interface.leaveTeam(team.id, session);
703
+ },
648
704
  async listPermissions(scope, options) {
649
705
  const recursive = options?.recursive ?? true;
650
706
  const permissions = await app._currentUserPermissionsCache.getOrWait([session, scope.id, recursive], "write-only");
@@ -677,6 +733,14 @@ var _StackClientAppImpl = class __StackClientAppImpl {
677
733
  },
678
734
  async updatePassword(options) {
679
735
  return await app._updatePassword(options, session);
736
+ },
737
+ async getTeamProfile(team) {
738
+ const result = await app._currentUserTeamProfileCache.getOrWait([session, team.id], "write-only");
739
+ return app._editableTeamProfileFromCrud(result);
740
+ },
741
+ useTeamProfile(team) {
742
+ const result = useAsyncCache(app._currentUserTeamProfileCache, [session, team.id], "user.useTeamProfile()");
743
+ return app._editableTeamProfileFromCrud(result);
680
744
  }
681
745
  };
682
746
  }
@@ -930,33 +994,48 @@ var _StackClientAppImpl = class __StackClientAppImpl {
930
994
  }
931
995
  );
932
996
  }
997
+ /**
998
+ * @deprecated
999
+ * TODO remove
1000
+ */
1001
+ async _experimentalMfa(error, session) {
1002
+ const otp = prompt("Please enter the six-digit TOTP code from your authenticator app.");
1003
+ if (!otp) {
1004
+ throw new import_stack_shared.KnownErrors.InvalidTotpCode();
1005
+ }
1006
+ return await this._interface.totpMfa(
1007
+ error.details?.attempt_code ?? (0, import_errors.throwErr)("attempt code missing"),
1008
+ otp,
1009
+ session
1010
+ );
1011
+ }
1012
+ /**
1013
+ * @deprecated
1014
+ * TODO remove
1015
+ */
1016
+ async _catchMfaRequiredError(callback) {
1017
+ try {
1018
+ return await callback();
1019
+ } catch (e) {
1020
+ if (e instanceof import_stack_shared.KnownErrors.MultiFactorAuthenticationRequired) {
1021
+ return await this._experimentalMfa(e, this._getSession());
1022
+ }
1023
+ throw e;
1024
+ }
1025
+ }
933
1026
  async signInWithCredential(options) {
934
1027
  this._ensurePersistentTokenStore();
935
1028
  const session = this._getSession();
936
1029
  let result;
937
1030
  try {
938
- result = await this._interface.signInWithCredential(options.email, options.password, session);
1031
+ result = await this._catchMfaRequiredError(async () => {
1032
+ return await this._interface.signInWithCredential(options.email, options.password, session);
1033
+ });
939
1034
  } catch (e) {
940
- if (options.__experimental_mfa && e instanceof import_stack_shared.KnownErrors.MultiFactorAuthenticationRequired) {
941
- const otp = prompt("Please enter the six-digit TOTP code from your authenticator app.");
942
- try {
943
- if (!otp) {
944
- throw new import_stack_shared.KnownErrors.InvalidTotpCode();
945
- }
946
- result = await this._interface.totpMfa(
947
- e.details?.attempt_code ?? (0, import_errors.throwErr)("attempt code missing"),
948
- otp,
949
- session
950
- );
951
- } catch (e2) {
952
- if (e2 instanceof import_stack_shared.KnownErrors.InvalidTotpCode) {
953
- return e2;
954
- }
955
- throw e2;
956
- }
957
- } else {
958
- throw e;
1035
+ if (e instanceof import_stack_shared.KnownErrors.InvalidTotpCode) {
1036
+ return e;
959
1037
  }
1038
+ throw e;
960
1039
  }
961
1040
  if (!(result instanceof import_stack_shared.KnownError)) {
962
1041
  await this._signInToAccountWithTokens(result);
@@ -982,7 +1061,17 @@ var _StackClientAppImpl = class __StackClientAppImpl {
982
1061
  }
983
1062
  async signInWithMagicLink(code) {
984
1063
  this._ensurePersistentTokenStore();
985
- const result = await this._interface.signInWithMagicLink(code);
1064
+ let result;
1065
+ try {
1066
+ result = await this._catchMfaRequiredError(async () => {
1067
+ return await this._interface.signInWithMagicLink(code);
1068
+ });
1069
+ } catch (e) {
1070
+ if (e instanceof import_stack_shared.KnownErrors.InvalidTotpCode) {
1071
+ return e;
1072
+ }
1073
+ throw e;
1074
+ }
986
1075
  if (result instanceof import_stack_shared.KnownError) {
987
1076
  return result;
988
1077
  }
@@ -995,10 +1084,21 @@ var _StackClientAppImpl = class __StackClientAppImpl {
995
1084
  }
996
1085
  async callOAuthCallback() {
997
1086
  this._ensurePersistentTokenStore();
998
- const result = await (0, import_auth.callOAuthCallback)(this._interface, this.urls.oauthCallback);
1087
+ let result;
1088
+ try {
1089
+ result = await this._catchMfaRequiredError(async () => {
1090
+ return await (0, import_auth.callOAuthCallback)(this._interface, this.urls.oauthCallback);
1091
+ });
1092
+ } catch (e) {
1093
+ if (e instanceof import_stack_shared.KnownErrors.InvalidTotpCode) {
1094
+ alert("Invalid TOTP code. Please try signing in again.");
1095
+ }
1096
+ throw e;
1097
+ }
999
1098
  if (result) {
1099
+ console.log("OAuth callback result", result);
1000
1100
  await this._signInToAccountWithTokens(result);
1001
- if (result.afterCallbackRedirectUrl) {
1101
+ if ("afterCallbackRedirectUrl" in result && result.afterCallbackRedirectUrl) {
1002
1102
  await _redirectTo(result.afterCallbackRedirectUrl, { replace: true });
1003
1103
  return true;
1004
1104
  } else if (result.newUser) {
@@ -1152,9 +1252,6 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1152
1252
  this._serverTeamsCache = createCache(async ([userId]) => {
1153
1253
  return await this._interface.listServerTeams({ userId });
1154
1254
  });
1155
- this._serverTeamUsersCache = createCache(async ([teamId]) => {
1156
- return await this._interface.listServerTeamUsers(teamId);
1157
- });
1158
1255
  this._serverTeamUserPermissionsCache = createCache(async ([teamId, userId, recursive]) => {
1159
1256
  return await this._interface.listServerTeamPermissions({ teamId, userId, recursive }, null);
1160
1257
  });
@@ -1184,12 +1281,33 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1184
1281
  });
1185
1282
  }
1186
1283
  );
1284
+ this._serverTeamMemberProfilesCache = createCache(
1285
+ async ([teamId]) => {
1286
+ return await this._interface.listServerTeamMemberProfiles({ teamId });
1287
+ }
1288
+ );
1289
+ this._serverUserTeamProfileCache = createCache(
1290
+ async ([teamId, userId]) => {
1291
+ return await this._interface.getServerTeamMemberProfile({ teamId, userId });
1292
+ }
1293
+ );
1187
1294
  }
1188
1295
  async _updateServerUser(userId, update) {
1189
1296
  const result = await this._interface.updateServerUser(userId, serverUserUpdateOptionsToCrud(update));
1190
1297
  await this._refreshUsers();
1191
1298
  return result;
1192
1299
  }
1300
+ _serverEditableTeamProfileFromCrud(crud) {
1301
+ const app = this;
1302
+ const clientProfile = this._editableTeamProfileFromCrud(crud);
1303
+ return {
1304
+ ...clientProfile,
1305
+ async update(update) {
1306
+ await clientProfile.update(update);
1307
+ await app._serverUserTeamProfileCache.refresh([crud.team_id, crud.user_id]);
1308
+ }
1309
+ };
1310
+ }
1193
1311
  _serverUserFromCrud(crud) {
1194
1312
  const app = this;
1195
1313
  async function getConnectedAccount(id, options) {
@@ -1268,6 +1386,9 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1268
1386
  await app._serverTeamsCache.refresh([void 0]);
1269
1387
  return app._serverTeamFromCrud(team);
1270
1388
  },
1389
+ leaveTeam: async (team) => {
1390
+ await app._interface.leaveServerTeam({ teamId: team.id, userId: crud.id });
1391
+ },
1271
1392
  async listPermissions(scope, options) {
1272
1393
  const recursive = options?.recursive ?? true;
1273
1394
  const permissions = await app._serverTeamUserPermissionsCache.getOrWait([scope.id, crud.id, recursive], "write-only");
@@ -1297,6 +1418,23 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1297
1418
  },
1298
1419
  async updatePassword(options) {
1299
1420
  return await app._checkFeatureSupport("updatePassword() on ServerUser", {});
1421
+ },
1422
+ async getTeamProfile(team) {
1423
+ const result = await app._serverUserTeamProfileCache.getOrWait([team.id, crud.id], "write-only");
1424
+ return app._serverEditableTeamProfileFromCrud(result);
1425
+ },
1426
+ useTeamProfile(team) {
1427
+ const result = useAsyncCache(app._serverUserTeamProfileCache, [team.id, crud.id], "user.useTeamProfile()");
1428
+ return (0, import_react2.useMemo)(() => app._serverEditableTeamProfileFromCrud(result), [result]);
1429
+ }
1430
+ };
1431
+ }
1432
+ _serverTeamUserFromCrud(crud) {
1433
+ return {
1434
+ ...this._serverUserFromCrud(crud.user),
1435
+ teamProfile: {
1436
+ displayName: crud.display_name,
1437
+ profileImageUrl: crud.profile_image_url
1300
1438
  }
1301
1439
  };
1302
1440
  }
@@ -1317,9 +1455,6 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1317
1455
  displayName: crud.display_name,
1318
1456
  profileImageUrl: crud.profile_image_url,
1319
1457
  createdAt: new Date(crud.created_at_millis),
1320
- async listUsers() {
1321
- return (await app._interface.listServerTeamUsers(crud.id)).map((u) => app._serverUserFromCrud(u));
1322
- },
1323
1458
  async update(update) {
1324
1459
  await app._interface.updateServerTeam(crud.id, serverTeamUpdateOptionsToCrud(update));
1325
1460
  await app._serverTeamsCache.refresh([void 0]);
@@ -1328,23 +1463,27 @@ var _StackServerAppImpl = class extends _StackClientAppImpl {
1328
1463
  await app._interface.deleteServerTeam(crud.id);
1329
1464
  await app._serverTeamsCache.refresh([void 0]);
1330
1465
  },
1466
+ async listUsers() {
1467
+ const result = await app._serverTeamMemberProfilesCache.getOrWait([crud.id], "write-only");
1468
+ return result.map((u) => app._serverTeamUserFromCrud(u));
1469
+ },
1331
1470
  useUsers() {
1332
- const result = useAsyncCache(app._serverTeamUsersCache, [crud.id], "team.useUsers()");
1333
- return (0, import_react2.useMemo)(() => result.map((u) => app._serverUserFromCrud(u)), [result]);
1471
+ const result = useAsyncCache(app._serverTeamMemberProfilesCache, [crud.id], "team.useUsers()");
1472
+ return (0, import_react2.useMemo)(() => result.map((u) => app._serverTeamUserFromCrud(u)), [result]);
1334
1473
  },
1335
1474
  async addUser(userId) {
1336
1475
  await app._interface.addServerUserToTeam({
1337
1476
  teamId: crud.id,
1338
1477
  userId
1339
1478
  });
1340
- await app._serverTeamUsersCache.refresh([crud.id]);
1479
+ await app._serverTeamMemberProfilesCache.refresh([crud.id]);
1341
1480
  },
1342
1481
  async removeUser(userId) {
1343
1482
  await app._interface.removeServerUserFromTeam({
1344
1483
  teamId: crud.id,
1345
1484
  userId
1346
1485
  });
1347
- await app._serverTeamUsersCache.refresh([crud.id]);
1486
+ await app._serverTeamMemberProfilesCache.refresh([crud.id]);
1348
1487
  },
1349
1488
  async inviteUser(options) {
1350
1489
  return await app._interface.sendTeamInvitation({
@@ -1541,6 +1680,7 @@ var _StackAdminAppImpl = class extends _StackServerAppImpl {
1541
1680
  signUpEnabled: data.config.sign_up_enabled,
1542
1681
  credentialEnabled: data.config.credential_enabled,
1543
1682
  magicLinkEnabled: data.config.magic_link_enabled,
1683
+ clientTeamCreationEnabled: data.config.client_team_creation_enabled,
1544
1684
  allowLocalhost: data.config.allow_localhost,
1545
1685
  oauthProviders: data.config.oauth_providers.map((p) => p.type === "shared" ? {
1546
1686
  id: p.id,
@@ -1577,6 +1717,9 @@ var _StackAdminAppImpl = class extends _StackServerAppImpl {
1577
1717
  await app._interface.updateProject(adminProjectUpdateOptionsToCrud(update));
1578
1718
  await onRefresh();
1579
1719
  },
1720
+ async delete() {
1721
+ await app._interface.deleteProject();
1722
+ },
1580
1723
  async getProductionModeErrors() {
1581
1724
  return (0, import_production_mode.getProductionModeErrors)(data);
1582
1725
  },
@@ -1781,6 +1924,7 @@ function adminProjectUpdateOptionsToCrud(options) {
1781
1924
  magic_link_enabled: options.config?.magicLinkEnabled,
1782
1925
  allow_localhost: options.config?.allowLocalhost,
1783
1926
  create_team_on_sign_up: options.config?.createTeamOnSignUp,
1927
+ client_team_creation_enabled: options.config?.clientTeamCreationEnabled,
1784
1928
  team_creator_default_permissions: options.config?.teamCreatorDefaultPermissions,
1785
1929
  team_member_default_permissions: options.config?.teamMemberDefaultPermissions
1786
1930
  }
@@ -1801,6 +1945,12 @@ function apiKeyCreateOptionsToCrud(options) {
1801
1945
  has_super_secret_admin_key: options.hasSuperSecretAdminKey
1802
1946
  };
1803
1947
  }
1948
+ function teamUpdateOptionsToCrud(options) {
1949
+ return {
1950
+ display_name: options.displayName,
1951
+ profile_image_url: options.profileImageUrl
1952
+ };
1953
+ }
1804
1954
  function teamCreateOptionsToCrud(options) {
1805
1955
  return {
1806
1956
  display_name: options.displayName,