@credo-ts/tenants 0.6.1-pr-2091-20241119140918 → 0.6.1

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 (126) hide show
  1. package/build/TenantAgent.d.mts +12 -0
  2. package/build/TenantAgent.d.mts.map +1 -0
  3. package/build/TenantAgent.mjs +23 -0
  4. package/build/TenantAgent.mjs.map +1 -0
  5. package/build/TenantsApi.d.mts +37 -0
  6. package/build/TenantsApi.d.mts.map +1 -0
  7. package/build/TenantsApi.mjs +107 -0
  8. package/build/TenantsApi.mjs.map +1 -0
  9. package/build/TenantsApiOptions.d.mts +19 -0
  10. package/build/TenantsApiOptions.d.mts.map +1 -0
  11. package/build/TenantsModule.d.mts +23 -0
  12. package/build/TenantsModule.d.mts.map +1 -0
  13. package/build/TenantsModule.mjs +40 -0
  14. package/build/TenantsModule.mjs.map +1 -0
  15. package/build/TenantsModuleConfig.d.mts +35 -0
  16. package/build/TenantsModuleConfig.d.mts.map +1 -0
  17. package/build/TenantsModuleConfig.mjs +18 -0
  18. package/build/TenantsModuleConfig.mjs.map +1 -0
  19. package/build/_virtual/_@oxc-project_runtime@0.99.0/helpers/decorate.mjs +10 -0
  20. package/build/_virtual/_@oxc-project_runtime@0.99.0/helpers/decorateMetadata.mjs +7 -0
  21. package/build/_virtual/_@oxc-project_runtime@0.99.0/helpers/decorateParam.mjs +9 -0
  22. package/build/context/TenantAgentContextProvider.d.mts +52 -0
  23. package/build/context/TenantAgentContextProvider.d.mts.map +1 -0
  24. package/build/context/TenantAgentContextProvider.mjs +149 -0
  25. package/build/context/TenantAgentContextProvider.mjs.map +1 -0
  26. package/build/context/TenantSessionCoordinator.d.mts +71 -0
  27. package/build/context/TenantSessionCoordinator.d.mts.map +1 -0
  28. package/build/context/TenantSessionCoordinator.mjs +186 -0
  29. package/build/context/TenantSessionCoordinator.mjs.map +1 -0
  30. package/build/context/TenantSessionMutex.mjs +66 -0
  31. package/build/context/TenantSessionMutex.mjs.map +1 -0
  32. package/build/index.d.mts +10 -0
  33. package/build/index.mjs +9 -0
  34. package/build/models/TenantConfig.d.mts +7 -0
  35. package/build/models/TenantConfig.d.mts.map +1 -0
  36. package/build/repository/TenantRecord.d.mts +36 -0
  37. package/build/repository/TenantRecord.d.mts.map +1 -0
  38. package/build/repository/TenantRecord.mjs +29 -0
  39. package/build/repository/TenantRecord.mjs.map +1 -0
  40. package/build/repository/TenantRepository.d.mts +11 -0
  41. package/build/repository/TenantRepository.d.mts.map +1 -0
  42. package/build/repository/TenantRepository.mjs +25 -0
  43. package/build/repository/TenantRepository.mjs.map +1 -0
  44. package/build/repository/TenantRoutingRecord.d.mts +28 -0
  45. package/build/repository/TenantRoutingRecord.d.mts.map +1 -0
  46. package/build/repository/TenantRoutingRecord.mjs +28 -0
  47. package/build/repository/TenantRoutingRecord.mjs.map +1 -0
  48. package/build/repository/TenantRoutingRepository.d.mts +11 -0
  49. package/build/repository/TenantRoutingRepository.d.mts.map +1 -0
  50. package/build/repository/TenantRoutingRepository.mjs +25 -0
  51. package/build/repository/TenantRoutingRepository.mjs.map +1 -0
  52. package/build/repository/index.d.mts +4 -0
  53. package/build/repository/index.mjs +4 -0
  54. package/build/services/TenantRecordService.d.mts +26 -0
  55. package/build/services/TenantRecordService.d.mts.map +1 -0
  56. package/build/services/TenantRecordService.mjs +63 -0
  57. package/build/services/TenantRecordService.mjs.map +1 -0
  58. package/build/services/index.d.mts +1 -0
  59. package/build/services/index.mjs +1 -0
  60. package/build/updates/0.4-0.5/index.d.mts +7 -0
  61. package/build/updates/0.4-0.5/index.d.mts.map +1 -0
  62. package/build/updates/0.4-0.5/index.mjs +10 -0
  63. package/build/updates/0.4-0.5/index.mjs.map +1 -0
  64. package/build/updates/0.4-0.5/tenantRecord.mjs +28 -0
  65. package/build/updates/0.4-0.5/tenantRecord.mjs.map +1 -0
  66. package/package.json +15 -14
  67. package/build/TenantAgent.d.ts +0 -8
  68. package/build/TenantAgent.js +0 -25
  69. package/build/TenantAgent.js.map +0 -1
  70. package/build/TenantsApi.d.ts +0 -25
  71. package/build/TenantsApi.js +0 -117
  72. package/build/TenantsApi.js.map +0 -1
  73. package/build/TenantsApiOptions.d.ts +0 -14
  74. package/build/TenantsApiOptions.js +0 -3
  75. package/build/TenantsApiOptions.js.map +0 -1
  76. package/build/TenantsModule.d.ts +0 -19
  77. package/build/TenantsModule.js +0 -47
  78. package/build/TenantsModule.js.map +0 -1
  79. package/build/TenantsModuleConfig.d.ts +0 -31
  80. package/build/TenantsModuleConfig.js +0 -20
  81. package/build/TenantsModuleConfig.js.map +0 -1
  82. package/build/context/TenantAgentContextProvider.d.ts +0 -40
  83. package/build/context/TenantAgentContextProvider.js +0 -175
  84. package/build/context/TenantAgentContextProvider.js.map +0 -1
  85. package/build/context/TenantSessionCoordinator.d.ts +0 -54
  86. package/build/context/TenantSessionCoordinator.js +0 -195
  87. package/build/context/TenantSessionCoordinator.js.map +0 -1
  88. package/build/context/TenantSessionMutex.d.ts +0 -29
  89. package/build/context/TenantSessionMutex.js +0 -84
  90. package/build/context/TenantSessionMutex.js.map +0 -1
  91. package/build/context/types.d.ts +0 -0
  92. package/build/context/types.js +0 -2
  93. package/build/context/types.js.map +0 -1
  94. package/build/index.d.ts +0 -5
  95. package/build/index.js +0 -24
  96. package/build/index.js.map +0 -1
  97. package/build/models/TenantConfig.d.ts +0 -4
  98. package/build/models/TenantConfig.js +0 -3
  99. package/build/models/TenantConfig.js.map +0 -1
  100. package/build/repository/TenantRecord.d.ts +0 -33
  101. package/build/repository/TenantRecord.js +0 -32
  102. package/build/repository/TenantRecord.js.map +0 -1
  103. package/build/repository/TenantRepository.d.ts +0 -7
  104. package/build/repository/TenantRepository.js +0 -32
  105. package/build/repository/TenantRepository.js.map +0 -1
  106. package/build/repository/TenantRoutingRecord.d.ts +0 -26
  107. package/build/repository/TenantRoutingRecord.js +0 -24
  108. package/build/repository/TenantRoutingRecord.js.map +0 -1
  109. package/build/repository/TenantRoutingRepository.d.ts +0 -7
  110. package/build/repository/TenantRoutingRepository.js +0 -34
  111. package/build/repository/TenantRoutingRepository.js.map +0 -1
  112. package/build/repository/index.d.ts +0 -4
  113. package/build/repository/index.js +0 -21
  114. package/build/repository/index.js.map +0 -1
  115. package/build/services/TenantRecordService.d.ts +0 -17
  116. package/build/services/TenantRecordService.js +0 -78
  117. package/build/services/TenantRecordService.js.map +0 -1
  118. package/build/services/index.d.ts +0 -1
  119. package/build/services/index.js +0 -18
  120. package/build/services/index.js.map +0 -1
  121. package/build/updates/0.4-0.5/index.d.ts +0 -2
  122. package/build/updates/0.4-0.5/index.js +0 -8
  123. package/build/updates/0.4-0.5/index.js.map +0 -1
  124. package/build/updates/0.4-0.5/tenantRecord.d.ts +0 -10
  125. package/build/updates/0.4-0.5/tenantRecord.js +0 -26
  126. package/build/updates/0.4-0.5/tenantRecord.js.map +0 -1
@@ -1,31 +0,0 @@
1
- /**
2
- * TenantsModuleConfigOptions defines the interface for the options of the TenantsModuleConfig class.
3
- * This can contain optional parameters that have default values in the config class itself.
4
- */
5
- export interface TenantsModuleConfigOptions {
6
- /**
7
- * Maximum number of concurrent tenant sessions that can be active at the same time. Defaults to
8
- * 100 concurrent sessions. The default is low on purpose, to make sure deployments determine their own
9
- * session limit based on the hardware and usage of the tenants module. Use `Infinity` to allow unlimited
10
- * concurrent sessions.
11
- *
12
- * @default 100
13
- */
14
- sessionLimit?: number;
15
- /**
16
- * Timeout in milliseconds for acquiring a tenant session. If the {@link TenantsModuleConfigOptions.maxNumberOfSessions} is reached and
17
- * a tenant sessions couldn't be acquired within the specified timeout, an error will be thrown and the session creation will be aborted.
18
- * Use `Infinity` to disable the timeout.
19
- *
20
- * @default 1000
21
- */
22
- sessionAcquireTimeout?: number;
23
- }
24
- export declare class TenantsModuleConfig {
25
- private options;
26
- constructor(options?: TenantsModuleConfigOptions);
27
- /** See {@link TenantsModuleConfigOptions.sessionLimit} */
28
- get sessionLimit(): number;
29
- /** See {@link TenantsModuleConfigOptions.sessionAcquireTimeout} */
30
- get sessionAcquireTimeout(): number;
31
- }
@@ -1,20 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.TenantsModuleConfig = void 0;
4
- class TenantsModuleConfig {
5
- constructor(options) {
6
- this.options = options !== null && options !== void 0 ? options : {};
7
- }
8
- /** See {@link TenantsModuleConfigOptions.sessionLimit} */
9
- get sessionLimit() {
10
- var _a;
11
- return (_a = this.options.sessionLimit) !== null && _a !== void 0 ? _a : 100;
12
- }
13
- /** See {@link TenantsModuleConfigOptions.sessionAcquireTimeout} */
14
- get sessionAcquireTimeout() {
15
- var _a;
16
- return (_a = this.options.sessionAcquireTimeout) !== null && _a !== void 0 ? _a : 1000;
17
- }
18
- }
19
- exports.TenantsModuleConfig = TenantsModuleConfig;
20
- //# sourceMappingURL=TenantsModuleConfig.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"TenantsModuleConfig.js","sourceRoot":"","sources":["../src/TenantsModuleConfig.ts"],"names":[],"mappings":";;;AAyBA,MAAa,mBAAmB;IAG9B,YAAmB,OAAoC;QACrD,IAAI,CAAC,OAAO,GAAG,OAAO,aAAP,OAAO,cAAP,OAAO,GAAI,EAAE,CAAA;IAC9B,CAAC;IAED,0DAA0D;IAC1D,IAAW,YAAY;;QACrB,OAAO,MAAA,IAAI,CAAC,OAAO,CAAC,YAAY,mCAAI,GAAG,CAAA;IACzC,CAAC;IAED,mEAAmE;IACnE,IAAW,qBAAqB;;QAC9B,OAAO,MAAA,IAAI,CAAC,OAAO,CAAC,qBAAqB,mCAAI,IAAI,CAAA;IACnD,CAAC;CACF;AAhBD,kDAgBC"}
@@ -1,40 +0,0 @@
1
- import type { TenantRecord } from '../repository';
2
- import type { AgentContextProvider, UpdateAssistantUpdateOptions } from '@credo-ts/core';
3
- import { AgentContext, EventEmitter, Logger } from '@credo-ts/core';
4
- import { TenantRecordService } from '../services';
5
- import { TenantSessionCoordinator } from './TenantSessionCoordinator';
6
- export declare class TenantAgentContextProvider implements AgentContextProvider {
7
- private tenantRecordService;
8
- private rootAgentContext;
9
- private eventEmitter;
10
- private logger;
11
- private tenantSessionCoordinator;
12
- constructor(tenantRecordService: TenantRecordService, rootAgentContext: AgentContext, eventEmitter: EventEmitter, tenantSessionCoordinator: TenantSessionCoordinator, logger: Logger);
13
- getAgentContextForContextCorrelationId(contextCorrelationId: string): Promise<AgentContext>;
14
- getContextForInboundMessage(inboundMessage: unknown, options?: {
15
- contextCorrelationId?: string;
16
- }): Promise<AgentContext>;
17
- endSessionForAgentContext(agentContext: AgentContext): Promise<void>;
18
- private getRecipientKeysFromEncryptedMessage;
19
- private registerRecipientKeyForTenant;
20
- private listenForRoutingKeyCreatedEvents;
21
- /**
22
- * Method to allow updating the tenant storage, this method can be called from the TenantsApi
23
- * to update the storage for a tenant manually
24
- */
25
- updateTenantStorage(tenantRecord: TenantRecord, updateOptions?: UpdateAssistantUpdateOptions): Promise<void>;
26
- /**
27
- * Handle the case where the tenant storage is outdated. If auto-update is disabled we will throw an error
28
- * and not update the storage. If auto-update is enabled we will update the storage.
29
- *
30
- * When this method is called we can be sure that we are in the mutex runExclusive lock and thus other sessions
31
- * will not be able to open a session for this tenant until we're done.
32
- *
33
- * NOTE: We don't support multi-instance locking for now. That means you can only have a single instance open and
34
- * it will prevent multiple processes from updating the tenant storage at the same time. However if multi-instances
35
- * are used, we can't prevent multiple instances from updating the tenant storage at the same time.
36
- * In the future we can make the tenantSessionCoordinator an interface and allowing a instance-tenant-lock as well
37
- * as an tenant-lock (across all instances)
38
- */
39
- private _updateTenantStorage;
40
- }
@@ -1,175 +0,0 @@
1
- "use strict";
2
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
- return c > 3 && r && Object.defineProperty(target, key, r), r;
7
- };
8
- var __metadata = (this && this.__metadata) || function (k, v) {
9
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
- };
11
- var __param = (this && this.__param) || function (paramIndex, decorator) {
12
- return function (target, key) { decorator(target, key, paramIndex); }
13
- };
14
- Object.defineProperty(exports, "__esModule", { value: true });
15
- exports.TenantAgentContextProvider = void 0;
16
- const core_1 = require("@credo-ts/core");
17
- const TenantAgent_1 = require("../TenantAgent");
18
- const services_1 = require("../services");
19
- const TenantSessionCoordinator_1 = require("./TenantSessionCoordinator");
20
- let TenantAgentContextProvider = class TenantAgentContextProvider {
21
- constructor(tenantRecordService, rootAgentContext, eventEmitter, tenantSessionCoordinator, logger) {
22
- this.tenantRecordService = tenantRecordService;
23
- this.rootAgentContext = rootAgentContext;
24
- this.eventEmitter = eventEmitter;
25
- this.tenantSessionCoordinator = tenantSessionCoordinator;
26
- this.logger = logger;
27
- // Start listener for newly created routing keys, so we can register a mapping for each new key for the tenant
28
- this.listenForRoutingKeyCreatedEvents();
29
- }
30
- async getAgentContextForContextCorrelationId(contextCorrelationId) {
31
- // It could be that the root agent context is requested, in that case we return the root agent context
32
- if (contextCorrelationId === this.rootAgentContext.contextCorrelationId) {
33
- return this.rootAgentContext;
34
- }
35
- // TODO: maybe we can look at not having to retrieve the tenant record if there's already a context available.
36
- const tenantRecord = await this.tenantRecordService.getTenantById(this.rootAgentContext, contextCorrelationId);
37
- const shouldUpdate = !(0, core_1.isStorageUpToDate)(tenantRecord.storageVersion);
38
- // If the tenant storage is not up to date, and autoUpdate is disabled we throw an error
39
- if (shouldUpdate && !this.rootAgentContext.config.autoUpdateStorageOnStartup) {
40
- throw new core_1.CredoError(`Current agent storage for tenant ${tenantRecord.id} is not up to date. ` +
41
- `To prevent the tenant state from getting corrupted the tenant initialization is aborted. ` +
42
- `Make sure to update the tenant storage (currently at ${tenantRecord.storageVersion}) to the latest version (${core_1.UpdateAssistant.frameworkStorageVersion}). ` +
43
- `You can also downgrade your version of Credo.`);
44
- }
45
- const agentContext = await this.tenantSessionCoordinator.getContextForSession(tenantRecord, {
46
- runInMutex: shouldUpdate ? (agentContext) => this._updateTenantStorage(tenantRecord, agentContext) : undefined,
47
- });
48
- this.logger.debug(`Created tenant agent context for tenant '${contextCorrelationId}'`);
49
- return agentContext;
50
- }
51
- async getContextForInboundMessage(inboundMessage, options) {
52
- this.logger.debug('Getting context for inbound message in tenant agent context provider', {
53
- contextCorrelationId: options === null || options === void 0 ? void 0 : options.contextCorrelationId,
54
- });
55
- let tenantId = options === null || options === void 0 ? void 0 : options.contextCorrelationId;
56
- let recipientKeys = [];
57
- if (!tenantId && (0, core_1.isValidJweStructure)(inboundMessage)) {
58
- this.logger.trace("Inbound message is a JWE, extracting tenant id from JWE's protected header");
59
- recipientKeys = this.getRecipientKeysFromEncryptedMessage(inboundMessage);
60
- this.logger.trace(`Found ${recipientKeys.length} recipient keys in JWE's protected header`);
61
- // FIXME: what if there are multiple recipients in the same agent? If we receive the messages twice we will process it for
62
- // the first found recipient multiple times. This is however a case I've never seen before and will add quite some complexity
63
- // to resolve. I think we're fine to ignore this case for now.
64
- for (const recipientKey of recipientKeys) {
65
- const tenantRoutingRecord = await this.tenantRecordService.findTenantRoutingRecordByRecipientKey(this.rootAgentContext, recipientKey);
66
- if (tenantRoutingRecord) {
67
- this.logger.debug(`Found tenant routing record for recipient key ${recipientKeys[0].fingerprint}`, {
68
- tenantId: tenantRoutingRecord.tenantId,
69
- });
70
- tenantId = tenantRoutingRecord.tenantId;
71
- break;
72
- }
73
- }
74
- }
75
- if (!tenantId) {
76
- this.logger.error("Couldn't determine tenant id for inbound message. Unable to create context", {
77
- inboundMessage,
78
- recipientKeys: recipientKeys.map((key) => key.fingerprint),
79
- });
80
- throw new core_1.CredoError("Couldn't determine tenant id for inbound message. Unable to create context");
81
- }
82
- const agentContext = await this.getAgentContextForContextCorrelationId(tenantId);
83
- return agentContext;
84
- }
85
- async endSessionForAgentContext(agentContext) {
86
- await this.tenantSessionCoordinator.endAgentContextSession(agentContext);
87
- }
88
- getRecipientKeysFromEncryptedMessage(jwe) {
89
- const jweProtected = core_1.JsonEncoder.fromBase64(jwe.protected);
90
- if (!Array.isArray(jweProtected.recipients))
91
- return [];
92
- const recipientKeys = [];
93
- for (const recipient of jweProtected.recipients) {
94
- // Check if recipient.header.kid is a string
95
- if ((0, core_1.isJsonObject)(recipient) && (0, core_1.isJsonObject)(recipient.header) && typeof recipient.header.kid === 'string') {
96
- // This won't work with other key types, we should detect what the encoding is of kid, and based on that
97
- // determine how we extract the key from the message
98
- const key = core_1.Key.fromPublicKeyBase58(recipient.header.kid, core_1.KeyType.Ed25519);
99
- recipientKeys.push(key);
100
- }
101
- }
102
- return recipientKeys;
103
- }
104
- async registerRecipientKeyForTenant(tenantId, recipientKey) {
105
- this.logger.debug(`Registering recipient key ${recipientKey.fingerprint} for tenant ${tenantId}`);
106
- const tenantRecord = await this.tenantRecordService.getTenantById(this.rootAgentContext, tenantId);
107
- await this.tenantRecordService.addTenantRoutingRecord(this.rootAgentContext, tenantRecord.id, recipientKey);
108
- }
109
- listenForRoutingKeyCreatedEvents() {
110
- this.logger.debug('Listening for routing key created events in tenant agent context provider');
111
- this.eventEmitter.on(core_1.RoutingEventTypes.RoutingCreatedEvent, async (event) => {
112
- const contextCorrelationId = event.metadata.contextCorrelationId;
113
- const recipientKey = event.payload.routing.recipientKey;
114
- // We don't want to register the key if it's for the root agent context
115
- if (contextCorrelationId === this.rootAgentContext.contextCorrelationId)
116
- return;
117
- this.logger.debug(`Received routing key created event for tenant ${contextCorrelationId}, registering recipient key ${recipientKey.fingerprint} in base wallet`);
118
- await this.registerRecipientKeyForTenant(contextCorrelationId, recipientKey);
119
- });
120
- }
121
- /**
122
- * Method to allow updating the tenant storage, this method can be called from the TenantsApi
123
- * to update the storage for a tenant manually
124
- */
125
- async updateTenantStorage(tenantRecord, updateOptions) {
126
- const agentContext = await this.tenantSessionCoordinator.getContextForSession(tenantRecord, {
127
- // runInMutex allows us to run the updateTenantStorage method in a mutex lock
128
- // prevent other sessions from being started while the update is in progress
129
- runInMutex: (agentContext) => this._updateTenantStorage(tenantRecord, agentContext, updateOptions),
130
- });
131
- // End sesion afterwards
132
- await agentContext.endSession();
133
- }
134
- /**
135
- * Handle the case where the tenant storage is outdated. If auto-update is disabled we will throw an error
136
- * and not update the storage. If auto-update is enabled we will update the storage.
137
- *
138
- * When this method is called we can be sure that we are in the mutex runExclusive lock and thus other sessions
139
- * will not be able to open a session for this tenant until we're done.
140
- *
141
- * NOTE: We don't support multi-instance locking for now. That means you can only have a single instance open and
142
- * it will prevent multiple processes from updating the tenant storage at the same time. However if multi-instances
143
- * are used, we can't prevent multiple instances from updating the tenant storage at the same time.
144
- * In the future we can make the tenantSessionCoordinator an interface and allowing a instance-tenant-lock as well
145
- * as an tenant-lock (across all instances)
146
- */
147
- async _updateTenantStorage(tenantRecord, agentContext, updateOptions) {
148
- var _a;
149
- try {
150
- // Update the tenant storage
151
- const tenantAgent = new TenantAgent_1.TenantAgent(agentContext);
152
- const updateAssistant = new core_1.UpdateAssistant(tenantAgent);
153
- await updateAssistant.initialize();
154
- await updateAssistant.update(Object.assign(Object.assign({}, updateOptions), { backupBeforeStorageUpdate: (_a = updateOptions === null || updateOptions === void 0 ? void 0 : updateOptions.backupBeforeStorageUpdate) !== null && _a !== void 0 ? _a : agentContext.config.backupBeforeStorageUpdate }));
155
- // Update the storage version in the tenant record
156
- tenantRecord.storageVersion = await updateAssistant.getCurrentAgentStorageVersion();
157
- const tenantRecordService = this.rootAgentContext.dependencyManager.resolve(services_1.TenantRecordService);
158
- await tenantRecordService.updateTenant(this.rootAgentContext, tenantRecord);
159
- }
160
- catch (error) {
161
- this.logger.error(`Error occurred while updating tenant storage for tenant ${tenantRecord.id}`, error);
162
- throw error;
163
- }
164
- }
165
- };
166
- exports.TenantAgentContextProvider = TenantAgentContextProvider;
167
- exports.TenantAgentContextProvider = TenantAgentContextProvider = __decorate([
168
- (0, core_1.injectable)(),
169
- __param(4, (0, core_1.inject)(core_1.InjectionSymbols.Logger)),
170
- __metadata("design:paramtypes", [services_1.TenantRecordService,
171
- core_1.AgentContext,
172
- core_1.EventEmitter,
173
- TenantSessionCoordinator_1.TenantSessionCoordinator, Object])
174
- ], TenantAgentContextProvider);
175
- //# sourceMappingURL=TenantAgentContextProvider.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"TenantAgentContextProvider.js","sourceRoot":"","sources":["../../src/context/TenantAgentContextProvider.ts"],"names":[],"mappings":"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"}
@@ -1,54 +0,0 @@
1
- import type { TenantRecord } from '../repository';
2
- import type { MutexInterface } from 'async-mutex';
3
- import { AgentContext, Logger } from '@credo-ts/core';
4
- import { TenantsModuleConfig } from '../TenantsModuleConfig';
5
- /**
6
- * Coordinates all agent context instance for tenant sessions.
7
- *
8
- * This class keeps a mapping of tenant ids (context correlation ids) to agent context sessions mapping. Each mapping contains the agent context,
9
- * the current session count and a mutex for making operations against the session mapping (opening / closing an agent context). The mutex ensures
10
- * we're not susceptible to race conditions where multiple calls to open/close an agent context are made at the same time. Even though JavaScript is
11
- * single threaded, promises can introduce race conditions as one process can stop and another process can be picked up.
12
- *
13
- * NOTE: the implementation doesn't yet cache agent context objects after they aren't being used for any sessions anymore. This means if a wallet is being used
14
- * often in a short time it will be opened/closed very often. This is an improvement to be made in the near future.
15
- */
16
- export declare class TenantSessionCoordinator {
17
- private rootAgentContext;
18
- private logger;
19
- private tenantAgentContextMapping;
20
- private sessionMutex;
21
- private tenantsModuleConfig;
22
- constructor(rootAgentContext: AgentContext, logger: Logger, tenantsModuleConfig: TenantsModuleConfig);
23
- getSessionCountForTenant(tenantId: string): number;
24
- /**
25
- * Get agent context to use for a session. If an agent context for this tenant does not exist yet
26
- * it will create it and store it for later use. If the agent context does already exist it will
27
- * be returned.
28
- *
29
- * @parm tenantRecord The tenant record for which to get the agent context
30
- */
31
- getContextForSession(tenantRecord: TenantRecord, { runInMutex, }?: {
32
- /** optional callback that will be run inside the mutex lock */
33
- runInMutex?: (agentContext: AgentContext) => Promise<void>;
34
- }): Promise<AgentContext>;
35
- /**
36
- * End a session for the provided agent context. It will decrease the session count for the agent context.
37
- * If the number of sessions is zero after the context for this session has been ended, the agent context will be closed.
38
- */
39
- endAgentContextSession(agentContext: AgentContext): Promise<void>;
40
- private hasTenantSessionMapping;
41
- private getTenantSessionsMapping;
42
- private mutexForTenant;
43
- private createAgentContext;
44
- private closeAgentContext;
45
- }
46
- interface TenantContextSessions {
47
- sessionCount: number;
48
- agentContext?: AgentContext;
49
- mutex: MutexInterface;
50
- }
51
- export interface TenantAgentContextMapping {
52
- [tenantId: string]: TenantContextSessions | undefined;
53
- }
54
- export {};
@@ -1,195 +0,0 @@
1
- "use strict";
2
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
- return c > 3 && r && Object.defineProperty(target, key, r), r;
7
- };
8
- var __metadata = (this && this.__metadata) || function (k, v) {
9
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
- };
11
- var __param = (this && this.__param) || function (paramIndex, decorator) {
12
- return function (target, key) { decorator(target, key, paramIndex); }
13
- };
14
- var __rest = (this && this.__rest) || function (s, e) {
15
- var t = {};
16
- for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
17
- t[p] = s[p];
18
- if (s != null && typeof Object.getOwnPropertySymbols === "function")
19
- for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
20
- if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
21
- t[p[i]] = s[p[i]];
22
- }
23
- return t;
24
- };
25
- Object.defineProperty(exports, "__esModule", { value: true });
26
- exports.TenantSessionCoordinator = void 0;
27
- const core_1 = require("@credo-ts/core");
28
- const async_mutex_1 = require("async-mutex");
29
- const TenantsModuleConfig_1 = require("../TenantsModuleConfig");
30
- const TenantSessionMutex_1 = require("./TenantSessionMutex");
31
- /**
32
- * Coordinates all agent context instance for tenant sessions.
33
- *
34
- * This class keeps a mapping of tenant ids (context correlation ids) to agent context sessions mapping. Each mapping contains the agent context,
35
- * the current session count and a mutex for making operations against the session mapping (opening / closing an agent context). The mutex ensures
36
- * we're not susceptible to race conditions where multiple calls to open/close an agent context are made at the same time. Even though JavaScript is
37
- * single threaded, promises can introduce race conditions as one process can stop and another process can be picked up.
38
- *
39
- * NOTE: the implementation doesn't yet cache agent context objects after they aren't being used for any sessions anymore. This means if a wallet is being used
40
- * often in a short time it will be opened/closed very often. This is an improvement to be made in the near future.
41
- */
42
- let TenantSessionCoordinator = class TenantSessionCoordinator {
43
- constructor(rootAgentContext, logger, tenantsModuleConfig) {
44
- this.tenantAgentContextMapping = {};
45
- this.rootAgentContext = rootAgentContext;
46
- this.logger = logger;
47
- this.tenantsModuleConfig = tenantsModuleConfig;
48
- this.sessionMutex = new TenantSessionMutex_1.TenantSessionMutex(this.logger, this.tenantsModuleConfig.sessionLimit,
49
- // TODO: we should probably allow a higher session acquire timeout if the storage is being updated?
50
- this.tenantsModuleConfig.sessionAcquireTimeout);
51
- }
52
- getSessionCountForTenant(tenantId) {
53
- var _a, _b;
54
- return (_b = (_a = this.tenantAgentContextMapping[tenantId]) === null || _a === void 0 ? void 0 : _a.sessionCount) !== null && _b !== void 0 ? _b : 0;
55
- }
56
- /**
57
- * Get agent context to use for a session. If an agent context for this tenant does not exist yet
58
- * it will create it and store it for later use. If the agent context does already exist it will
59
- * be returned.
60
- *
61
- * @parm tenantRecord The tenant record for which to get the agent context
62
- */
63
- async getContextForSession(tenantRecord, { runInMutex, } = {}) {
64
- this.logger.debug(`Getting context for session with tenant '${tenantRecord.id}'`);
65
- // Wait for a session to be available
66
- await this.sessionMutex.acquireSession();
67
- try {
68
- return await this.mutexForTenant(tenantRecord.id).runExclusive(async () => {
69
- this.logger.debug(`Acquired lock for tenant '${tenantRecord.id}' to get context`);
70
- const tenantSessions = this.getTenantSessionsMapping(tenantRecord.id);
71
- // If we don't have an agent context already, create one and initialize it
72
- if (!tenantSessions.agentContext) {
73
- this.logger.debug(`No agent context has been initialized for tenant '${tenantRecord.id}', creating one`);
74
- tenantSessions.agentContext = await this.createAgentContext(tenantRecord);
75
- }
76
- // If we already have a context with sessions in place return the context and increment
77
- // the session count.
78
- tenantSessions.sessionCount++;
79
- this.logger.debug(`Increased agent context session count for tenant '${tenantRecord.id}' to ${tenantSessions.sessionCount}`);
80
- if (runInMutex) {
81
- try {
82
- await runInMutex(tenantSessions.agentContext);
83
- }
84
- catch (error) {
85
- // If the runInMutex failed we should release the session again
86
- tenantSessions.sessionCount--;
87
- this.logger.debug(`Decreased agent context session count for tenant '${tenantSessions.agentContext.contextCorrelationId}' to ${tenantSessions.sessionCount} due to failure in mutex script`, error);
88
- if (tenantSessions.sessionCount <= 0 && tenantSessions.agentContext) {
89
- await this.closeAgentContext(tenantSessions.agentContext);
90
- delete this.tenantAgentContextMapping[tenantSessions.agentContext.contextCorrelationId];
91
- }
92
- throw error;
93
- }
94
- }
95
- return tenantSessions.agentContext;
96
- });
97
- }
98
- catch (error) {
99
- this.logger.debug(`Releasing session because an error occurred while getting the context for tenant ${tenantRecord.id}`, {
100
- errorMessage: error.message,
101
- });
102
- // If there was an error acquiring the session, we MUST release it, otherwise this will lead to deadlocks over time.
103
- this.sessionMutex.releaseSession();
104
- // Re-throw error
105
- throw error;
106
- }
107
- }
108
- /**
109
- * End a session for the provided agent context. It will decrease the session count for the agent context.
110
- * If the number of sessions is zero after the context for this session has been ended, the agent context will be closed.
111
- */
112
- async endAgentContextSession(agentContext) {
113
- this.logger.debug(`Ending session for agent context with contextCorrelationId ${agentContext.contextCorrelationId}'`);
114
- const hasTenantSessionMapping = this.hasTenantSessionMapping(agentContext.contextCorrelationId);
115
- // Custom handling for the root agent context. We don't keep track of the total number of sessions for the root
116
- // agent context, and we always keep the dependency manager intact.
117
- if (!hasTenantSessionMapping && agentContext.contextCorrelationId === this.rootAgentContext.contextCorrelationId) {
118
- this.logger.debug('Ending session for root agent context. Not disposing dependency manager');
119
- return;
120
- }
121
- // This should not happen
122
- if (!hasTenantSessionMapping) {
123
- this.logger.error(`Unknown agent context with contextCorrelationId '${agentContext.contextCorrelationId}'. Cannot end session`);
124
- throw new core_1.CredoError(`Unknown agent context with contextCorrelationId '${agentContext.contextCorrelationId}'. Cannot end session`);
125
- }
126
- await this.mutexForTenant(agentContext.contextCorrelationId).runExclusive(async () => {
127
- this.logger.debug(`Acquired lock for tenant '${agentContext.contextCorrelationId}' to end session context`);
128
- const tenantSessions = this.getTenantSessionsMapping(agentContext.contextCorrelationId);
129
- // TODO: check if session count is already 0
130
- tenantSessions.sessionCount--;
131
- this.logger.debug(`Decreased agent context session count for tenant '${agentContext.contextCorrelationId}' to ${tenantSessions.sessionCount}`);
132
- if (tenantSessions.sessionCount <= 0 && tenantSessions.agentContext) {
133
- await this.closeAgentContext(tenantSessions.agentContext);
134
- delete this.tenantAgentContextMapping[agentContext.contextCorrelationId];
135
- }
136
- });
137
- // Release a session so new sessions can be acquired
138
- this.sessionMutex.releaseSession();
139
- }
140
- hasTenantSessionMapping(tenantId) {
141
- return this.tenantAgentContextMapping[tenantId] !== undefined;
142
- }
143
- getTenantSessionsMapping(tenantId) {
144
- let tenantSessionMapping = this.tenantAgentContextMapping[tenantId];
145
- if (tenantSessionMapping)
146
- return tenantSessionMapping;
147
- tenantSessionMapping = {
148
- sessionCount: 0,
149
- mutex: (0, async_mutex_1.withTimeout)(new async_mutex_1.Mutex(),
150
- // NOTE: It can take a while to create an indy wallet. We're using RAW key derivation which should
151
- // be fast enough to not cause a problem. This wil also only be problem when the wallet is being created
152
- // for the first time or being acquired while wallet initialization is in progress.
153
- this.tenantsModuleConfig.sessionAcquireTimeout, new core_1.CredoError(`Error acquiring lock for tenant ${tenantId}. Wallet initialization or shutdown took too long.`)),
154
- };
155
- this.tenantAgentContextMapping[tenantId] = tenantSessionMapping;
156
- return tenantSessionMapping;
157
- }
158
- mutexForTenant(tenantId) {
159
- const tenantSessions = this.getTenantSessionsMapping(tenantId);
160
- return tenantSessions.mutex;
161
- }
162
- async createAgentContext(tenantRecord) {
163
- var _a, _b;
164
- const tenantDependencyManager = this.rootAgentContext.dependencyManager.createChild();
165
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
166
- const _c = (_b = (_a = this.rootAgentContext.config) === null || _a === void 0 ? void 0 : _a.walletConfig) !== null && _b !== void 0 ? _b : {}, { id, key, keyDerivationMethod } = _c, strippedWalletConfig = __rest(_c, ["id", "key", "keyDerivationMethod"]);
167
- const tenantConfig = this.rootAgentContext.config.extend(Object.assign(Object.assign({}, tenantRecord.config), { walletConfig: Object.assign(Object.assign({}, strippedWalletConfig), tenantRecord.config.walletConfig) }));
168
- const agentContext = new core_1.AgentContext({
169
- contextCorrelationId: tenantRecord.id,
170
- dependencyManager: tenantDependencyManager,
171
- });
172
- tenantDependencyManager.registerInstance(core_1.AgentContext, agentContext);
173
- tenantDependencyManager.registerInstance(core_1.AgentConfig, tenantConfig);
174
- // NOTE: we're using the wallet api here because that correctly handle creating if it doesn't exist yet
175
- // and will also write the storage version to the storage, which is needed by the update assistant. We either
176
- // need to move this out of the module, or just keep using the module here.
177
- const walletApi = agentContext.dependencyManager.resolve(core_1.WalletApi);
178
- if (!tenantConfig.walletConfig) {
179
- throw new core_1.WalletError('Cannot initialize tenant without Wallet config.');
180
- }
181
- await walletApi.initialize(tenantConfig.walletConfig);
182
- return agentContext;
183
- }
184
- async closeAgentContext(agentContext) {
185
- this.logger.debug(`Closing agent context for tenant '${agentContext.contextCorrelationId}'`);
186
- await agentContext.dependencyManager.dispose();
187
- }
188
- };
189
- exports.TenantSessionCoordinator = TenantSessionCoordinator;
190
- exports.TenantSessionCoordinator = TenantSessionCoordinator = __decorate([
191
- (0, core_1.injectable)(),
192
- __param(1, (0, core_1.inject)(core_1.InjectionSymbols.Logger)),
193
- __metadata("design:paramtypes", [core_1.AgentContext, Object, TenantsModuleConfig_1.TenantsModuleConfig])
194
- ], TenantSessionCoordinator);
195
- //# sourceMappingURL=TenantSessionCoordinator.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"TenantSessionCoordinator.js","sourceRoot":"","sources":["../../src/context/TenantSessionCoordinator.ts"],"names":[],"mappings":"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"}
@@ -1,29 +0,0 @@
1
- import type { Logger } from '@credo-ts/core';
2
- /**
3
- * Keep track of the total number of tenant sessions currently active. This doesn't actually manage the tenant sessions itself, or have anything to do with
4
- * the agent context. It merely counts the current number of sessions, and provides a mutex to lock new sessions from being created once the maximum number
5
- * of sessions has been created. Session that can't be required withing the specified sessionsAcquireTimeout will throw an error.
6
- */
7
- export declare class TenantSessionMutex {
8
- private _currentSessions;
9
- readonly maxSessions: number;
10
- private sessionMutex;
11
- private logger;
12
- constructor(logger: Logger, maxSessions: number | undefined, sessionAcquireTimeout: number);
13
- /**
14
- * Getter to retrieve the total number of current sessions.
15
- */
16
- get currentSessions(): number;
17
- private set currentSessions(value);
18
- /**
19
- * Wait to acquire a session. Will use the session semaphore to keep total number of sessions limited.
20
- * For each session that is acquired using this method, the sessions MUST be closed by calling `releaseSession`.
21
- * Failing to do so can lead to deadlocks over time.
22
- */
23
- acquireSession(): Promise<void>;
24
- /**
25
- * Release a session from the session mutex. If the total number of current sessions drops below
26
- * the max number of sessions, the session mutex will be released so new sessions can be started.
27
- */
28
- releaseSession(): void;
29
- }