@stackframe/stack 2.8.30 → 2.8.32

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 (43) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/dist/components/selected-team-switcher.js +19 -95
  3. package/dist/components/selected-team-switcher.js.map +1 -1
  4. package/dist/components/team-switcher.js +153 -0
  5. package/dist/components/team-switcher.js.map +1 -0
  6. package/dist/esm/components/selected-team-switcher.js +22 -108
  7. package/dist/esm/components/selected-team-switcher.js.map +1 -1
  8. package/dist/esm/components/team-switcher.js +142 -0
  9. package/dist/esm/components/team-switcher.js.map +1 -0
  10. package/dist/esm/index.js +2 -0
  11. package/dist/esm/index.js.map +1 -1
  12. package/dist/esm/lib/stack-app/apps/implementations/admin-app-impl.js +12 -0
  13. package/dist/esm/lib/stack-app/apps/implementations/admin-app-impl.js.map +1 -1
  14. package/dist/esm/lib/stack-app/apps/implementations/client-app-impl.js +38 -1
  15. package/dist/esm/lib/stack-app/apps/implementations/client-app-impl.js.map +1 -1
  16. package/dist/esm/lib/stack-app/apps/implementations/common.js +1 -1
  17. package/dist/esm/lib/stack-app/apps/implementations/common.js.map +1 -1
  18. package/dist/esm/lib/stack-app/apps/implementations/server-app-impl.js +60 -0
  19. package/dist/esm/lib/stack-app/apps/implementations/server-app-impl.js.map +1 -1
  20. package/dist/esm/lib/stack-app/apps/interfaces/admin-app.js.map +1 -1
  21. package/dist/esm/lib/stack-app/projects/index.js +2 -1
  22. package/dist/esm/lib/stack-app/projects/index.js.map +1 -1
  23. package/dist/esm/lib/stack-app/teams/index.js.map +1 -1
  24. package/dist/esm/lib/stack-app/users/index.js.map +1 -1
  25. package/dist/index.d.mts +78 -10
  26. package/dist/index.d.ts +78 -10
  27. package/dist/index.js +3 -0
  28. package/dist/index.js.map +1 -1
  29. package/dist/lib/stack-app/apps/implementations/admin-app-impl.js +12 -0
  30. package/dist/lib/stack-app/apps/implementations/admin-app-impl.js.map +1 -1
  31. package/dist/lib/stack-app/apps/implementations/client-app-impl.js +38 -1
  32. package/dist/lib/stack-app/apps/implementations/client-app-impl.js.map +1 -1
  33. package/dist/lib/stack-app/apps/implementations/common.js +1 -1
  34. package/dist/lib/stack-app/apps/implementations/common.js.map +1 -1
  35. package/dist/lib/stack-app/apps/implementations/server-app-impl.js +60 -0
  36. package/dist/lib/stack-app/apps/implementations/server-app-impl.js.map +1 -1
  37. package/dist/lib/stack-app/apps/interfaces/admin-app.js.map +1 -1
  38. package/dist/lib/stack-app/customers/index.js.map +1 -1
  39. package/dist/lib/stack-app/projects/index.js +2 -1
  40. package/dist/lib/stack-app/projects/index.js.map +1 -1
  41. package/dist/lib/stack-app/teams/index.js.map +1 -1
  42. package/dist/lib/stack-app/users/index.js.map +1 -1
  43. package/package.json +4 -4
package/CHANGELOG.md CHANGED
@@ -1,5 +1,25 @@
1
1
  # @stackframe/stack
2
2
 
3
+ ## 2.8.32
4
+
5
+ ### Patch Changes
6
+
7
+ - Various changes
8
+ - Updated dependencies
9
+ - @stackframe/stack-shared@2.8.32
10
+ - @stackframe/stack-ui@2.8.32
11
+ - @stackframe/stack-sc@2.8.32
12
+
13
+ ## 2.8.31
14
+
15
+ ### Patch Changes
16
+
17
+ - Various changes
18
+ - Updated dependencies
19
+ - @stackframe/stack-sc@2.8.31
20
+ - @stackframe/stack-shared@2.8.31
21
+ - @stackframe/stack-ui@2.8.31
22
+
3
23
  ## 2.8.30
4
24
 
5
25
  ### Patch Changes
@@ -25,14 +25,11 @@ __export(selected_team_switcher_exports, {
25
25
  SelectedTeamSwitcher: () => SelectedTeamSwitcher
26
26
  });
27
27
  module.exports = __toCommonJS(selected_team_switcher_exports);
28
- var import_errors = require("@stackframe/stack-shared/dist/utils/errors");
29
28
  var import_promises = require("@stackframe/stack-shared/dist/utils/promises");
30
29
  var import_stack_ui = require("@stackframe/stack-ui");
31
- var import_lucide_react = require("lucide-react");
32
30
  var import_react = require("react");
33
31
  var import__ = require("../index.js");
34
- var import_translations = require("../lib/translations.js");
35
- var import_team_icon = require("./team-icon.js");
32
+ var import_team_switcher = require("./team-switcher.js");
36
33
  var import_jsx_runtime = require("react/jsx-runtime");
37
34
  function SelectedTeamSwitcher(props) {
38
35
  return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.Suspense, { fallback: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Fallback, {}), children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Inner, { ...props }) });
@@ -41,7 +38,6 @@ function Fallback() {
41
38
  return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Skeleton, { className: "h-9 w-full max-w-64 stack-scope" });
42
39
  }
43
40
  function Inner(props) {
44
- const { t } = (0, import_translations.useTranslation)();
45
41
  const appFromHook = (0, import__.useStackApp)();
46
42
  const userFromHook = (0, import__.useUser)();
47
43
  const app = props.mockUser ? {
@@ -58,103 +54,31 @@ function Inner(props) {
58
54
  }
59
55
  // Mock function
60
56
  } : userFromHook;
61
- const project = app.useProject();
62
57
  const navigate = app.useNavigate();
63
- const selectedTeam = user?.selectedTeam || props.selectedTeam;
64
- const rawTeams = user?.useTeams();
65
- const teams = (0, import_react.useMemo)(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);
66
58
  (0, import_react.useEffect)(() => {
67
59
  if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {
68
60
  (0, import_promises.runAsynchronouslyWithAlert)(user?.setSelectedTeam(props.selectedTeam));
69
61
  }
70
62
  }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);
71
- return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
72
- import_stack_ui.Select,
63
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
64
+ import_team_switcher.TeamSwitcher,
73
65
  {
74
- value: selectedTeam?.id || (props.allowNull ? "null-sentinel" : void 0),
75
- onValueChange: (value) => {
76
- (0, import_promises.runAsynchronouslyWithAlert)(async () => {
77
- let team = null;
78
- if (value !== "null-sentinel") {
79
- team = teams?.find((team2) => team2.id === value) || null;
80
- if (!team) {
81
- throw new import_errors.StackAssertionError("Team not found, this should not happen");
82
- }
83
- } else {
84
- team = null;
85
- }
86
- if (props.onChange) {
87
- props.onChange(team);
88
- }
89
- if (props.mockUser) return;
90
- if (!props.noUpdateSelectedTeam) {
91
- await user?.setSelectedTeam(team);
92
- }
93
- if (props.urlMap) {
94
- navigate(props.urlMap(team));
95
- }
96
- });
97
- },
98
- children: [
99
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectTrigger, { className: "stack-scope max-w-64", children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectValue, { placeholder: "Select team" }) }),
100
- /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectContent, { className: "stack-scope", children: [
101
- user?.selectedTeam ? /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectGroup, { children: [
102
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center justify-between", children: [
103
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)("span", { children: t("Current team") }),
104
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
105
- import_stack_ui.Button,
106
- {
107
- variant: "ghost",
108
- size: "icon",
109
- className: "h-6 w-6",
110
- onClick: () => {
111
- if (!props.mockUser) {
112
- navigate(`${app.urls.accountSettings}#team-${user.selectedTeam?.id}`);
113
- }
114
- },
115
- children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_lucide_react.Settings, { className: "h-4 w-4" })
116
- }
117
- )
118
- ] }) }),
119
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: user.selectedTeam.id, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
120
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team: user.selectedTeam }),
121
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-40 truncate", children: user.selectedTeam.displayName })
122
- ] }) })
123
- ] }) : void 0,
124
- props.allowNull && /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectGroup, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: "null-sentinel", children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
125
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team: "personal" }),
126
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-40 truncate", children: props.nullLabel || t("No team") })
127
- ] }) }) }),
128
- teams?.length ? /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectGroup, { children: [
129
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: t("Other teams") }),
130
- teams.filter((team) => team.id !== user?.selectedTeam?.id).map((team) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: team.id, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
131
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team }),
132
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-64 truncate", children: team.displayName })
133
- ] }) }, team.id))
134
- ] }) : null,
135
- !teams?.length && !props.allowNull ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectGroup, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: t("No teams yet") }) }) : null,
136
- project.config.clientTeamCreationEnabled && /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_jsx_runtime.Fragment, { children: [
137
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectSeparator, {}),
138
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
139
- import_stack_ui.Button,
140
- {
141
- onClick: () => {
142
- if (!props.mockUser) {
143
- navigate(`${app.urls.accountSettings}#team-creation`);
144
- }
145
- },
146
- className: "w-full",
147
- variant: "ghost",
148
- children: [
149
- /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_lucide_react.PlusCircle, { className: "mr-2 h-4 w-4" }),
150
- " ",
151
- t("Create a team")
152
- ]
153
- }
154
- ) })
155
- ] })
156
- ] })
157
- ]
66
+ team: props.selectedTeam,
67
+ allowNull: props.allowNull,
68
+ nullLabel: props.nullLabel,
69
+ triggerClassName: props.triggerClassName,
70
+ onChange: async (team) => {
71
+ if (props.onChange) {
72
+ props.onChange(team);
73
+ }
74
+ if (props.mockUser) return;
75
+ if (!props.noUpdateSelectedTeam) {
76
+ await user?.setSelectedTeam(team);
77
+ }
78
+ if (props.urlMap) {
79
+ navigate(props.urlMap(team));
80
+ }
81
+ }
158
82
  }
159
83
  );
160
84
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/components/selected-team-switcher.tsx"],"sourcesContent":["'use client';\n\n\n//===========================================\n// THIS FILE IS AUTO-GENERATED FROM TEMPLATE. DO NOT EDIT IT DIRECTLY\n//===========================================\nimport { StackAssertionError } from \"@stackframe/stack-shared/dist/utils/errors\";\nimport { runAsynchronouslyWithAlert } from \"@stackframe/stack-shared/dist/utils/promises\";\nimport {\n Button,\n Select,\n SelectContent,\n SelectGroup,\n SelectItem,\n SelectLabel,\n SelectSeparator,\n SelectTrigger,\n SelectValue,\n Skeleton,\n Typography\n} from \"@stackframe/stack-ui\";\nimport { PlusCircle, Settings } from \"lucide-react\";\nimport { Suspense, useEffect, useMemo } from \"react\";\nimport { Team, useStackApp, useUser } from \"..\";\nimport { useTranslation } from \"../lib/translations\";\nimport { TeamIcon } from \"./team-icon\";\n\ntype MockTeam = {\n id: string,\n displayName: string,\n profileImageUrl?: string | null,\n};\n\ntype SelectedTeamSwitcherProps<AllowNull extends boolean = false> = {\n urlMap?: (team: AllowNull extends true ? Team | null : Team) => string,\n selectedTeam?: Team,\n noUpdateSelectedTeam?: boolean,\n allowNull?: AllowNull,\n nullLabel?: string,\n onChange?: (team: AllowNull extends true ? Team | null : Team) => void,\n // Mock data props\n mockUser?: {\n selectedTeam?: MockTeam,\n },\n mockTeams?: MockTeam[],\n mockProject?: {\n config: {\n clientTeamCreationEnabled: boolean,\n },\n },\n};\n\nexport function SelectedTeamSwitcher<AllowNull extends boolean = false>(props: SelectedTeamSwitcherProps<AllowNull>) {\n return <Suspense fallback={<Fallback />}>\n <Inner {...props} />\n </Suspense>;\n}\n\nfunction Fallback() {\n return <Skeleton className=\"h-9 w-full max-w-64 stack-scope\" />;\n}\n\nfunction Inner<AllowNull extends boolean>(props: SelectedTeamSwitcherProps<AllowNull>) {\n const { t } = useTranslation();\n const appFromHook = useStackApp();\n const userFromHook = useUser();\n\n // Use mock data if provided, otherwise use real data\n const app = props.mockUser ? {\n useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },\n useNavigate: () => () => {}, // Mock navigate function\n urls: { accountSettings: '/account-settings' },\n } : appFromHook;\n\n const user = props.mockUser ? {\n selectedTeam: props.mockUser.selectedTeam,\n useTeams: () => props.mockTeams || [],\n setSelectedTeam: async () => {}, // Mock function\n } : userFromHook;\n\n const project = app.useProject();\n const navigate = app.useNavigate();\n const selectedTeam = user?.selectedTeam || props.selectedTeam;\n const rawTeams = user?.useTeams();\n const teams = useMemo(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);\n\n useEffect(() => {\n if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {\n runAsynchronouslyWithAlert(user?.setSelectedTeam(props.selectedTeam));\n }\n }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);\n\n return (\n <Select\n value={selectedTeam?.id || (props.allowNull ? 'null-sentinel' : undefined)}\n onValueChange={(value) => {\n runAsynchronouslyWithAlert(async () => {\n let team: MockTeam | null = null;\n if (value !== 'null-sentinel') {\n team = teams?.find(team => team.id === value) || null;\n if (!team) {\n throw new StackAssertionError('Team not found, this should not happen');\n }\n } else {\n team = null;\n }\n\n // Call onChange callback if provided\n if (props.onChange) {\n props.onChange(team as Team);\n }\n\n // Skip actual navigation/updates in mock mode\n if (props.mockUser) return;\n\n if (!props.noUpdateSelectedTeam) {\n await user?.setSelectedTeam(team as Team);\n }\n if (props.urlMap) {\n navigate(props.urlMap(team as Team));\n }\n });\n }}\n >\n <SelectTrigger className=\"stack-scope max-w-64\">\n <SelectValue placeholder=\"Select team\"/>\n </SelectTrigger>\n <SelectContent className=\"stack-scope\">\n {user?.selectedTeam ? <SelectGroup>\n <SelectLabel>\n <div className=\"flex items-center justify-between\">\n <span>\n {t('Current team')}\n </span>\n <Button\n variant='ghost'\n size='icon'\n className=\"h-6 w-6\"\n onClick={() => {\n // Skip navigation in mock mode\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-${user.selectedTeam?.id}`);\n }\n }}\n >\n <Settings className=\"h-4 w-4\"/>\n </Button>\n </div>\n </SelectLabel>\n <SelectItem value={user.selectedTeam.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={user.selectedTeam as Team} />\n <Typography className=\"max-w-40 truncate\">{user.selectedTeam.displayName}</Typography>\n </div>\n </SelectItem>\n </SelectGroup> : undefined}\n\n {props.allowNull && <SelectGroup>\n <SelectItem value=\"null-sentinel\">\n <div className=\"flex items-center gap-2\">\n <TeamIcon team='personal' />\n <Typography className=\"max-w-40 truncate\">{props.nullLabel || t('No team')}</Typography>\n </div>\n </SelectItem>\n </SelectGroup>}\n\n {teams?.length ?\n <SelectGroup>\n <SelectLabel>{t('Other teams')}</SelectLabel>\n {teams.filter(team => team.id !== user?.selectedTeam?.id)\n .map(team => (\n <SelectItem value={team.id} key={team.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={team as Team} />\n <Typography className=\"max-w-64 truncate\">{team.displayName}</Typography>\n </div>\n </SelectItem>\n ))}\n </SelectGroup> : null}\n\n {!teams?.length && !props.allowNull ?\n <SelectGroup>\n <SelectLabel>{t('No teams yet')}</SelectLabel>\n </SelectGroup> : null}\n\n {project.config.clientTeamCreationEnabled && <>\n <SelectSeparator/>\n <div>\n <Button\n onClick={() => {\n // Skip navigation in mock mode\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-creation`);\n }\n }}\n className=\"w-full\"\n variant='ghost'\n >\n <PlusCircle className=\"mr-2 h-4 w-4\"/> {t('Create a team')}\n </Button>\n </div>\n </>}\n </SelectContent>\n </Select>\n );\n}\n"],"mappings":"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","names":["team"]}
1
+ {"version":3,"sources":["../../src/components/selected-team-switcher.tsx"],"sourcesContent":["'use client';\n\n\n//===========================================\n// THIS FILE IS AUTO-GENERATED FROM TEMPLATE. DO NOT EDIT IT DIRECTLY\n//===========================================\nimport { runAsynchronouslyWithAlert } from \"@stackframe/stack-shared/dist/utils/promises\";\nimport {\n Skeleton,\n} from \"@stackframe/stack-ui\";\nimport { Suspense, useEffect } from \"react\";\nimport { Team, useStackApp, useUser } from \"..\";\nimport { TeamSwitcher } from \"./team-switcher\";\n\ntype MockTeam = {\n id: string,\n displayName: string,\n profileImageUrl?: string | null,\n};\n\ntype SelectedTeamSwitcherProps<AllowNull extends boolean = false> = {\n urlMap?: (team: AllowNull extends true ? Team | null : Team) => string,\n selectedTeam?: Team,\n noUpdateSelectedTeam?: boolean,\n allowNull?: AllowNull,\n nullLabel?: string,\n onChange?: (team: AllowNull extends true ? Team | null : Team) => void,\n triggerClassName?: string,\n // Mock data props\n mockUser?: {\n selectedTeam?: MockTeam,\n },\n mockTeams?: MockTeam[],\n mockProject?: {\n config: {\n clientTeamCreationEnabled: boolean,\n },\n },\n};\n\nexport function SelectedTeamSwitcher<AllowNull extends boolean = false>(props: SelectedTeamSwitcherProps<AllowNull>) {\n return <Suspense fallback={<Fallback />}>\n <Inner {...props} />\n </Suspense>;\n}\n\nfunction Fallback() {\n return <Skeleton className=\"h-9 w-full max-w-64 stack-scope\" />;\n}\n\nfunction Inner<AllowNull extends boolean>(props: SelectedTeamSwitcherProps<AllowNull>) {\n const appFromHook = useStackApp();\n const userFromHook = useUser();\n\n // Use mock data if provided, otherwise use real data\n const app = props.mockUser ? {\n useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },\n useNavigate: () => () => {}, // Mock navigate function\n urls: { accountSettings: '/account-settings' },\n } : appFromHook;\n\n const user = props.mockUser ? {\n selectedTeam: props.mockUser.selectedTeam,\n useTeams: () => props.mockTeams || [],\n setSelectedTeam: async () => {}, // Mock function\n } : userFromHook;\n\n const navigate = app.useNavigate();\n\n useEffect(() => {\n if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {\n runAsynchronouslyWithAlert(user?.setSelectedTeam(props.selectedTeam));\n }\n }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);\n\n return (\n <TeamSwitcher\n team={props.selectedTeam}\n allowNull={props.allowNull}\n nullLabel={props.nullLabel}\n triggerClassName={props.triggerClassName}\n onChange={async (team) => {\n if (props.onChange) {\n props.onChange(team as Team);\n }\n // Skip actual navigation/updates in mock mode\n if (props.mockUser) return;\n if (!props.noUpdateSelectedTeam) {\n await user?.setSelectedTeam(team as Team);\n }\n if (props.urlMap) {\n navigate(props.urlMap(team as Team));\n }\n }}\n />\n );\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAMA,sBAA2C;AAC3C,sBAEO;AACP,mBAAoC;AACpC,eAA2C;AAC3C,2BAA6B;AA6BA;AADtB,SAAS,qBAAwD,OAA6C;AACnH,SAAO,4CAAC,yBAAS,UAAU,4CAAC,YAAS,GACnC,sDAAC,SAAO,GAAG,OAAO,GACpB;AACF;AAEA,SAAS,WAAW;AAClB,SAAO,4CAAC,4BAAS,WAAU,mCAAkC;AAC/D;AAEA,SAAS,MAAiC,OAA6C;AACrF,QAAM,kBAAc,sBAAY;AAChC,QAAM,mBAAe,kBAAQ;AAG7B,QAAM,MAAM,MAAM,WAAW;AAAA,IAC3B,YAAY,MAAM,MAAM,eAAe,EAAE,QAAQ,EAAE,2BAA2B,MAAM,EAAE;AAAA,IACtF,aAAa,MAAM,MAAM;AAAA,IAAC;AAAA;AAAA,IAC1B,MAAM,EAAE,iBAAiB,oBAAoB;AAAA,EAC/C,IAAI;AAEJ,QAAM,OAAO,MAAM,WAAW;AAAA,IAC5B,cAAc,MAAM,SAAS;AAAA,IAC7B,UAAU,MAAM,MAAM,aAAa,CAAC;AAAA,IACpC,iBAAiB,YAAY;AAAA,IAAC;AAAA;AAAA,EAChC,IAAI;AAEJ,QAAM,WAAW,IAAI,YAAY;AAEjC,8BAAU,MAAM;AACd,QAAI,CAAC,MAAM,wBAAwB,MAAM,gBAAgB,CAAC,MAAM,UAAU;AACxE,sDAA2B,MAAM,gBAAgB,MAAM,YAAY,CAAC;AAAA,IACtE;AAAA,EACF,GAAG,CAAC,MAAM,sBAAsB,MAAM,cAAc,MAAM,QAAQ,CAAC;AAEnE,SACE;AAAA,IAAC;AAAA;AAAA,MACC,MAAM,MAAM;AAAA,MACZ,WAAW,MAAM;AAAA,MACjB,WAAW,MAAM;AAAA,MACjB,kBAAkB,MAAM;AAAA,MACxB,UAAU,OAAO,SAAS;AACxB,YAAI,MAAM,UAAU;AAClB,gBAAM,SAAS,IAAY;AAAA,QAC7B;AAEA,YAAI,MAAM,SAAU;AACpB,YAAI,CAAC,MAAM,sBAAsB;AAC/B,gBAAM,MAAM,gBAAgB,IAAY;AAAA,QAC1C;AACA,YAAI,MAAM,QAAQ;AAChB,mBAAS,MAAM,OAAO,IAAY,CAAC;AAAA,QACrC;AAAA,MACF;AAAA;AAAA,EACF;AAEJ;","names":[]}
@@ -0,0 +1,153 @@
1
+ "use client";
2
+ "use strict";
3
+ "use client";
4
+ var __defProp = Object.defineProperty;
5
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
6
+ var __getOwnPropNames = Object.getOwnPropertyNames;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
21
+
22
+ // src/components/team-switcher.tsx
23
+ var team_switcher_exports = {};
24
+ __export(team_switcher_exports, {
25
+ TeamSwitcher: () => TeamSwitcher
26
+ });
27
+ module.exports = __toCommonJS(team_switcher_exports);
28
+ var import_errors = require("@stackframe/stack-shared/dist/utils/errors");
29
+ var import_promises = require("@stackframe/stack-shared/dist/utils/promises");
30
+ var import_stack_ui = require("@stackframe/stack-ui");
31
+ var import_lucide_react = require("lucide-react");
32
+ var import_react = require("react");
33
+ var import__ = require("../index.js");
34
+ var import_translations = require("../lib/translations.js");
35
+ var import_team_icon = require("./team-icon.js");
36
+ var import_jsx_runtime = require("react/jsx-runtime");
37
+ function TeamSwitcher(props) {
38
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.Suspense, { fallback: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Fallback, {}), children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Inner, { ...props }) });
39
+ }
40
+ function Fallback() {
41
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Skeleton, { className: "h-9 w-full max-w-64 stack-scope" });
42
+ }
43
+ function Inner(props) {
44
+ const { t } = (0, import_translations.useTranslation)();
45
+ const appFromHook = (0, import__.useStackApp)();
46
+ const userFromHook = (0, import__.useUser)();
47
+ const app = props.mockUser ? {
48
+ useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },
49
+ useNavigate: () => () => {
50
+ },
51
+ // Mock navigate function
52
+ urls: { accountSettings: "/account-settings" }
53
+ } : appFromHook;
54
+ const user = props.mockUser ? {
55
+ selectedTeam: props.mockUser.team,
56
+ useTeams: () => props.mockTeams || [],
57
+ setSelectedTeam: async () => {
58
+ }
59
+ // Mock function
60
+ } : userFromHook;
61
+ const navigate = app.useNavigate();
62
+ const project = app.useProject();
63
+ const rawTeams = user?.useTeams();
64
+ const selectedTeam = props.team || rawTeams?.find((team) => team.id === props.teamId) || user?.selectedTeam;
65
+ const teams = (0, import_react.useMemo)(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);
66
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
67
+ import_stack_ui.Select,
68
+ {
69
+ value: selectedTeam?.id || (props.allowNull ? "null-sentinel" : void 0),
70
+ onValueChange: (value) => {
71
+ (0, import_promises.runAsynchronouslyWithAlert)(async () => {
72
+ let team = null;
73
+ if (value !== "null-sentinel") {
74
+ team = teams?.find((team2) => team2.id === value) || null;
75
+ if (!team) {
76
+ throw new import_errors.StackAssertionError("Team not found, this should not happen");
77
+ }
78
+ } else {
79
+ team = null;
80
+ }
81
+ if (props.onChange) {
82
+ await props.onChange(team);
83
+ }
84
+ });
85
+ },
86
+ children: [
87
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectTrigger, { className: (0, import_stack_ui.cn)("stack-scope max-w-64", props.triggerClassName), children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectValue, { placeholder: "Select team" }) }),
88
+ /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectContent, { className: "stack-scope", children: [
89
+ selectedTeam ? /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectGroup, { children: [
90
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center justify-between", children: [
91
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)("span", { children: t("Current team") }),
92
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
93
+ import_stack_ui.Button,
94
+ {
95
+ variant: "ghost",
96
+ size: "icon",
97
+ className: "h-6 w-6",
98
+ onClick: () => {
99
+ if (!props.mockUser) {
100
+ navigate(`${app.urls.accountSettings}#team-${selectedTeam.id}`);
101
+ }
102
+ },
103
+ children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_lucide_react.Settings, { className: "h-4 w-4" })
104
+ }
105
+ )
106
+ ] }) }),
107
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: selectedTeam.id, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
108
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team: selectedTeam }),
109
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-40 truncate", children: selectedTeam.displayName })
110
+ ] }) })
111
+ ] }) : void 0,
112
+ props.allowNull && /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectGroup, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: "null-sentinel", children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
113
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team: "personal" }),
114
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-40 truncate", children: props.nullLabel || t("No team") })
115
+ ] }) }) }),
116
+ teams?.length ? /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_stack_ui.SelectGroup, { children: [
117
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: t("Other teams") }),
118
+ teams.filter((team) => team.id !== selectedTeam?.id).map((team) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectItem, { value: team.id, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "flex items-center gap-2", children: [
119
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_team_icon.TeamIcon, { team }),
120
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.Typography, { className: "max-w-64 truncate", children: team.displayName })
121
+ ] }) }, team.id))
122
+ ] }) : null,
123
+ !teams?.length && !props.allowNull ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectGroup, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectLabel, { children: t("No teams yet") }) }) : null,
124
+ project.config.clientTeamCreationEnabled && /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_jsx_runtime.Fragment, { children: [
125
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_stack_ui.SelectSeparator, {}),
126
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
127
+ import_stack_ui.Button,
128
+ {
129
+ onClick: () => {
130
+ if (!props.mockUser) {
131
+ navigate(`${app.urls.accountSettings}#team-creation`);
132
+ }
133
+ },
134
+ className: "w-full",
135
+ variant: "ghost",
136
+ children: [
137
+ /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_lucide_react.PlusCircle, { className: "mr-2 h-4 w-4" }),
138
+ " ",
139
+ t("Create a team")
140
+ ]
141
+ }
142
+ ) })
143
+ ] })
144
+ ] })
145
+ ]
146
+ }
147
+ );
148
+ }
149
+ // Annotate the CommonJS export names for ESM import in node:
150
+ 0 && (module.exports = {
151
+ TeamSwitcher
152
+ });
153
+ //# sourceMappingURL=team-switcher.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/components/team-switcher.tsx"],"sourcesContent":["'use client';\n\n\n//===========================================\n// THIS FILE IS AUTO-GENERATED FROM TEMPLATE. DO NOT EDIT IT DIRECTLY\n//===========================================\nimport { StackAssertionError } from \"@stackframe/stack-shared/dist/utils/errors\";\nimport { runAsynchronouslyWithAlert } from \"@stackframe/stack-shared/dist/utils/promises\";\nimport {\n cn,\n Button,\n Select,\n SelectContent,\n SelectGroup,\n SelectItem,\n SelectLabel,\n SelectSeparator,\n SelectTrigger,\n SelectValue,\n Skeleton,\n Typography,\n} from \"@stackframe/stack-ui\";\nimport { PlusCircle, Settings } from \"lucide-react\";\nimport { Suspense, useMemo } from \"react\";\nimport { Team, useStackApp, useUser } from \"..\";\nimport { useTranslation } from \"../lib/translations\";\nimport { TeamIcon } from \"./team-icon\";\n\ntype MockTeam = {\n id: string,\n displayName: string,\n profileImageUrl?: string | null,\n};\n\ntype TeamSwitcherProps<AllowNull extends boolean = false> = {\n team?: Team,\n teamId?: string,\n allowNull?: AllowNull,\n nullLabel?: string,\n triggerClassName?: string,\n onChange?: (team: AllowNull extends true ? Team | null : Team) => Promise<void>,\n // Mock data props\n mockUser?: {\n team?: MockTeam,\n },\n mockTeams?: MockTeam[],\n mockProject?: {\n config: {\n clientTeamCreationEnabled: boolean,\n },\n },\n};\n\nexport function TeamSwitcher<AllowNull extends boolean = false>(props: TeamSwitcherProps<AllowNull>) {\n return <Suspense fallback={<Fallback />}>\n <Inner {...props} />\n </Suspense>;\n}\n\nfunction Fallback() {\n return <Skeleton className=\"h-9 w-full max-w-64 stack-scope\" />;\n}\n\nfunction Inner<AllowNull extends boolean>(props: TeamSwitcherProps<AllowNull>) {\n const { t } = useTranslation();\n const appFromHook = useStackApp();\n const userFromHook = useUser();\n\n // Use mock data if provided, otherwise use real data\n const app = props.mockUser ? {\n useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },\n useNavigate: () => () => {}, // Mock navigate function\n urls: { accountSettings: '/account-settings' },\n } : appFromHook;\n\n const user = props.mockUser ? {\n selectedTeam: props.mockUser.team,\n useTeams: () => props.mockTeams || [],\n setSelectedTeam: async () => {}, // Mock function\n } : userFromHook;\n\n const navigate = app.useNavigate();\n const project = app.useProject();\n const rawTeams = user?.useTeams();\n const selectedTeam = props.team || rawTeams?.find(team => team.id === props.teamId) || user?.selectedTeam;\n const teams = useMemo(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);\n\n\n return (\n <Select\n value={selectedTeam?.id || (props.allowNull ? 'null-sentinel' : undefined)}\n onValueChange={(value) => {\n runAsynchronouslyWithAlert(async () => {\n let team: MockTeam | null = null;\n if (value !== 'null-sentinel') {\n team = teams?.find(team => team.id === value) || null;\n if (!team) {\n throw new StackAssertionError('Team not found, this should not happen');\n }\n } else {\n team = null;\n }\n\n // Call onChange callback if provided\n if (props.onChange) {\n await props.onChange(team as Team);\n }\n });\n }}\n >\n <SelectTrigger className={cn(\"stack-scope max-w-64\", props.triggerClassName)}>\n <SelectValue placeholder=\"Select team\"/>\n </SelectTrigger>\n <SelectContent className=\"stack-scope\">\n {selectedTeam ? <SelectGroup>\n <SelectLabel>\n <div className=\"flex items-center justify-between\">\n <span>\n {t('Current team')}\n </span>\n <Button\n variant='ghost'\n size='icon'\n className=\"h-6 w-6\"\n onClick={() => {\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-${selectedTeam.id}`);\n }\n }}\n >\n <Settings className=\"h-4 w-4\"/>\n </Button>\n </div>\n </SelectLabel>\n <SelectItem value={selectedTeam.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={selectedTeam as Team} />\n <Typography className=\"max-w-40 truncate\">{selectedTeam.displayName}</Typography>\n </div>\n </SelectItem>\n </SelectGroup> : undefined}\n\n {props.allowNull && <SelectGroup>\n <SelectItem value=\"null-sentinel\">\n <div className=\"flex items-center gap-2\">\n <TeamIcon team='personal' />\n <Typography className=\"max-w-40 truncate\">{props.nullLabel || t('No team')}</Typography>\n </div>\n </SelectItem>\n </SelectGroup>}\n\n {teams?.length ?\n <SelectGroup>\n <SelectLabel>{t('Other teams')}</SelectLabel>\n {teams.filter(team => team.id !== selectedTeam?.id)\n .map(team => (\n <SelectItem value={team.id} key={team.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={team as Team} />\n <Typography className=\"max-w-64 truncate\">{team.displayName}</Typography>\n </div>\n </SelectItem>\n ))}\n </SelectGroup> : null}\n\n {!teams?.length && !props.allowNull ?\n <SelectGroup>\n <SelectLabel>{t('No teams yet')}</SelectLabel>\n </SelectGroup> : null}\n\n {project.config.clientTeamCreationEnabled && <>\n <SelectSeparator/>\n <div>\n <Button\n onClick={() => {\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-creation`);\n }\n }}\n className=\"w-full\"\n variant='ghost'\n >\n <PlusCircle className=\"mr-2 h-4 w-4\"/> {t('Create a team')}\n </Button>\n </div>\n </>}\n </SelectContent>\n </Select>\n );\n}\n"],"mappings":"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","names":["team"]}
@@ -2,27 +2,14 @@
2
2
  "use client";
3
3
 
4
4
  // src/components/selected-team-switcher.tsx
5
- import { StackAssertionError } from "@stackframe/stack-shared/dist/utils/errors";
6
5
  import { runAsynchronouslyWithAlert } from "@stackframe/stack-shared/dist/utils/promises";
7
6
  import {
8
- Button,
9
- Select,
10
- SelectContent,
11
- SelectGroup,
12
- SelectItem,
13
- SelectLabel,
14
- SelectSeparator,
15
- SelectTrigger,
16
- SelectValue,
17
- Skeleton,
18
- Typography
7
+ Skeleton
19
8
  } from "@stackframe/stack-ui";
20
- import { PlusCircle, Settings } from "lucide-react";
21
- import { Suspense, useEffect, useMemo } from "react";
9
+ import { Suspense, useEffect } from "react";
22
10
  import { useStackApp, useUser } from "../index.js";
23
- import { useTranslation } from "../lib/translations.js";
24
- import { TeamIcon } from "./team-icon.js";
25
- import { Fragment, jsx, jsxs } from "react/jsx-runtime";
11
+ import { TeamSwitcher } from "./team-switcher.js";
12
+ import { jsx } from "react/jsx-runtime";
26
13
  function SelectedTeamSwitcher(props) {
27
14
  return /* @__PURE__ */ jsx(Suspense, { fallback: /* @__PURE__ */ jsx(Fallback, {}), children: /* @__PURE__ */ jsx(Inner, { ...props }) });
28
15
  }
@@ -30,7 +17,6 @@ function Fallback() {
30
17
  return /* @__PURE__ */ jsx(Skeleton, { className: "h-9 w-full max-w-64 stack-scope" });
31
18
  }
32
19
  function Inner(props) {
33
- const { t } = useTranslation();
34
20
  const appFromHook = useStackApp();
35
21
  const userFromHook = useUser();
36
22
  const app = props.mockUser ? {
@@ -47,103 +33,31 @@ function Inner(props) {
47
33
  }
48
34
  // Mock function
49
35
  } : userFromHook;
50
- const project = app.useProject();
51
36
  const navigate = app.useNavigate();
52
- const selectedTeam = user?.selectedTeam || props.selectedTeam;
53
- const rawTeams = user?.useTeams();
54
- const teams = useMemo(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);
55
37
  useEffect(() => {
56
38
  if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {
57
39
  runAsynchronouslyWithAlert(user?.setSelectedTeam(props.selectedTeam));
58
40
  }
59
41
  }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);
60
- return /* @__PURE__ */ jsxs(
61
- Select,
42
+ return /* @__PURE__ */ jsx(
43
+ TeamSwitcher,
62
44
  {
63
- value: selectedTeam?.id || (props.allowNull ? "null-sentinel" : void 0),
64
- onValueChange: (value) => {
65
- runAsynchronouslyWithAlert(async () => {
66
- let team = null;
67
- if (value !== "null-sentinel") {
68
- team = teams?.find((team2) => team2.id === value) || null;
69
- if (!team) {
70
- throw new StackAssertionError("Team not found, this should not happen");
71
- }
72
- } else {
73
- team = null;
74
- }
75
- if (props.onChange) {
76
- props.onChange(team);
77
- }
78
- if (props.mockUser) return;
79
- if (!props.noUpdateSelectedTeam) {
80
- await user?.setSelectedTeam(team);
81
- }
82
- if (props.urlMap) {
83
- navigate(props.urlMap(team));
84
- }
85
- });
86
- },
87
- children: [
88
- /* @__PURE__ */ jsx(SelectTrigger, { className: "stack-scope max-w-64", children: /* @__PURE__ */ jsx(SelectValue, { placeholder: "Select team" }) }),
89
- /* @__PURE__ */ jsxs(SelectContent, { className: "stack-scope", children: [
90
- user?.selectedTeam ? /* @__PURE__ */ jsxs(SelectGroup, { children: [
91
- /* @__PURE__ */ jsx(SelectLabel, { children: /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between", children: [
92
- /* @__PURE__ */ jsx("span", { children: t("Current team") }),
93
- /* @__PURE__ */ jsx(
94
- Button,
95
- {
96
- variant: "ghost",
97
- size: "icon",
98
- className: "h-6 w-6",
99
- onClick: () => {
100
- if (!props.mockUser) {
101
- navigate(`${app.urls.accountSettings}#team-${user.selectedTeam?.id}`);
102
- }
103
- },
104
- children: /* @__PURE__ */ jsx(Settings, { className: "h-4 w-4" })
105
- }
106
- )
107
- ] }) }),
108
- /* @__PURE__ */ jsx(SelectItem, { value: user.selectedTeam.id, children: /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2", children: [
109
- /* @__PURE__ */ jsx(TeamIcon, { team: user.selectedTeam }),
110
- /* @__PURE__ */ jsx(Typography, { className: "max-w-40 truncate", children: user.selectedTeam.displayName })
111
- ] }) })
112
- ] }) : void 0,
113
- props.allowNull && /* @__PURE__ */ jsx(SelectGroup, { children: /* @__PURE__ */ jsx(SelectItem, { value: "null-sentinel", children: /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2", children: [
114
- /* @__PURE__ */ jsx(TeamIcon, { team: "personal" }),
115
- /* @__PURE__ */ jsx(Typography, { className: "max-w-40 truncate", children: props.nullLabel || t("No team") })
116
- ] }) }) }),
117
- teams?.length ? /* @__PURE__ */ jsxs(SelectGroup, { children: [
118
- /* @__PURE__ */ jsx(SelectLabel, { children: t("Other teams") }),
119
- teams.filter((team) => team.id !== user?.selectedTeam?.id).map((team) => /* @__PURE__ */ jsx(SelectItem, { value: team.id, children: /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2", children: [
120
- /* @__PURE__ */ jsx(TeamIcon, { team }),
121
- /* @__PURE__ */ jsx(Typography, { className: "max-w-64 truncate", children: team.displayName })
122
- ] }) }, team.id))
123
- ] }) : null,
124
- !teams?.length && !props.allowNull ? /* @__PURE__ */ jsx(SelectGroup, { children: /* @__PURE__ */ jsx(SelectLabel, { children: t("No teams yet") }) }) : null,
125
- project.config.clientTeamCreationEnabled && /* @__PURE__ */ jsxs(Fragment, { children: [
126
- /* @__PURE__ */ jsx(SelectSeparator, {}),
127
- /* @__PURE__ */ jsx("div", { children: /* @__PURE__ */ jsxs(
128
- Button,
129
- {
130
- onClick: () => {
131
- if (!props.mockUser) {
132
- navigate(`${app.urls.accountSettings}#team-creation`);
133
- }
134
- },
135
- className: "w-full",
136
- variant: "ghost",
137
- children: [
138
- /* @__PURE__ */ jsx(PlusCircle, { className: "mr-2 h-4 w-4" }),
139
- " ",
140
- t("Create a team")
141
- ]
142
- }
143
- ) })
144
- ] })
145
- ] })
146
- ]
45
+ team: props.selectedTeam,
46
+ allowNull: props.allowNull,
47
+ nullLabel: props.nullLabel,
48
+ triggerClassName: props.triggerClassName,
49
+ onChange: async (team) => {
50
+ if (props.onChange) {
51
+ props.onChange(team);
52
+ }
53
+ if (props.mockUser) return;
54
+ if (!props.noUpdateSelectedTeam) {
55
+ await user?.setSelectedTeam(team);
56
+ }
57
+ if (props.urlMap) {
58
+ navigate(props.urlMap(team));
59
+ }
60
+ }
147
61
  }
148
62
  );
149
63
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/components/selected-team-switcher.tsx"],"sourcesContent":["'use client';\n\n\n//===========================================\n// THIS FILE IS AUTO-GENERATED FROM TEMPLATE. DO NOT EDIT IT DIRECTLY\n//===========================================\nimport { StackAssertionError } from \"@stackframe/stack-shared/dist/utils/errors\";\nimport { runAsynchronouslyWithAlert } from \"@stackframe/stack-shared/dist/utils/promises\";\nimport {\n Button,\n Select,\n SelectContent,\n SelectGroup,\n SelectItem,\n SelectLabel,\n SelectSeparator,\n SelectTrigger,\n SelectValue,\n Skeleton,\n Typography\n} from \"@stackframe/stack-ui\";\nimport { PlusCircle, Settings } from \"lucide-react\";\nimport { Suspense, useEffect, useMemo } from \"react\";\nimport { Team, useStackApp, useUser } from \"..\";\nimport { useTranslation } from \"../lib/translations\";\nimport { TeamIcon } from \"./team-icon\";\n\ntype MockTeam = {\n id: string,\n displayName: string,\n profileImageUrl?: string | null,\n};\n\ntype SelectedTeamSwitcherProps<AllowNull extends boolean = false> = {\n urlMap?: (team: AllowNull extends true ? Team | null : Team) => string,\n selectedTeam?: Team,\n noUpdateSelectedTeam?: boolean,\n allowNull?: AllowNull,\n nullLabel?: string,\n onChange?: (team: AllowNull extends true ? Team | null : Team) => void,\n // Mock data props\n mockUser?: {\n selectedTeam?: MockTeam,\n },\n mockTeams?: MockTeam[],\n mockProject?: {\n config: {\n clientTeamCreationEnabled: boolean,\n },\n },\n};\n\nexport function SelectedTeamSwitcher<AllowNull extends boolean = false>(props: SelectedTeamSwitcherProps<AllowNull>) {\n return <Suspense fallback={<Fallback />}>\n <Inner {...props} />\n </Suspense>;\n}\n\nfunction Fallback() {\n return <Skeleton className=\"h-9 w-full max-w-64 stack-scope\" />;\n}\n\nfunction Inner<AllowNull extends boolean>(props: SelectedTeamSwitcherProps<AllowNull>) {\n const { t } = useTranslation();\n const appFromHook = useStackApp();\n const userFromHook = useUser();\n\n // Use mock data if provided, otherwise use real data\n const app = props.mockUser ? {\n useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },\n useNavigate: () => () => {}, // Mock navigate function\n urls: { accountSettings: '/account-settings' },\n } : appFromHook;\n\n const user = props.mockUser ? {\n selectedTeam: props.mockUser.selectedTeam,\n useTeams: () => props.mockTeams || [],\n setSelectedTeam: async () => {}, // Mock function\n } : userFromHook;\n\n const project = app.useProject();\n const navigate = app.useNavigate();\n const selectedTeam = user?.selectedTeam || props.selectedTeam;\n const rawTeams = user?.useTeams();\n const teams = useMemo(() => rawTeams?.sort((a, b) => b.id === selectedTeam?.id ? 1 : -1), [rawTeams, selectedTeam]);\n\n useEffect(() => {\n if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {\n runAsynchronouslyWithAlert(user?.setSelectedTeam(props.selectedTeam));\n }\n }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);\n\n return (\n <Select\n value={selectedTeam?.id || (props.allowNull ? 'null-sentinel' : undefined)}\n onValueChange={(value) => {\n runAsynchronouslyWithAlert(async () => {\n let team: MockTeam | null = null;\n if (value !== 'null-sentinel') {\n team = teams?.find(team => team.id === value) || null;\n if (!team) {\n throw new StackAssertionError('Team not found, this should not happen');\n }\n } else {\n team = null;\n }\n\n // Call onChange callback if provided\n if (props.onChange) {\n props.onChange(team as Team);\n }\n\n // Skip actual navigation/updates in mock mode\n if (props.mockUser) return;\n\n if (!props.noUpdateSelectedTeam) {\n await user?.setSelectedTeam(team as Team);\n }\n if (props.urlMap) {\n navigate(props.urlMap(team as Team));\n }\n });\n }}\n >\n <SelectTrigger className=\"stack-scope max-w-64\">\n <SelectValue placeholder=\"Select team\"/>\n </SelectTrigger>\n <SelectContent className=\"stack-scope\">\n {user?.selectedTeam ? <SelectGroup>\n <SelectLabel>\n <div className=\"flex items-center justify-between\">\n <span>\n {t('Current team')}\n </span>\n <Button\n variant='ghost'\n size='icon'\n className=\"h-6 w-6\"\n onClick={() => {\n // Skip navigation in mock mode\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-${user.selectedTeam?.id}`);\n }\n }}\n >\n <Settings className=\"h-4 w-4\"/>\n </Button>\n </div>\n </SelectLabel>\n <SelectItem value={user.selectedTeam.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={user.selectedTeam as Team} />\n <Typography className=\"max-w-40 truncate\">{user.selectedTeam.displayName}</Typography>\n </div>\n </SelectItem>\n </SelectGroup> : undefined}\n\n {props.allowNull && <SelectGroup>\n <SelectItem value=\"null-sentinel\">\n <div className=\"flex items-center gap-2\">\n <TeamIcon team='personal' />\n <Typography className=\"max-w-40 truncate\">{props.nullLabel || t('No team')}</Typography>\n </div>\n </SelectItem>\n </SelectGroup>}\n\n {teams?.length ?\n <SelectGroup>\n <SelectLabel>{t('Other teams')}</SelectLabel>\n {teams.filter(team => team.id !== user?.selectedTeam?.id)\n .map(team => (\n <SelectItem value={team.id} key={team.id}>\n <div className=\"flex items-center gap-2\">\n <TeamIcon team={team as Team} />\n <Typography className=\"max-w-64 truncate\">{team.displayName}</Typography>\n </div>\n </SelectItem>\n ))}\n </SelectGroup> : null}\n\n {!teams?.length && !props.allowNull ?\n <SelectGroup>\n <SelectLabel>{t('No teams yet')}</SelectLabel>\n </SelectGroup> : null}\n\n {project.config.clientTeamCreationEnabled && <>\n <SelectSeparator/>\n <div>\n <Button\n onClick={() => {\n // Skip navigation in mock mode\n if (!props.mockUser) {\n navigate(`${app.urls.accountSettings}#team-creation`);\n }\n }}\n className=\"w-full\"\n variant='ghost'\n >\n <PlusCircle className=\"mr-2 h-4 w-4\"/> {t('Create a team')}\n </Button>\n </div>\n </>}\n </SelectContent>\n </Select>\n );\n}\n"],"mappings":"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","names":["team"]}
1
+ {"version":3,"sources":["../../../src/components/selected-team-switcher.tsx"],"sourcesContent":["'use client';\n\n\n//===========================================\n// THIS FILE IS AUTO-GENERATED FROM TEMPLATE. DO NOT EDIT IT DIRECTLY\n//===========================================\nimport { runAsynchronouslyWithAlert } from \"@stackframe/stack-shared/dist/utils/promises\";\nimport {\n Skeleton,\n} from \"@stackframe/stack-ui\";\nimport { Suspense, useEffect } from \"react\";\nimport { Team, useStackApp, useUser } from \"..\";\nimport { TeamSwitcher } from \"./team-switcher\";\n\ntype MockTeam = {\n id: string,\n displayName: string,\n profileImageUrl?: string | null,\n};\n\ntype SelectedTeamSwitcherProps<AllowNull extends boolean = false> = {\n urlMap?: (team: AllowNull extends true ? Team | null : Team) => string,\n selectedTeam?: Team,\n noUpdateSelectedTeam?: boolean,\n allowNull?: AllowNull,\n nullLabel?: string,\n onChange?: (team: AllowNull extends true ? Team | null : Team) => void,\n triggerClassName?: string,\n // Mock data props\n mockUser?: {\n selectedTeam?: MockTeam,\n },\n mockTeams?: MockTeam[],\n mockProject?: {\n config: {\n clientTeamCreationEnabled: boolean,\n },\n },\n};\n\nexport function SelectedTeamSwitcher<AllowNull extends boolean = false>(props: SelectedTeamSwitcherProps<AllowNull>) {\n return <Suspense fallback={<Fallback />}>\n <Inner {...props} />\n </Suspense>;\n}\n\nfunction Fallback() {\n return <Skeleton className=\"h-9 w-full max-w-64 stack-scope\" />;\n}\n\nfunction Inner<AllowNull extends boolean>(props: SelectedTeamSwitcherProps<AllowNull>) {\n const appFromHook = useStackApp();\n const userFromHook = useUser();\n\n // Use mock data if provided, otherwise use real data\n const app = props.mockUser ? {\n useProject: () => props.mockProject || { config: { clientTeamCreationEnabled: false } },\n useNavigate: () => () => {}, // Mock navigate function\n urls: { accountSettings: '/account-settings' },\n } : appFromHook;\n\n const user = props.mockUser ? {\n selectedTeam: props.mockUser.selectedTeam,\n useTeams: () => props.mockTeams || [],\n setSelectedTeam: async () => {}, // Mock function\n } : userFromHook;\n\n const navigate = app.useNavigate();\n\n useEffect(() => {\n if (!props.noUpdateSelectedTeam && props.selectedTeam && !props.mockUser) {\n runAsynchronouslyWithAlert(user?.setSelectedTeam(props.selectedTeam));\n }\n }, [props.noUpdateSelectedTeam, props.selectedTeam, props.mockUser]);\n\n return (\n <TeamSwitcher\n team={props.selectedTeam}\n allowNull={props.allowNull}\n nullLabel={props.nullLabel}\n triggerClassName={props.triggerClassName}\n onChange={async (team) => {\n if (props.onChange) {\n props.onChange(team as Team);\n }\n // Skip actual navigation/updates in mock mode\n if (props.mockUser) return;\n if (!props.noUpdateSelectedTeam) {\n await user?.setSelectedTeam(team as Team);\n }\n if (props.urlMap) {\n navigate(props.urlMap(team as Team));\n }\n }}\n />\n );\n}\n"],"mappings":";;;AAMA,SAAS,kCAAkC;AAC3C;AAAA,EACE;AAAA,OACK;AACP,SAAS,UAAU,iBAAiB;AACpC,SAAe,aAAa,eAAe;AAC3C,SAAS,oBAAoB;AA6BA;AADtB,SAAS,qBAAwD,OAA6C;AACnH,SAAO,oBAAC,YAAS,UAAU,oBAAC,YAAS,GACnC,8BAAC,SAAO,GAAG,OAAO,GACpB;AACF;AAEA,SAAS,WAAW;AAClB,SAAO,oBAAC,YAAS,WAAU,mCAAkC;AAC/D;AAEA,SAAS,MAAiC,OAA6C;AACrF,QAAM,cAAc,YAAY;AAChC,QAAM,eAAe,QAAQ;AAG7B,QAAM,MAAM,MAAM,WAAW;AAAA,IAC3B,YAAY,MAAM,MAAM,eAAe,EAAE,QAAQ,EAAE,2BAA2B,MAAM,EAAE;AAAA,IACtF,aAAa,MAAM,MAAM;AAAA,IAAC;AAAA;AAAA,IAC1B,MAAM,EAAE,iBAAiB,oBAAoB;AAAA,EAC/C,IAAI;AAEJ,QAAM,OAAO,MAAM,WAAW;AAAA,IAC5B,cAAc,MAAM,SAAS;AAAA,IAC7B,UAAU,MAAM,MAAM,aAAa,CAAC;AAAA,IACpC,iBAAiB,YAAY;AAAA,IAAC;AAAA;AAAA,EAChC,IAAI;AAEJ,QAAM,WAAW,IAAI,YAAY;AAEjC,YAAU,MAAM;AACd,QAAI,CAAC,MAAM,wBAAwB,MAAM,gBAAgB,CAAC,MAAM,UAAU;AACxE,iCAA2B,MAAM,gBAAgB,MAAM,YAAY,CAAC;AAAA,IACtE;AAAA,EACF,GAAG,CAAC,MAAM,sBAAsB,MAAM,cAAc,MAAM,QAAQ,CAAC;AAEnE,SACE;AAAA,IAAC;AAAA;AAAA,MACC,MAAM,MAAM;AAAA,MACZ,WAAW,MAAM;AAAA,MACjB,WAAW,MAAM;AAAA,MACjB,kBAAkB,MAAM;AAAA,MACxB,UAAU,OAAO,SAAS;AACxB,YAAI,MAAM,UAAU;AAClB,gBAAM,SAAS,IAAY;AAAA,QAC7B;AAEA,YAAI,MAAM,SAAU;AACpB,YAAI,CAAC,MAAM,sBAAsB;AAC/B,gBAAM,MAAM,gBAAgB,IAAY;AAAA,QAC1C;AACA,YAAI,MAAM,QAAQ;AAChB,mBAAS,MAAM,OAAO,IAAY,CAAC;AAAA,QACrC;AAAA,MACF;AAAA;AAAA,EACF;AAEJ;","names":[]}