codeforlife 2.12.7 → 2.14.4

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 (96) hide show
  1. package/dist/{Countdown-snRYiLrs.js → Countdown-B1ilD_qY.js} +2 -2
  2. package/dist/{Countdown-snRYiLrs.js.map → Countdown-B1ilD_qY.js.map} +1 -1
  3. package/dist/{Countdown-CL7dyZrl.cjs → Countdown-DJ5b4A3w.cjs} +2 -2
  4. package/dist/{Countdown-CL7dyZrl.cjs.map → Countdown-DJ5b4A3w.cjs.map} +1 -1
  5. package/dist/{LinkButton-CRDs950E.js → LinkButton-BVU_MF2a.js} +2 -2
  6. package/dist/{LinkButton-CRDs950E.js.map → LinkButton-BVU_MF2a.js.map} +1 -1
  7. package/dist/{LinkButton-BQMG96aQ.cjs → LinkButton-BbGJHgCY.cjs} +2 -2
  8. package/dist/{LinkButton-BQMG96aQ.cjs.map → LinkButton-BbGJHgCY.cjs.map} +1 -1
  9. package/dist/{Navigate-Ch0ljYa-.cjs → Navigate-CioAG5Y-.cjs} +2 -2
  10. package/dist/{Navigate-Ch0ljYa-.cjs.map → Navigate-CioAG5Y-.cjs.map} +1 -1
  11. package/dist/{Navigate-Zt9DRJve.js → Navigate-DfeA_eki.js} +2 -2
  12. package/dist/{Navigate-Zt9DRJve.js.map → Navigate-DfeA_eki.js.map} +1 -1
  13. package/dist/api/endpoints/index.cjs.js +1 -1
  14. package/dist/api/endpoints/index.es.js +1 -1
  15. package/dist/api/index.cjs.js +1 -1
  16. package/dist/api/index.cjs.js.map +1 -1
  17. package/dist/api/index.es.js +21 -19
  18. package/dist/api/index.es.js.map +1 -1
  19. package/dist/auth-D-8t6wfR.js +238 -0
  20. package/dist/auth-D-8t6wfR.js.map +1 -0
  21. package/dist/auth-uyv8Mv88.cjs +2 -0
  22. package/dist/auth-uyv8Mv88.cjs.map +1 -0
  23. package/dist/components/form/index.cjs.js +1 -1
  24. package/dist/components/form/index.es.js +1 -1
  25. package/dist/components/index.cjs.js +1 -1
  26. package/dist/components/index.es.js +5 -5
  27. package/dist/components/page/index.cjs.js +1 -1
  28. package/dist/components/page/index.es.js +1 -1
  29. package/dist/components/router/index.cjs.js +1 -1
  30. package/dist/components/router/index.es.js +2 -2
  31. package/dist/features/index.cjs.js +1 -1
  32. package/dist/features/index.cjs.js.map +1 -1
  33. package/dist/features/index.es.js +13 -14
  34. package/dist/features/index.es.js.map +1 -1
  35. package/dist/hooks/index.cjs.js +1 -1
  36. package/dist/hooks/index.es.js +1 -1
  37. package/dist/index-C8T09ieQ.cjs +2 -0
  38. package/dist/index-C8T09ieQ.cjs.map +1 -0
  39. package/dist/index-Cxq_P-ni.js +242 -0
  40. package/dist/index-Cxq_P-ni.js.map +1 -0
  41. package/dist/index-Da4T5FYK.cjs +2 -0
  42. package/dist/{index-BsxcGeQL.cjs.map → index-Da4T5FYK.cjs.map} +1 -1
  43. package/dist/{index-uvqsz6fM.js → index-De-EwYmr.js} +4 -5
  44. package/dist/{index-uvqsz6fM.js.map → index-De-EwYmr.js.map} +1 -1
  45. package/dist/session-CJM1Czfv.js +33 -0
  46. package/dist/session-CJM1Czfv.js.map +1 -0
  47. package/dist/session-J-ezj9cg.cjs +2 -0
  48. package/dist/session-J-ezj9cg.cjs.map +1 -0
  49. package/dist/slices/index.cjs.js +1 -1
  50. package/dist/slices/index.cjs.js.map +1 -1
  51. package/dist/slices/index.es.js +27 -3
  52. package/dist/slices/index.es.js.map +1 -1
  53. package/dist/src/api/createApi.d.ts +4 -1
  54. package/dist/src/api/endpoints/session.d.ts +3 -2
  55. package/dist/src/components/page/Page.d.ts +3 -2
  56. package/dist/src/hooks/auth.d.ts +4 -3
  57. package/dist/src/slices/index.d.ts +1 -1
  58. package/dist/src/slices/session.d.ts +2 -10
  59. package/dist/src/utils/settings.d.ts +37 -0
  60. package/dist/utils/auth.cjs.js +1 -1
  61. package/dist/utils/auth.cjs.js.map +1 -1
  62. package/dist/utils/auth.es.js +18 -18
  63. package/dist/utils/auth.es.js.map +1 -1
  64. package/dist/utils/router.cjs.js +1 -1
  65. package/dist/utils/router.es.js +1 -1
  66. package/dist/utils/settings.cjs.js +2 -0
  67. package/dist/utils/settings.cjs.js.map +1 -0
  68. package/dist/utils/settings.d.ts +2 -0
  69. package/dist/utils/settings.es.js +37 -0
  70. package/dist/utils/settings.es.js.map +1 -0
  71. package/package.json +10 -10
  72. package/dist/auth-B6anBtxF.js +0 -238
  73. package/dist/auth-B6anBtxF.js.map +0 -1
  74. package/dist/auth-C2OUeLmQ.cjs +0 -2
  75. package/dist/auth-C2OUeLmQ.cjs.map +0 -1
  76. package/dist/index-B3QkMBQe.cjs +0 -2
  77. package/dist/index-B3QkMBQe.cjs.map +0 -1
  78. package/dist/index-BsxcGeQL.cjs +0 -2
  79. package/dist/index-C08WO83n.js +0 -237
  80. package/dist/index-C08WO83n.js.map +0 -1
  81. package/dist/session-CE2U7oL1.cjs +0 -2
  82. package/dist/session-CE2U7oL1.cjs.map +0 -1
  83. package/dist/session-COyN01K0.js +0 -33
  84. package/dist/session-COyN01K0.js.map +0 -1
  85. package/dist/session-eOp0H-EC.cjs +0 -2
  86. package/dist/session-eOp0H-EC.cjs.map +0 -1
  87. package/dist/session-oI-Ht2C8.js +0 -30
  88. package/dist/session-oI-Ht2C8.js.map +0 -1
  89. package/dist/settings/index.cjs.js +0 -2
  90. package/dist/settings/index.cjs.js.map +0 -1
  91. package/dist/settings/index.d.ts +0 -2
  92. package/dist/settings/index.es.js +0 -18
  93. package/dist/settings/index.es.js.map +0 -1
  94. package/dist/src/settings/custom.d.ts +0 -12
  95. package/dist/src/settings/index.d.ts +0 -3
  96. package/dist/src/settings/vite.d.ts +0 -10
@@ -0,0 +1,33 @@
1
+ import "@reduxjs/toolkit/query/react";
2
+ import "@reduxjs/toolkit";
3
+ function c(n, r, e = "session/login/") {
4
+ return n.mutation({
5
+ query: (o) => ({ url: e, method: "POST", body: o }),
6
+ async onQueryStarted(o, { dispatch: a, queryFulfilled: t }) {
7
+ try {
8
+ await t, a(r());
9
+ } catch (i) {
10
+ console.error("Failed to call login endpoint...", i);
11
+ }
12
+ }
13
+ });
14
+ }
15
+ function d(n, r, e, o = "session/logout/") {
16
+ return r.mutation({
17
+ query: () => ({ url: o, method: "POST" }),
18
+ async onQueryStarted(a, { dispatch: t, queryFulfilled: i }) {
19
+ try {
20
+ await i;
21
+ } catch (l) {
22
+ console.error("Failed to call logout endpoint...", l);
23
+ } finally {
24
+ t(e()), t(n.util.resetApiState());
25
+ }
26
+ }
27
+ });
28
+ }
29
+ export {
30
+ c as a,
31
+ d as b
32
+ };
33
+ //# sourceMappingURL=session-CJM1Czfv.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"session-CJM1Czfv.js","sources":["../src/api/endpoints/session.ts"],"sourcesContent":["import { type Api, type EndpointBuilder } from \"@reduxjs/toolkit/query/react\"\nimport { type ActionCreatorWithoutPayload } from \"@reduxjs/toolkit\"\n\nexport type ExchangeOAuth2CodeArg = {\n code: string\n code_verifier: string\n redirect_uri: string\n}\n\nexport function buildLoginEndpoint<ResultType, QueryArg>(\n build: EndpointBuilder<any, any, any>,\n action: ActionCreatorWithoutPayload,\n url: string = \"session/login/\",\n) {\n return build.mutation<ResultType, QueryArg>({\n query: body => ({ url, method: \"POST\", body }),\n async onQueryStarted(_, { dispatch, queryFulfilled }) {\n try {\n await queryFulfilled\n dispatch(action())\n } catch (error) {\n console.error(\"Failed to call login endpoint...\", error)\n }\n },\n })\n}\n\nexport function buildLogoutEndpoint<ResultType, QueryArg>(\n api: Api<any, any, any, any, any>,\n build: EndpointBuilder<any, any, any>,\n action: ActionCreatorWithoutPayload,\n url: string = \"session/logout/\",\n) {\n return build.mutation<ResultType, QueryArg>({\n query: () => ({ url, method: \"POST\" }),\n async onQueryStarted(_, { dispatch, queryFulfilled }) {\n try {\n await queryFulfilled\n } catch (error) {\n console.error(\"Failed to call logout endpoint...\", error)\n } finally {\n dispatch(action())\n // eslint-disable-next-line @typescript-eslint/no-unsafe-call,@typescript-eslint/no-unsafe-member-access\n dispatch(api.util.resetApiState())\n }\n },\n })\n}\n"],"names":["buildLoginEndpoint","build","action","url","body","_","dispatch","queryFulfilled","error","buildLogoutEndpoint","api"],"mappings":";;AASO,SAASA,EACdC,GACAC,GACAC,IAAc,kBACd;AACA,SAAOF,EAAM,SAA+B;AAAA,IAC1C,OAAO,CAAAG,OAAS,EAAE,KAAAD,GAAK,QAAQ,QAAQ,MAAAC;IACvC,MAAM,eAAeC,GAAG,EAAE,UAAAC,GAAU,gBAAAC,KAAkB;AACpD,UAAI;AACF,cAAMA,GACND,EAASJ,GAAQ;AAAA,MACnB,SAASM,GAAO;AACd,gBAAQ,MAAM,oCAAoCA,CAAK;AAAA,MACzD;AAAA,IACF;AAAA,EAAA,CACD;AACH;AAEO,SAASC,EACdC,GACAT,GACAC,GACAC,IAAc,mBACd;AACA,SAAOF,EAAM,SAA+B;AAAA,IAC1C,OAAO,OAAO,EAAE,KAAAE,GAAK,QAAQ,OAAA;AAAA,IAC7B,MAAM,eAAeE,GAAG,EAAE,UAAAC,GAAU,gBAAAC,KAAkB;AACpD,UAAI;AACF,cAAMA;AAAA,MACR,SAASC,GAAO;AACd,gBAAQ,MAAM,qCAAqCA,CAAK;AAAA,MAC1D,UAAA;AACE,QAAAF,EAASJ,GAAQ,GAEjBI,EAASI,EAAI,KAAK,eAAe;AAAA,MACnC;AAAA,IACF;AAAA,EAAA,CACD;AACH;"}
@@ -0,0 +1,2 @@
1
+ "use strict";require("@reduxjs/toolkit/query/react");require("@reduxjs/toolkit");function a(n,e,r="session/login/"){return n.mutation({query:o=>({url:r,method:"POST",body:o}),async onQueryStarted(o,{dispatch:u,queryFulfilled:t}){try{await t,u(e())}catch(i){console.error("Failed to call login endpoint...",i)}}})}function d(n,e,r,o="session/logout/"){return e.mutation({query:()=>({url:o,method:"POST"}),async onQueryStarted(u,{dispatch:t,queryFulfilled:i}){try{await i}catch(l){console.error("Failed to call logout endpoint...",l)}finally{t(r()),t(n.util.resetApiState())}}})}exports.buildLoginEndpoint=a;exports.buildLogoutEndpoint=d;
2
+ //# sourceMappingURL=session-J-ezj9cg.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"session-J-ezj9cg.cjs","sources":["../src/api/endpoints/session.ts"],"sourcesContent":["import { type Api, type EndpointBuilder } from \"@reduxjs/toolkit/query/react\"\nimport { type ActionCreatorWithoutPayload } from \"@reduxjs/toolkit\"\n\nexport type ExchangeOAuth2CodeArg = {\n code: string\n code_verifier: string\n redirect_uri: string\n}\n\nexport function buildLoginEndpoint<ResultType, QueryArg>(\n build: EndpointBuilder<any, any, any>,\n action: ActionCreatorWithoutPayload,\n url: string = \"session/login/\",\n) {\n return build.mutation<ResultType, QueryArg>({\n query: body => ({ url, method: \"POST\", body }),\n async onQueryStarted(_, { dispatch, queryFulfilled }) {\n try {\n await queryFulfilled\n dispatch(action())\n } catch (error) {\n console.error(\"Failed to call login endpoint...\", error)\n }\n },\n })\n}\n\nexport function buildLogoutEndpoint<ResultType, QueryArg>(\n api: Api<any, any, any, any, any>,\n build: EndpointBuilder<any, any, any>,\n action: ActionCreatorWithoutPayload,\n url: string = \"session/logout/\",\n) {\n return build.mutation<ResultType, QueryArg>({\n query: () => ({ url, method: \"POST\" }),\n async onQueryStarted(_, { dispatch, queryFulfilled }) {\n try {\n await queryFulfilled\n } catch (error) {\n console.error(\"Failed to call logout endpoint...\", error)\n } finally {\n dispatch(action())\n // eslint-disable-next-line @typescript-eslint/no-unsafe-call,@typescript-eslint/no-unsafe-member-access\n dispatch(api.util.resetApiState())\n }\n },\n })\n}\n"],"names":["buildLoginEndpoint","build","action","url","body","_","dispatch","queryFulfilled","error","buildLogoutEndpoint","api"],"mappings":"iFASO,SAASA,EACdC,EACAC,EACAC,EAAc,iBACd,CACA,OAAOF,EAAM,SAA+B,CAC1C,MAAOG,IAAS,CAAE,IAAAD,EAAK,OAAQ,OAAQ,KAAAC,IACvC,MAAM,eAAeC,EAAG,CAAE,SAAAC,EAAU,eAAAC,GAAkB,CACpD,GAAI,CACF,MAAMA,EACND,EAASJ,GAAQ,CACnB,OAASM,EAAO,CACd,QAAQ,MAAM,mCAAoCA,CAAK,CACzD,CACF,CAAA,CACD,CACH,CAEO,SAASC,EACdC,EACAT,EACAC,EACAC,EAAc,kBACd,CACA,OAAOF,EAAM,SAA+B,CAC1C,MAAO,KAAO,CAAE,IAAAE,EAAK,OAAQ,MAAA,GAC7B,MAAM,eAAeE,EAAG,CAAE,SAAAC,EAAU,eAAAC,GAAkB,CACpD,GAAI,CACF,MAAMA,CACR,OAASC,EAAO,CACd,QAAQ,MAAM,oCAAqCA,CAAK,CAC1D,QAAA,CACEF,EAASJ,GAAQ,EAEjBI,EAASI,EAAI,KAAK,eAAe,CACnC,CACF,CAAA,CACD,CACH"}
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("../session-CE2U7oL1.cjs");exports.createSlice=e.createSlice;exports.sessionSlice=e.sessionSlice;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const t=require("@reduxjs/toolkit"),n=require("js-cookie"),s=t.buildCreateSlice({creators:{asyncThunk:t.asyncThunkCreator}});function c(r){const i={isLoggedIn:!!n.get(r)};return s({name:"session",initialState:i,reducers:e=>({login:e.reducer(o=>{o.isLoggedIn=!0}),logout:e.reducer(o=>{o.isLoggedIn=!1})}),selectors:{selectIsLoggedIn:e=>e.isLoggedIn}})}exports.createSessionSlice=c;exports.createSlice=s;
2
2
  //# sourceMappingURL=index.cjs.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs.js","sources":[],"sourcesContent":[],"names":[],"mappings":""}
1
+ {"version":3,"file":"index.cjs.js","sources":["../../src/slices/createSlice.ts","../../src/slices/session.ts"],"sourcesContent":["import { asyncThunkCreator, buildCreateSlice } from \"@reduxjs/toolkit\"\n\n// `buildCreateSlice` allows us to create a slice with async thunks.\nconst createSlice = buildCreateSlice({\n creators: { asyncThunk: asyncThunkCreator },\n})\n\nexport default createSlice\n","import Cookies from \"js-cookie\"\n\nimport createSlice from \"./createSlice\"\n\nexport interface SessionState {\n isLoggedIn: boolean\n}\n\nexport default function createSessionSlice(sessionMetadataCookieName: string) {\n const initialState: SessionState = {\n isLoggedIn: Boolean(Cookies.get(sessionMetadataCookieName)),\n }\n\n return createSlice({\n name: \"session\",\n initialState,\n reducers: create => ({\n login: create.reducer(state => {\n state.isLoggedIn = true\n }),\n logout: create.reducer(state => {\n state.isLoggedIn = false\n }),\n }),\n selectors: {\n selectIsLoggedIn: session => session.isLoggedIn,\n },\n })\n}\n"],"names":["createSlice","buildCreateSlice","asyncThunkCreator","createSessionSlice","sessionMetadataCookieName","initialState","Cookies","create","state","session"],"mappings":"2IAGMA,EAAcC,EAAAA,iBAAiB,CACnC,SAAU,CAAE,WAAYC,EAAAA,iBAAA,CAC1B,CAAC,ECGD,SAAwBC,EAAmBC,EAAmC,CAC5E,MAAMC,EAA6B,CACjC,WAAY,EAAQC,EAAQ,IAAIF,CAAyB,CAAC,EAG5D,OAAOJ,EAAY,CACjB,KAAM,UACN,aAAAK,EACA,SAAUE,IAAW,CACnB,MAAOA,EAAO,QAAQC,GAAS,CAC7BA,EAAM,WAAa,EACrB,CAAC,EACD,OAAQD,EAAO,QAAQC,GAAS,CAC9BA,EAAM,WAAa,EACrB,CAAC,CAAA,GAEH,UAAW,CACT,oBAA6BC,EAAQ,UAAA,CACvC,CACD,CACH"}
@@ -1,6 +1,30 @@
1
- import { c, s as a } from "../session-oI-Ht2C8.js";
1
+ import { buildCreateSlice as n, asyncThunkCreator as t } from "@reduxjs/toolkit";
2
+ import i from "js-cookie";
3
+ const c = n({
4
+ creators: { asyncThunk: t }
5
+ });
6
+ function l(r) {
7
+ const s = {
8
+ isLoggedIn: !!i.get(r)
9
+ };
10
+ return c({
11
+ name: "session",
12
+ initialState: s,
13
+ reducers: (e) => ({
14
+ login: e.reducer((o) => {
15
+ o.isLoggedIn = !0;
16
+ }),
17
+ logout: e.reducer((o) => {
18
+ o.isLoggedIn = !1;
19
+ })
20
+ }),
21
+ selectors: {
22
+ selectIsLoggedIn: (e) => e.isLoggedIn
23
+ }
24
+ });
25
+ }
2
26
  export {
3
- c as createSlice,
4
- a as sessionSlice
27
+ l as createSessionSlice,
28
+ c as createSlice
5
29
  };
6
30
  //# sourceMappingURL=index.es.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.es.js","sources":[],"sourcesContent":[],"names":[],"mappings":";"}
1
+ {"version":3,"file":"index.es.js","sources":["../../src/slices/createSlice.ts","../../src/slices/session.ts"],"sourcesContent":["import { asyncThunkCreator, buildCreateSlice } from \"@reduxjs/toolkit\"\n\n// `buildCreateSlice` allows us to create a slice with async thunks.\nconst createSlice = buildCreateSlice({\n creators: { asyncThunk: asyncThunkCreator },\n})\n\nexport default createSlice\n","import Cookies from \"js-cookie\"\n\nimport createSlice from \"./createSlice\"\n\nexport interface SessionState {\n isLoggedIn: boolean\n}\n\nexport default function createSessionSlice(sessionMetadataCookieName: string) {\n const initialState: SessionState = {\n isLoggedIn: Boolean(Cookies.get(sessionMetadataCookieName)),\n }\n\n return createSlice({\n name: \"session\",\n initialState,\n reducers: create => ({\n login: create.reducer(state => {\n state.isLoggedIn = true\n }),\n logout: create.reducer(state => {\n state.isLoggedIn = false\n }),\n }),\n selectors: {\n selectIsLoggedIn: session => session.isLoggedIn,\n },\n })\n}\n"],"names":["createSlice","buildCreateSlice","asyncThunkCreator","createSessionSlice","sessionMetadataCookieName","initialState","Cookies","create","state","session"],"mappings":";;AAGA,MAAMA,IAAcC,EAAiB;AAAA,EACnC,UAAU,EAAE,YAAYC,EAAA;AAC1B,CAAC;ACGD,SAAwBC,EAAmBC,GAAmC;AAC5E,QAAMC,IAA6B;AAAA,IACjC,YAAY,EAAQC,EAAQ,IAAIF,CAAyB;AAAA,EAAC;AAG5D,SAAOJ,EAAY;AAAA,IACjB,MAAM;AAAA,IACN,cAAAK;AAAA,IACA,UAAU,CAAAE,OAAW;AAAA,MACnB,OAAOA,EAAO,QAAQ,CAAAC,MAAS;AAC7B,QAAAA,EAAM,aAAa;AAAA,MACrB,CAAC;AAAA,MACD,QAAQD,EAAO,QAAQ,CAAAC,MAAS;AAC9B,QAAAA,EAAM,aAAa;AAAA,MACrB,CAAC;AAAA,IAAA;AAAA,IAEH,WAAW;AAAA,MACT,kBAAkB,OAAWC,EAAQ;AAAA,IAAA;AAAA,EACvC,CACD;AACH;"}
@@ -1,6 +1,9 @@
1
1
  import { Api, BaseQueryApi, FetchArgs, FetchBaseQueryError, FetchBaseQueryMeta, MutationDefinition, QueryReturnValue, coreModuleName, reactHooksModuleName } from '@reduxjs/toolkit/query/react';
2
+ import { ActionCreatorWithoutPayload } from '@reduxjs/toolkit';
2
3
  import { TagTypes as DefaultTagTypes } from './tagTypes';
3
- export default function createApi<TagTypes extends string = never>({ tagTypes, }?: {
4
+ export default function createApi<TagTypes extends string = never>({ serviceApiUrl, logoutAction, tagTypes, }: {
5
+ serviceApiUrl: string;
6
+ logoutAction: ActionCreatorWithoutPayload;
4
7
  tagTypes?: readonly TagTypes[];
5
8
  }): Api<(args: string | FetchArgs, api: BaseQueryApi, extraOptions: {}) => Promise<QueryReturnValue<unknown, FetchBaseQueryError, FetchBaseQueryMeta>>, {
6
9
  logout: MutationDefinition<null, any, any, null, any, any>;
@@ -1,9 +1,10 @@
1
1
  import { Api, EndpointBuilder } from '@reduxjs/toolkit/query/react';
2
+ import { ActionCreatorWithoutPayload } from '@reduxjs/toolkit';
2
3
  import { MutationDefinition } from '@reduxjs/toolkit/query';
3
4
  export type ExchangeOAuth2CodeArg = {
4
5
  code: string;
5
6
  code_verifier: string;
6
7
  redirect_uri: string;
7
8
  };
8
- export declare function buildLoginEndpoint<ResultType, QueryArg>(build: EndpointBuilder<any, any, any>, url?: string): MutationDefinition<QueryArg, any, any, ResultType, any, any>;
9
- export declare function buildLogoutEndpoint<ResultType, QueryArg>(api: Api<any, any, any, any, any>, build: EndpointBuilder<any, any, any>, url?: string): MutationDefinition<QueryArg, any, any, ResultType, any, any>;
9
+ export declare function buildLoginEndpoint<ResultType, QueryArg>(build: EndpointBuilder<any, any, any>, action: ActionCreatorWithoutPayload, url?: string): MutationDefinition<QueryArg, any, any, ResultType, any, any>;
10
+ export declare function buildLogoutEndpoint<ResultType, QueryArg>(api: Api<any, any, any, any, any>, build: EndpointBuilder<any, any, any>, action: ActionCreatorWithoutPayload, url?: string): MutationDefinition<QueryArg, any, any, ResultType, any, any>;
@@ -1,6 +1,6 @@
1
1
  import { JSX } from 'react';
2
2
  import { NotificationProps } from './Notification';
3
- import { SessionMetadata, UseSessionChildren, UseSessionOptions } from '../../hooks/auth';
3
+ import { SelectIsLoggedIn, SessionMetadata, UseSessionChildren, UseSessionOptions } from '../../hooks/auth';
4
4
  export type PageState = {
5
5
  notifications: Array<{
6
6
  index?: number;
@@ -12,8 +12,9 @@ export type PageState = {
12
12
  };
13
13
  };
14
14
  export interface PageProps<SessionUserType extends SessionMetadata["user_type"] | undefined> {
15
+ selectIsLoggedIn: SelectIsLoggedIn;
15
16
  children: UseSessionChildren<SessionUserType>;
16
17
  session?: UseSessionOptions<SessionUserType>;
17
18
  }
18
- declare const Page: <SessionUserType extends SessionMetadata["user_type"] | undefined = undefined>({ children, session, }: PageProps<SessionUserType>) => JSX.Element;
19
+ declare const Page: <SessionUserType extends SessionMetadata["user_type"] | undefined = undefined>({ selectIsLoggedIn, children, session, }: PageProps<SessionUserType>) => JSX.Element;
19
20
  export default Page;
@@ -3,15 +3,16 @@ import { TypedUseMutation } from '@reduxjs/toolkit/query/react';
3
3
  import { AuthFactor, User } from '../api';
4
4
  import { OAuth2CodeChallenge, OAuth2CodeChallengeLengths, OAuth2RequestCodeUrlSearchParams } from '../utils/auth';
5
5
  import { ExchangeOAuth2CodeArg } from '../api/endpoints/session';
6
+ export type SelectIsLoggedIn = (state: any) => boolean;
6
7
  export interface SessionMetadata {
7
8
  user_id: User["id"];
8
9
  user_type: "teacher" | "student" | "indy";
9
10
  auth_factors: Array<AuthFactor["type"]>;
10
11
  otp_bypass_token_exists: boolean;
11
12
  }
12
- export declare function useSessionMetadata<T = SessionMetadata>(cookieName?: string): T | undefined;
13
+ export declare function useSessionMetadata<T = SessionMetadata>(selectIsLoggedIn: SelectIsLoggedIn): T | undefined;
13
14
  export declare namespace useSessionMetadata {
14
- var predefine: <SessionMetadata>(cookieName?: string) => () => SessionMetadata | undefined;
15
+ var predefine: <SessionMetadata>(selectIsLoggedIn: SelectIsLoggedIn) => () => SessionMetadata | undefined;
15
16
  }
16
17
  export type UseSessionChildrenFunction<Required extends boolean> = (metadata: Required extends true ? SessionMetadata : SessionMetadata | undefined) => ReactNode;
17
18
  export type UseSessionChildren<UserType extends SessionMetadata["user_type"] | undefined> = ReactNode | (UserType extends undefined ? UseSessionChildrenFunction<false> : UseSessionChildrenFunction<true>);
@@ -19,7 +20,7 @@ export type UseSessionOptions<UserType extends SessionMetadata["user_type"] | un
19
20
  userType: UserType;
20
21
  next: boolean;
21
22
  }>;
22
- export declare function useSession<UserType extends SessionMetadata["user_type"] | undefined = undefined>(children: UseSessionChildren<UserType>, options?: UseSessionOptions<UserType>): string | number | bigint | boolean | import("react/jsx-runtime").JSX.Element | Iterable<ReactNode> | Promise<string | number | bigint | boolean | ReactPortal | ReactElement<unknown, string | JSXElementConstructor<any>> | Iterable<ReactNode> | null | undefined> | null | undefined;
23
+ export declare function useSession<UserType extends SessionMetadata["user_type"] | undefined = undefined>(selectIsLoggedIn: SelectIsLoggedIn, children: UseSessionChildren<UserType>, options?: UseSessionOptions<UserType>): string | number | bigint | boolean | import("react/jsx-runtime").JSX.Element | Iterable<ReactNode> | Promise<string | number | bigint | boolean | ReactPortal | ReactElement<unknown, string | JSXElementConstructor<any>> | Iterable<ReactNode> | null | undefined> | null | undefined;
23
24
  export declare function useOAuth2State(provider: string, length?: number, storageKey?: string): [string | undefined, () => void];
24
25
  export declare function useOAuth2CodeChallenge(provider: string, length?: OAuth2CodeChallengeLengths, storageKey?: string): [OAuth2CodeChallenge | undefined, () => void];
25
26
  interface BaseUseOAuth2KwArgs<SessionMetadata> {
@@ -1,2 +1,2 @@
1
1
  export { default as createSlice } from './createSlice';
2
- export { default as sessionSlice, type SessionState } from './session';
2
+ export { default as createSessionSlice, type SessionState } from './session';
@@ -1,9 +1,8 @@
1
- import { Slice, CaseReducer, ActionCreatorWithoutPayload } from '@reduxjs/toolkit';
2
- import { Selector } from 'reselect';
1
+ import { Slice, CaseReducer } from '@reduxjs/toolkit';
3
2
  export interface SessionState {
4
3
  isLoggedIn: boolean;
5
4
  }
6
- declare const sessionSlice: Slice<SessionState, {
5
+ export default function createSessionSlice(sessionMetadataCookieName: string): Slice<SessionState, {
7
6
  login: CaseReducer<SessionState, {
8
7
  payload: void;
9
8
  type: string;
@@ -19,10 +18,3 @@ declare const sessionSlice: Slice<SessionState, {
19
18
  }, "session", "session", {
20
19
  selectIsLoggedIn: (session: SessionState) => boolean;
21
20
  }>;
22
- export default sessionSlice;
23
- export declare const login: ActionCreatorWithoutPayload<"session/login">, logout: ActionCreatorWithoutPayload<"session/logout">;
24
- export declare const selectIsLoggedIn: Selector<{
25
- session: SessionState;
26
- }, boolean, []> & {
27
- unwrapped: (session: SessionState) => boolean;
28
- };
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Set up the settings. This should be called once at the root of the app.
3
+ *
4
+ * @param env The environment variables (passed as `import.meta.env`).
5
+ * @returns An object containing the common settings.
6
+ */
7
+ export declare function setup(env: ImportMetaEnv): {
8
+ SERVICE_NAME: string;
9
+ SERVICE_TITLE: string;
10
+ SERVICE_API_URL: string;
11
+ CSRF_COOKIE_NAME: string;
12
+ SESSION_COOKIE_NAME: string;
13
+ SESSION_METADATA_COOKIE_NAME: string;
14
+ };
15
+ export type GetSettingOptions<T = string> = T extends string ? {
16
+ defaultValue: string;
17
+ } : {
18
+ cast: (value: string) => T;
19
+ defaultValue?: T;
20
+ };
21
+ export declare function getSetting(name: string): string | undefined;
22
+ export declare function getSetting(name: string, options: {
23
+ defaultValue: string;
24
+ }): string;
25
+ export declare function getSetting<T>(name: string, options: {
26
+ cast: (value: string) => T;
27
+ }): T | undefined;
28
+ export declare function getSetting<T>(name: string, options: {
29
+ cast: (value: string) => T;
30
+ defaultValue: T;
31
+ }): T;
32
+ export declare const getServiceName: () => string;
33
+ export declare const getServiceTitle: () => string;
34
+ export declare const getServiceApiUrl: () => string;
35
+ export declare const getCsrfCookieName: () => string;
36
+ export declare const getSessionCookieName: () => string;
37
+ export declare const getSessionMetadataCookieName: () => string;
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const o=require("js-cookie"),n=require("../settings/index.cjs.js"),E=require("./general.cjs.js");function i(){o.remove(n.SESSION_COOKIE_NAME),o.remove(n.SESSION_METADATA_COOKIE_NAME)}function c(){return o.get(n.CSRF_COOKIE_NAME)}function g(t,e){return`oauth2.${t}.${e}`}const u=["S256"],C=[43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128];async function O(t){const e=E.generateSecureRandomString(t),r=new TextEncoder().encode(e),a=await window.crypto.subtle.digest("SHA-256",r);return{verifier:e,challenge:btoa(String.fromCharCode(...new Uint8Array(a))).replace(/\+/g,"-").replace(/\//g,"_").replace(/=+$/,""),method:"S256"}}exports.OAUTH2_CODE_CHALLENGE_LENGTHS=C;exports.OAUTH2_CODE_CHALLENGE_METHODS=u;exports.generateOAuth2CodeChallenge=O;exports.getCsrfCookie=c;exports.logout=i;exports.makeOAuth2StorageKey=g;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const o=require("js-cookie"),n=require("./settings.cjs.js"),i=require("./general.cjs.js");function g(){o.remove(n.getSessionCookieName()),o.remove(n.getSessionMetadataCookieName())}function s(){return o.get(n.getCsrfCookieName())}function u(t,e){return`oauth2.${t}.${e}`}const c=["S256"],C=[43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128];async function l(t){const e=i.generateSecureRandomString(t),r=new TextEncoder().encode(e),a=await window.crypto.subtle.digest("SHA-256",r);return{verifier:e,challenge:btoa(String.fromCharCode(...new Uint8Array(a))).replace(/\+/g,"-").replace(/\//g,"_").replace(/=+$/,""),method:"S256"}}exports.OAUTH2_CODE_CHALLENGE_LENGTHS=C;exports.OAUTH2_CODE_CHALLENGE_METHODS=c;exports.generateOAuth2CodeChallenge=l;exports.getCsrfCookie=s;exports.logout=g;exports.makeOAuth2StorageKey=u;
2
2
  //# sourceMappingURL=auth.cjs.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"auth.cjs.js","sources":["../../src/utils/auth.ts"],"sourcesContent":["import Cookies from \"js-cookie\"\n\nimport {\n CSRF_COOKIE_NAME,\n SESSION_COOKIE_NAME,\n SESSION_METADATA_COOKIE_NAME,\n} from \"../settings\"\nimport { generateSecureRandomString } from \"./general\"\n\nexport function logout() {\n Cookies.remove(SESSION_COOKIE_NAME)\n Cookies.remove(SESSION_METADATA_COOKIE_NAME)\n}\n\n// https://docs.djangoproject.com/en/3.2/ref/csrf/\nexport function getCsrfCookie() {\n return Cookies.get(CSRF_COOKIE_NAME)\n}\n\nexport function makeOAuth2StorageKey(provider: string, key: string) {\n return `oauth2.${provider}.${key}`\n}\n\nexport const OAUTH2_CODE_CHALLENGE_METHODS = [\"S256\"] as const\n\nexport type OAuth2CodeChallengeMethods =\n (typeof OAUTH2_CODE_CHALLENGE_METHODS)[number]\n\nexport const OAUTH2_CODE_CHALLENGE_LENGTHS = [\n 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61,\n 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,\n 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,\n 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,\n 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128,\n] as const\n\nexport type OAuth2CodeChallengeLengths =\n (typeof OAUTH2_CODE_CHALLENGE_LENGTHS)[number]\n\nexport type OAuth2RequestCodeUrlSearchParams = {\n client_id: string\n redirect_uri: string\n scope: string\n response_type: string\n access_type: string\n prompt?: string\n state: string\n code_challenge: string\n code_challenge_method: string\n}\n\nexport type OAuth2ReceiveCodeUrlSearchParams = {\n code: string\n state: string\n}\n\nexport type OAuth2CodeChallenge = {\n verifier: string\n challenge: string\n method: OAuth2CodeChallengeMethods\n}\n\nexport async function generateOAuth2CodeChallenge(\n length: OAuth2CodeChallengeLengths,\n): Promise<OAuth2CodeChallenge> {\n const verifier = generateSecureRandomString(length)\n const data = new TextEncoder().encode(verifier)\n const digest = await window.crypto.subtle.digest(\"SHA-256\", data)\n\n return {\n verifier,\n challenge: btoa(String.fromCharCode(...new Uint8Array(digest)))\n .replace(/\\+/g, \"-\")\n .replace(/\\//g, \"_\")\n .replace(/=+$/, \"\"),\n method: \"S256\",\n }\n}\n"],"names":["logout","Cookies","SESSION_COOKIE_NAME","SESSION_METADATA_COOKIE_NAME","getCsrfCookie","CSRF_COOKIE_NAME","makeOAuth2StorageKey","provider","key","OAUTH2_CODE_CHALLENGE_METHODS","OAUTH2_CODE_CHALLENGE_LENGTHS","generateOAuth2CodeChallenge","length","verifier","generateSecureRandomString","data","digest"],"mappings":"iLASO,SAASA,GAAS,CACvBC,EAAQ,OAAOC,qBAAmB,EAClCD,EAAQ,OAAOE,8BAA4B,CAC7C,CAGO,SAASC,GAAgB,CAC9B,OAAOH,EAAQ,IAAII,kBAAgB,CACrC,CAEO,SAASC,EAAqBC,EAAkBC,EAAa,CAClE,MAAO,UAAUD,CAAQ,IAAIC,CAAG,EAClC,CAEO,MAAMC,EAAgC,CAAC,MAAM,EAKvCC,EAAgC,CAC3C,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IACtE,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,GACnE,EA4BA,eAAsBC,EACpBC,EAC8B,CAC9B,MAAMC,EAAWC,EAAAA,2BAA2BF,CAAM,EAC5CG,EAAO,IAAI,cAAc,OAAOF,CAAQ,EACxCG,EAAS,MAAM,OAAO,OAAO,OAAO,OAAO,UAAWD,CAAI,EAEhE,MAAO,CACL,SAAAF,EACA,UAAW,KAAK,OAAO,aAAa,GAAG,IAAI,WAAWG,CAAM,CAAC,CAAC,EAC3D,QAAQ,MAAO,GAAG,EAClB,QAAQ,MAAO,GAAG,EAClB,QAAQ,MAAO,EAAE,EACpB,OAAQ,MAAA,CAEZ"}
1
+ {"version":3,"file":"auth.cjs.js","sources":["../../src/utils/auth.ts"],"sourcesContent":["import Cookies from \"js-cookie\"\n\nimport {\n getCsrfCookieName,\n getSessionCookieName,\n getSessionMetadataCookieName,\n} from \"../utils/settings\"\nimport { generateSecureRandomString } from \"./general\"\n\nexport function logout() {\n Cookies.remove(getSessionCookieName())\n Cookies.remove(getSessionMetadataCookieName())\n}\n\n// https://docs.djangoproject.com/en/3.2/ref/csrf/\nexport function getCsrfCookie() {\n return Cookies.get(getCsrfCookieName())\n}\n\nexport function makeOAuth2StorageKey(provider: string, key: string) {\n return `oauth2.${provider}.${key}`\n}\n\nexport const OAUTH2_CODE_CHALLENGE_METHODS = [\"S256\"] as const\n\nexport type OAuth2CodeChallengeMethods =\n (typeof OAUTH2_CODE_CHALLENGE_METHODS)[number]\n\nexport const OAUTH2_CODE_CHALLENGE_LENGTHS = [\n 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61,\n 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,\n 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,\n 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,\n 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128,\n] as const\n\nexport type OAuth2CodeChallengeLengths =\n (typeof OAUTH2_CODE_CHALLENGE_LENGTHS)[number]\n\nexport type OAuth2RequestCodeUrlSearchParams = {\n client_id: string\n redirect_uri: string\n scope: string\n response_type: string\n access_type: string\n prompt?: string\n state: string\n code_challenge: string\n code_challenge_method: string\n}\n\nexport type OAuth2ReceiveCodeUrlSearchParams = {\n code: string\n state: string\n}\n\nexport type OAuth2CodeChallenge = {\n verifier: string\n challenge: string\n method: OAuth2CodeChallengeMethods\n}\n\nexport async function generateOAuth2CodeChallenge(\n length: OAuth2CodeChallengeLengths,\n): Promise<OAuth2CodeChallenge> {\n const verifier = generateSecureRandomString(length)\n const data = new TextEncoder().encode(verifier)\n const digest = await window.crypto.subtle.digest(\"SHA-256\", data)\n\n return {\n verifier,\n challenge: btoa(String.fromCharCode(...new Uint8Array(digest)))\n .replace(/\\+/g, \"-\")\n .replace(/\\//g, \"_\")\n .replace(/=+$/, \"\"),\n method: \"S256\",\n }\n}\n"],"names":["logout","Cookies","getSessionCookieName","getSessionMetadataCookieName","getCsrfCookie","getCsrfCookieName","makeOAuth2StorageKey","provider","key","OAUTH2_CODE_CHALLENGE_METHODS","OAUTH2_CODE_CHALLENGE_LENGTHS","generateOAuth2CodeChallenge","length","verifier","generateSecureRandomString","data","digest"],"mappings":"0KASO,SAASA,GAAS,CACvBC,EAAQ,OAAOC,EAAAA,sBAAsB,EACrCD,EAAQ,OAAOE,EAAAA,8BAA8B,CAC/C,CAGO,SAASC,GAAgB,CAC9B,OAAOH,EAAQ,IAAII,EAAAA,mBAAmB,CACxC,CAEO,SAASC,EAAqBC,EAAkBC,EAAa,CAClE,MAAO,UAAUD,CAAQ,IAAIC,CAAG,EAClC,CAEO,MAAMC,EAAgC,CAAC,MAAM,EAKvCC,EAAgC,CAC3C,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GAAI,GACxE,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IACtE,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,IAAK,GACnE,EA4BA,eAAsBC,EACpBC,EAC8B,CAC9B,MAAMC,EAAWC,EAAAA,2BAA2BF,CAAM,EAC5CG,EAAO,IAAI,cAAc,OAAOF,CAAQ,EACxCG,EAAS,MAAM,OAAO,OAAO,OAAO,OAAO,UAAWD,CAAI,EAEhE,MAAO,CACL,SAAAF,EACA,UAAW,KAAK,OAAO,aAAa,GAAG,IAAI,WAAWG,CAAM,CAAC,CAAC,EAC3D,QAAQ,MAAO,GAAG,EAClB,QAAQ,MAAO,GAAG,EAClB,QAAQ,MAAO,EAAE,EACpB,OAAQ,MAAA,CAEZ"}
@@ -1,16 +1,16 @@
1
- import o from "js-cookie";
2
- import { CSRF_COOKIE_NAME as a, SESSION_COOKIE_NAME as c, SESSION_METADATA_COOKIE_NAME as i } from "../settings/index.es.js";
3
- import { generateSecureRandomString as E } from "./general.es.js";
4
- function g() {
5
- o.remove(c), o.remove(i);
1
+ import t from "js-cookie";
2
+ import { getCsrfCookieName as a, getSessionCookieName as i, getSessionMetadataCookieName as c } from "./settings.es.js";
3
+ import { generateSecureRandomString as g } from "./general.es.js";
4
+ function u() {
5
+ t.remove(i()), t.remove(c());
6
6
  }
7
- function A() {
8
- return o.get(a);
7
+ function d() {
8
+ return t.get(a());
9
9
  }
10
- function _(t, e) {
11
- return `oauth2.${t}.${e}`;
10
+ function f(o, e) {
11
+ return `oauth2.${o}.${e}`;
12
12
  }
13
- const u = ["S256"], m = [
13
+ const S = ["S256"], l = [
14
14
  43,
15
15
  44,
16
16
  45,
@@ -98,8 +98,8 @@ const u = ["S256"], m = [
98
98
  127,
99
99
  128
100
100
  ];
101
- async function s(t) {
102
- const e = E(t), r = new TextEncoder().encode(e), n = await window.crypto.subtle.digest("SHA-256", r);
101
+ async function E(o) {
102
+ const e = g(o), r = new TextEncoder().encode(e), n = await window.crypto.subtle.digest("SHA-256", r);
103
103
  return {
104
104
  verifier: e,
105
105
  challenge: btoa(String.fromCharCode(...new Uint8Array(n))).replace(/\+/g, "-").replace(/\//g, "_").replace(/=+$/, ""),
@@ -107,11 +107,11 @@ async function s(t) {
107
107
  };
108
108
  }
109
109
  export {
110
- m as OAUTH2_CODE_CHALLENGE_LENGTHS,
111
- u as OAUTH2_CODE_CHALLENGE_METHODS,
112
- s as generateOAuth2CodeChallenge,
113
- A as getCsrfCookie,
114
- g as logout,
115
- _ as makeOAuth2StorageKey
110
+ l as OAUTH2_CODE_CHALLENGE_LENGTHS,
111
+ S as OAUTH2_CODE_CHALLENGE_METHODS,
112
+ E as generateOAuth2CodeChallenge,
113
+ d as getCsrfCookie,
114
+ u as logout,
115
+ f as makeOAuth2StorageKey
116
116
  };
117
117
  //# sourceMappingURL=auth.es.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"auth.es.js","sources":["../../src/utils/auth.ts"],"sourcesContent":["import Cookies from \"js-cookie\"\n\nimport {\n CSRF_COOKIE_NAME,\n SESSION_COOKIE_NAME,\n SESSION_METADATA_COOKIE_NAME,\n} from \"../settings\"\nimport { generateSecureRandomString } from \"./general\"\n\nexport function logout() {\n Cookies.remove(SESSION_COOKIE_NAME)\n Cookies.remove(SESSION_METADATA_COOKIE_NAME)\n}\n\n// https://docs.djangoproject.com/en/3.2/ref/csrf/\nexport function getCsrfCookie() {\n return Cookies.get(CSRF_COOKIE_NAME)\n}\n\nexport function makeOAuth2StorageKey(provider: string, key: string) {\n return `oauth2.${provider}.${key}`\n}\n\nexport const OAUTH2_CODE_CHALLENGE_METHODS = [\"S256\"] as const\n\nexport type OAuth2CodeChallengeMethods =\n (typeof OAUTH2_CODE_CHALLENGE_METHODS)[number]\n\nexport const OAUTH2_CODE_CHALLENGE_LENGTHS = [\n 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61,\n 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,\n 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,\n 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,\n 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128,\n] as const\n\nexport type OAuth2CodeChallengeLengths =\n (typeof OAUTH2_CODE_CHALLENGE_LENGTHS)[number]\n\nexport type OAuth2RequestCodeUrlSearchParams = {\n client_id: string\n redirect_uri: string\n scope: string\n response_type: string\n access_type: string\n prompt?: string\n state: string\n code_challenge: string\n code_challenge_method: string\n}\n\nexport type OAuth2ReceiveCodeUrlSearchParams = {\n code: string\n state: string\n}\n\nexport type OAuth2CodeChallenge = {\n verifier: string\n challenge: string\n method: OAuth2CodeChallengeMethods\n}\n\nexport async function generateOAuth2CodeChallenge(\n length: OAuth2CodeChallengeLengths,\n): Promise<OAuth2CodeChallenge> {\n const verifier = generateSecureRandomString(length)\n const data = new TextEncoder().encode(verifier)\n const digest = await window.crypto.subtle.digest(\"SHA-256\", data)\n\n return {\n verifier,\n challenge: btoa(String.fromCharCode(...new Uint8Array(digest)))\n .replace(/\\+/g, \"-\")\n .replace(/\\//g, \"_\")\n .replace(/=+$/, \"\"),\n method: \"S256\",\n }\n}\n"],"names":["logout","Cookies","SESSION_COOKIE_NAME","SESSION_METADATA_COOKIE_NAME","getCsrfCookie","CSRF_COOKIE_NAME","makeOAuth2StorageKey","provider","key","OAUTH2_CODE_CHALLENGE_METHODS","OAUTH2_CODE_CHALLENGE_LENGTHS","generateOAuth2CodeChallenge","length","verifier","generateSecureRandomString","data","digest"],"mappings":";;;AASO,SAASA,IAAS;AACvB,EAAAC,EAAQ,OAAOC,CAAmB,GAClCD,EAAQ,OAAOE,CAA4B;AAC7C;AAGO,SAASC,IAAgB;AAC9B,SAAOH,EAAQ,IAAII,CAAgB;AACrC;AAEO,SAASC,EAAqBC,GAAkBC,GAAa;AAClE,SAAO,UAAUD,CAAQ,IAAIC,CAAG;AAClC;AAEO,MAAMC,IAAgC,CAAC,MAAM,GAKvCC,IAAgC;AAAA,EAC3C;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EACtE;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AACnE;AA4BA,eAAsBC,EACpBC,GAC8B;AAC9B,QAAMC,IAAWC,EAA2BF,CAAM,GAC5CG,IAAO,IAAI,cAAc,OAAOF,CAAQ,GACxCG,IAAS,MAAM,OAAO,OAAO,OAAO,OAAO,WAAWD,CAAI;AAEhE,SAAO;AAAA,IACL,UAAAF;AAAA,IACA,WAAW,KAAK,OAAO,aAAa,GAAG,IAAI,WAAWG,CAAM,CAAC,CAAC,EAC3D,QAAQ,OAAO,GAAG,EAClB,QAAQ,OAAO,GAAG,EAClB,QAAQ,OAAO,EAAE;AAAA,IACpB,QAAQ;AAAA,EAAA;AAEZ;"}
1
+ {"version":3,"file":"auth.es.js","sources":["../../src/utils/auth.ts"],"sourcesContent":["import Cookies from \"js-cookie\"\n\nimport {\n getCsrfCookieName,\n getSessionCookieName,\n getSessionMetadataCookieName,\n} from \"../utils/settings\"\nimport { generateSecureRandomString } from \"./general\"\n\nexport function logout() {\n Cookies.remove(getSessionCookieName())\n Cookies.remove(getSessionMetadataCookieName())\n}\n\n// https://docs.djangoproject.com/en/3.2/ref/csrf/\nexport function getCsrfCookie() {\n return Cookies.get(getCsrfCookieName())\n}\n\nexport function makeOAuth2StorageKey(provider: string, key: string) {\n return `oauth2.${provider}.${key}`\n}\n\nexport const OAUTH2_CODE_CHALLENGE_METHODS = [\"S256\"] as const\n\nexport type OAuth2CodeChallengeMethods =\n (typeof OAUTH2_CODE_CHALLENGE_METHODS)[number]\n\nexport const OAUTH2_CODE_CHALLENGE_LENGTHS = [\n 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61,\n 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,\n 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99,\n 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,\n 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128,\n] as const\n\nexport type OAuth2CodeChallengeLengths =\n (typeof OAUTH2_CODE_CHALLENGE_LENGTHS)[number]\n\nexport type OAuth2RequestCodeUrlSearchParams = {\n client_id: string\n redirect_uri: string\n scope: string\n response_type: string\n access_type: string\n prompt?: string\n state: string\n code_challenge: string\n code_challenge_method: string\n}\n\nexport type OAuth2ReceiveCodeUrlSearchParams = {\n code: string\n state: string\n}\n\nexport type OAuth2CodeChallenge = {\n verifier: string\n challenge: string\n method: OAuth2CodeChallengeMethods\n}\n\nexport async function generateOAuth2CodeChallenge(\n length: OAuth2CodeChallengeLengths,\n): Promise<OAuth2CodeChallenge> {\n const verifier = generateSecureRandomString(length)\n const data = new TextEncoder().encode(verifier)\n const digest = await window.crypto.subtle.digest(\"SHA-256\", data)\n\n return {\n verifier,\n challenge: btoa(String.fromCharCode(...new Uint8Array(digest)))\n .replace(/\\+/g, \"-\")\n .replace(/\\//g, \"_\")\n .replace(/=+$/, \"\"),\n method: \"S256\",\n }\n}\n"],"names":["logout","Cookies","getSessionCookieName","getSessionMetadataCookieName","getCsrfCookie","getCsrfCookieName","makeOAuth2StorageKey","provider","key","OAUTH2_CODE_CHALLENGE_METHODS","OAUTH2_CODE_CHALLENGE_LENGTHS","generateOAuth2CodeChallenge","length","verifier","generateSecureRandomString","data","digest"],"mappings":";;;AASO,SAASA,IAAS;AACvB,EAAAC,EAAQ,OAAOC,GAAsB,GACrCD,EAAQ,OAAOE,GAA8B;AAC/C;AAGO,SAASC,IAAgB;AAC9B,SAAOH,EAAQ,IAAII,GAAmB;AACxC;AAEO,SAASC,EAAqBC,GAAkBC,GAAa;AAClE,SAAO,UAAUD,CAAQ,IAAIC,CAAG;AAClC;AAEO,MAAMC,IAAgC,CAAC,MAAM,GAKvCC,IAAgC;AAAA,EAC3C;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EAAI;AAAA,EACxE;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EACtE;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AAAA,EAAK;AACnE;AA4BA,eAAsBC,EACpBC,GAC8B;AAC9B,QAAMC,IAAWC,EAA2BF,CAAM,GAC5CG,IAAO,IAAI,cAAc,OAAOF,CAAQ,GACxCG,IAAS,MAAM,OAAO,OAAO,OAAO,OAAO,WAAWD,CAAI;AAEhE,SAAO;AAAA,IACL,UAAAF;AAAA,IACA,WAAW,KAAK,OAAO,aAAa,GAAG,IAAI,WAAWG,CAAM,CAAC,CAAC,EAC3D,QAAQ,OAAO,GAAG,EAClB,QAAQ,OAAO,GAAG,EAClB,QAAQ,OAAO,EAAE;AAAA,IACpB,QAAQ;AAAA,EAAA;AAEZ;"}
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const l=require("react-router");require("react/jsx-runtime");require("react");require("@mui/icons-material");require("@mui/material");require("../palette-BnIdHKDE.cjs");require("../auth-C2OUeLmQ.cjs");function q(e,o={}){function c(r,g,t){typeof r.__=="object"&&(t=t?{...t,...r.__}:r.__);const _=typeof e=="string"&&t?l.generatePath(e,t):e;Object.entries(r).forEach(([u,i])=>{if(u!=="__")if(i=i,typeof i=="string"){if(typeof _=="string"&&(!g||u!=="_")){let n=_+i;n.endsWith("/")&&(n=n.slice(0,-1)),r[u]=n}}else c(i,!1,t)})}const f={...o,_:typeof e=="string"?e:"",__:e};return e===""?f._="/":c(f,!0),f}function s(e,o){return e.__[o]}exports.getParam=s;exports.path=q;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const l=require("react-router");require("react/jsx-runtime");require("react");require("@mui/icons-material");require("@mui/material");require("../palette-BnIdHKDE.cjs");require("../auth-uyv8Mv88.cjs");function q(e,o={}){function c(r,g,t){typeof r.__=="object"&&(t=t?{...t,...r.__}:r.__);const _=typeof e=="string"&&t?l.generatePath(e,t):e;Object.entries(r).forEach(([u,i])=>{if(u!=="__")if(i=i,typeof i=="string"){if(typeof _=="string"&&(!g||u!=="_")){let n=_+i;n.endsWith("/")&&(n=n.slice(0,-1)),r[u]=n}}else c(i,!1,t)})}const f={...o,_:typeof e=="string"?e:"",__:e};return e===""?f._="/":c(f,!0),f}function s(e,o){return e.__[o]}exports.getParam=s;exports.path=q;
2
2
  //# sourceMappingURL=router.cjs.js.map
@@ -4,7 +4,7 @@ import "react";
4
4
  import "@mui/icons-material";
5
5
  import "@mui/material";
6
6
  import "../palette-CYwuLBW7.js";
7
- import "../auth-B6anBtxF.js";
7
+ import "../auth-D-8t6wfR.js";
8
8
  function x(t, n = {}) {
9
9
  function c(i, l, e) {
10
10
  typeof i.__ == "object" && (e = e ? { ...e, ...i.__ } : i.__);
@@ -0,0 +1,2 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});let S={},i=!1;function _(a){return S=a,i=!0,{SERVICE_NAME:t(),SERVICE_TITLE:s(),SERVICE_API_URL:l(),CSRF_COOKIE_NAME:n(),SESSION_COOKIE_NAME:r(),SESSION_METADATA_COOKIE_NAME:u()}}function e(a,E={}){if(!i)throw new Error("Settings have not been set up. Please call setup(import.meta.env) before calling getSetting.");const o=S[`VITE_${a}`];return o===void 0?E?.defaultValue:"cast"in E?E.cast(o):o}const t=()=>e("SERVICE_NAME",{defaultValue:"REPLACE_ME"}),s=()=>e("SERVICE_TITLE",{defaultValue:`Code for Life | ${t()}`}),l=()=>e("SERVICE_API_URL",{defaultValue:"http://localhost:8000"}),n=()=>e("CSRF_COOKIE_NAME",{defaultValue:`${t()}_csrftoken`}),r=()=>e("SESSION_COOKIE_NAME",{defaultValue:"session_key"}),u=()=>e("SESSION_METADATA_COOKIE_NAME",{defaultValue:"session_metadata"});exports.getCsrfCookieName=n;exports.getServiceApiUrl=l;exports.getServiceName=t;exports.getServiceTitle=s;exports.getSessionCookieName=r;exports.getSessionMetadataCookieName=u;exports.getSetting=e;exports.setup=_;
2
+ //# sourceMappingURL=settings.cjs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"settings.cjs.js","sources":["../../src/utils/settings.ts"],"sourcesContent":["let ENV: ImportMetaEnv = {} as ImportMetaEnv\nlet SETUP = false\n\n/**\n * Set up the settings. This should be called once at the root of the app.\n *\n * @param env The environment variables (passed as `import.meta.env`).\n * @returns An object containing the common settings.\n */\nexport function setup(env: ImportMetaEnv) {\n ENV = env\n SETUP = true\n\n return {\n SERVICE_NAME: getServiceName(),\n SERVICE_TITLE: getServiceTitle(),\n SERVICE_API_URL: getServiceApiUrl(),\n CSRF_COOKIE_NAME: getCsrfCookieName(),\n SESSION_COOKIE_NAME: getSessionCookieName(),\n SESSION_METADATA_COOKIE_NAME: getSessionMetadataCookieName(),\n }\n}\n\nexport type GetSettingOptions<T = string> = T extends string\n ? { defaultValue: string }\n : { cast: (value: string) => T; defaultValue?: T }\n\nexport function getSetting(name: string): string | undefined\n\nexport function getSetting(\n name: string,\n options: { defaultValue: string },\n): string\n\nexport function getSetting<T>(\n name: string,\n options: { cast: (value: string) => T },\n): T | undefined\n\nexport function getSetting<T>(\n name: string,\n options: { cast: (value: string) => T; defaultValue: T },\n): T\n\nexport function getSetting<T = string>(\n name: string,\n options: GetSettingOptions<T> = {} as GetSettingOptions<T>,\n): string | T | undefined {\n if (!SETUP) {\n throw new Error(\n \"Settings have not been set up. Please call \" +\n \"setup(import.meta.env) before calling getSetting.\",\n )\n }\n\n // Shorthand to access environment variables.\n const value = ENV[`VITE_${name}`] as string | undefined\n if (value === undefined) return options?.defaultValue\n return \"cast\" in options ? options.cast(value) : value\n}\n\n// The name of the current service.\nexport const getServiceName = () =>\n getSetting(\"SERVICE_NAME\", { defaultValue: \"REPLACE_ME\" })\n\n// The title of the current service. Used in the <title/> within the <head/>.\nexport const getServiceTitle = () =>\n getSetting(\"SERVICE_TITLE\", {\n defaultValue: `Code for Life | ${getServiceName()}`,\n })\n\n// The api url of the current service.\nexport const getServiceApiUrl = () =>\n getSetting(\"SERVICE_API_URL\", { defaultValue: \"http://localhost:8000\" })\n\n// The names of cookies.\nexport const getCsrfCookieName = () =>\n getSetting(\"CSRF_COOKIE_NAME\", {\n defaultValue: `${getServiceName()}_csrftoken`,\n })\nexport const getSessionCookieName = () =>\n getSetting(\"SESSION_COOKIE_NAME\", { defaultValue: \"session_key\" })\nexport const getSessionMetadataCookieName = () =>\n getSetting(\"SESSION_METADATA_COOKIE_NAME\", {\n defaultValue: \"session_metadata\",\n })\n"],"names":["ENV","SETUP","setup","env","getServiceName","getServiceTitle","getServiceApiUrl","getCsrfCookieName","getSessionCookieName","getSessionMetadataCookieName","getSetting","name","options","value"],"mappings":"gFAAA,IAAIA,EAAqB,CAAA,EACrBC,EAAQ,GAQL,SAASC,EAAMC,EAAoB,CACxC,OAAAH,EAAMG,EACNF,EAAQ,GAED,CACL,aAAcG,EAAA,EACd,cAAeC,EAAA,EACf,gBAAiBC,EAAA,EACjB,iBAAkBC,EAAA,EAClB,oBAAqBC,EAAA,EACrB,6BAA8BC,EAAA,CAA6B,CAE/D,CAuBO,SAASC,EACdC,EACAC,EAAgC,GACR,CACxB,GAAI,CAACX,EACH,MAAM,IAAI,MACR,8FAAA,EAMJ,MAAMY,EAAQb,EAAI,QAAQW,CAAI,EAAE,EAChC,OAAIE,IAAU,OAAkBD,GAAS,aAClC,SAAUA,EAAUA,EAAQ,KAAKC,CAAK,EAAIA,CACnD,CAGO,MAAMT,EAAiB,IAC5BM,EAAW,eAAgB,CAAE,aAAc,aAAc,EAG9CL,EAAkB,IAC7BK,EAAW,gBAAiB,CAC1B,aAAc,mBAAmBN,GAAgB,EACnD,CAAC,EAGUE,EAAmB,IAC9BI,EAAW,kBAAmB,CAAE,aAAc,wBAAyB,EAG5DH,EAAoB,IAC/BG,EAAW,mBAAoB,CAC7B,aAAc,GAAGN,EAAA,CAAgB,YACnC,CAAC,EACUI,EAAuB,IAClCE,EAAW,sBAAuB,CAAE,aAAc,cAAe,EACtDD,EAA+B,IAC1CC,EAAW,+BAAgC,CACzC,aAAc,kBAChB,CAAC"}
@@ -0,0 +1,2 @@
1
+ export * from '../src/utils/settings'
2
+ export {}
@@ -0,0 +1,37 @@
1
+ let l = {}, o = !1;
2
+ function r(t) {
3
+ return l = t, o = !0, {
4
+ SERVICE_NAME: S(),
5
+ SERVICE_TITLE: _(),
6
+ SERVICE_API_URL: n(),
7
+ CSRF_COOKIE_NAME: s(),
8
+ SESSION_COOKIE_NAME: u(),
9
+ SESSION_METADATA_COOKIE_NAME: i()
10
+ };
11
+ }
12
+ function e(t, E = {}) {
13
+ if (!o)
14
+ throw new Error(
15
+ "Settings have not been set up. Please call setup(import.meta.env) before calling getSetting."
16
+ );
17
+ const a = l[`VITE_${t}`];
18
+ return a === void 0 ? E?.defaultValue : "cast" in E ? E.cast(a) : a;
19
+ }
20
+ const S = () => e("SERVICE_NAME", { defaultValue: "REPLACE_ME" }), _ = () => e("SERVICE_TITLE", {
21
+ defaultValue: `Code for Life | ${S()}`
22
+ }), n = () => e("SERVICE_API_URL", { defaultValue: "http://localhost:8000" }), s = () => e("CSRF_COOKIE_NAME", {
23
+ defaultValue: `${S()}_csrftoken`
24
+ }), u = () => e("SESSION_COOKIE_NAME", { defaultValue: "session_key" }), i = () => e("SESSION_METADATA_COOKIE_NAME", {
25
+ defaultValue: "session_metadata"
26
+ });
27
+ export {
28
+ s as getCsrfCookieName,
29
+ n as getServiceApiUrl,
30
+ S as getServiceName,
31
+ _ as getServiceTitle,
32
+ u as getSessionCookieName,
33
+ i as getSessionMetadataCookieName,
34
+ e as getSetting,
35
+ r as setup
36
+ };
37
+ //# sourceMappingURL=settings.es.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"settings.es.js","sources":["../../src/utils/settings.ts"],"sourcesContent":["let ENV: ImportMetaEnv = {} as ImportMetaEnv\nlet SETUP = false\n\n/**\n * Set up the settings. This should be called once at the root of the app.\n *\n * @param env The environment variables (passed as `import.meta.env`).\n * @returns An object containing the common settings.\n */\nexport function setup(env: ImportMetaEnv) {\n ENV = env\n SETUP = true\n\n return {\n SERVICE_NAME: getServiceName(),\n SERVICE_TITLE: getServiceTitle(),\n SERVICE_API_URL: getServiceApiUrl(),\n CSRF_COOKIE_NAME: getCsrfCookieName(),\n SESSION_COOKIE_NAME: getSessionCookieName(),\n SESSION_METADATA_COOKIE_NAME: getSessionMetadataCookieName(),\n }\n}\n\nexport type GetSettingOptions<T = string> = T extends string\n ? { defaultValue: string }\n : { cast: (value: string) => T; defaultValue?: T }\n\nexport function getSetting(name: string): string | undefined\n\nexport function getSetting(\n name: string,\n options: { defaultValue: string },\n): string\n\nexport function getSetting<T>(\n name: string,\n options: { cast: (value: string) => T },\n): T | undefined\n\nexport function getSetting<T>(\n name: string,\n options: { cast: (value: string) => T; defaultValue: T },\n): T\n\nexport function getSetting<T = string>(\n name: string,\n options: GetSettingOptions<T> = {} as GetSettingOptions<T>,\n): string | T | undefined {\n if (!SETUP) {\n throw new Error(\n \"Settings have not been set up. Please call \" +\n \"setup(import.meta.env) before calling getSetting.\",\n )\n }\n\n // Shorthand to access environment variables.\n const value = ENV[`VITE_${name}`] as string | undefined\n if (value === undefined) return options?.defaultValue\n return \"cast\" in options ? options.cast(value) : value\n}\n\n// The name of the current service.\nexport const getServiceName = () =>\n getSetting(\"SERVICE_NAME\", { defaultValue: \"REPLACE_ME\" })\n\n// The title of the current service. Used in the <title/> within the <head/>.\nexport const getServiceTitle = () =>\n getSetting(\"SERVICE_TITLE\", {\n defaultValue: `Code for Life | ${getServiceName()}`,\n })\n\n// The api url of the current service.\nexport const getServiceApiUrl = () =>\n getSetting(\"SERVICE_API_URL\", { defaultValue: \"http://localhost:8000\" })\n\n// The names of cookies.\nexport const getCsrfCookieName = () =>\n getSetting(\"CSRF_COOKIE_NAME\", {\n defaultValue: `${getServiceName()}_csrftoken`,\n })\nexport const getSessionCookieName = () =>\n getSetting(\"SESSION_COOKIE_NAME\", { defaultValue: \"session_key\" })\nexport const getSessionMetadataCookieName = () =>\n getSetting(\"SESSION_METADATA_COOKIE_NAME\", {\n defaultValue: \"session_metadata\",\n })\n"],"names":["ENV","SETUP","setup","env","getServiceName","getServiceTitle","getServiceApiUrl","getCsrfCookieName","getSessionCookieName","getSessionMetadataCookieName","getSetting","name","options","value"],"mappings":"AAAA,IAAIA,IAAqB,CAAA,GACrBC,IAAQ;AAQL,SAASC,EAAMC,GAAoB;AACxC,SAAAH,IAAMG,GACNF,IAAQ,IAED;AAAA,IACL,cAAcG,EAAA;AAAA,IACd,eAAeC,EAAA;AAAA,IACf,iBAAiBC,EAAA;AAAA,IACjB,kBAAkBC,EAAA;AAAA,IAClB,qBAAqBC,EAAA;AAAA,IACrB,8BAA8BC,EAAA;AAAA,EAA6B;AAE/D;AAuBO,SAASC,EACdC,GACAC,IAAgC,IACR;AACxB,MAAI,CAACX;AACH,UAAM,IAAI;AAAA,MACR;AAAA,IAAA;AAMJ,QAAMY,IAAQb,EAAI,QAAQW,CAAI,EAAE;AAChC,SAAIE,MAAU,SAAkBD,GAAS,eAClC,UAAUA,IAAUA,EAAQ,KAAKC,CAAK,IAAIA;AACnD;AAGO,MAAMT,IAAiB,MAC5BM,EAAW,gBAAgB,EAAE,cAAc,cAAc,GAG9CL,IAAkB,MAC7BK,EAAW,iBAAiB;AAAA,EAC1B,cAAc,mBAAmBN,GAAgB;AACnD,CAAC,GAGUE,IAAmB,MAC9BI,EAAW,mBAAmB,EAAE,cAAc,yBAAyB,GAG5DH,IAAoB,MAC/BG,EAAW,oBAAoB;AAAA,EAC7B,cAAc,GAAGN,EAAA,CAAgB;AACnC,CAAC,GACUI,IAAuB,MAClCE,EAAW,uBAAuB,EAAE,cAAc,eAAe,GACtDD,IAA+B,MAC1CC,EAAW,gCAAgC;AAAA,EACzC,cAAc;AAChB,CAAC;"}
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "name": "codeforlife",
3
3
  "description": "Common frontend code",
4
4
  "private": false,
5
- "version": "2.12.7",
5
+ "version": "2.14.4",
6
6
  "type": "module",
7
7
  "types": "dist/index.d.ts",
8
8
  "module": "dist/index.es.js",
@@ -83,11 +83,6 @@
83
83
  "import": "./dist/server/entry.es.js",
84
84
  "require": "./dist/server/entry.cjs.js"
85
85
  },
86
- "./settings": {
87
- "types": "./dist/settings/index.d.ts",
88
- "import": "./dist/settings/index.es.js",
89
- "require": "./dist/settings/index.cjs.js"
90
- },
91
86
  "./slices": {
92
87
  "types": "./dist/slices/index.d.ts",
93
88
  "import": "./dist/slices/index.es.js",
@@ -133,6 +128,11 @@
133
128
  "import": "./dist/utils/schema.es.js",
134
129
  "require": "./dist/utils/schema.cjs.js"
135
130
  },
131
+ "./utils/settings": {
132
+ "types": "./dist/utils/settings.d.ts",
133
+ "import": "./dist/utils/settings.es.js",
134
+ "require": "./dist/utils/settings.cjs.js"
135
+ },
136
136
  "./utils/store": {
137
137
  "types": "./dist/utils/store.d.ts",
138
138
  "import": "./dist/utils/store.es.js",
@@ -179,7 +179,7 @@
179
179
  ],
180
180
  "dependencies": {
181
181
  "@emotion/cache": "11.14.0",
182
- "@emotion/react": "11.12.0",
182
+ "@emotion/react": "11.14.0",
183
183
  "@emotion/server": "11.11.0",
184
184
  "@emotion/styled": "11.14.1",
185
185
  "@mui/icons-material": "7.3.2",
@@ -188,15 +188,15 @@
188
188
  "@reduxjs/toolkit": "2.9.0",
189
189
  "compression": "1.8.1",
190
190
  "dayjs": "1.11.19",
191
- "express": "4.22.0",
191
+ "express": "4.22.1",
192
192
  "formik": "2.4.9",
193
193
  "js-cookie": "3.0.5",
194
194
  "memory-cache": "0.2.0",
195
- "qs": "6.14.1",
195
+ "qs": "6.14.2",
196
196
  "react": "19.1.1",
197
197
  "react-dom": "19.1.1",
198
198
  "react-redux": "9.2.0",
199
- "react-router": "7.9.1",
199
+ "react-router": "7.12.0",
200
200
  "sirv": "3.0.2",
201
201
  "yup": "1.7.1"
202
202
  },