insite-users-server 2.0.99 → 2.0.101

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 (41) hide show
  1. package/dist/abilities/Error.d.ts +6 -0
  2. package/dist/abilities/Error.d.ts.map +1 -0
  3. package/dist/abilities/Map.d.ts +28 -11
  4. package/dist/abilities/Map.d.ts.map +1 -1
  5. package/dist/abilities/index.d.ts +1 -0
  6. package/dist/abilities/index.d.ts.map +1 -1
  7. package/dist/abilities/types.d.ts +13 -1
  8. package/dist/abilities/types.d.ts.map +1 -1
  9. package/dist/index.d.ts +4 -2
  10. package/dist/index.d.ts.map +1 -1
  11. package/dist/index.js +3 -3
  12. package/dist/index.js.map +4 -4
  13. package/dist/orgs/Org.d.ts +1 -1
  14. package/dist/orgs/Org.d.ts.map +1 -1
  15. package/dist/orgs/Orgs.d.ts +14 -13
  16. package/dist/orgs/Orgs.d.ts.map +1 -1
  17. package/dist/roles/Error.d.ts +7 -0
  18. package/dist/roles/Error.d.ts.map +1 -0
  19. package/dist/roles/Role.d.ts +1 -1
  20. package/dist/roles/Role.d.ts.map +1 -1
  21. package/dist/roles/Roles.d.ts +13 -9
  22. package/dist/roles/Roles.d.ts.map +1 -1
  23. package/dist/roles/index.d.ts +1 -0
  24. package/dist/roles/index.d.ts.map +1 -1
  25. package/dist/sessions/Session.d.ts +1 -1
  26. package/dist/sessions/Session.d.ts.map +1 -1
  27. package/dist/sessions/Sessions.d.ts +6 -5
  28. package/dist/sessions/Sessions.d.ts.map +1 -1
  29. package/dist/users/Error.d.ts +9 -0
  30. package/dist/users/Error.d.ts.map +1 -0
  31. package/dist/users/User.d.ts +1 -1
  32. package/dist/users/User.d.ts.map +1 -1
  33. package/dist/users/Users.d.ts +21 -18
  34. package/dist/users/Users.d.ts.map +1 -1
  35. package/dist/users/avatars/Avatars.d.ts +8 -3
  36. package/dist/users/avatars/Avatars.d.ts.map +1 -1
  37. package/dist/users/avatars/index.d.ts +1 -1
  38. package/dist/users/avatars/index.d.ts.map +1 -1
  39. package/dist/users/index.d.ts +1 -0
  40. package/dist/users/index.d.ts.map +1 -1
  41. package/package.json +12 -9
@@ -0,0 +1,6 @@
1
+ import { Err } from "@nesvet/n";
2
+ export declare class AbilityError extends Err {
3
+ constructor(longId?: string);
4
+ name: string;
5
+ }
6
+ //# sourceMappingURL=Error.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Error.d.ts","sourceRoot":"","sources":["../../src/abilities/Error.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAGhC,qBAAa,YAAa,SAAQ,GAAG;gBACxB,MAAM,CAAC,EAAE,MAAM;IAK3B,IAAI,SAAkB;CAEtB"}
@@ -1,14 +1,31 @@
1
- import type { AbilitiesSchema, AbilitySchema } from "insite-common";
2
- import type { User } from "../users/User";
3
- import type { AbilityWithParams, GenericAbilities } from "./types";
4
- export declare class AbilitiesMap<AS extends AbilitiesSchema = AbilitiesSchema> extends Map<string, AbilitySchema> {
1
+ import type { Abilities, AbilitiesSchema, AbilityParamSchema } from "insite-common";
2
+ import { type Ability, type AbilityParam, type AbilityParamItems, type AbilitySchema, type GenericAbilities } from "./types";
3
+ export declare class AbilitiesMap<AS extends AbilitiesSchema> extends Map<string, AbilitySchema> {
5
4
  #private;
6
- constructor(schema: AbilitiesSchema);
7
- schema: AbilitiesSchema;
8
- merge(target: GenericAbilities, source: GenericAbilities): GenericAbilities;
9
- getMinimumOf(_id: string): true | AbilityWithParams;
10
- getMaximum(): GenericAbilities;
11
- getSchemeFor(user: User<AS>): AbilitySchema[];
12
- adjust(abilities: GenericAbilities): boolean;
5
+ constructor(abilitiesSchema: AS);
6
+ get(longId: string, parent?: AbilitySchema | null): AbilitySchema | undefined;
7
+ getSchema: (longId: string, parent?: AbilitySchema | null) => AbilitySchema | undefined;
8
+ getParamSchema(longId: string, paramId: string): AbilityParamSchema | undefined;
9
+ getDefaultParam(longId: string, paramId: string, max?: boolean): AbilityParam | undefined;
10
+ getDefaultParam(schema: AbilityParamSchema, max?: boolean): AbilityParam;
11
+ getDefaultAbility(schema: string, max?: boolean): Ability | undefined;
12
+ getDefaultAbility(schema: AbilitySchema, max?: boolean): Ability;
13
+ getDefaultAbilities(): Abilities<AS>;
14
+ getDefaultAbilities(schemas: AbilitySchema[], max?: boolean): Abilities<AS>;
15
+ getDefaultAbilities(schema: AbilitySchema, max?: boolean): Abilities<AS>;
16
+ getDefaultAbilities(longIds: string[], max?: boolean): Abilities<AS>;
17
+ getDefaultAbilities(longId: string, max?: boolean): Abilities<AS>;
18
+ getSchemeFor(abilities: GenericAbilities): AbilitySchema[];
19
+ getParam(abilities: GenericAbilities, longId: string, paramId: string): AbilityParam | undefined;
20
+ setParam(abilities: GenericAbilities, longId: string, paramId: string, value: AbilityParam): Abilities<AS>;
21
+ isParamFits(longId: string, paramId: string, value: AbilityParam, referenceValue?: AbilityParam): boolean;
22
+ adjustParam(paramSchema: AbilityParamSchema, value: AbilityParam): number | AbilityParamItems;
23
+ adjust(abilities: GenericAbilities, parent?: AbilitySchema | null): Abilities<AS>;
24
+ merge(target: GenericAbilities, source: GenericAbilities, parent?: AbilitySchema | null): Abilities<AS>;
25
+ hasAbility(abilities: GenericAbilities, longId: string): boolean;
26
+ setAbility(target: GenericAbilities, schema: AbilitySchema): Abilities<AS>;
27
+ setAbility(target: GenericAbilities, longId: string): Abilities<AS>;
28
+ unsetAbility(target: GenericAbilities, schema: AbilitySchema): Abilities<AS>;
29
+ unsetAbility(target: GenericAbilities, longId: string): Abilities<AS>;
13
30
  }
14
31
  //# sourceMappingURL=Map.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"Map.d.ts","sourceRoot":"","sources":["../../src/abilities/Map.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAA0B,aAAa,EAAE,MAAM,eAAe,CAAC;AAC5F,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAC1C,OAAO,KAAK,EAKX,iBAAiB,EACjB,gBAAgB,EAChB,MAAM,SAAS,CAAC;AAgBjB,qBAAa,YAAY,CAAC,EAAE,SAAS,eAAe,GAAG,eAAe,CAAE,SAAQ,GAAG,CAAC,MAAM,EAAE,aAAa,CAAC;;gBAC7F,MAAM,EAAE,eAAe;IASnC,MAAM,kBAAC;IAWP,KAAK,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,gBAAgB;IAgCxD,YAAY,CAAC,GAAG,EAAE,MAAM;IAgBxB,UAAU;IAkBV,YAAY,CAAC,IAAI,EAAE,IAAI,CAAC,EAAE,CAAC;IA2B3B,MAAM,CAAC,SAAS,EAAE,gBAAgB;CAkElC"}
1
+ {"version":3,"file":"Map.d.ts","sourceRoot":"","sources":["../../src/abilities/Map.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,SAAS,EAAE,eAAe,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AACpF,OAAO,EAIN,KAAK,OAAO,EAEZ,KAAK,YAAY,EACjB,KAAK,iBAAiB,EAEtB,KAAK,aAAa,EAClB,KAAK,gBAAgB,EACrB,MAAM,SAAS,CAAC;AAMjB,qBAAa,YAAY,CAAC,EAAE,SAAS,eAAe,CAAE,SAAQ,GAAG,CAAC,MAAM,EAAE,aAAa,CAAC;;gBAC3E,eAAe,EAAE,EAAE;IAmC/B,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,aAAa,GAAG,IAAI;IAcjD,SAAS,WAdG,MAAM,WAAW,aAAa,GAAG,IAAI,+BAc5B;IAErB,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM;IAI9C,eAAe,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,YAAY,GAAG,SAAS;IACzF,eAAe,CAAC,MAAM,EAAE,kBAAkB,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,YAAY;IAuBxE,iBAAiB,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,OAAO,GAAG,SAAS;IACrE,iBAAiB,CAAC,MAAM,EAAE,aAAa,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,OAAO;IA2BhE,mBAAmB,IAAI,SAAS,CAAC,EAAE,CAAC;IACpC,mBAAmB,CAAC,OAAO,EAAE,aAAa,EAAE,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC,EAAE,CAAC;IAC3E,mBAAmB,CAAC,MAAM,EAAE,aAAa,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC,EAAE,CAAC;IACxE,mBAAmB,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC,EAAE,CAAC;IACpE,mBAAmB,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC,EAAE,CAAC;IAmDjE,YAAY,CAAC,SAAS,EAAE,gBAAgB;IAqCxC,QAAQ,CAAC,SAAS,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM;IAarE,QAAQ,CAAC,SAAS,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,YAAY,GAAG,SAAS,CAAC,EAAE,CAAC;IAW1G,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,YAAY,EAAE,cAAc,CAAC,EAAE,YAAY;IA+B/F,WAAW,CAAC,WAAW,EAAE,kBAAkB,EAAE,KAAK,EAAE,YAAY;IAyBhE,MAAM,CAAC,SAAS,EAAE,gBAAgB,EAAE,MAAM,CAAC,EAAE,aAAa,GAAG,IAAI,GAAG,SAAS,CAAC,EAAE,CAAC;IAwCjF,KAAK,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,CAAC,EAAE,aAAa,GAAG,IAAI,GAAG,SAAS,CAAC,EAAE,CAAC;IA0CvG,UAAU,CAAC,SAAS,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM;IAItD,UAAU,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,aAAa,GAAG,SAAS,CAAC,EAAE,CAAC;IAC1E,UAAU,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,EAAE,CAAC;IAYnE,YAAY,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,aAAa,GAAG,SAAS,CAAC,EAAE,CAAC;IAC5E,YAAY,CAAC,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,EAAE,CAAC;CAmBrE"}
@@ -1,3 +1,4 @@
1
+ export * from "./Error";
1
2
  export * from "./Map";
2
3
  export { AbilityBoolean, AbilityParam, AbilityParamItems, AbilityParamNumber, AbilityWithParams, GenericAbilities } from "./types";
3
4
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/abilities/index.ts"],"names":[],"mappings":"AAAA,cAAc,OAAO,CAAC;AACtB,OAAO,EAAE,cAAc,EAAE,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/abilities/index.ts"],"names":[],"mappings":"AAAA,cAAc,SAAS,CAAC;AACxB,cAAc,OAAO,CAAC;AACtB,OAAO,EAAE,cAAc,EAAE,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC"}
@@ -1,10 +1,22 @@
1
+ import type { AbilitySchema as OriginalAbilitySchema } from "insite-common";
1
2
  type AbilityParamItem = string;
2
3
  export type AbilityParamItems = AbilityParamItem[];
3
4
  export type AbilityParamNumber = number;
4
5
  export type AbilityParam = AbilityParamItems | AbilityParamNumber;
5
6
  export type AbilityWithParams = Record<string, AbilityParam>;
7
+ export type AbilityObject = Record<string, Ability | AbilityParam>;
6
8
  export type AbilityBoolean = true;
7
- export type Ability = AbilityBoolean | AbilityWithParams;
9
+ export type Ability = AbilityBoolean | {
10
+ [key: string]: Ability | AbilityParam;
11
+ };
12
+ export type AbilitySchema = Omit<OriginalAbilitySchema, "abilities"> & {
13
+ level: number;
14
+ longId: string;
15
+ abilities?: AbilitySchema[];
16
+ };
8
17
  export type GenericAbilities = Record<string, Ability>;
18
+ export declare function isAbilityObject(value: Ability): value is AbilityObject;
19
+ export declare function isAbilityParamNumber(value: AbilityParam): value is AbilityParamNumber;
20
+ export declare function isAbilityParamItems(value: AbilityParam): value is AbilityParamItems;
9
21
  export {};
10
22
  //# sourceMappingURL=types.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/abilities/types.ts"],"names":[],"mappings":"AAAA,KAAK,gBAAgB,GAAG,MAAM,CAAC;AAC/B,MAAM,MAAM,iBAAiB,GAAG,gBAAgB,EAAE,CAAC;AACnD,MAAM,MAAM,kBAAkB,GAAG,MAAM,CAAC;AACxC,MAAM,MAAM,YAAY,GAAG,iBAAiB,GAAG,kBAAkB,CAAC;AAElE,MAAM,MAAM,iBAAiB,GAAG,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;AAC7D,MAAM,MAAM,cAAc,GAAG,IAAI,CAAC;AAClC,MAAM,MAAM,OAAO,GAAG,cAAc,GAAG,iBAAiB,CAAC;AACzD,MAAM,MAAM,gBAAgB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/abilities/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,IAAI,qBAAqB,EAAE,MAAM,eAAe,CAAC;AAG5E,KAAK,gBAAgB,GAAG,MAAM,CAAC;AAC/B,MAAM,MAAM,iBAAiB,GAAG,gBAAgB,EAAE,CAAC;AACnD,MAAM,MAAM,kBAAkB,GAAG,MAAM,CAAC;AACxC,MAAM,MAAM,YAAY,GAAG,iBAAiB,GAAG,kBAAkB,CAAC;AAElE,MAAM,MAAM,iBAAiB,GAAG,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;AAC7D,MAAM,MAAM,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,GAAG,YAAY,CAAC,CAAC;AACnE,MAAM,MAAM,cAAc,GAAG,IAAI,CAAC;AAClC,MAAM,MAAM,OAAO,GAAG,cAAc,GAAG;IAAE,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,GAAG,YAAY,CAAA;CAAE,CAAC;AAEjF,MAAM,MAAM,aAAa,GAAG,IAAI,CAAC,qBAAqB,EAAE,WAAW,CAAC,GAAG;IACtE,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,aAAa,EAAE,CAAC;CAC5B,CAAC;AAEF,MAAM,MAAM,gBAAgB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAEvD,wBAAgB,eAAe,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,aAAa,CAEtE;AAED,wBAAgB,oBAAoB,CAAC,KAAK,EAAE,YAAY,GAAG,KAAK,IAAI,kBAAkB,CAErF;AAED,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,YAAY,GAAG,KAAK,IAAI,iBAAiB,CAEnF"}
package/dist/index.d.ts CHANGED
@@ -1,7 +1,9 @@
1
1
  export type { AbilitiesMap, AbilityBoolean, AbilityParam, AbilityParamItems, AbilityParamNumber, AbilityWithParams, GenericAbilities } from "./abilities";
2
+ export { AbilityError } from "./abilities";
2
3
  export type { Org, OrgDoc, Orgs } from "./orgs";
3
4
  export type { Role, RoleDoc, Roles } from "./roles";
5
+ export { RolesError } from "./roles";
4
6
  export type { Session, SessionDoc, Sessions } from "./sessions";
5
- export { type AvatarDoc, Users } from "./users";
6
- export type { Options, User, UserDoc } from "./users";
7
+ export { SubordinationError, Users } from "./users";
8
+ export type { AvatarDoc, Options, User, UserDoc } from "./users";
7
9
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC1J,YAAY,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAC;AAChD,YAAY,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AACpD,YAAY,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAChE,OAAO,EAAE,KAAK,SAAS,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAChD,YAAY,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC1J,OAAO,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAC3C,YAAY,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAC;AAChD,YAAY,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AACpD,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,YAAY,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAChE,OAAO,EAAE,kBAAkB,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AACpD,YAAY,EAAE,SAAS,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC"}
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import*as M from"argon2";import fe from"eventemitter3";function j(r){if(r instanceof Set){let e=[];for(let t of r)e.push(t._id);return e}return r.map(e=>e._id)}function v(){}function f(r,e=0,t={}){let{leading:s=!1,trailing:i=!0}=t,{maxWait:o=1/0}=t,n,a,l,c,d,u,h,x,X=async()=>{let O=Date.now();O>=l?(n=void 0,l=void 0,clearTimeout(a),typeof h=="function"&&await h(),b.resolve(x),b.promise.isResolved=!0,u=s):(clearTimeout(n),n=setTimeout(X,l-O))},G=Number.isFinite(o)?()=>{h===A&&(h=!1),A(),a=setTimeout(G,o)}:null;async function A(){return x=await r.apply(c,d)}s&&typeof s=="boolean"&&(s=A),u=s,i&&typeof i=="boolean"&&(i=A),h=i;let b=Object.assign(function(...O){return d=O,c=this,l=Date.now()+e,h=i,b.promise.isResolved&&(b.promise=Object.assign(new Promise(ne=>{b.resolve=ne,typeof u=="function"&&(u(),u=!1,h===A&&(h=!1)),n||(n=setTimeout(X,e),G&&(a=setTimeout(G,o)))}),{isResolved:!1})),b.promise},{callback:r,promise:Object.assign(Promise.resolve(),{isResolved:!0}),resolve:v,run:A,clear:async O=>{clearTimeout(n),n=void 0,clearTimeout(a),b.promise.isResolved=!0,b.resolve(O?await A():x)}});return b}f.noop=Object.assign(()=>{},{callback:v,promise:Object.assign(Promise.resolve(),{isResolved:!0}),resolve:v,run:v,clear:v});function m(r,e){if(r){for(let t of e)delete r[t];return r}return null}function $(r){for(let e in r)delete r[e];return r}var C=class extends Array{constructor(){super(),Object.freeze(this)}push(){return 0}unshift(){return 0}splice(){return[]}};var w=class extends Set{constructor(){super()}add(){return this}};function F(r,e,t=!1){return t&&(e=e.filter(s=>r.has(s))),e.map(s=>r.get(s))}function Z(r,e){for(let t of e)if(r.has(t))return!0;return!1}function Q(r,e,t,s,i=!0){return Array.isArray(r)&&(r=r.length),typeof s!="string"&&(i=s??!0,s=t),(i?`${r}\xA0`:"")+Q.raw(r,e,t,s)}Q.raw=(r,e,t,s=t)=>{r=Math.abs(r);let i=r%10,o=r%100;return i===1&&o!==11?e:i>=2&&i<=4&&!(o>=12&&o<=15)?t:s};function q(r,...e){let t=[];e:for(let s of r){for(let i of e)if(i instanceof Set?!i.has(s):!i.includes(s))continue e;t.push(s)}return t}function E(r,e){return Math.floor(Math.random()*(e-r+1)+r)}function Y(r,e){return r.delete(e),r.add(e),r}function y(r,e){let t,s=0;for(let i of e)for(;(t=r.indexOf(i))>-1;)r.splice(t,1),s++;return s}function ee(r,e){let t=r.indexOf(e);return t>-1?(r.splice(t,1),!0):!1}function te(r,e){for(let t of[...r].sort(e))r.delete(t),r.add(t);return r}import{newObjectIdString as ge}from"insite-db";function le(r){return typeof r=="object"}function ae(r){return typeof r=="number"}function ce(r){return Array.isArray(r)}var L=class extends Map{constructor(e){super(),this.schema=e,this.#e(this.schema)}schema;#e(e){for(let t of e)this.set(t._id,t),t.subAbilities&&this.#e(t.subAbilities)}merge(e,t){for(let[s,i]of Object.entries(t)){let o=this.get(s);if(o){if(o.isInheritable!==!1&&i){if(!(s in e))e[s]=structuredClone(i);else if(o.params){let n=e[s],a=i;for(let l of o.params)if(l.isInheritable!==!1&&l._id in a){if(!(l._id in n))n[l._id]=structuredClone(a[l._id]);else if(l.type==="number")n[l._id]<a[l._id]&&(n[l._id]=a[l._id]);else if(l.type==="items"){let c=n[l._id];for(let d of a[l._id])c.includes(d)||c.push(d)}}}}}else delete t[s]}return e}getMinimumOf(e){let t=this.get(e);if(t?.params){let s={};for(let i of t.params)i.type==="number"?s[i._id]=i.min??0:i.type==="items"&&(s[i._id]=[]);return s}return!0}getMaximum(){return[...this.values()].reduce((e,t)=>{if(t.params){let s={};for(let i of t.params)i.type==="number"?s[i._id]=i.max??0:i.type==="items"&&(s[i._id]=i.items.map(o=>o._id));e[t._id]=s}else e[t._id]=!0;return e},{})}getSchemeFor(e){return function t(s){for(let i=0;i<s.length;i++){let o=s[i],n=e.abilities[o._id];if(n){if(o.params)for(let a of o.params){let l=n[a._id];if(a.type==="number")"max"in a&&(a.max=l);else if(a.type==="items")for(let c=0;c<a.items.length;c++)l.includes(a.items[c]._id)||a.items.splice(c--,1)}o.subAbilities&&t(o.subAbilities)}else s.splice(i--,1)}return s}(structuredClone(this.schema))}adjust(e){let t={},s=!1;for(let[i,o]of Object.entries(e)){let n=this.get(i);if(n)if(n.params){let a={};if(le(o)){for(let l of n.params)if(l._id in o){let c=o[l._id];if(l.type==="number"){ae(c)||(c=l.min??0);let d=a[l._id]=Math.max(Math.min(c,l.max??1/0),l.min??0);c!==d&&(s=!0)}else if(l.type==="items"){ce(c)||(c=[]);let d=a[l._id]=q(l.items.map(u=>u._id),c);(c.length!==d.length||c.some(u=>!d.includes(u)))&&(s=!0)}}}else{for(let l of n.params)l.type==="number"?a[l._id]=l.min??0:l.type==="items"&&(a[l._id]=[]);s=!0}t[i]=a}else t[i]=!0,o!==!0&&(s=!0);else s=!0}return s?(Object.assign($(e),t),!0):!1}};import{newObjectIdString as pe}from"insite-db";var K=new Map,g=class{constructor(e,t){this.orgs=e,this._id=t._id,e.set(this._id,this),this.update(t)}_id;title="";initials="";displayLabel="";_o=0;orgs;isOrg=!0;ownerOrgs=new Set;ownerUsers=new Set;users=new Set;slaveOrgs=new Set;ownerIds=[];update({_id:e,title:t,owners:s,...i},o){if(Object.assign(this,i),t!==void 0&&(this.title=t,this.initials=t?.[0]?.toUpperCase()??"",this.displayLabel=t),s){this.ownerIds=s;let n=this.ownerIds.join(",");n!==K.get(this._id)&&(K.set(this._id,n),this.orgs.users.isInited&&this.orgs.updateDebounced(),this.orgs.users.emit("orgs-org-update",this,o))}}delete(){this.orgs.delete(this._id),K.delete(this._id),this.orgs.replace(this._id),this.orgs.updateDebounced()}};var p={_id:/^[\dA-Fa-f]{24}$/,email:/^[^\s@]{1,63}@[^\s@]{1,63}\.[^\s@]{1,63}$/,argon2:/^\$argon2(?:i|d|id)\$v=\d+\$m=\d+,t=\d+,p=\d+(?:\$[\d+/A-Za-z]+){2}$/,sessionId:/^[\dA-Fa-f]{16,32}\$[\dA-Fa-f]{16,32}$/,role:/^[\d_a-z-]{1,64}$/,ip:/^(?:\d{1,3}\.){3}\d{1,3}$/};var _={required:["_id","title","note","owners","createdAt"],properties:{_id:{bsonType:"string",pattern:p._id.source},title:{bsonType:"string",maxLength:512},note:{bsonType:"string",maxLength:131072},owners:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:p._id.source},additionalItems:!1},createdAt:{bsonType:"number"}},additionalProperties:!1};var de=[[{owners:1}]];function ie(){throw new Error("Direct usage of orgs collection.deleteOne or .deleteMany is forbidden. Use orgs.collectionDelete instead.")}var W=class extends Map{constructor(e,t={}){super(),this.users=e,this.collections=e.collections,this.preinitOptions=t}users;collections;preinitOptions;collection;null;load(e){new g(this,e)}#e(e,t){t=[e,...t];for(let s of e.ownerOrgs){this.#e(s,t);for(let i of t)s.slaveOrgs.add(i)}}sorted=[];update(){let e=[...this.values()],t=[];for(let s of e){s.ownerOrgs.clear(),s.ownerUsers.clear(),s.slaveOrgs.clear();for(let i of s.ownerIds){let o=this.get(i);if(o)s.ownerOrgs.add(o);else{let n=this.users.get(i);n&&s.ownerUsers.add(n)}}!s.ownerOrgs.size&&s._id&&t.push(s)}for(let s of e)e.some(i=>i.ownerOrgs.has(s))||this.#e(s,[]);t.sort(this.#t);for(let s of e)te(s.slaveOrgs,this.#t);for(let s=0;s<t.length;s++){let i=t[s];for(let o of[...i.slaveOrgs].reverse())if(o.ownerOrgs.has(i)){let n=t.indexOf(o);~n&&(t.splice(n,1),s--),t.splice(s+1,0,o)}}for(let{length:s}=t,i=0;i<s;)t[i]._o=i++;this.sorted=t,this.users.emit("orgs-update"),this.users.isInited&&(this.users.updateDebounced.clear(),this.users.update())}#t(e,t){return t.slaveOrgs.size-e.slaveOrgs.size||(e.title>t.title?1:e.title<t.title?-1:0)}updateDebounced=f(this.update,250);preinit=async()=>{let{schema:e,indexes:t,null:s}=this.preinitOptions;e&&(e.required&&y(e.required,_.required),e.properties&&m(e,Object.keys(_.properties)));let i={..._,...e,required:[..._.required,...e?.required??[]],properties:{..._.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("orgs",{jsonSchema:i}),{deleteOne:ie,deleteMany:ie}),this.collection.ensureIndexes([...de,...t??[]]),this.null=Object.assign(new g(this,{...s,_id:"",title:"",note:"",owners:[],createdAt:Date.now()}),{_id:null,ownerIds:new C,ownerOrgs:new w,ownerUsers:new w,slaveOrgs:new w});for(let o of await this.collection.find().toArray())this.load(o);delete this.preinitOptions,delete this.preinit};init=async()=>{await this.update(),this.collection.changeListeners.add(e=>{switch(e.operationType){case"insert":{let t=new g(this,e.fullDocument);this.users.emit("orgs-org-update",t,e);break}case"replace":this.get(e.documentKey._id)?.update(e.fullDocument,e);break;case"update":this.get(e.documentKey._id)?.update(e.updateDescription.updatedFields,e);break;case"delete":this.get(e.documentKey._id)?.delete(),this.users.emit("orgs-org-update",null,e)}}),delete this.init};new({title:e,note:t,...s},i){return this.collection.insertOne({_id:pe(),title:e??"",note:t??"",owners:i?[i]:[],...m(s,["_id","owners"]),createdAt:Date.now()})}collectionDelete(e){let t=typeof e=="string"?e:e._id;return this.collection.bulkWrite([{updateMany:{filter:{owners:t},update:{$pullAll:{owners:[t]}}}},{deleteOne:{filter:{_id:t}}}])}replaceMap=new Map;replaceHandlers=new Set;async replace(e){let t=this.replaceMap.get(e)??null;t&&this.replaceMap.delete(e);for(let s of this.replaceHandlers)await s(e,t)}};var B=new Map,I=class{constructor(e,t){this.#e=e,this._id=t._id,e.set(this._id,this),this.update(t)}#e;_id;ownInvolveIds;ownAbilities;title="";displayTitle="";_o=0;ownInvolves=[];involves=new Set;abilities={};inheritedAbilities={};update({_id:e,involves:t,abilities:s,title:i,...o},n){if(Object.assign(this,o),t&&(this.ownInvolveIds=t),s&&(this.ownAbilities=s),i!==void 0&&(this.title=i,this.displayTitle=i||this._id),t||s){let a=[this.ownInvolveIds.join(","),JSON.stringify(this.ownAbilities)].join(`
2
- `);a!==B.get(this._id)&&(B.set(this._id,a),this.#e.users.isInited&&this.#e.updateDebounced(),this.#e.users.emit("roles-role-update",this,n))}}delete(){this.#e.delete(this._id),B.delete(this._id),this.#e.updateDebounced()}};var D={required:["_id","involves","abilities","title","description","createdAt"],properties:{_id:{bsonType:"string",pattern:p.role.source,not:{enum:["root"]}},involves:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:p.role.source,not:{enum:["root"]}},additionalItems:!1},abilities:{bsonType:"object"},title:{bsonType:"string",maxLength:256},description:{bsonType:"string",maxLength:10240},createdAt:{bsonType:"number"}},additionalProperties:!1};var ue=[[{involves:1}]];function se(){throw new Error("Direct usage of roles collection.deleteOne or .deleteMany is forbidden. Use roles.collectionDelete instead.")}var k=class extends Map{constructor(e,t={}){super();let{root:s,...i}=t;this.users=e,this.collections=e.collections,this.abilitiesMap=e.abilitiesMap,this.root=new I(this,{...s,_id:"root",involves:[],abilities:this.abilitiesMap.getMaximum(),title:"Root",description:"Root",createdAt:Date.now()}),this.initOptions=i}users;collections;collection;abilitiesMap;root;initOptions;load(e){new I(this,e)}resolve(e,t){t=[e,...t];for(let s of e.ownInvolveIds){let i=this.get(s);if(i){for(let o of t)Y(o.involves,i),this.abilitiesMap.merge(o.inheritedAbilities,i.abilities);i!==e&&this.resolve(i,t)}}}sorted=[];#e(e,t){return t.involves.size-e.involves.size||(e.title&&t.title?e.title>t.title?1:e.title<t.title?-1:0:e.title?-1:t.title||e._id>t._id?1:e._id<t._id?-1:0)}update(){let e=[...this.values()];this.root.ownInvolveIds=[];for(let i of e)i!==this.root&&!e.some(o=>o.ownInvolveIds.includes(i._id))&&this.root.ownInvolveIds.push(i._id),i.involves.clear(),i.abilities=structuredClone(i.ownAbilities),i.inheritedAbilities={};this.root.involves.add(this.root),this.resolve(this.root,[]);for(let i of e)i.ownInvolves=F(this,i.ownInvolveIds,!0).sort(this.#e).reverse();let t=[this.root];for(let i=0;i<t.length;i++){let o=t[i];for(let n of o.ownInvolves){let a=t.indexOf(n);~a&&(t.splice(a,1),i--),t.splice(i+1,0,n)}}let s=0;for(let i of t)this.abilitiesMap.merge(i.abilities,i.inheritedAbilities),i._o=s++;this.sorted=t,this.users.emit("roles-update"),this.users.isInited&&(this.users.updateDebounced.clear(),this.users.update(!0))}updateDebounced=f(this.update,250);init=async()=>{let{schema:e,indexes:t}=this.initOptions;e&&(e.required&&y(e.required,D.required),e.properties&&m(e,Object.keys(D.properties)));let s={...D,...e,required:[...D.required,...e?.required??[]],properties:{...D.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("roles",{jsonSchema:s}),{deleteOne:se,deleteMany:se}),this.collection.ensureIndexes([...ue,...t??[]]);for(let i of await this.collection.find().toArray())this.abilitiesMap.adjust(i.abilities)&&await this.collection.updateOne({_id:i._id},{$set:{abilities:i.abilities}}),this.load(i);this.update(),this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":{let o=new I(this,i.fullDocument);this.users.emit("roles-role-update",o,i);break}case"replace":this.get(i.documentKey._id)?.update(i.fullDocument,i);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields,i);break;case"delete":this.get(i.documentKey._id)?.delete(),this.users.emit("roles-role-update",null,i)}}),delete this.initOptions,delete this.init};new({_id:e,involves:t,title:s,description:i,...o}){return this.collection.insertOne({_id:e,involves:t||[],abilities:{},title:s??"",description:i??"",...m(o,["abilities"]),createdAt:Date.now()})}collectionDelete(e){let t=typeof e=="string"?e:e._id;return this.collection.bulkWrite([{updateMany:{filter:{involves:t},update:{$pullAll:{involves:[t]}}}},{deleteOne:{filter:{_id:t}}}])}cleanUpIds(e){let t=q(this.sorted,F(this,e,!0)),s=[];for(let i of t)t.every(o=>o===i||!o.involves.has(i))&&s.push(i._id);return s}};import oe from"node:crypto";var R={required:["_id","user","remoteAddress","isOnline","createdAt","prolongedAt","expiresAt"],properties:{_id:{bsonType:"string",pattern:p.sessionId.source},user:{bsonType:"string",pattern:p._id.source},userAgent:{bsonType:"string",maxLength:4096},remoteAddress:{bsonType:"string",pattern:p.ip.source},isOnline:{bsonType:"bool"},createdAt:{bsonType:"number"},prolongedAt:{bsonType:"number"},expiresAt:{bsonType:"date"}}};var P=class{constructor(e,t){let s=e.users.get(t.user);s?(this.#e=e,this._id=t._id,this.#e.set(this._id,this),this.user=s,this.user.sessions.add(this),this.#e.users.bySessionId.set(this._id,this.user),this.update(t)):e.collection.deleteOne({_id:t._id})}_id;user;isOnline=!1;userAgent;remoteAddress;createdAt;prolongedAt;expiresAt;#e;update({_id:e,user:t,isOnline:s,...i}){s!==void 0&&this.isOnline!==s&&(this.isOnline=s,this.#e.isInited&&this.user.isOnline!==this.isOnline&&this.user.updateIsOnline()),Object.assign(this,i)}prolong({_id:e,user:t,...s}){let i=Date.now();return s.prolongedAt=i,s.expiresAt=new Date(i+this.#e.collection.expireAfterSeconds*1e3),this.update(s),this.#e.collection.updateOne({_id:this._id},{$set:s})}offline(){let e={isOnline:!1};return this.update(e),this.#e.collection.updateOne({_id:this._id},{$set:e})}delete(){this.#e.delete(this._id),this.user.sessions.delete(this),this.#e.users.bySessionId.delete(this._id),this.#e.users.emit("session-delete",this),this.isOnline&&this.user.updateIsOnline()}};var z=3600*24*7,me=[[{user:1}],[{expiresAt:1},{expireAfterSeconds:z}]],N=class extends Map{constructor(e,t={}){super(),this.users=e,this.collections=e.collections,this.initOptions=t}users;collections;initOptions;collection;isInited=!1;uid(){let e;do e=`${oe.randomBytes(E(8,16)).toString("hex")}$${oe.randomBytes(E(8,16)).toString("hex")}`;while(this.has(e));return e}load(e){new P(this,e)}init=async()=>{let{schema:e,indexes:t}=this.initOptions;e&&(e.required&&y(e.required,R.required),e.properties&&m(e,Object.keys(R.properties)));let s={...R,...e,required:[...R.required,...e?.required??[]],properties:{...R.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("sessions",{jsonSchema:s}),{expireAfterSeconds:z}),this.collection.ensureIndexes([...me,...t??[]]),await this.collection.updateMany({isOnline:!0},{$set:{isOnline:!1}});for(let i of await this.collection.find().toArray())this.load(i);this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":this.has(i.documentKey._id)||new P(this,i.fullDocument),this.users.get(i.fullDocument.user)?.trimSessions();break;case"replace":this.get(i.documentKey._id)?.update(i.fullDocument);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields);break;case"delete":this.get(i.documentKey._id)?.delete()}}),this.isInited=!0,delete this.initOptions,delete this.init};async new(e,t){let s=Date.now(),i={userAgent:"",remoteAddress:"127.0.0.1",isOnline:!0,...t,_id:this.uid(),user:e._id,createdAt:s,prolongedAt:s,expiresAt:new Date(s+z*1e3)},o=new P(this,i);return await this.collection.insertOne(i),o}};var re={required:["_id","type","size","ts","data"],properties:{_id:{bsonType:"string",pattern:p._id.source},type:{bsonType:"string",maxLength:256},size:{bsonType:"number"},ts:{bsonType:"string",maxLength:10},data:{bsonType:"binData"}},additionalProperties:!1};var U=class{constructor(e){this.users=e,this.collections=e.collections}users;collections;collection;init=async()=>{this.collection=await this.collections.ensure("users.avatars",{jsonSchema:re}),delete this.init}};var T={required:["_id","email","password","roles","name","org","job","createdAt"],properties:{_id:{bsonType:"string",pattern:p._id.source},email:{bsonType:"string",pattern:p.email.source},password:{bsonType:"string",pattern:p.argon2.source},roles:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:p.role.source},additionalItems:!1},name:{bsonType:"object",required:["first","middle","last"],properties:{first:{bsonType:"string",maxLength:512},middle:{bsonType:"string",maxLength:512},last:{bsonType:"string",maxLength:512}},additionalProperties:!1},org:{oneOf:[{bsonType:"string",pattern:p._id.source},{bsonType:"null"}]},job:{bsonType:"string",maxLength:512},avatar:{oneOf:[{bsonType:"string",maxLength:10},{bsonType:"null"}]},createdAt:{bsonType:"number"}},additionalProperties:!1};var H=new Map,J=new Map,he=process.env.INSITE_STATIC_URL??"http://localhost:8080",S=class{constructor(e,t){this.#e=e,this._id=t._id,e.set(this._id,this),this.update(t),e.isInited&&e.emit("user-create",this)}_id;email;name={first:"",middle:"",last:""};initials="";displayLabel="";org;job="";avatar=null;avatarUrl=null;#e;isUser=!0;isRoot;roles=new Set;ownRoles=[];ownRoleIds=[];slaveRoles=new Set;slaveRoleIds=[];abilities={};slaveOrgs=new Set;slaveUsers=new Set;slaves=new Set;slaveIds=[];permissiveIds=[];sessions=new Set;isOnline=!1;update({_id:e,name:t,email:s,roles:i,org:o,avatar:n,...a}){Object.assign(this,a);let l;s&&this.email!==s&&(this.#e.byEmail.delete(this.email),this.email=s,this.#e.byEmail.set(s,this),l=!0);let c,d;t&&(this.name.first!==t.first||this.name.middle!==t.middle||this.name.last!==t.last)&&(d=this.name.last!==t.last,this.name={first:t.first??"",middle:t.middle??"",last:t.last??""},this.initials=((t.first?.[0]??"")+(t.last?.[0]??"")||this.email[0]).toUpperCase(),c=!0),(l||c)&&(this.displayLabel=`${this.name.first} ${this.name.last}`.trim()||this.name.middle||this.email);let u;if(i){this.ownRoleIds=i;let x=this.ownRoleIds.join(",");x!==H.get(this._id)&&(H.set(this._id,x),this.updateRoles(),u=!0)}let h;o!==void 0&&this.org?._id!==o&&(this.org?.users.delete(this),this.org=o&&this.#e.orgs.get(o)||this.#e.orgs.null,this.org.users.add(this),h=!0),n!==void 0&&this.avatar!==n&&(this.avatar=n,this.avatarUrl=n&&`${he}/avatars/${this._id}-${n}.webp`),u||h?(this.updatePermissions(),d&&(this.#e.isSortRequired=!0),this.#e.isInited&&this.#e.updateDebounced()):d&&this.#e.sortDebounced()}updateRoles(){if(this.#e.isInited){this.ownRoles=[],this.roles.clear(),this.slaveRoles.clear(),$(this.abilities);for(let e of this.ownRoleIds){let t=this.#e.roles.get(e);if(t){this.ownRoles.push(t),this.roles.add(t);for(let s of t.involves)this.roles.add(s),this.slaveRoles.add(s);this.slaveRoleIds=j(this.slaveRoles),this.#e.abilitiesMap.merge(this.abilities,t.abilities)}}this.roles.has(this.#e.roles.root)&&(this.isRoot=!0),this.trimSessions()}}updatePermissions(){if(this.#e.isInited){this.slaveOrgs.clear(),this.slaveUsers.clear(),this.slaves.clear();let e=new Set;for(let i of this.#e.orgs.sorted)if((i.ownerUsers.has(this)||this.isRoot)&&!this.slaveOrgs.has(i)){this.slaveOrgs.add(i),this.slaves.add(i),e.add(i._id);for(let o of i.slaveOrgs)this.slaveOrgs.add(o),this.slaves.add(o),e.add(o._id)}for(let i of new Set([this.org,...this.slaveOrgs,this.#e.orgs.null]))for(let o of i.users)o!==this&&(Z(this.slaveRoles,o.ownRoles)||!o.ownRoles.length)&&(this.slaveUsers.add(o),this.slaves.add(o),e.add(o._id));this.slaveIds=[...e];let t=[];if(this.org._id){t.push(this.org._id);for(let i of this.org.slaveOrgs)this.slaveOrgs.has(i)||t.push(i._id)}this.permissiveIds=[...t,this._id,...e];let s=[this.permissiveIds.join(","),this.ownRoleIds.join(","),JSON.stringify(this.abilities),this.slaveRoleIds.join(",")].join(`
3
- `);s!==J.get(this._id)&&(J.set(this._id,s),this.#e.emit("user-permissions-change",this))}}trimSessions(){let e=this.abilities.login?.sessionsLimit??0;return this.sessions.size>e?this.#e.sessions.collection.deleteMany({_id:{$in:j([...this.sessions].sort((t,s)=>t.expiresAt.valueOf()-s.expiresAt.valueOf()).slice(0,this.sessions.size-e))}}):null}updateIsOnline=f(()=>{let e=!1;for(let t of this.sessions)if(t.isOnline){e=!0;break}this.isOnline!==e&&(this.isOnline=e,this.#e.emit("user-is-online",this))},500);delete(){this.org.users.delete(this),this.#e.delete(this._id),this.#e.byEmail.delete(this.email),ee(this.#e.sorted,this),H.delete(this._id),J.delete(this._id),this.#e.replace(this._id),this.#e.updateDebounced()}};var be=[[{email:1},{unique:!0}],[{org:1}]],V=class r extends Map{constructor(e,t){super();let s=new fe;this._events=s._events,this._eventsCount=s._eventsCount,this.emit=s.emit,this.on=s.on,this.once=s.once,this.addListener=s.addListener,this.off=s.off,this.removeListener=s.removeListener,this.collections=e,this.abilitiesMap=new L(t.abilities),this.initOptions=t,this.#e=this.init()}_events;_eventsCount;emit;on;once;addListener;off;removeListener;initOptions;collections;abilitiesMap;collection;roles;sessions;orgs;avatars;isInited=!1;byEmail=new Map;bySessionId=new Map;sorted=[];isSortRequired=!1;load(e){new S(this,e)}sort(){this.isSortRequired=!1,this.sorted=[...this.values()].sort((e,t)=>e.name.last>t.name.last?1:e.name.last<t.name.last?-1:0)}sortDebounced=f(()=>this.sort(),250);update(e){if(e)for(let t of this.values())t.updateRoles();for(let t of this.values())t.updatePermissions();this.isSortRequired&&this.sort()}updateDebounced=f(()=>this.update(),250);preinit=async()=>{let{indexes:e,schema:t,initialRoot:s}=this.initOptions;t&&(t.required&&y(t.required,T.required),t.properties&&m(t,Object.keys(T.properties)));let i={...T,...t,required:[...T.required,...t?.required??[]],properties:{...T.properties,...t?.properties}};this.collection=await this.collections.ensure("users",{jsonSchema:i}),this.collection.ensureIndexes([...be,...e??[]]),await this.collection.countDocuments({roles:"root"})||await this.new({email:process.env.INSITE_ROOT_EMAIL??"insite@root.email",password:process.env.INSITE_ROOT_PASSWORD??"inSiteRootPassword",roles:["root"],name:{first:"Root"},org:null,job:"Root",...s&&m(s,["roles","org"])});for(let o of await this.collection.find().toArray())this.load(o);delete this.preinit};#e;init=async()=>{let{roles:e,orgs:t,sessions:s}=this.initOptions;return this.roles=new k(this,e),this.orgs=new W(this,t),this.sessions=new N(this,s),this.avatars=new U(this),await this.roles.init(),await this.orgs.preinit(),await this.preinit(),await this.orgs.init(),await this.avatars.init(),this.isInited=!0,this.update(!0),this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":new S(this,i.fullDocument);break;case"replace":this.get(i.documentKey._id)?.update(i.fullDocument);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields);break;case"delete":this.get(i.documentKey._id)?.delete()}}),await this.sessions.init(),delete this.initOptions,delete this.init,this};whenReady(){return this.#e}async new({email:e,password:t,roles:s,name:i,org:o,job:n,...a}){if(this.byEmail.has(e))throw new Error("User exists");return await this.collection.insertOne({_id:ge(),email:e,password:await M.hash(t),roles:this.isInited?this.roles.cleanUpIds(s):s,name:{first:i.first??"",middle:i.middle??"",last:i.last??""},org:o??null,job:n??"",...m(a,["_id"]),createdAt:Date.now()}),!0}async changePassword(e,t){if(!this.has(e))throw new Error("usernotfound");if(!t)throw new Error("emptypasswordisnotallowed");await Promise.all([this.collection.updateOne({_id:e},{$set:{password:await M.hash(t)}}),this.sessions.collection.deleteMany({user:e})])}async login(e,t,s){let i=this.byEmail.get(e);if(!i)throw new Error("usernotfound");if(!await M.verify(i.password,t))throw new Error("incorrectpassword");if(!i.abilities.login)throw new Error("userisnotabletologin");return this.sessions.new(i,s)}logout(e){return e.delete(),this.sessions.collection.deleteOne({_id:e._id})}#t(e,t){return e instanceof S&&t instanceof S?e.name.last&&t.name.last?e.name.last>t.name.last?1:e.name.last<t.name.last?-1:0:!e.name.last&&!t.name.last?e.displayLabel>t.displayLabel?1:e.displayLabel<t.displayLabel?-1:0:e.name.last?-1:1:e instanceof g&&t instanceof g?e.title>t.title?1:e.title<t.title?-1:0:e instanceof g?-1:1}sortIds(e){return j(e.map(t=>this.get(t)||this.orgs.get(t)).filter(Boolean).sort(this.#t))}replaceMap=new Map;replaceHandlers=new Set;async replace(e){let t=this.replaceMap.get(e)??null;t&&this.replaceMap.delete(e);for(let s of this.replaceHandlers)await s(e,t)}static init(e,t){return new r(e,t).whenReady()}};export{V as Users};
1
+ function x(o){if(o instanceof Set){let e=[];for(let t of o)e.push(t._id);return e}return o.map(e=>e._id)}function ce(o,...e){let t=0;for(let s of e)o.includes(s)||(o.push(s),t++);return t}function E(o,e,t){if(o&&e){if(e.includes(".")){let s=e.split("."),i=o;for(let r=0;r<s.length-1;r++){let n=s[r],l=i[n];i=l&&typeof l=="object"?l:i[n]={}}return i[s.at(-1)]=t}return o[e]=t}return null}function pe(o,...e){for(let t of e)for(let s in t)Object.hasOwn(t,s)&&E(o,s,t[s]);return o}function _(){}function m(o,e=0,t={}){let{leading:s=!1,trailing:i=!0}=t,{maxWait:r=1/0}=t,n,l,a,p,g,y,d,O,ae=async()=>{let v=Date.now();v>=a?(n=void 0,a=void 0,clearTimeout(l),typeof d=="function"&&await d(),b.resolve(O),b.promise.isResolved=!0,y=s):(clearTimeout(n),n=setTimeout(ae,a-v))},J=Number.isFinite(r)?()=>{d===S&&(d=!1),S(),l=setTimeout(J,r)}:null;async function S(){return O=await o.apply(p,g)}s&&typeof s=="boolean"&&(s=S),y=s,i&&typeof i=="boolean"&&(i=S),d=i;let b=Object.assign(function(...v){return g=v,p=this,a=Date.now()+e,d=i,b.promise.isResolved&&(b.promise=Object.assign(new Promise(ve=>{b.resolve=ve,typeof y=="function"&&(y(),y=!1,d===S&&(d=!1)),n||(n=setTimeout(ae,e),J&&(l=setTimeout(J,r)))}),{isResolved:!1})),b.promise},{callback:o,promise:Object.assign(Promise.resolve(),{isResolved:!0}),resolve:_,run:S,clear:async v=>{clearTimeout(n),n=void 0,clearTimeout(l),b.promise.isResolved=!0,b.resolve(v?await S():O)}});return b}m.noop=Object.assign(()=>{},{callback:_,promise:Object.assign(Promise.resolve(),{isResolved:!0}),resolve:_,run:_,clear:_});function de(o,e){if(o&&e){if(e.includes(".")){let t=e.split("."),s=o;for(let r=0;r<t.length-1;r++){let n=t[r],l=s[n];if(l&&typeof l=="object")s=l;else return!1}let i=t.at(-1);return i in s&&delete s[i]}return e in o&&delete o[e]}return!1}function u(o,e){if(o){for(let t of e)delete o[t];return o}return null}function k(o){for(let e in o)delete o[e];return o}var q=class extends Array{constructor(){super(),Object.freeze(this)}push(){return 0}unshift(){return 0}splice(){return[]}};var I=class extends Set{constructor(){super()}add(){return this}};var A=class extends Error{constructor(e,t=null,s){super(e),t&&typeof t=="object"&&(s=t,t=null),this.tag=t,s&&Object.assign(this,s)}name="Err-or";tag};function X(o,e,t=!1){return t&&(e=e.filter(s=>o.has(s))),e.map(s=>o.get(s))}function G(o,e){if(e){if(e.includes(".")){let t=o;for(let s of e.split("."))if(t=t?.[s],t===void 0)break;return t}return o[e]}return o}function ue(o,e){for(let t of e)if(o.has(t))return!0;return!1}function me(o,e,t,s,i=!0){return Array.isArray(o)&&(o=o.length),typeof s!="string"&&(i=s??!0,s=t),(i?`${o}\xA0`:"")+me.raw(o,e,t,s)}me.raw=(o,e,t,s=t)=>{o=Math.abs(o);let i=o%10,r=o%100;return i===1&&r!==11?e:i>=2&&i<=4&&!(r>=12&&r<=15)?t:s};function L(...o){let e=[];if(o.length){let[t,...s]=o;e:for(let i of t){for(let r of s)if(r instanceof Set?!r.has(i):!r.includes(i))continue e;e.push(i)}}return e}function fe(o,e){let t={};for(let s of e)s in o&&(t[s]=o[s]);return t}function N(o,e){return Math.floor(Math.random()*(e-o+1)+o)}function he(o,e){return o.delete(e),o.add(e),o}function f(o,e){let t,s=0;for(let i of e)for(;(t=o.indexOf(i))>-1;)o.splice(t,1),s++;return s}function be(o,e){let t=o.indexOf(e);return t>-1?(o.splice(t,1),!0):!1}function ge(o,e){for(let t of[...o].sort(e))o.delete(t),o.add(t);return o}var $=new WeakMap,W=class extends Promise{constructor(e){let t,s;super((i,r)=>{t=i,s=r}),$.set(this,{resolve:t,reject:s}),e?.(this.resolve,this.reject)}isPending=!0;isFulfilled=!1;isRejected=!1;state="pending";result;resolve=e=>{if(this.isPending){this.isPending=!1,this.isFulfilled=!0,this.state="fulfilled",this.result=e;let t=$.get(this);t&&(t.resolve.call(this,e),$.delete(this))}};reject=e=>{if(this.isPending){this.isPending=!1,this.isRejected=!0,this.state="rejected",this.result=e;let t=$.get(this);t&&(t.reject.call(this,e),$.delete(this))}}};function ye(...o){return[...new Set(o.flat())]}function M(o,e){return o.filter(t=>!e.includes(t))}var Z=class extends A{constructor(e){super("User lacks ability","lacksability",{ability:e})}name="AbilityError"};function Y(o){return typeof o=="object"}function Q(o){return typeof o=="number"}function V(o){return Array.isArray(o)}var Ae=new Map,B=class extends Map{constructor(e){super();for(let t of e)delete t.top,this.#e.push(t);(function t(s,i,r){for(let n of s){if(Ae.set(n,i),n.level=r,!i||n.top){if(n.longId=n._id,this.has(n._id))throw new Error(`Top-level ability duplicate: ${n._id}`);this.set(n._id,n)}else n.longId=i?`${i.longId}.${n._id}`:n._id;n.abilities&&t.call(this,n.abilities,n,r+1)}}).call(this,e,null,0)}#e=[];get(e,t){let s=e.split("."),i=t??super.get(s.shift());if(i&&s.length){for(let r of s)if(i=i?.abilities?.find(({_id:n,top:l})=>!l&&n===r),!i)break}return i}getSchema=this.get;getParamSchema(e,t){return this.get(e)?.params?.find(({_id:s})=>s===t)}getDefaultParam(e,t,s){(t===void 0||typeof t=="boolean")&&(s=t);let i=typeof e=="string"?this.getParamSchema(e,t):e;if(i)switch(i.type){case"number":return s?i.max??1/0:i.min??0;case"items":return s?i.items.map(({_id:r})=>r):[]}}getDefaultAbility(e,t=!e){if(typeof e=="string"&&(e=this.get(e)),e){if(e.abilities||e.params){let s={};if(e.params)for(let i of e.params)s[i._id]=this.getDefaultParam(i,t);if(t&&e.abilities)for(let i of e.abilities)i.top||(s[i._id]=this.getDefaultAbility(i,t));return s}return!0}}getDefaultAbilities(e,t=!e){let s=(e?(Array.isArray(e)?e:[e]).map(r=>typeof r=="string"?this.get(r):r).filter(Boolean):[...this.values()]).sort((r,n)=>r.level-n.level),i=new Map;for(let r of s)(function n(l){let a=Ae.get(l);a&&(n(a),i.has(a)||i.set(a,!1))})(r),t?function n(l){if(i.has(l)||i.set(l,!0),l.abilities)for(let a of l.abilities)a.top&&n(a)}(r):i.has(r)||i.set(r,!1);return pe({},Object.fromEntries([...i].map(([r,n])=>[r.longId,this.getDefaultAbility(r,n)])))}getSchemeFor(e){return e=this.adjust(structuredClone(e)),function t(s,i){for(let r=0;r<s.length;r++){let n=s[r],l=n.top?e[n._id]:i[n._id];if(l){if(n.params)for(let a of n.params){let p=l[a._id];switch(a.type){case"number":a.max=p;break;case"items":a.items=a.items.filter(({_id:g})=>p.includes(g))}}n.abilities&&(t(n.abilities,l),n.abilities.length||delete n.abilities)}else s.splice(r--,1)}return s}(structuredClone(this.#e),e)}getParam(e,t,s){if(this.getParamSchema(t,s)){let i=G(e,`${t}.${s}`);return this.isParamFits(t,s,i)?i:this.getDefaultParam(t,s)}}setParam(e,t,s,i){let r=this.getParamSchema(t,s);if(!r)throw new Error(`No such ability param: ${t}.${s}`);return E(e,`${t}.${s}`,this.adjustParam(r,i)),e}isParamFits(e,t,s,i){if(s!==void 0){let r=this.getParamSchema(e,t);if(r)switch(r.type){case"number":return Q(s)&&(r.min===void 0||s>=r.min)&&(i===void 0?r.max===void 0||s<=r.max:s<=i);case"items":return V(s)&&s.length===new Set(s).size&&(i===void 0?s.every(n=>r.items.find(({_id:l})=>l===n)):s.every(n=>i.includes(n)))}}return!1}adjustParam(e,t){switch(e.type){case"number":return Q(t)?Math.max(Math.min(t,e.max??1/0),e.min??0):e.min??0;default:return V(t)?L(e.items.map(s=>s._id),t):[]}}adjust(e,t){let s={};for(let[i,r]of Object.entries(e)){let n=this.get(i,t);if(n)if(n.params||n.abilities){let l={};if(n.params)if(Y(r))for(let a of n.params)l[a._id]=this.adjustParam(a,r[a._id]);else for(let a of n.params)l[a._id]=this.getDefaultParam(a);n.abilities&&Y(r)&&Object.assign(l,this.adjust(fe(r,n.abilities.filter(a=>!a.top).map(a=>a._id)),n)),s[i]=l}else s[i]=!0}return Object.assign(k(e),s)}merge(e,t,s){s||(this.adjust(e),t=this.adjust(structuredClone(t)));for(let[i,r]of Object.entries(t)){let n=this.get(i,s);if(n&&n.isInheritable!==!1)if(i in e&&(n.params||n.abilities)){let l=e[i],a=r;if(n.params){for(let p of n.params)if(p.isInheritable!==!1)switch(p.type){case"number":l[p._id]=Math.max(l[p._id],a[p._id]);break;case"items":ce(l[p._id],...a[p._id])}}n.abilities&&this.merge(l,a,n)}else e[i]=r}return e}hasAbility(e,t){return!!G(e,t)}setAbility(e,t){let s=typeof t=="string"?this.get(t):t;if(!s)throw new Error(`No such ability: ${t}`);return this.merge(e,this.getDefaultAbilities(s)),e}unsetAbility(e,t){let s=typeof t=="string"?this.get(t):t;if(!s)throw new Error(`No such ability: ${t}`);return function i(r){if(de(e,r.longId),r.abilities)for(let n of r.abilities)i(n)}(s),e}};var ee=class extends A{constructor(e){super(`User lacks role${Array.isArray(e)?"s":""}`,"lacksroles",{roles:Array.isArray(e)?e:[e]})}name="RolesError"};var te=new Map,D=class{constructor(e,t){this.#e=e,this._id=t._id,e.set(this._id,this),this.update(t)}#e;_id;ownInvolveIds;ownAbilities;title="";displayTitle="";_o=0;ownInvolves=[];involves=new Set;abilities={};inheritedAbilities={};update({_id:e,involves:t,abilities:s,title:i,...r},n){if(Object.assign(this,r),t&&(this.ownInvolveIds=t),s&&(this.ownAbilities=s),i!==void 0&&(this.title=i,this.displayTitle=i||this._id),t||s){let l=[this.ownInvolveIds.join(","),JSON.stringify(this.ownAbilities)].join(`
2
+ `);l!==te.get(this._id)&&(te.set(this._id,l),this.#e.users.isInited&&this.#e.updateDebounced().then(()=>this.#e.users.emit("roles-role-update",this,n)))}}delete(){this.#e.delete(this._id),te.delete(this._id),this.#e.updateDebounced()}};var c={_id:/^[\dA-Fa-f]{24}$/,email:/^[^\s@]{1,63}@[^\s@]{1,63}\.[^\s@]{1,63}$/,argon2:/^\$argon2(?:i|d|id)\$v=\d+\$m=\d+,t=\d+,p=\d+(?:\$[\d+/A-Za-z]+){2}$/,sessionId:/^[\dA-Fa-f]{16,32}\$[\dA-Fa-f]{16,32}$/,role:/^[\d_a-z-]{1,64}$/,ip:/^(?:\d{1,3}\.){3}\d{1,3}$/};var P={required:["_id","involves","abilities","title","description","createdAt"],properties:{_id:{bsonType:"string",pattern:c.role.source,not:{enum:["root"]}},involves:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:c.role.source,not:{enum:["root"]}},additionalItems:!1},abilities:{bsonType:"object"},title:{bsonType:"string",maxLength:256},description:{bsonType:"string",maxLength:10240},createdAt:{bsonType:"number"}},additionalProperties:!1};var _e=[[{involves:1}]];function Se(){throw new Error("Direct usage of roles collection.deleteOne or .deleteMany is forbidden. Use roles.deleteRole instead.")}var F=class extends Map{constructor(e,t={}){super();let{root:s,...i}=t;this.users=e,this.collections=e.collections,this.abilities=e.abilities,this.root=new D(this,{...s,_id:"root",involves:[],abilities:this.abilities.getDefaultAbilities(),title:"Root",description:"Root",createdAt:Date.now()}),this.initOptions=i}users;collections;collection;abilities;root;initOptions;#e=!1;async init(){if(!this.#e){this.#e=!0;let{schema:e,indexes:t}=this.initOptions;e&&(e.required&&f(e.required,P.required),e.properties&&u(e,Object.keys(P.properties)));let s={...P,...e,required:[...P.required,...e?.required??[]],properties:{...P.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("roles",{jsonSchema:s}),{deleteOne:Se,deleteMany:Se}),this.collection.ensureIndexes([..._e,...t??[]]);for(let i of await this.collection.find().toArray())this.abilities.adjust(i.abilities)&&await this.collection.updateOne({_id:i._id},{$set:{abilities:i.abilities}}),this.load(i);this.update(),this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":{let r=new D(this,i.fullDocument);this.users.emit("roles-role-update",r,i);break}case"replace":this.get(i.documentKey._id)?.update(i.fullDocument,i);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields,i);break;case"delete":this.get(i.documentKey._id)?.delete(),this.users.emit("roles-role-update",null,i)}}),delete this.initOptions}}load(e){new D(this,e)}resolve(e,t){t=[e,...t];for(let s of e.ownInvolveIds){let i=this.get(s);if(i){for(let r of t)he(r.involves,i),this.abilities.merge(r.inheritedAbilities,i.abilities);i!==e&&this.resolve(i,t)}}}sorted=[];#t(e,t){return t.involves.size-e.involves.size||(e.title&&t.title?e.title>t.title?1:e.title<t.title?-1:0:e.title?-1:t.title||e._id>t._id?1:e._id<t._id?-1:0)}update(){let e=[...this.values()];this.root.ownInvolveIds=[];for(let i of e)i!==this.root&&!e.some(r=>r.ownInvolveIds.includes(i._id))&&this.root.ownInvolveIds.push(i._id),i.involves.clear(),i.abilities=structuredClone(i.ownAbilities),i.inheritedAbilities={};this.root.involves.add(this.root),this.resolve(this.root,[]);for(let i of e)i.ownInvolves=X(this,i.ownInvolveIds,!0).sort(this.#t).reverse();let t=[this.root];for(let i=0;i<t.length;i++){let r=t[i];for(let n of r.ownInvolves){let l=t.indexOf(n);~l&&(t.splice(l,1),i--),t.splice(i+1,0,n)}}let s=0;for(let i of t)this.abilities.merge(i.abilities,i.inheritedAbilities),i._o=s++;this.sorted=t,this.users.emit("roles-update"),this.users.isInited&&(this.users.updateDebounced.clear(),this.users.update(!0))}updateDebounced=m(this.update,100);create({_id:e,involves:t,title:s,description:i,...r}){return this.collection.insertOne({_id:e,involves:t||[],abilities:{},title:s??"",description:i??"",...u(r,["abilities"]),createdAt:Date.now()})}async updateRole(e,t){let s=this.get(e);if(!s)return!1;if(t.involves){f(t.involves,[e]);for(let i of t.involves)this.get(i)?.involves.has(s)&&f(t.involves,[i]);t.involves=this.cleanUpIds(t.involves)}return await this.collection.updateOne({_id:e},{$set:t}),!0}deleteRole(e){let t=typeof e=="string"?e:e._id;return this.collection.bulkWrite([{updateMany:{filter:{involves:t},update:{$pullAll:{involves:[t]}}}},{deleteOne:{filter:{_id:t}}}])}cleanUpIds(e){let t=L(this.sorted,X(this,e,!0)),s=[];for(let i of t)t.every(r=>r===i||!r.involves.has(i))&&s.push(i._id);return s}async setAbility(e,t,s){let i=this.get(e);return i?(await this.collection.updateOne({_id:e},{$set:{abilities:s?this.abilities.setAbility(i.ownAbilities,t):this.abilities.unsetAbility(i.ownAbilities,t)}}),!0):!1}async setAbilityParam(e,t,s,i){let r=this.get(e);return r?(await this.collection.updateOne({_id:e},{$set:{abilities:this.abilities.setParam(r.ownAbilities,t,s,i)}}),!0):!1}};var ie=class extends A{constructor(e,t){super("Insubordination attempt","subordination",{type:e,ids:Array.isArray(t)?t:[t]})}name="SubordinationError"};import*as C from"argon2";import Te from"eventemitter3";import{newObjectIdString as Ue}from"insite-db";import{newObjectIdString as Ie}from"insite-db";var se=new Map,h=class{constructor(e,t){this.orgs=e,this._id=t._id,e.set(this._id,this),this.update(t)}_id;title="";initials="";displayLabel="";_o=0;orgs;isOrg=!0;ownerOrgs=new Set;ownerUsers=new Set;users=new Set;slaveOrgs=new Set;ownerIds=[];update({_id:e,title:t,owners:s,...i},r){if(Object.assign(this,i),t!==void 0&&(this.title=t,this.initials=t?.[0]?.toUpperCase()??"",this.displayLabel=t),s){this.ownerIds=s;let n=this.ownerIds.join(",");n!==se.get(this._id)&&(se.set(this._id,n),this.orgs.users.isInited&&this.orgs.updateDebounced(),this.orgs.users.emit("orgs-org-update",this,r))}}delete(){this.orgs.delete(this._id),se.delete(this._id),this.orgs.replace(this._id),this.orgs.updateDebounced()}};var R={required:["_id","title","note","owners","createdAt"],properties:{_id:{bsonType:"string",pattern:c._id.source},title:{bsonType:"string",maxLength:512},note:{bsonType:"string",maxLength:131072},owners:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:c._id.source},additionalItems:!1},createdAt:{bsonType:"number"}},additionalProperties:!1};var De=[[{owners:1}]];function xe(){throw new Error("Direct usage of orgs collection.deleteOne or .deleteMany is forbidden. Use orgs.deleteOrg instead.")}var K=class extends Map{constructor(e,t={}){super(),this.users=e,this.collections=e.collections,this.preinitOptions=t}users;collections;preinitOptions;collection;null;#e=!1;async preinit(){if(!this.#e){this.#e=!0;let{schema:e,indexes:t,null:s}=this.preinitOptions;e&&(e.required&&f(e.required,R.required),e.properties&&u(e,Object.keys(R.properties)));let i={...R,...e,required:[...R.required,...e?.required??[]],properties:{...R.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("orgs",{jsonSchema:i}),{deleteOne:xe,deleteMany:xe}),this.collection.ensureIndexes([...De,...t??[]]),this.null=Object.assign(new h(this,{...s,_id:"",title:"",note:"",owners:[],createdAt:Date.now()}),{_id:null,ownerIds:new q,ownerOrgs:new I,ownerUsers:new I,slaveOrgs:new I});for(let r of await this.collection.find().toArray())this.load(r);delete this.preinitOptions}}#t=!1;init(){this.#t||(this.#t=!0,this.update(),this.collection.changeListeners.add(e=>{switch(e.operationType){case"insert":{let t=new h(this,e.fullDocument);this.users.emit("orgs-org-update",t,e);break}case"replace":this.get(e.documentKey._id)?.update(e.fullDocument,e);break;case"update":this.get(e.documentKey._id)?.update(e.updateDescription.updatedFields,e);break;case"delete":this.get(e.documentKey._id)?.delete(),this.users.emit("orgs-org-update",null,e)}}))}load(e){new h(this,e)}#i(e,t){t=[e,...t];for(let s of e.ownerOrgs){this.#i(s,t);for(let i of t)s.slaveOrgs.add(i)}}sorted=[];update(){let e=[...this.values()],t=[];for(let s of e){s.ownerOrgs.clear(),s.ownerUsers.clear(),s.slaveOrgs.clear();for(let i of s.ownerIds){let r=this.get(i);if(r)s.ownerOrgs.add(r);else{let n=this.users.get(i);n&&s.ownerUsers.add(n)}}!s.ownerOrgs.size&&s._id&&t.push(s)}for(let s of e)e.some(i=>i.ownerOrgs.has(s))||this.#i(s,[]);t.sort(this.#s);for(let s of e)ge(s.slaveOrgs,this.#s);for(let s=0;s<t.length;s++){let i=t[s];for(let r of[...i.slaveOrgs].reverse())if(r.ownerOrgs.has(i)){let n=t.indexOf(r);~n&&(t.splice(n,1),s--),t.splice(s+1,0,r)}}for(let s=0,{length:i}=t;s<i;)t[s]._o=s++;this.sorted=t,this.users.emit("orgs-update"),this.users.isInited&&(this.users.updateDebounced.clear(),this.users.update())}#s(e,t){return t.slaveOrgs.size-e.slaveOrgs.size||(e.title>t.title?1:e.title<t.title?-1:0)}updateDebounced=m(this.update,250);create({title:e,note:t,...s},i){return this.collection.insertOne({_id:Ie(),title:e??"",note:t??"",owners:i?[i]:[],...u(s,["_id","owners"]),createdAt:Date.now()})}async updateOrg(e,t,s){let i=this.get(e);return i?(t.owners&&(t.owners=this.users.sortIds(ye(s?M(i.ownerIds,s.slaveIds):[],M(t.owners,[e,...x(i.slaveOrgs)])))),await this.collection.updateOne({_id:e},{$set:t}),!0):!1}deleteOrg(e){let t=typeof e=="string"?e:e._id;return this.collection.bulkWrite([{updateMany:{filter:{owners:t},update:{$pullAll:{owners:[t]}}}},{deleteOne:{filter:{_id:t}}}])}replaceMap=new Map;replaceHandlers=new Set;async replace(e){let t=this.replaceMap.get(e)??null;t&&this.replaceMap.delete(e);for(let s of this.replaceHandlers)await s(e,t)}};import we from"node:crypto";var j={required:["_id","user","remoteAddress","isOnline","createdAt","prolongedAt","expiresAt"],properties:{_id:{bsonType:"string",pattern:c.sessionId.source},user:{bsonType:"string",pattern:c._id.source},userAgent:{bsonType:"string",maxLength:4096},remoteAddress:{bsonType:"string",pattern:c.ip.source},isOnline:{bsonType:"bool"},createdAt:{bsonType:"number"},prolongedAt:{bsonType:"number"},expiresAt:{bsonType:"date"}}};var T=class{constructor(e,t){let s=e.users.get(t.user);s?(this.#e=e,this._id=t._id,this.#e.set(this._id,this),this.user=s,this.user.sessions.add(this),this.#e.users.bySessionId.set(this._id,this.user),this.update(t)):e.collection.deleteOne({_id:t._id})}_id;user;isOnline=!1;userAgent;remoteAddress;createdAt;prolongedAt;expiresAt;#e;update({_id:e,user:t,isOnline:s,...i}){s!==void 0&&this.isOnline!==s&&(this.isOnline=s,this.#e.isInited&&this.user.isOnline!==this.isOnline&&this.user.updateIsOnline()),Object.assign(this,i)}prolong({_id:e,user:t,...s}){let i=Date.now();return s.prolongedAt=i,s.expiresAt=new Date(i+this.#e.collection.expireAfterSeconds*1e3),this.update(s),this.#e.collection.updateOne({_id:this._id},{$set:s})}offline(){let e={isOnline:!1};return this.update(e),this.#e.collection.updateOne({_id:this._id},{$set:e})}delete(){this.#e.delete(this._id),this.user.sessions.delete(this),this.#e.users.bySessionId.delete(this._id),this.#e.users.emit("session-delete",this),this.isOnline&&this.user.updateIsOnline()}};var re=3600*24*7,Pe=[[{user:1}],[{expiresAt:1},{expireAfterSeconds:re}]],z=class extends Map{constructor(e,t={}){super(),this.users=e,this.collections=e.collections,this.initOptions=t}users;collections;initOptions;collection;isInited=!1;async init(){if(!this.isInited){this.isInited=!0;let{schema:e,indexes:t}=this.initOptions;e&&(e.required&&f(e.required,j.required),e.properties&&u(e,Object.keys(j.properties)));let s={...j,...e,required:[...j.required,...e?.required??[]],properties:{...j.properties,...e?.properties}};this.collection=Object.assign(await this.collections.ensure("sessions",{jsonSchema:s}),{expireAfterSeconds:re}),this.collection.ensureIndexes([...Pe,...t??[]]),await this.collection.updateMany({isOnline:!0},{$set:{isOnline:!1}});for(let i of await this.collection.find().toArray())this.load(i);this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":this.has(i.documentKey._id)||new T(this,i.fullDocument),this.users.get(i.fullDocument.user)?.trimSessions();break;case"replace":this.get(i.documentKey._id)?.update(i.fullDocument);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields);break;case"delete":this.get(i.documentKey._id)?.delete()}}),delete this.initOptions}}uid(){let e;do e=`${we.randomBytes(N(8,16)).toString("hex")}$${we.randomBytes(N(8,16)).toString("hex")}`;while(this.has(e));return e}load(e){new T(this,e)}async create(e,t){let s=Date.now(),i={userAgent:"",remoteAddress:"127.0.0.1",isOnline:!0,...t,_id:this.uid(),user:e._id,createdAt:s,prolongedAt:s,expiresAt:new Date(s+re*1e3)},r=new T(this,i);return await this.collection.insertOne(i),r}async destroySession(e){let{deletedCount:t}=await this.collection.deleteOne({_id:e});return!!t}};import{Binary as Re}from"insite-db";var Oe={required:["_id","type","size","ts","data"],properties:{_id:{bsonType:"string",pattern:c._id.source},type:{bsonType:"string",maxLength:256},size:{bsonType:"number"},ts:{bsonType:"string",maxLength:10},data:{bsonType:"binData"}},additionalProperties:!1};var H=class{constructor(e){this.users=e,this.collections=e.collections}TYPES_ACCEPTED=["image/webp"];MAX_SIZE=1024*512;users;collections;collection;#e=!1;async init(){this.#e||(this.#e=!0,this.collection=await this.collections.ensure("users.avatars",{jsonSchema:Oe}))}async save(e,t,s){let i=Re.createFromBase64(s.slice(s.indexOf(","))),r=Date.now().toString(36);await Promise.all([this.collection.replaceOne({_id:e},{type:t,size:i.length(),ts:r,data:i},{upsert:!0}),this.users.collection.updateOne({_id:e},{$set:{avatar:r}})])}async deleteAvatar(e){let[{deletedCount:t}]=await Promise.all([this.collection.deleteOne({_id:e}),this.users.collection.updateOne({_id:e},{$set:{avatar:null}})]);return!!t}};var U={required:["_id","email","password","roles","name","org","job","createdAt"],properties:{_id:{bsonType:"string",pattern:c._id.source},email:{bsonType:"string",pattern:c.email.source},password:{bsonType:"string",pattern:c.argon2.source},roles:{bsonType:"array",uniqueItems:!0,items:{bsonType:"string",pattern:c.role.source},additionalItems:!1},name:{bsonType:"object",required:["first","middle","last"],properties:{first:{bsonType:"string",maxLength:512},middle:{bsonType:"string",maxLength:512},last:{bsonType:"string",maxLength:512}},additionalProperties:!1},org:{oneOf:[{bsonType:"string",pattern:c._id.source},{bsonType:"null"}]},job:{bsonType:"string",maxLength:512},avatar:{oneOf:[{bsonType:"string",maxLength:10},{bsonType:"null"}]},createdAt:{bsonType:"number"}},additionalProperties:!1};var oe=new Map,ne=new Map,je=process.env.INSITE_STATIC_URL??"http://localhost:8080",w=class{constructor(e,t){this.#e=e,this._id=t._id,e.set(this._id,this),this.update(t),e.isInited&&e.emit("user-create",this)}_id;email;name={first:"",middle:"",last:""};initials="";displayLabel="";org;job="";avatar=null;avatarUrl=null;#e;isUser=!0;isRoot;roles=new Set;ownRoles=[];ownRoleIds=[];slaveRoles=new Set;slaveRoleIds=[];abilities={};slaveOrgs=new Set;slaveUsers=new Set;slaves=new Set;slaveIds=[];permissiveIds=[];sessions=new Set;isOnline=!1;update({_id:e,name:t,email:s,roles:i,org:r,avatar:n,...l}){Object.assign(this,l);let a;s&&this.email!==s&&(this.#e.byEmail.delete(this.email),this.email=s,this.#e.byEmail.set(s,this),a=!0);let p,g;t&&(this.name.first!==t.first||this.name.middle!==t.middle||this.name.last!==t.last)&&(g=this.name.last!==t.last,this.name={first:t.first??"",middle:t.middle??"",last:t.last??""},this.initials=((t.first?.[0]??"")+(t.last?.[0]??"")||this.email[0]).toUpperCase(),p=!0),(a||p)&&(this.displayLabel=`${this.name.first} ${this.name.last}`.trim()||this.name.middle||this.email);let y;if(i){this.ownRoleIds=i;let O=this.ownRoleIds.join(",");O!==oe.get(this._id)&&(oe.set(this._id,O),this.updateRoles(),y=!0)}let d;r!==void 0&&this.org?._id!==r&&(this.org?.users.delete(this),this.org=r&&this.#e.orgs.get(r)||this.#e.orgs.null,this.org.users.add(this),d=!0),n!==void 0&&this.avatar!==n&&(this.avatar=n,this.avatarUrl=n&&`${je}/avatars/${this._id}-${n}.webp`),y||d?(this.updatePermissions(),g&&(this.#e.isSortRequired=!0),this.#e.isInited&&this.#e.updateDebounced()):g&&this.#e.sortDebounced()}updateRoles(){if(this.#e.isInited){this.ownRoles=[],this.roles.clear(),this.slaveRoles.clear(),k(this.abilities);for(let e of this.ownRoleIds){let t=this.#e.roles.get(e);if(t){this.ownRoles.push(t),this.roles.add(t);for(let s of t.involves)this.roles.add(s),this.slaveRoles.add(s);this.slaveRoleIds=x(this.slaveRoles),this.#e.abilities.merge(this.abilities,t.abilities)}}this.roles.has(this.#e.roles.root)&&(this.isRoot=!0),this.trimSessions()}}updatePermissions(){if(this.#e.isInited){this.slaveOrgs.clear(),this.slaveUsers.clear(),this.slaves.clear();let e=new Set;for(let i of this.#e.orgs.sorted)if((i.ownerUsers.has(this)||this.isRoot)&&!this.slaveOrgs.has(i)){this.slaveOrgs.add(i),this.slaves.add(i),e.add(i._id);for(let r of i.slaveOrgs)this.slaveOrgs.add(r),this.slaves.add(r),e.add(r._id)}for(let i of new Set([this.org,...this.slaveOrgs,this.#e.orgs.null]))for(let r of i.users)r!==this&&(ue(this.slaveRoles,r.ownRoles)||!r.ownRoles.length)&&(this.slaveUsers.add(r),this.slaves.add(r),e.add(r._id));this.slaveIds=[...e];let t=[];if(this.org._id){t.push(this.org._id);for(let i of this.org.slaveOrgs)this.slaveOrgs.has(i)||t.push(i._id)}this.permissiveIds=[...t,this._id,...e];let s=[this.permissiveIds.join(","),this.ownRoleIds.join(","),JSON.stringify(this.abilities),this.slaveRoleIds.join(",")].join(`
3
+ `);s!==ne.get(this._id)&&(ne.set(this._id,s),this.#e.emit("user-permissions-change",this))}}trimSessions(){let e=this.abilities.login?.sessionsLimit??0;return this.sessions.size>e?this.#e.sessions.collection.deleteMany({_id:{$in:x([...this.sessions].sort((t,s)=>t.expiresAt.valueOf()-s.expiresAt.valueOf()).slice(0,this.sessions.size-e))}}):null}updateIsOnline=m(()=>{let e=!1;for(let t of this.sessions)if(t.isOnline){e=!0;break}this.isOnline!==e&&(this.isOnline=e,this.#e.emit("user-is-online",this))},500);delete(){this.org.users.delete(this),this.#e.delete(this._id),this.#e.byEmail.delete(this.email),be(this.#e.sorted,this),oe.delete(this._id),ne.delete(this._id),this.#e.replace(this._id),this.#e.updateDebounced()}};var $e=[[{email:1},{unique:!0}],[{org:1}]],le=class o extends Map{constructor(e,t){super();let s=new Te;this._events=s._events,this._eventsCount=s._eventsCount,this.emit=s.emit,this.on=s.on,this.once=s.once,this.addListener=s.addListener,this.off=s.off,this.removeListener=s.removeListener,this.collections=e,this.abilities=new B(t.abilities),this.initOptions=t,this.init()}_events;_eventsCount;emit;on;once;addListener;off;removeListener;initOptions;collections;abilities;collection;roles;sessions;orgs;avatars;byEmail=new Map;bySessionId=new Map;sorted=[];isSortRequired=!1;#e=!1;async preinit(){if(!this.#e){this.#e=!0;let{indexes:e,schema:t,initialRoot:s}=this.initOptions;t&&(t.required&&f(t.required,U.required),t.properties&&u(t,Object.keys(U.properties)));let i={...U,...t,required:[...U.required,...t?.required??[]],properties:{...U.properties,...t?.properties}};this.collection=await this.collections.ensure("users",{jsonSchema:i}),this.collection.ensureIndexes([...$e,...e??[]]),await this.collection.countDocuments({roles:"root"})||await this.create({email:process.env.INSITE_ROOT_EMAIL??"insite@root.email",password:process.env.INSITE_ROOT_PASSWORD??"inSiteRootPassword",name:{first:"Root"},job:"Root",...s,roles:["root"],org:null});for(let r of await this.collection.find().toArray())this.load(r)}}isInited=!1;async init(){if(!this.isInited){this.isInited=!0;let{roles:e,orgs:t,sessions:s}=this.initOptions;this.roles=new F(this,e),this.orgs=new K(this,t),this.sessions=new z(this,s),this.avatars=new H(this),await this.roles.init(),await this.orgs.preinit(),await this.preinit(),await this.orgs.init(),await this.avatars.init(),this.update(!0),this.collection.changeListeners.add(i=>{switch(i.operationType){case"insert":new w(this,i.fullDocument);break;case"replace":this.get(i.documentKey._id)?.update(i.fullDocument);break;case"update":this.get(i.documentKey._id)?.update(i.updateDescription.updatedFields);break;case"delete":this.get(i.documentKey._id)?.delete()}}),await this.sessions.init(),delete this.initOptions,this.#t.resolve(this)}}load(e){new w(this,e)}sort(){this.isSortRequired=!1,this.sorted=[...this.values()].sort((e,t)=>e.name.last>t.name.last?1:e.name.last<t.name.last?-1:0)}sortDebounced=m(()=>this.sort(),250);update(e){if(e)for(let t of this.values())t.updateRoles();for(let t of this.values())t.updatePermissions();this.isSortRequired&&this.sort()}updateDebounced=m(()=>this.update(),250);#t=new W;whenReady(){return this.#t}async create({email:e,password:t,roles:s,name:i,org:r,job:n,...l}){if(this.byEmail.has(e))throw new Error("User exists");return await this.collection.insertOne({_id:Ue(),email:e,password:await C.hash(t),roles:this.isInited?this.roles.cleanUpIds(s):s,name:{first:i.first??"",middle:i.middle??"",last:i.last??""},org:r??null,job:n??"",...u(l,["_id"]),createdAt:Date.now()}),!0}async updateUser(e,t,s){let i=this.get(e);return i?(t.roles&&(t.roles=i.isRoot?["root"]:this.roles.cleanUpIds(s?M(i.ownRoleIds,s.slaveRoleIds).concat(t.roles):t.roles)),await this.collection.updateOne({_id:e},{$set:t}),!0):!1}async changePassword(e,t){if(!this.has(e))throw new Error("usernotfound");if(!t)throw new Error("emptypasswordisnotallowed");await Promise.all([this.collection.updateOne({_id:e},{$set:{password:await C.hash(t)}}),this.sessions.collection.deleteMany({user:e})])}async login(e,t,s){let i=this.byEmail.get(e);if(!i)throw new Error("usernotfound");if(!await C.verify(i.password,t))throw new Error("incorrectpassword");if(!i.abilities.login)throw new Error("userisnotabletologin");return this.sessions.create(i,s)}logout(e){return e.delete(),this.sessions.collection.deleteOne({_id:e._id})}#i(e,t){return e instanceof w&&t instanceof w?e.name.last&&t.name.last?e.name.last>t.name.last?1:e.name.last<t.name.last?-1:0:!e.name.last&&!t.name.last?e.displayLabel>t.displayLabel?1:e.displayLabel<t.displayLabel?-1:0:e.name.last?-1:1:e instanceof h&&t instanceof h?e.title>t.title?1:e.title<t.title?-1:0:e instanceof h?-1:1}sortIds(e){return x(e.map(t=>this.get(t)||this.orgs.get(t)).filter(Boolean).sort(this.#i))}replaceMap=new Map;replaceHandlers=new Set;async replace(e){let t=this.replaceMap.get(e)??null;t&&this.replaceMap.delete(e);for(let s of this.replaceHandlers)await s(e,t)}async deleteUser(e){let{deletedCount:t}=await this.collection.deleteOne({_id:e});return!!t}static init(e,t){return new o(e,t).whenReady()}};export{Z as AbilityError,ee as RolesError,ie as SubordinationError,le as Users};
4
4
  //# sourceMappingURL=index.js.map