@globalart/nestjs-typeorm-outbox 1.7.2 → 1.7.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +15 -6
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +6 -3
- package/dist/index.d.mts +6 -3
- package/dist/index.mjs +15 -6
- package/dist/index.mjs.map +1 -1
- package/package.json +5 -4
package/dist/index.cjs
CHANGED
|
@@ -16,12 +16,12 @@ const InjectTypeormOutboxModuleConfig = () => (0, _nestjs_common.Inject)(TYPEORM
|
|
|
16
16
|
const InjectTypeormOutboxService = () => (0, _nestjs_common.Inject)(TYPEORM_OUTBOX_SERVICE_TOKEN);
|
|
17
17
|
const InjectTypeormOutboxBroker = () => (0, _nestjs_common.Inject)(TYPEORM_OUTBOX_BROKER_TOKEN);
|
|
18
18
|
//#endregion
|
|
19
|
-
//#region \0@oxc-project+runtime@0.
|
|
19
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorateMetadata.js
|
|
20
20
|
function __decorateMetadata(k, v) {
|
|
21
21
|
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
22
22
|
}
|
|
23
23
|
//#endregion
|
|
24
|
-
//#region \0@oxc-project+runtime@0.
|
|
24
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorate.js
|
|
25
25
|
function __decorate(decorators, target, key, desc) {
|
|
26
26
|
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
27
27
|
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
@@ -124,13 +124,13 @@ var TypeormOutboxRegisterCronModuleOptions = class {
|
|
|
124
124
|
brokerConfig = {};
|
|
125
125
|
deleteItem = true;
|
|
126
126
|
typeOrmConnectionName = "default";
|
|
127
|
-
cronExpression =
|
|
127
|
+
cronExpression = "* * * * * *";
|
|
128
128
|
};
|
|
129
129
|
var TypeormOutboxModuleOptions = class {
|
|
130
130
|
typeOrmConnectionName = "default";
|
|
131
131
|
};
|
|
132
132
|
//#endregion
|
|
133
|
-
//#region \0@oxc-project+runtime@0.
|
|
133
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorateParam.js
|
|
134
134
|
function __decorateParam(paramIndex, decorator) {
|
|
135
135
|
return function(target, key) {
|
|
136
136
|
decorator(target, key, paramIndex);
|
|
@@ -149,7 +149,7 @@ let TypeormOutboxCronService = class TypeormOutboxCronService {
|
|
|
149
149
|
isRunning = false;
|
|
150
150
|
onApplicationBootstrap() {
|
|
151
151
|
this.validateBrokerClient();
|
|
152
|
-
this.cronJob = new cron.CronJob(this.moduleConfig.cronExpression ??
|
|
152
|
+
this.cronJob = new cron.CronJob(this.moduleConfig.cronExpression ?? "* * * * * *", () => {
|
|
153
153
|
if (this.isRunning) return;
|
|
154
154
|
this.isRunning = true;
|
|
155
155
|
this.executeCronJob().finally(() => {
|
|
@@ -164,11 +164,20 @@ let TypeormOutboxCronService = class TypeormOutboxCronService {
|
|
|
164
164
|
}
|
|
165
165
|
validateBrokerClient() {
|
|
166
166
|
const brokerConfig = this.moduleConfig.brokerConfig;
|
|
167
|
+
if (brokerConfig !== null && typeof brokerConfig === "object" && "customClass" in brokerConfig) {
|
|
168
|
+
if (brokerConfig.customClass == null) throw new Error(`[TypeormOutboxCronService] Broker config with customClass must provide a non-null customClass (e.g. PlatformaticKafkaClient)`);
|
|
169
|
+
return;
|
|
170
|
+
}
|
|
171
|
+
if (brokerConfig !== null && typeof brokerConfig === "object" && "strategy" in brokerConfig) {
|
|
172
|
+
if (brokerConfig.strategy == null) throw new Error(`[TypeormOutboxCronService] Custom broker config must provide a non-null strategy (e.g. createPlatformaticKafkaMicroservice)`);
|
|
173
|
+
return;
|
|
174
|
+
}
|
|
175
|
+
const transport = brokerConfig?.transport;
|
|
167
176
|
if (![
|
|
168
177
|
_nestjs_microservices.Transport.KAFKA,
|
|
169
178
|
_nestjs_microservices.Transport.NATS,
|
|
170
179
|
_nestjs_microservices.Transport.MQTT
|
|
171
|
-
].includes(
|
|
180
|
+
].includes(transport)) throw new Error(`[TypeormOutboxCronService] Broker config must be KafkaOptions, NatsOptions, MqttOptions, customClass (e.g. PlatformaticKafkaClient), or a custom strategy (e.g. createPlatformaticKafkaMicroservice)`);
|
|
172
181
|
}
|
|
173
182
|
async executeCronJob() {
|
|
174
183
|
const entities = await this.claimPendingEntities();
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.cjs","names":["CronJob","Transport","TypeOrmModule","ClientProxyFactory"],"sources":["../src/core/typeorm-outbox.di-tokens.ts","../src/core/typeorm-outbox.entity.ts","../src/core/typeorm-outbox.enums.ts","../src/core/typeorm-outbox.interfaces.ts","../src/core/typeorm-outbox-cron.service.ts","../src/core/typeorm-outbox.service.ts","../src/core/typeorm-outbox.module.ts"],"sourcesContent":["import { Inject } from \"@nestjs/common\";\n\nexport const TYPEORM_OUTBOX_CRON_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_CRON_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_SERVICE_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_SERVICE_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_BROKER_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_BROKER_TOKEN\",\n);\n\nexport const InjectTypeormOutboxCronConfig = () =>\n Inject(TYPEORM_OUTBOX_CRON_CONFIG_TOKEN);\nexport const InjectTypeormOutboxModuleConfig = () =>\n Inject(TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN);\nexport const InjectTypeormOutboxService = () =>\n Inject(TYPEORM_OUTBOX_SERVICE_TOKEN);\nexport const InjectTypeormOutboxBroker = () =>\n Inject(TYPEORM_OUTBOX_BROKER_TOKEN);\n","import {\n Column,\n CreateDateColumn,\n Entity,\n PrimaryColumn,\n PrimaryGeneratedColumn,\n UpdateDateColumn,\n} from \"typeorm\";\n\n@Entity(\"outbox_messages\")\nexport class TypeormOutboxEntity {\n @PrimaryColumn()\n id!: string;\n\n @Column({ name: 'status', default: 'pending' })\n status!: string;\n\n @CreateDateColumn({ name: \"created_at\" })\n createdAt!: Date;\n\n @UpdateDateColumn({ name: \"updated_at\" })\n updatedAt!: Date;\n\n @Column(\"character varying\", { name: \"destination_topic\" })\n destinationTopic!: string;\n\n @Column(\"jsonb\", { nullable: true })\n headers!: Record<string, string>;\n\n @Column(\"jsonb\", { nullable: true })\n keys!: Record<string, unknown>;\n\n @Column(\"jsonb\")\n value!: Record<string, any>;\n}\n","export enum CronExpression {\n EVERY_SECOND = \"* * * * * *\",\n EVERY_2_SECONDS = \"*/2 * * * * *\",\n EVERY_3_SECONDS = \"*/3 * * * * *\",\n EVERY_4_SECONDS = \"*/4 * * * * *\",\n EVERY_5_SECONDS = \"*/5 * * * * *\",\n EVERY_6_SECONDS = \"*/6 * * * * *\",\n EVERY_7_SECONDS = \"*/7 * * * * *\",\n EVERY_8_SECONDS = \"*/8 * * * * *\",\n EVERY_9_SECONDS = \"*/9 * * * * *\",\n EVERY_10_SECONDS = \"*/10 * * * * *\",\n EVERY_11_SECONDS = \"*/11 * * * * *\",\n EVERY_12_SECONDS = \"*/12 * * * * *\",\n EVERY_13_SECONDS = \"*/13 * * * * *\",\n EVERY_14_SECONDS = \"*/14 * * * * *\",\n EVERY_15_SECONDS = \"*/15 * * * * *\",\n EVERY_16_SECONDS = \"*/16 * * * * *\",\n EVERY_17_SECONDS = \"*/17 * * * * *\",\n EVERY_18_SECONDS = \"*/18 * * * * *\",\n EVERY_19_SECONDS = \"*/19 * * * * *\",\n EVERY_20_SECONDS = \"*/20 * * * * *\",\n EVERY_21_SECONDS = \"*/21 * * * * *\",\n EVERY_22_SECONDS = \"*/22 * * * * *\",\n EVERY_23_SECONDS = \"*/23 * * * * *\",\n EVERY_24_SECONDS = \"*/24 * * * * *\",\n EVERY_25_SECONDS = \"*/25 * * * * *\",\n EVERY_26_SECONDS = \"*/26 * * * * *\",\n EVERY_27_SECONDS = \"*/27 * * * * *\",\n EVERY_28_SECONDS = \"*/28 * * * * *\",\n EVERY_29_SECONDS = \"*/29 * * * * *\",\n EVERY_30_SECONDS = \"*/30 * * * * *\",\n EVERY_31_SECONDS = \"*/31 * * * * *\",\n EVERY_32_SECONDS = \"*/32 * * * * *\",\n EVERY_33_SECONDS = \"*/33 * * * * *\",\n EVERY_34_SECONDS = \"*/34 * * * * *\",\n EVERY_35_SECONDS = \"*/35 * * * * *\",\n EVERY_36_SECONDS = \"*/36 * * * * *\",\n EVERY_37_SECONDS = \"*/37 * * * * *\",\n EVERY_38_SECONDS = \"*/38 * * * * *\",\n EVERY_39_SECONDS = \"*/39 * * * * *\",\n EVERY_40_SECONDS = \"*/40 * * * * *\",\n EVERY_41_SECONDS = \"*/41 * * * * *\",\n EVERY_42_SECONDS = \"*/42 * * * * *\",\n EVERY_43_SECONDS = \"*/43 * * * * *\",\n EVERY_44_SECONDS = \"*/44 * * * * *\",\n EVERY_45_SECONDS = \"*/45 * * * * *\",\n EVERY_46_SECONDS = \"*/46 * * * * *\",\n EVERY_47_SECONDS = \"*/47 * * * * *\",\n EVERY_48_SECONDS = \"*/48 * * * * *\",\n EVERY_49_SECONDS = \"*/49 * * * * *\",\n EVERY_50_SECONDS = \"*/50 * * * * *\",\n EVERY_51_SECONDS = \"*/51 * * * * *\",\n EVERY_52_SECONDS = \"*/52 * * * * *\",\n EVERY_53_SECONDS = \"*/53 * * * * *\",\n EVERY_54_SECONDS = \"*/54 * * * * *\",\n EVERY_55_SECONDS = \"*/55 * * * * *\",\n EVERY_56_SECONDS = \"*/56 * * * * *\",\n EVERY_57_SECONDS = \"*/57 * * * * *\",\n EVERY_58_SECONDS = \"*/58 * * * * *\",\n EVERY_59_SECONDS = \"*/59 * * * * *\",\n EVERY_MINUTE = \"0 * * * * *\",\n}","import { KafkaOptions, MqttOptions, NatsOptions } from \"@nestjs/microservices\";\nimport { InjectionToken, ModuleMetadata, Type } from \"@nestjs/common\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\ntype BrokerConfig = MqttOptions | NatsOptions | KafkaOptions;\n\nexport class TypeormOutboxRegisterCronModuleOptions {\n brokerConfig: BrokerConfig = {};\n deleteItem?: boolean = true;\n typeOrmConnectionName?: string = \"default\";\n cronExpression?: string = CronExpression.EVERY_SECOND;\n}\n\nexport interface TypeormOutboxRegisterCronAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useExisting?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useClass?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useFactory?: (\n ...args: any[]\n ) =>\n | Promise<TypeormOutboxRegisterCronModuleOptions>\n | TypeormOutboxRegisterCronModuleOptions;\n}\n\nexport class TypeormOutboxModuleOptions {\n typeOrmConnectionName?: string = \"default\";\n}\n\nexport interface TypeormOutboxModuleAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useFactory?: (\n ...args: any[]\n ) => Promise<TypeormOutboxModuleOptions> | TypeormOutboxModuleOptions;\n}\n","import {\n Injectable,\n OnApplicationBootstrap,\n OnApplicationShutdown,\n} from \"@nestjs/common\";\nimport {\n InjectTypeormOutboxBroker,\n InjectTypeormOutboxCronConfig,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { firstValueFrom } from \"rxjs\";\nimport { ClientProxy, Transport } from \"@nestjs/microservices\";\nimport { CronJob } from \"cron\";\nimport { TypeormOutboxRegisterCronModuleOptions } from \"./typeorm-outbox.interfaces\";\nimport { DataSource } from \"typeorm\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\n@Injectable()\nexport class TypeormOutboxCronService\n implements OnApplicationBootstrap, OnApplicationShutdown\n{\n constructor(\n @InjectTypeormOutboxBroker()\n private readonly brokerClient: ClientProxy,\n @InjectTypeormOutboxCronConfig()\n private readonly moduleConfig: TypeormOutboxRegisterCronModuleOptions,\n private readonly dataSource: DataSource,\n ) {}\n\n private cronJob!: CronJob;\n private isRunning = false;\n\n onApplicationBootstrap() {\n this.validateBrokerClient();\n this.cronJob = new CronJob(\n this.moduleConfig.cronExpression ?? CronExpression.EVERY_SECOND,\n () => {\n if (this.isRunning) return;\n this.isRunning = true;\n this.executeCronJob().finally(() => {\n this.isRunning = false;\n });\n },\n );\n this.cronJob.start();\n }\n\n onApplicationShutdown() {\n if (!this.cronJob) {\n return;\n }\n this.cronJob.stop();\n }\n\n private validateBrokerClient() {\n const brokerConfig = this.moduleConfig.brokerConfig;\n if (\n ![Transport.KAFKA, Transport.NATS, Transport.MQTT].includes(\n brokerConfig?.transport as Transport,\n )\n ) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config must be an instance of KafkaOptions, NatsOptions, or MqttOptions`,\n );\n }\n }\n\n private async executeCronJob() {\n const entities = await this.claimPendingEntities();\n if (!entities.length) return;\n\n for (const entity of entities) {\n await firstValueFrom(\n this.brokerClient.emit(entity.destinationTopic, {\n key: entity.keys,\n value: entity.value,\n headers: entity.headers,\n }),\n );\n\n await this.finalizeEntity(entity.id);\n }\n }\n\n private async claimPendingEntities(): Promise<TypeormOutboxEntity[]> {\n const queryRunner = this.dataSource.createQueryRunner();\n await queryRunner.connect();\n\n try {\n await queryRunner.startTransaction();\n\n const entities = await queryRunner.manager\n .createQueryBuilder(TypeormOutboxEntity, \"e\")\n .where(\"e.status = :status\", { status: \"pending\" })\n .orderBy(\"e.createdAt\", \"ASC\")\n .setLock(\"pessimistic_partial_write\")\n .getMany();\n\n if (entities.length) {\n await queryRunner.manager.update(\n TypeormOutboxEntity,\n entities.map((e) => e.id),\n { status: \"processing\" },\n );\n }\n\n await queryRunner.commitTransaction();\n return entities;\n } catch (error) {\n await queryRunner.rollbackTransaction();\n throw error;\n } finally {\n await queryRunner.release();\n }\n }\n\n private async finalizeEntity(id: string): Promise<void> {\n if (this.moduleConfig.deleteItem) {\n await this.dataSource.manager.delete(TypeormOutboxEntity, id);\n } else {\n await this.dataSource.manager.update(\n TypeormOutboxEntity,\n { id },\n { status: \"sent\" },\n );\n }\n }\n}","import { Injectable } from \"@nestjs/common\";\nimport { InjectRepository } from \"@nestjs/typeorm\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { Repository } from \"typeorm\";\nimport { randomUUID } from \"crypto\";\n\nexport interface CreateOutboxOptions {\n destinationTopic: string;\n value: any;\n headers?: any;\n keys?: any;\n}\n\n@Injectable()\nexport class TypeormOutboxService {\n constructor(\n @InjectRepository(TypeormOutboxEntity)\n private readonly outboxRepository: Repository<TypeormOutboxEntity>,\n ) {}\n\n async create(options: CreateOutboxOptions): Promise<TypeormOutboxEntity> {\n return this.outboxRepository.save({\n id: randomUUID(),\n destinationTopic: options.destinationTopic,\n headers: options.headers,\n keys: options.keys,\n value: options.value,\n });\n }\n}\n","import { TypeOrmModule } from \"@nestjs/typeorm\";\nimport { DynamicModule, Module, Provider } from \"@nestjs/common\";\nimport {\n TypeormOutboxRegisterCronAsyncOptions,\n TypeormOutboxRegisterCronModuleOptions,\n TypeormOutboxModuleOptions,\n TypeormOutboxModuleAsyncOptions,\n} from \"./typeorm-outbox.interfaces\";\nimport {\n TYPEORM_OUTBOX_BROKER_TOKEN,\n TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n TYPEORM_OUTBOX_SERVICE_TOKEN,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { TypeormOutboxService } from \"./typeorm-outbox.service\";\nimport { ClientProxyFactory } from \"@nestjs/microservices\";\nimport { TypeormOutboxCronService } from \"./typeorm-outbox-cron.service\";\n\nconst serviceProvider = (): Provider => ({\n provide: TYPEORM_OUTBOX_SERVICE_TOKEN,\n useClass: TypeormOutboxService,\n});\n\nconst brokerProvider = (useValue: any = {}): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useValue,\n});\n\nconst typeOrmFeature = (connectionName = \"default\") =>\n TypeOrmModule.forFeature([TypeormOutboxEntity], connectionName);\n\nconst mergeModuleOptions = <T extends object>(\n defaults: new () => T,\n overrides?: Partial<T>,\n): T => ({ ...new defaults(), ...overrides });\n\nconst moduleConfigProvider = (\n options: TypeormOutboxModuleOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useValue: mergeModuleOptions(TypeormOutboxModuleOptions, options),\n});\n\nconst asyncModuleConfigProvider = (\n options: TypeormOutboxModuleAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronConfigProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronBrokerProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useFactory: async (...args: any[]) => {\n const config = mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n );\n return ClientProxyFactory.create(config?.brokerConfig ?? {});\n },\n inject: options.inject || [],\n});\n\n@Module({})\nexport class TypeormOutboxModule {\n static forRoot(options: TypeormOutboxModuleOptions = {}): DynamicModule {\n const providers = [\n moduleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature(options.typeOrmConnectionName)],\n providers,\n exports: providers,\n };\n }\n\n static forRootAsync(options: TypeormOutboxModuleAsyncOptions): DynamicModule {\n const providers = [\n asyncModuleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers,\n exports: providers,\n };\n }\n\n static registerCronAsync(\n options: TypeormOutboxRegisterCronAsyncOptions,\n ): DynamicModule {\n const providers = [\n cronConfigProvider(options),\n cronBrokerProvider(options),\n serviceProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers: [TypeormOutboxCronService, ...providers],\n exports: providers,\n };\n }\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.cjs","names":["CronJob","Transport","TypeOrmModule","ClientProxyFactory"],"sources":["../src/core/typeorm-outbox.di-tokens.ts","../src/core/typeorm-outbox.entity.ts","../src/core/typeorm-outbox.enums.ts","../src/core/typeorm-outbox.interfaces.ts","../src/core/typeorm-outbox-cron.service.ts","../src/core/typeorm-outbox.service.ts","../src/core/typeorm-outbox.module.ts"],"sourcesContent":["import { Inject } from \"@nestjs/common\";\n\nexport const TYPEORM_OUTBOX_CRON_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_CRON_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_SERVICE_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_SERVICE_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_BROKER_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_BROKER_TOKEN\",\n);\n\nexport const InjectTypeormOutboxCronConfig = () =>\n Inject(TYPEORM_OUTBOX_CRON_CONFIG_TOKEN);\nexport const InjectTypeormOutboxModuleConfig = () =>\n Inject(TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN);\nexport const InjectTypeormOutboxService = () =>\n Inject(TYPEORM_OUTBOX_SERVICE_TOKEN);\nexport const InjectTypeormOutboxBroker = () =>\n Inject(TYPEORM_OUTBOX_BROKER_TOKEN);\n","import {\n Column,\n CreateDateColumn,\n Entity,\n PrimaryColumn,\n PrimaryGeneratedColumn,\n UpdateDateColumn,\n} from \"typeorm\";\n\n@Entity(\"outbox_messages\")\nexport class TypeormOutboxEntity {\n @PrimaryColumn()\n id!: string;\n\n @Column({ name: 'status', default: 'pending' })\n status!: string;\n\n @CreateDateColumn({ name: \"created_at\" })\n createdAt!: Date;\n\n @UpdateDateColumn({ name: \"updated_at\" })\n updatedAt!: Date;\n\n @Column(\"character varying\", { name: \"destination_topic\" })\n destinationTopic!: string;\n\n @Column(\"jsonb\", { nullable: true })\n headers!: Record<string, string>;\n\n @Column(\"jsonb\", { nullable: true })\n keys!: Record<string, unknown>;\n\n @Column(\"jsonb\")\n value!: Record<string, any>;\n}\n","export enum CronExpression {\n EVERY_SECOND = \"* * * * * *\",\n EVERY_2_SECONDS = \"*/2 * * * * *\",\n EVERY_3_SECONDS = \"*/3 * * * * *\",\n EVERY_4_SECONDS = \"*/4 * * * * *\",\n EVERY_5_SECONDS = \"*/5 * * * * *\",\n EVERY_6_SECONDS = \"*/6 * * * * *\",\n EVERY_7_SECONDS = \"*/7 * * * * *\",\n EVERY_8_SECONDS = \"*/8 * * * * *\",\n EVERY_9_SECONDS = \"*/9 * * * * *\",\n EVERY_10_SECONDS = \"*/10 * * * * *\",\n EVERY_11_SECONDS = \"*/11 * * * * *\",\n EVERY_12_SECONDS = \"*/12 * * * * *\",\n EVERY_13_SECONDS = \"*/13 * * * * *\",\n EVERY_14_SECONDS = \"*/14 * * * * *\",\n EVERY_15_SECONDS = \"*/15 * * * * *\",\n EVERY_16_SECONDS = \"*/16 * * * * *\",\n EVERY_17_SECONDS = \"*/17 * * * * *\",\n EVERY_18_SECONDS = \"*/18 * * * * *\",\n EVERY_19_SECONDS = \"*/19 * * * * *\",\n EVERY_20_SECONDS = \"*/20 * * * * *\",\n EVERY_21_SECONDS = \"*/21 * * * * *\",\n EVERY_22_SECONDS = \"*/22 * * * * *\",\n EVERY_23_SECONDS = \"*/23 * * * * *\",\n EVERY_24_SECONDS = \"*/24 * * * * *\",\n EVERY_25_SECONDS = \"*/25 * * * * *\",\n EVERY_26_SECONDS = \"*/26 * * * * *\",\n EVERY_27_SECONDS = \"*/27 * * * * *\",\n EVERY_28_SECONDS = \"*/28 * * * * *\",\n EVERY_29_SECONDS = \"*/29 * * * * *\",\n EVERY_30_SECONDS = \"*/30 * * * * *\",\n EVERY_31_SECONDS = \"*/31 * * * * *\",\n EVERY_32_SECONDS = \"*/32 * * * * *\",\n EVERY_33_SECONDS = \"*/33 * * * * *\",\n EVERY_34_SECONDS = \"*/34 * * * * *\",\n EVERY_35_SECONDS = \"*/35 * * * * *\",\n EVERY_36_SECONDS = \"*/36 * * * * *\",\n EVERY_37_SECONDS = \"*/37 * * * * *\",\n EVERY_38_SECONDS = \"*/38 * * * * *\",\n EVERY_39_SECONDS = \"*/39 * * * * *\",\n EVERY_40_SECONDS = \"*/40 * * * * *\",\n EVERY_41_SECONDS = \"*/41 * * * * *\",\n EVERY_42_SECONDS = \"*/42 * * * * *\",\n EVERY_43_SECONDS = \"*/43 * * * * *\",\n EVERY_44_SECONDS = \"*/44 * * * * *\",\n EVERY_45_SECONDS = \"*/45 * * * * *\",\n EVERY_46_SECONDS = \"*/46 * * * * *\",\n EVERY_47_SECONDS = \"*/47 * * * * *\",\n EVERY_48_SECONDS = \"*/48 * * * * *\",\n EVERY_49_SECONDS = \"*/49 * * * * *\",\n EVERY_50_SECONDS = \"*/50 * * * * *\",\n EVERY_51_SECONDS = \"*/51 * * * * *\",\n EVERY_52_SECONDS = \"*/52 * * * * *\",\n EVERY_53_SECONDS = \"*/53 * * * * *\",\n EVERY_54_SECONDS = \"*/54 * * * * *\",\n EVERY_55_SECONDS = \"*/55 * * * * *\",\n EVERY_56_SECONDS = \"*/56 * * * * *\",\n EVERY_57_SECONDS = \"*/57 * * * * *\",\n EVERY_58_SECONDS = \"*/58 * * * * *\",\n EVERY_59_SECONDS = \"*/59 * * * * *\",\n EVERY_MINUTE = \"0 * * * * *\",\n}","import {\n type CustomClientOptions,\n KafkaOptions,\n MqttOptions,\n NatsOptions,\n} from \"@nestjs/microservices\";\nimport { InjectionToken, ModuleMetadata, Type } from \"@nestjs/common\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\nexport type CustomMicroserviceBrokerConfig = {\n strategy: unknown;\n};\n\ntype BrokerConfig =\n | MqttOptions\n | NatsOptions\n | KafkaOptions\n | CustomMicroserviceBrokerConfig\n | CustomClientOptions;\n\nexport class TypeormOutboxRegisterCronModuleOptions {\n brokerConfig: BrokerConfig = {};\n deleteItem?: boolean = true;\n typeOrmConnectionName?: string = \"default\";\n cronExpression?: string = CronExpression.EVERY_SECOND;\n}\n\nexport interface TypeormOutboxRegisterCronAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useExisting?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useClass?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useFactory?: (\n ...args: any[]\n ) =>\n | Promise<TypeormOutboxRegisterCronModuleOptions>\n | TypeormOutboxRegisterCronModuleOptions;\n}\n\nexport class TypeormOutboxModuleOptions {\n typeOrmConnectionName?: string = \"default\";\n}\n\nexport interface TypeormOutboxModuleAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useFactory?: (\n ...args: any[]\n ) => Promise<TypeormOutboxModuleOptions> | TypeormOutboxModuleOptions;\n}\n","import {\n Injectable,\n OnApplicationBootstrap,\n OnApplicationShutdown,\n} from \"@nestjs/common\";\nimport {\n InjectTypeormOutboxBroker,\n InjectTypeormOutboxCronConfig,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { firstValueFrom } from \"rxjs\";\nimport {\n type CustomClientOptions,\n ClientProxy,\n Transport,\n} from \"@nestjs/microservices\";\nimport { CronJob } from \"cron\";\nimport { TypeormOutboxRegisterCronModuleOptions } from \"./typeorm-outbox.interfaces\";\nimport { DataSource } from \"typeorm\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\n@Injectable()\nexport class TypeormOutboxCronService\n implements OnApplicationBootstrap, OnApplicationShutdown\n{\n constructor(\n @InjectTypeormOutboxBroker()\n private readonly brokerClient: ClientProxy,\n @InjectTypeormOutboxCronConfig()\n private readonly moduleConfig: TypeormOutboxRegisterCronModuleOptions,\n private readonly dataSource: DataSource,\n ) {}\n\n private cronJob!: CronJob;\n private isRunning = false;\n\n onApplicationBootstrap() {\n this.validateBrokerClient();\n this.cronJob = new CronJob(\n this.moduleConfig.cronExpression ?? CronExpression.EVERY_SECOND,\n () => {\n if (this.isRunning) return;\n this.isRunning = true;\n this.executeCronJob().finally(() => {\n this.isRunning = false;\n });\n },\n );\n this.cronJob.start();\n }\n\n onApplicationShutdown() {\n if (!this.cronJob) {\n return;\n }\n this.cronJob.stop();\n }\n\n private validateBrokerClient() {\n const brokerConfig = this.moduleConfig.brokerConfig;\n if (\n brokerConfig !== null &&\n typeof brokerConfig === \"object\" &&\n \"customClass\" in brokerConfig\n ) {\n if ((brokerConfig as CustomClientOptions).customClass == null) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config with customClass must provide a non-null customClass (e.g. PlatformaticKafkaClient)`,\n );\n }\n return;\n }\n if (\n brokerConfig !== null &&\n typeof brokerConfig === \"object\" &&\n \"strategy\" in brokerConfig\n ) {\n if ((brokerConfig as { strategy?: unknown }).strategy == null) {\n throw new Error(\n `[TypeormOutboxCronService] Custom broker config must provide a non-null strategy (e.g. createPlatformaticKafkaMicroservice)`,\n );\n }\n return;\n }\n const transport = (brokerConfig as { transport?: Transport } | null)\n ?.transport;\n if (\n ![Transport.KAFKA, Transport.NATS, Transport.MQTT].includes(\n transport as Transport,\n )\n ) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config must be KafkaOptions, NatsOptions, MqttOptions, customClass (e.g. PlatformaticKafkaClient), or a custom strategy (e.g. createPlatformaticKafkaMicroservice)`,\n );\n }\n }\n\n private async executeCronJob() {\n const entities = await this.claimPendingEntities();\n if (!entities.length) return;\n\n for (const entity of entities) {\n await firstValueFrom(\n this.brokerClient.emit(entity.destinationTopic, {\n key: entity.keys,\n value: entity.value,\n headers: entity.headers,\n }),\n );\n\n await this.finalizeEntity(entity.id);\n }\n }\n\n private async claimPendingEntities(): Promise<TypeormOutboxEntity[]> {\n const queryRunner = this.dataSource.createQueryRunner();\n await queryRunner.connect();\n\n try {\n await queryRunner.startTransaction();\n\n const entities = await queryRunner.manager\n .createQueryBuilder(TypeormOutboxEntity, \"e\")\n .where(\"e.status = :status\", { status: \"pending\" })\n .orderBy(\"e.createdAt\", \"ASC\")\n .setLock(\"pessimistic_partial_write\")\n .getMany();\n\n if (entities.length) {\n await queryRunner.manager.update(\n TypeormOutboxEntity,\n entities.map((e) => e.id),\n { status: \"processing\" },\n );\n }\n\n await queryRunner.commitTransaction();\n return entities;\n } catch (error) {\n await queryRunner.rollbackTransaction();\n throw error;\n } finally {\n await queryRunner.release();\n }\n }\n\n private async finalizeEntity(id: string): Promise<void> {\n if (this.moduleConfig.deleteItem) {\n await this.dataSource.manager.delete(TypeormOutboxEntity, id);\n } else {\n await this.dataSource.manager.update(\n TypeormOutboxEntity,\n { id },\n { status: \"sent\" },\n );\n }\n }\n}\n","import { Injectable } from \"@nestjs/common\";\nimport { InjectRepository } from \"@nestjs/typeorm\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { Repository } from \"typeorm\";\nimport { randomUUID } from \"crypto\";\n\nexport interface CreateOutboxOptions {\n destinationTopic: string;\n value: any;\n headers?: any;\n keys?: any;\n}\n\n@Injectable()\nexport class TypeormOutboxService {\n constructor(\n @InjectRepository(TypeormOutboxEntity)\n private readonly outboxRepository: Repository<TypeormOutboxEntity>,\n ) {}\n\n async create(options: CreateOutboxOptions): Promise<TypeormOutboxEntity> {\n return this.outboxRepository.save({\n id: randomUUID(),\n destinationTopic: options.destinationTopic,\n headers: options.headers,\n keys: options.keys,\n value: options.value,\n });\n }\n}\n","import { TypeOrmModule } from \"@nestjs/typeorm\";\nimport { DynamicModule, Module, Provider } from \"@nestjs/common\";\nimport {\n TypeormOutboxRegisterCronAsyncOptions,\n TypeormOutboxRegisterCronModuleOptions,\n TypeormOutboxModuleOptions,\n TypeormOutboxModuleAsyncOptions,\n} from \"./typeorm-outbox.interfaces\";\nimport {\n TYPEORM_OUTBOX_BROKER_TOKEN,\n TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n TYPEORM_OUTBOX_SERVICE_TOKEN,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { TypeormOutboxService } from \"./typeorm-outbox.service\";\nimport { ClientProxyFactory } from \"@nestjs/microservices\";\nimport { TypeormOutboxCronService } from \"./typeorm-outbox-cron.service\";\n\nconst serviceProvider = (): Provider => ({\n provide: TYPEORM_OUTBOX_SERVICE_TOKEN,\n useClass: TypeormOutboxService,\n});\n\nconst brokerProvider = (useValue: any = {}): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useValue,\n});\n\nconst typeOrmFeature = (connectionName = \"default\") =>\n TypeOrmModule.forFeature([TypeormOutboxEntity], connectionName);\n\nconst mergeModuleOptions = <T extends object>(\n defaults: new () => T,\n overrides?: Partial<T>,\n): T => ({ ...new defaults(), ...overrides });\n\nconst moduleConfigProvider = (\n options: TypeormOutboxModuleOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useValue: mergeModuleOptions(TypeormOutboxModuleOptions, options),\n});\n\nconst asyncModuleConfigProvider = (\n options: TypeormOutboxModuleAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronConfigProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronBrokerProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useFactory: async (...args: any[]) => {\n const config = mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n );\n return ClientProxyFactory.create(config?.brokerConfig ?? {});\n },\n inject: options.inject || [],\n});\n\n@Module({})\nexport class TypeormOutboxModule {\n static forRoot(options: TypeormOutboxModuleOptions = {}): DynamicModule {\n const providers = [\n moduleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature(options.typeOrmConnectionName)],\n providers,\n exports: providers,\n };\n }\n\n static forRootAsync(options: TypeormOutboxModuleAsyncOptions): DynamicModule {\n const providers = [\n asyncModuleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers,\n exports: providers,\n };\n }\n\n static registerCronAsync(\n options: TypeormOutboxRegisterCronAsyncOptions,\n ): DynamicModule {\n const providers = [\n cronConfigProvider(options),\n cronBrokerProvider(options),\n serviceProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers: [TypeormOutboxCronService, ...providers],\n exports: providers,\n };\n }\n}\n"],"mappings":"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"}
|
package/dist/index.d.cts
CHANGED
|
@@ -1,9 +1,12 @@
|
|
|
1
1
|
import { DynamicModule, InjectionToken, ModuleMetadata, OnApplicationBootstrap, OnApplicationShutdown, Type } from "@nestjs/common";
|
|
2
|
-
import { ClientProxy, KafkaOptions, MqttOptions, NatsOptions } from "@nestjs/microservices";
|
|
2
|
+
import { ClientProxy, CustomClientOptions, KafkaOptions, MqttOptions, NatsOptions } from "@nestjs/microservices";
|
|
3
3
|
import { DataSource, Repository } from "typeorm";
|
|
4
4
|
|
|
5
5
|
//#region src/core/typeorm-outbox.interfaces.d.ts
|
|
6
|
-
type
|
|
6
|
+
type CustomMicroserviceBrokerConfig = {
|
|
7
|
+
strategy: unknown;
|
|
8
|
+
};
|
|
9
|
+
type BrokerConfig = MqttOptions | NatsOptions | KafkaOptions | CustomMicroserviceBrokerConfig | CustomClientOptions;
|
|
7
10
|
declare class TypeormOutboxRegisterCronModuleOptions {
|
|
8
11
|
brokerConfig: BrokerConfig;
|
|
9
12
|
deleteItem?: boolean;
|
|
@@ -146,5 +149,5 @@ declare enum CronExpression {
|
|
|
146
149
|
EVERY_MINUTE = "0 * * * * *"
|
|
147
150
|
}
|
|
148
151
|
//#endregion
|
|
149
|
-
export { CreateOutboxOptions, CronExpression, InjectTypeormOutboxBroker, InjectTypeormOutboxCronConfig, InjectTypeormOutboxModuleConfig, InjectTypeormOutboxService, TYPEORM_OUTBOX_BROKER_TOKEN, TYPEORM_OUTBOX_CRON_CONFIG_TOKEN, TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN, TYPEORM_OUTBOX_SERVICE_TOKEN, TypeormOutboxCronService, TypeormOutboxEntity, TypeormOutboxModule, TypeormOutboxModuleAsyncOptions, TypeormOutboxModuleOptions, TypeormOutboxRegisterCronAsyncOptions, TypeormOutboxRegisterCronModuleOptions, TypeormOutboxService };
|
|
152
|
+
export { CreateOutboxOptions, CronExpression, CustomMicroserviceBrokerConfig, InjectTypeormOutboxBroker, InjectTypeormOutboxCronConfig, InjectTypeormOutboxModuleConfig, InjectTypeormOutboxService, TYPEORM_OUTBOX_BROKER_TOKEN, TYPEORM_OUTBOX_CRON_CONFIG_TOKEN, TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN, TYPEORM_OUTBOX_SERVICE_TOKEN, TypeormOutboxCronService, TypeormOutboxEntity, TypeormOutboxModule, TypeormOutboxModuleAsyncOptions, TypeormOutboxModuleOptions, TypeormOutboxRegisterCronAsyncOptions, TypeormOutboxRegisterCronModuleOptions, TypeormOutboxService };
|
|
150
153
|
//# sourceMappingURL=index.d.cts.map
|
package/dist/index.d.mts
CHANGED
|
@@ -1,9 +1,12 @@
|
|
|
1
1
|
import { DynamicModule, InjectionToken, ModuleMetadata, OnApplicationBootstrap, OnApplicationShutdown, Type } from "@nestjs/common";
|
|
2
2
|
import { DataSource, Repository } from "typeorm";
|
|
3
|
-
import { ClientProxy, KafkaOptions, MqttOptions, NatsOptions } from "@nestjs/microservices";
|
|
3
|
+
import { ClientProxy, CustomClientOptions, KafkaOptions, MqttOptions, NatsOptions } from "@nestjs/microservices";
|
|
4
4
|
|
|
5
5
|
//#region src/core/typeorm-outbox.interfaces.d.ts
|
|
6
|
-
type
|
|
6
|
+
type CustomMicroserviceBrokerConfig = {
|
|
7
|
+
strategy: unknown;
|
|
8
|
+
};
|
|
9
|
+
type BrokerConfig = MqttOptions | NatsOptions | KafkaOptions | CustomMicroserviceBrokerConfig | CustomClientOptions;
|
|
7
10
|
declare class TypeormOutboxRegisterCronModuleOptions {
|
|
8
11
|
brokerConfig: BrokerConfig;
|
|
9
12
|
deleteItem?: boolean;
|
|
@@ -146,5 +149,5 @@ declare enum CronExpression {
|
|
|
146
149
|
EVERY_MINUTE = "0 * * * * *"
|
|
147
150
|
}
|
|
148
151
|
//#endregion
|
|
149
|
-
export { CreateOutboxOptions, CronExpression, InjectTypeormOutboxBroker, InjectTypeormOutboxCronConfig, InjectTypeormOutboxModuleConfig, InjectTypeormOutboxService, TYPEORM_OUTBOX_BROKER_TOKEN, TYPEORM_OUTBOX_CRON_CONFIG_TOKEN, TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN, TYPEORM_OUTBOX_SERVICE_TOKEN, TypeormOutboxCronService, TypeormOutboxEntity, TypeormOutboxModule, TypeormOutboxModuleAsyncOptions, TypeormOutboxModuleOptions, TypeormOutboxRegisterCronAsyncOptions, TypeormOutboxRegisterCronModuleOptions, TypeormOutboxService };
|
|
152
|
+
export { CreateOutboxOptions, CronExpression, CustomMicroserviceBrokerConfig, InjectTypeormOutboxBroker, InjectTypeormOutboxCronConfig, InjectTypeormOutboxModuleConfig, InjectTypeormOutboxService, TYPEORM_OUTBOX_BROKER_TOKEN, TYPEORM_OUTBOX_CRON_CONFIG_TOKEN, TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN, TYPEORM_OUTBOX_SERVICE_TOKEN, TypeormOutboxCronService, TypeormOutboxEntity, TypeormOutboxModule, TypeormOutboxModuleAsyncOptions, TypeormOutboxModuleOptions, TypeormOutboxRegisterCronAsyncOptions, TypeormOutboxRegisterCronModuleOptions, TypeormOutboxService };
|
|
150
153
|
//# sourceMappingURL=index.d.mts.map
|
package/dist/index.mjs
CHANGED
|
@@ -15,12 +15,12 @@ const InjectTypeormOutboxModuleConfig = () => Inject(TYPEORM_OUTBOX_MODULE_CONFI
|
|
|
15
15
|
const InjectTypeormOutboxService = () => Inject(TYPEORM_OUTBOX_SERVICE_TOKEN);
|
|
16
16
|
const InjectTypeormOutboxBroker = () => Inject(TYPEORM_OUTBOX_BROKER_TOKEN);
|
|
17
17
|
//#endregion
|
|
18
|
-
//#region \0@oxc-project+runtime@0.
|
|
18
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorateMetadata.js
|
|
19
19
|
function __decorateMetadata(k, v) {
|
|
20
20
|
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
21
21
|
}
|
|
22
22
|
//#endregion
|
|
23
|
-
//#region \0@oxc-project+runtime@0.
|
|
23
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorate.js
|
|
24
24
|
function __decorate(decorators, target, key, desc) {
|
|
25
25
|
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
26
26
|
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
@@ -123,13 +123,13 @@ var TypeormOutboxRegisterCronModuleOptions = class {
|
|
|
123
123
|
brokerConfig = {};
|
|
124
124
|
deleteItem = true;
|
|
125
125
|
typeOrmConnectionName = "default";
|
|
126
|
-
cronExpression =
|
|
126
|
+
cronExpression = "* * * * * *";
|
|
127
127
|
};
|
|
128
128
|
var TypeormOutboxModuleOptions = class {
|
|
129
129
|
typeOrmConnectionName = "default";
|
|
130
130
|
};
|
|
131
131
|
//#endregion
|
|
132
|
-
//#region \0@oxc-project+runtime@0.
|
|
132
|
+
//#region \0@oxc-project+runtime@0.126.0/helpers/decorateParam.js
|
|
133
133
|
function __decorateParam(paramIndex, decorator) {
|
|
134
134
|
return function(target, key) {
|
|
135
135
|
decorator(target, key, paramIndex);
|
|
@@ -148,7 +148,7 @@ let TypeormOutboxCronService = class TypeormOutboxCronService {
|
|
|
148
148
|
isRunning = false;
|
|
149
149
|
onApplicationBootstrap() {
|
|
150
150
|
this.validateBrokerClient();
|
|
151
|
-
this.cronJob = new CronJob(this.moduleConfig.cronExpression ??
|
|
151
|
+
this.cronJob = new CronJob(this.moduleConfig.cronExpression ?? "* * * * * *", () => {
|
|
152
152
|
if (this.isRunning) return;
|
|
153
153
|
this.isRunning = true;
|
|
154
154
|
this.executeCronJob().finally(() => {
|
|
@@ -163,11 +163,20 @@ let TypeormOutboxCronService = class TypeormOutboxCronService {
|
|
|
163
163
|
}
|
|
164
164
|
validateBrokerClient() {
|
|
165
165
|
const brokerConfig = this.moduleConfig.brokerConfig;
|
|
166
|
+
if (brokerConfig !== null && typeof brokerConfig === "object" && "customClass" in brokerConfig) {
|
|
167
|
+
if (brokerConfig.customClass == null) throw new Error(`[TypeormOutboxCronService] Broker config with customClass must provide a non-null customClass (e.g. PlatformaticKafkaClient)`);
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
if (brokerConfig !== null && typeof brokerConfig === "object" && "strategy" in brokerConfig) {
|
|
171
|
+
if (brokerConfig.strategy == null) throw new Error(`[TypeormOutboxCronService] Custom broker config must provide a non-null strategy (e.g. createPlatformaticKafkaMicroservice)`);
|
|
172
|
+
return;
|
|
173
|
+
}
|
|
174
|
+
const transport = brokerConfig?.transport;
|
|
166
175
|
if (![
|
|
167
176
|
Transport.KAFKA,
|
|
168
177
|
Transport.NATS,
|
|
169
178
|
Transport.MQTT
|
|
170
|
-
].includes(
|
|
179
|
+
].includes(transport)) throw new Error(`[TypeormOutboxCronService] Broker config must be KafkaOptions, NatsOptions, MqttOptions, customClass (e.g. PlatformaticKafkaClient), or a custom strategy (e.g. createPlatformaticKafkaMicroservice)`);
|
|
171
180
|
}
|
|
172
181
|
async executeCronJob() {
|
|
173
182
|
const entities = await this.claimPendingEntities();
|
package/dist/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.mjs","names":[],"sources":["../src/core/typeorm-outbox.di-tokens.ts","../src/core/typeorm-outbox.entity.ts","../src/core/typeorm-outbox.enums.ts","../src/core/typeorm-outbox.interfaces.ts","../src/core/typeorm-outbox-cron.service.ts","../src/core/typeorm-outbox.service.ts","../src/core/typeorm-outbox.module.ts"],"sourcesContent":["import { Inject } from \"@nestjs/common\";\n\nexport const TYPEORM_OUTBOX_CRON_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_CRON_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_SERVICE_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_SERVICE_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_BROKER_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_BROKER_TOKEN\",\n);\n\nexport const InjectTypeormOutboxCronConfig = () =>\n Inject(TYPEORM_OUTBOX_CRON_CONFIG_TOKEN);\nexport const InjectTypeormOutboxModuleConfig = () =>\n Inject(TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN);\nexport const InjectTypeormOutboxService = () =>\n Inject(TYPEORM_OUTBOX_SERVICE_TOKEN);\nexport const InjectTypeormOutboxBroker = () =>\n Inject(TYPEORM_OUTBOX_BROKER_TOKEN);\n","import {\n Column,\n CreateDateColumn,\n Entity,\n PrimaryColumn,\n PrimaryGeneratedColumn,\n UpdateDateColumn,\n} from \"typeorm\";\n\n@Entity(\"outbox_messages\")\nexport class TypeormOutboxEntity {\n @PrimaryColumn()\n id!: string;\n\n @Column({ name: 'status', default: 'pending' })\n status!: string;\n\n @CreateDateColumn({ name: \"created_at\" })\n createdAt!: Date;\n\n @UpdateDateColumn({ name: \"updated_at\" })\n updatedAt!: Date;\n\n @Column(\"character varying\", { name: \"destination_topic\" })\n destinationTopic!: string;\n\n @Column(\"jsonb\", { nullable: true })\n headers!: Record<string, string>;\n\n @Column(\"jsonb\", { nullable: true })\n keys!: Record<string, unknown>;\n\n @Column(\"jsonb\")\n value!: Record<string, any>;\n}\n","export enum CronExpression {\n EVERY_SECOND = \"* * * * * *\",\n EVERY_2_SECONDS = \"*/2 * * * * *\",\n EVERY_3_SECONDS = \"*/3 * * * * *\",\n EVERY_4_SECONDS = \"*/4 * * * * *\",\n EVERY_5_SECONDS = \"*/5 * * * * *\",\n EVERY_6_SECONDS = \"*/6 * * * * *\",\n EVERY_7_SECONDS = \"*/7 * * * * *\",\n EVERY_8_SECONDS = \"*/8 * * * * *\",\n EVERY_9_SECONDS = \"*/9 * * * * *\",\n EVERY_10_SECONDS = \"*/10 * * * * *\",\n EVERY_11_SECONDS = \"*/11 * * * * *\",\n EVERY_12_SECONDS = \"*/12 * * * * *\",\n EVERY_13_SECONDS = \"*/13 * * * * *\",\n EVERY_14_SECONDS = \"*/14 * * * * *\",\n EVERY_15_SECONDS = \"*/15 * * * * *\",\n EVERY_16_SECONDS = \"*/16 * * * * *\",\n EVERY_17_SECONDS = \"*/17 * * * * *\",\n EVERY_18_SECONDS = \"*/18 * * * * *\",\n EVERY_19_SECONDS = \"*/19 * * * * *\",\n EVERY_20_SECONDS = \"*/20 * * * * *\",\n EVERY_21_SECONDS = \"*/21 * * * * *\",\n EVERY_22_SECONDS = \"*/22 * * * * *\",\n EVERY_23_SECONDS = \"*/23 * * * * *\",\n EVERY_24_SECONDS = \"*/24 * * * * *\",\n EVERY_25_SECONDS = \"*/25 * * * * *\",\n EVERY_26_SECONDS = \"*/26 * * * * *\",\n EVERY_27_SECONDS = \"*/27 * * * * *\",\n EVERY_28_SECONDS = \"*/28 * * * * *\",\n EVERY_29_SECONDS = \"*/29 * * * * *\",\n EVERY_30_SECONDS = \"*/30 * * * * *\",\n EVERY_31_SECONDS = \"*/31 * * * * *\",\n EVERY_32_SECONDS = \"*/32 * * * * *\",\n EVERY_33_SECONDS = \"*/33 * * * * *\",\n EVERY_34_SECONDS = \"*/34 * * * * *\",\n EVERY_35_SECONDS = \"*/35 * * * * *\",\n EVERY_36_SECONDS = \"*/36 * * * * *\",\n EVERY_37_SECONDS = \"*/37 * * * * *\",\n EVERY_38_SECONDS = \"*/38 * * * * *\",\n EVERY_39_SECONDS = \"*/39 * * * * *\",\n EVERY_40_SECONDS = \"*/40 * * * * *\",\n EVERY_41_SECONDS = \"*/41 * * * * *\",\n EVERY_42_SECONDS = \"*/42 * * * * *\",\n EVERY_43_SECONDS = \"*/43 * * * * *\",\n EVERY_44_SECONDS = \"*/44 * * * * *\",\n EVERY_45_SECONDS = \"*/45 * * * * *\",\n EVERY_46_SECONDS = \"*/46 * * * * *\",\n EVERY_47_SECONDS = \"*/47 * * * * *\",\n EVERY_48_SECONDS = \"*/48 * * * * *\",\n EVERY_49_SECONDS = \"*/49 * * * * *\",\n EVERY_50_SECONDS = \"*/50 * * * * *\",\n EVERY_51_SECONDS = \"*/51 * * * * *\",\n EVERY_52_SECONDS = \"*/52 * * * * *\",\n EVERY_53_SECONDS = \"*/53 * * * * *\",\n EVERY_54_SECONDS = \"*/54 * * * * *\",\n EVERY_55_SECONDS = \"*/55 * * * * *\",\n EVERY_56_SECONDS = \"*/56 * * * * *\",\n EVERY_57_SECONDS = \"*/57 * * * * *\",\n EVERY_58_SECONDS = \"*/58 * * * * *\",\n EVERY_59_SECONDS = \"*/59 * * * * *\",\n EVERY_MINUTE = \"0 * * * * *\",\n}","import { KafkaOptions, MqttOptions, NatsOptions } from \"@nestjs/microservices\";\nimport { InjectionToken, ModuleMetadata, Type } from \"@nestjs/common\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\ntype BrokerConfig = MqttOptions | NatsOptions | KafkaOptions;\n\nexport class TypeormOutboxRegisterCronModuleOptions {\n brokerConfig: BrokerConfig = {};\n deleteItem?: boolean = true;\n typeOrmConnectionName?: string = \"default\";\n cronExpression?: string = CronExpression.EVERY_SECOND;\n}\n\nexport interface TypeormOutboxRegisterCronAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useExisting?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useClass?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useFactory?: (\n ...args: any[]\n ) =>\n | Promise<TypeormOutboxRegisterCronModuleOptions>\n | TypeormOutboxRegisterCronModuleOptions;\n}\n\nexport class TypeormOutboxModuleOptions {\n typeOrmConnectionName?: string = \"default\";\n}\n\nexport interface TypeormOutboxModuleAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useFactory?: (\n ...args: any[]\n ) => Promise<TypeormOutboxModuleOptions> | TypeormOutboxModuleOptions;\n}\n","import {\n Injectable,\n OnApplicationBootstrap,\n OnApplicationShutdown,\n} from \"@nestjs/common\";\nimport {\n InjectTypeormOutboxBroker,\n InjectTypeormOutboxCronConfig,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { firstValueFrom } from \"rxjs\";\nimport { ClientProxy, Transport } from \"@nestjs/microservices\";\nimport { CronJob } from \"cron\";\nimport { TypeormOutboxRegisterCronModuleOptions } from \"./typeorm-outbox.interfaces\";\nimport { DataSource } from \"typeorm\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\n@Injectable()\nexport class TypeormOutboxCronService\n implements OnApplicationBootstrap, OnApplicationShutdown\n{\n constructor(\n @InjectTypeormOutboxBroker()\n private readonly brokerClient: ClientProxy,\n @InjectTypeormOutboxCronConfig()\n private readonly moduleConfig: TypeormOutboxRegisterCronModuleOptions,\n private readonly dataSource: DataSource,\n ) {}\n\n private cronJob!: CronJob;\n private isRunning = false;\n\n onApplicationBootstrap() {\n this.validateBrokerClient();\n this.cronJob = new CronJob(\n this.moduleConfig.cronExpression ?? CronExpression.EVERY_SECOND,\n () => {\n if (this.isRunning) return;\n this.isRunning = true;\n this.executeCronJob().finally(() => {\n this.isRunning = false;\n });\n },\n );\n this.cronJob.start();\n }\n\n onApplicationShutdown() {\n if (!this.cronJob) {\n return;\n }\n this.cronJob.stop();\n }\n\n private validateBrokerClient() {\n const brokerConfig = this.moduleConfig.brokerConfig;\n if (\n ![Transport.KAFKA, Transport.NATS, Transport.MQTT].includes(\n brokerConfig?.transport as Transport,\n )\n ) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config must be an instance of KafkaOptions, NatsOptions, or MqttOptions`,\n );\n }\n }\n\n private async executeCronJob() {\n const entities = await this.claimPendingEntities();\n if (!entities.length) return;\n\n for (const entity of entities) {\n await firstValueFrom(\n this.brokerClient.emit(entity.destinationTopic, {\n key: entity.keys,\n value: entity.value,\n headers: entity.headers,\n }),\n );\n\n await this.finalizeEntity(entity.id);\n }\n }\n\n private async claimPendingEntities(): Promise<TypeormOutboxEntity[]> {\n const queryRunner = this.dataSource.createQueryRunner();\n await queryRunner.connect();\n\n try {\n await queryRunner.startTransaction();\n\n const entities = await queryRunner.manager\n .createQueryBuilder(TypeormOutboxEntity, \"e\")\n .where(\"e.status = :status\", { status: \"pending\" })\n .orderBy(\"e.createdAt\", \"ASC\")\n .setLock(\"pessimistic_partial_write\")\n .getMany();\n\n if (entities.length) {\n await queryRunner.manager.update(\n TypeormOutboxEntity,\n entities.map((e) => e.id),\n { status: \"processing\" },\n );\n }\n\n await queryRunner.commitTransaction();\n return entities;\n } catch (error) {\n await queryRunner.rollbackTransaction();\n throw error;\n } finally {\n await queryRunner.release();\n }\n }\n\n private async finalizeEntity(id: string): Promise<void> {\n if (this.moduleConfig.deleteItem) {\n await this.dataSource.manager.delete(TypeormOutboxEntity, id);\n } else {\n await this.dataSource.manager.update(\n TypeormOutboxEntity,\n { id },\n { status: \"sent\" },\n );\n }\n }\n}","import { Injectable } from \"@nestjs/common\";\nimport { InjectRepository } from \"@nestjs/typeorm\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { Repository } from \"typeorm\";\nimport { randomUUID } from \"crypto\";\n\nexport interface CreateOutboxOptions {\n destinationTopic: string;\n value: any;\n headers?: any;\n keys?: any;\n}\n\n@Injectable()\nexport class TypeormOutboxService {\n constructor(\n @InjectRepository(TypeormOutboxEntity)\n private readonly outboxRepository: Repository<TypeormOutboxEntity>,\n ) {}\n\n async create(options: CreateOutboxOptions): Promise<TypeormOutboxEntity> {\n return this.outboxRepository.save({\n id: randomUUID(),\n destinationTopic: options.destinationTopic,\n headers: options.headers,\n keys: options.keys,\n value: options.value,\n });\n }\n}\n","import { TypeOrmModule } from \"@nestjs/typeorm\";\nimport { DynamicModule, Module, Provider } from \"@nestjs/common\";\nimport {\n TypeormOutboxRegisterCronAsyncOptions,\n TypeormOutboxRegisterCronModuleOptions,\n TypeormOutboxModuleOptions,\n TypeormOutboxModuleAsyncOptions,\n} from \"./typeorm-outbox.interfaces\";\nimport {\n TYPEORM_OUTBOX_BROKER_TOKEN,\n TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n TYPEORM_OUTBOX_SERVICE_TOKEN,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { TypeormOutboxService } from \"./typeorm-outbox.service\";\nimport { ClientProxyFactory } from \"@nestjs/microservices\";\nimport { TypeormOutboxCronService } from \"./typeorm-outbox-cron.service\";\n\nconst serviceProvider = (): Provider => ({\n provide: TYPEORM_OUTBOX_SERVICE_TOKEN,\n useClass: TypeormOutboxService,\n});\n\nconst brokerProvider = (useValue: any = {}): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useValue,\n});\n\nconst typeOrmFeature = (connectionName = \"default\") =>\n TypeOrmModule.forFeature([TypeormOutboxEntity], connectionName);\n\nconst mergeModuleOptions = <T extends object>(\n defaults: new () => T,\n overrides?: Partial<T>,\n): T => ({ ...new defaults(), ...overrides });\n\nconst moduleConfigProvider = (\n options: TypeormOutboxModuleOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useValue: mergeModuleOptions(TypeormOutboxModuleOptions, options),\n});\n\nconst asyncModuleConfigProvider = (\n options: TypeormOutboxModuleAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronConfigProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronBrokerProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useFactory: async (...args: any[]) => {\n const config = mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n );\n return ClientProxyFactory.create(config?.brokerConfig ?? {});\n },\n inject: options.inject || [],\n});\n\n@Module({})\nexport class TypeormOutboxModule {\n static forRoot(options: TypeormOutboxModuleOptions = {}): DynamicModule {\n const providers = [\n moduleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature(options.typeOrmConnectionName)],\n providers,\n exports: providers,\n };\n }\n\n static forRootAsync(options: TypeormOutboxModuleAsyncOptions): DynamicModule {\n const providers = [\n asyncModuleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers,\n exports: providers,\n };\n }\n\n static registerCronAsync(\n options: TypeormOutboxRegisterCronAsyncOptions,\n ): DynamicModule {\n const providers = [\n cronConfigProvider(options),\n cronBrokerProvider(options),\n serviceProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers: [TypeormOutboxCronService, ...providers],\n exports: providers,\n };\n }\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.mjs","names":[],"sources":["../src/core/typeorm-outbox.di-tokens.ts","../src/core/typeorm-outbox.entity.ts","../src/core/typeorm-outbox.enums.ts","../src/core/typeorm-outbox.interfaces.ts","../src/core/typeorm-outbox-cron.service.ts","../src/core/typeorm-outbox.service.ts","../src/core/typeorm-outbox.module.ts"],"sourcesContent":["import { Inject } from \"@nestjs/common\";\n\nexport const TYPEORM_OUTBOX_CRON_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_CRON_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_SERVICE_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_SERVICE_TOKEN\",\n);\nexport const TYPEORM_OUTBOX_BROKER_TOKEN = Symbol(\n \"TYPEORM_OUTBOX_BROKER_TOKEN\",\n);\n\nexport const InjectTypeormOutboxCronConfig = () =>\n Inject(TYPEORM_OUTBOX_CRON_CONFIG_TOKEN);\nexport const InjectTypeormOutboxModuleConfig = () =>\n Inject(TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN);\nexport const InjectTypeormOutboxService = () =>\n Inject(TYPEORM_OUTBOX_SERVICE_TOKEN);\nexport const InjectTypeormOutboxBroker = () =>\n Inject(TYPEORM_OUTBOX_BROKER_TOKEN);\n","import {\n Column,\n CreateDateColumn,\n Entity,\n PrimaryColumn,\n PrimaryGeneratedColumn,\n UpdateDateColumn,\n} from \"typeorm\";\n\n@Entity(\"outbox_messages\")\nexport class TypeormOutboxEntity {\n @PrimaryColumn()\n id!: string;\n\n @Column({ name: 'status', default: 'pending' })\n status!: string;\n\n @CreateDateColumn({ name: \"created_at\" })\n createdAt!: Date;\n\n @UpdateDateColumn({ name: \"updated_at\" })\n updatedAt!: Date;\n\n @Column(\"character varying\", { name: \"destination_topic\" })\n destinationTopic!: string;\n\n @Column(\"jsonb\", { nullable: true })\n headers!: Record<string, string>;\n\n @Column(\"jsonb\", { nullable: true })\n keys!: Record<string, unknown>;\n\n @Column(\"jsonb\")\n value!: Record<string, any>;\n}\n","export enum CronExpression {\n EVERY_SECOND = \"* * * * * *\",\n EVERY_2_SECONDS = \"*/2 * * * * *\",\n EVERY_3_SECONDS = \"*/3 * * * * *\",\n EVERY_4_SECONDS = \"*/4 * * * * *\",\n EVERY_5_SECONDS = \"*/5 * * * * *\",\n EVERY_6_SECONDS = \"*/6 * * * * *\",\n EVERY_7_SECONDS = \"*/7 * * * * *\",\n EVERY_8_SECONDS = \"*/8 * * * * *\",\n EVERY_9_SECONDS = \"*/9 * * * * *\",\n EVERY_10_SECONDS = \"*/10 * * * * *\",\n EVERY_11_SECONDS = \"*/11 * * * * *\",\n EVERY_12_SECONDS = \"*/12 * * * * *\",\n EVERY_13_SECONDS = \"*/13 * * * * *\",\n EVERY_14_SECONDS = \"*/14 * * * * *\",\n EVERY_15_SECONDS = \"*/15 * * * * *\",\n EVERY_16_SECONDS = \"*/16 * * * * *\",\n EVERY_17_SECONDS = \"*/17 * * * * *\",\n EVERY_18_SECONDS = \"*/18 * * * * *\",\n EVERY_19_SECONDS = \"*/19 * * * * *\",\n EVERY_20_SECONDS = \"*/20 * * * * *\",\n EVERY_21_SECONDS = \"*/21 * * * * *\",\n EVERY_22_SECONDS = \"*/22 * * * * *\",\n EVERY_23_SECONDS = \"*/23 * * * * *\",\n EVERY_24_SECONDS = \"*/24 * * * * *\",\n EVERY_25_SECONDS = \"*/25 * * * * *\",\n EVERY_26_SECONDS = \"*/26 * * * * *\",\n EVERY_27_SECONDS = \"*/27 * * * * *\",\n EVERY_28_SECONDS = \"*/28 * * * * *\",\n EVERY_29_SECONDS = \"*/29 * * * * *\",\n EVERY_30_SECONDS = \"*/30 * * * * *\",\n EVERY_31_SECONDS = \"*/31 * * * * *\",\n EVERY_32_SECONDS = \"*/32 * * * * *\",\n EVERY_33_SECONDS = \"*/33 * * * * *\",\n EVERY_34_SECONDS = \"*/34 * * * * *\",\n EVERY_35_SECONDS = \"*/35 * * * * *\",\n EVERY_36_SECONDS = \"*/36 * * * * *\",\n EVERY_37_SECONDS = \"*/37 * * * * *\",\n EVERY_38_SECONDS = \"*/38 * * * * *\",\n EVERY_39_SECONDS = \"*/39 * * * * *\",\n EVERY_40_SECONDS = \"*/40 * * * * *\",\n EVERY_41_SECONDS = \"*/41 * * * * *\",\n EVERY_42_SECONDS = \"*/42 * * * * *\",\n EVERY_43_SECONDS = \"*/43 * * * * *\",\n EVERY_44_SECONDS = \"*/44 * * * * *\",\n EVERY_45_SECONDS = \"*/45 * * * * *\",\n EVERY_46_SECONDS = \"*/46 * * * * *\",\n EVERY_47_SECONDS = \"*/47 * * * * *\",\n EVERY_48_SECONDS = \"*/48 * * * * *\",\n EVERY_49_SECONDS = \"*/49 * * * * *\",\n EVERY_50_SECONDS = \"*/50 * * * * *\",\n EVERY_51_SECONDS = \"*/51 * * * * *\",\n EVERY_52_SECONDS = \"*/52 * * * * *\",\n EVERY_53_SECONDS = \"*/53 * * * * *\",\n EVERY_54_SECONDS = \"*/54 * * * * *\",\n EVERY_55_SECONDS = \"*/55 * * * * *\",\n EVERY_56_SECONDS = \"*/56 * * * * *\",\n EVERY_57_SECONDS = \"*/57 * * * * *\",\n EVERY_58_SECONDS = \"*/58 * * * * *\",\n EVERY_59_SECONDS = \"*/59 * * * * *\",\n EVERY_MINUTE = \"0 * * * * *\",\n}","import {\n type CustomClientOptions,\n KafkaOptions,\n MqttOptions,\n NatsOptions,\n} from \"@nestjs/microservices\";\nimport { InjectionToken, ModuleMetadata, Type } from \"@nestjs/common\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\nexport type CustomMicroserviceBrokerConfig = {\n strategy: unknown;\n};\n\ntype BrokerConfig =\n | MqttOptions\n | NatsOptions\n | KafkaOptions\n | CustomMicroserviceBrokerConfig\n | CustomClientOptions;\n\nexport class TypeormOutboxRegisterCronModuleOptions {\n brokerConfig: BrokerConfig = {};\n deleteItem?: boolean = true;\n typeOrmConnectionName?: string = \"default\";\n cronExpression?: string = CronExpression.EVERY_SECOND;\n}\n\nexport interface TypeormOutboxRegisterCronAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useExisting?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useClass?: Type<TypeormOutboxRegisterCronModuleOptions>;\n useFactory?: (\n ...args: any[]\n ) =>\n | Promise<TypeormOutboxRegisterCronModuleOptions>\n | TypeormOutboxRegisterCronModuleOptions;\n}\n\nexport class TypeormOutboxModuleOptions {\n typeOrmConnectionName?: string = \"default\";\n}\n\nexport interface TypeormOutboxModuleAsyncOptions extends Pick<\n ModuleMetadata,\n \"imports\"\n> {\n inject?: InjectionToken[];\n useFactory?: (\n ...args: any[]\n ) => Promise<TypeormOutboxModuleOptions> | TypeormOutboxModuleOptions;\n}\n","import {\n Injectable,\n OnApplicationBootstrap,\n OnApplicationShutdown,\n} from \"@nestjs/common\";\nimport {\n InjectTypeormOutboxBroker,\n InjectTypeormOutboxCronConfig,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { firstValueFrom } from \"rxjs\";\nimport {\n type CustomClientOptions,\n ClientProxy,\n Transport,\n} from \"@nestjs/microservices\";\nimport { CronJob } from \"cron\";\nimport { TypeormOutboxRegisterCronModuleOptions } from \"./typeorm-outbox.interfaces\";\nimport { DataSource } from \"typeorm\";\nimport { CronExpression } from \"./typeorm-outbox.enums\";\n\n@Injectable()\nexport class TypeormOutboxCronService\n implements OnApplicationBootstrap, OnApplicationShutdown\n{\n constructor(\n @InjectTypeormOutboxBroker()\n private readonly brokerClient: ClientProxy,\n @InjectTypeormOutboxCronConfig()\n private readonly moduleConfig: TypeormOutboxRegisterCronModuleOptions,\n private readonly dataSource: DataSource,\n ) {}\n\n private cronJob!: CronJob;\n private isRunning = false;\n\n onApplicationBootstrap() {\n this.validateBrokerClient();\n this.cronJob = new CronJob(\n this.moduleConfig.cronExpression ?? CronExpression.EVERY_SECOND,\n () => {\n if (this.isRunning) return;\n this.isRunning = true;\n this.executeCronJob().finally(() => {\n this.isRunning = false;\n });\n },\n );\n this.cronJob.start();\n }\n\n onApplicationShutdown() {\n if (!this.cronJob) {\n return;\n }\n this.cronJob.stop();\n }\n\n private validateBrokerClient() {\n const brokerConfig = this.moduleConfig.brokerConfig;\n if (\n brokerConfig !== null &&\n typeof brokerConfig === \"object\" &&\n \"customClass\" in brokerConfig\n ) {\n if ((brokerConfig as CustomClientOptions).customClass == null) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config with customClass must provide a non-null customClass (e.g. PlatformaticKafkaClient)`,\n );\n }\n return;\n }\n if (\n brokerConfig !== null &&\n typeof brokerConfig === \"object\" &&\n \"strategy\" in brokerConfig\n ) {\n if ((brokerConfig as { strategy?: unknown }).strategy == null) {\n throw new Error(\n `[TypeormOutboxCronService] Custom broker config must provide a non-null strategy (e.g. createPlatformaticKafkaMicroservice)`,\n );\n }\n return;\n }\n const transport = (brokerConfig as { transport?: Transport } | null)\n ?.transport;\n if (\n ![Transport.KAFKA, Transport.NATS, Transport.MQTT].includes(\n transport as Transport,\n )\n ) {\n throw new Error(\n `[TypeormOutboxCronService] Broker config must be KafkaOptions, NatsOptions, MqttOptions, customClass (e.g. PlatformaticKafkaClient), or a custom strategy (e.g. createPlatformaticKafkaMicroservice)`,\n );\n }\n }\n\n private async executeCronJob() {\n const entities = await this.claimPendingEntities();\n if (!entities.length) return;\n\n for (const entity of entities) {\n await firstValueFrom(\n this.brokerClient.emit(entity.destinationTopic, {\n key: entity.keys,\n value: entity.value,\n headers: entity.headers,\n }),\n );\n\n await this.finalizeEntity(entity.id);\n }\n }\n\n private async claimPendingEntities(): Promise<TypeormOutboxEntity[]> {\n const queryRunner = this.dataSource.createQueryRunner();\n await queryRunner.connect();\n\n try {\n await queryRunner.startTransaction();\n\n const entities = await queryRunner.manager\n .createQueryBuilder(TypeormOutboxEntity, \"e\")\n .where(\"e.status = :status\", { status: \"pending\" })\n .orderBy(\"e.createdAt\", \"ASC\")\n .setLock(\"pessimistic_partial_write\")\n .getMany();\n\n if (entities.length) {\n await queryRunner.manager.update(\n TypeormOutboxEntity,\n entities.map((e) => e.id),\n { status: \"processing\" },\n );\n }\n\n await queryRunner.commitTransaction();\n return entities;\n } catch (error) {\n await queryRunner.rollbackTransaction();\n throw error;\n } finally {\n await queryRunner.release();\n }\n }\n\n private async finalizeEntity(id: string): Promise<void> {\n if (this.moduleConfig.deleteItem) {\n await this.dataSource.manager.delete(TypeormOutboxEntity, id);\n } else {\n await this.dataSource.manager.update(\n TypeormOutboxEntity,\n { id },\n { status: \"sent\" },\n );\n }\n }\n}\n","import { Injectable } from \"@nestjs/common\";\nimport { InjectRepository } from \"@nestjs/typeorm\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { Repository } from \"typeorm\";\nimport { randomUUID } from \"crypto\";\n\nexport interface CreateOutboxOptions {\n destinationTopic: string;\n value: any;\n headers?: any;\n keys?: any;\n}\n\n@Injectable()\nexport class TypeormOutboxService {\n constructor(\n @InjectRepository(TypeormOutboxEntity)\n private readonly outboxRepository: Repository<TypeormOutboxEntity>,\n ) {}\n\n async create(options: CreateOutboxOptions): Promise<TypeormOutboxEntity> {\n return this.outboxRepository.save({\n id: randomUUID(),\n destinationTopic: options.destinationTopic,\n headers: options.headers,\n keys: options.keys,\n value: options.value,\n });\n }\n}\n","import { TypeOrmModule } from \"@nestjs/typeorm\";\nimport { DynamicModule, Module, Provider } from \"@nestjs/common\";\nimport {\n TypeormOutboxRegisterCronAsyncOptions,\n TypeormOutboxRegisterCronModuleOptions,\n TypeormOutboxModuleOptions,\n TypeormOutboxModuleAsyncOptions,\n} from \"./typeorm-outbox.interfaces\";\nimport {\n TYPEORM_OUTBOX_BROKER_TOKEN,\n TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n TYPEORM_OUTBOX_SERVICE_TOKEN,\n} from \"./typeorm-outbox.di-tokens\";\nimport { TypeormOutboxEntity } from \"./typeorm-outbox.entity\";\nimport { TypeormOutboxService } from \"./typeorm-outbox.service\";\nimport { ClientProxyFactory } from \"@nestjs/microservices\";\nimport { TypeormOutboxCronService } from \"./typeorm-outbox-cron.service\";\n\nconst serviceProvider = (): Provider => ({\n provide: TYPEORM_OUTBOX_SERVICE_TOKEN,\n useClass: TypeormOutboxService,\n});\n\nconst brokerProvider = (useValue: any = {}): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useValue,\n});\n\nconst typeOrmFeature = (connectionName = \"default\") =>\n TypeOrmModule.forFeature([TypeormOutboxEntity], connectionName);\n\nconst mergeModuleOptions = <T extends object>(\n defaults: new () => T,\n overrides?: Partial<T>,\n): T => ({ ...new defaults(), ...overrides });\n\nconst moduleConfigProvider = (\n options: TypeormOutboxModuleOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useValue: mergeModuleOptions(TypeormOutboxModuleOptions, options),\n});\n\nconst asyncModuleConfigProvider = (\n options: TypeormOutboxModuleAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_MODULE_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronConfigProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_CRON_CONFIG_TOKEN,\n useFactory: async (...args: any[]) =>\n mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n ),\n inject: options.inject || [],\n});\n\nconst cronBrokerProvider = (\n options: TypeormOutboxRegisterCronAsyncOptions,\n): Provider => ({\n provide: TYPEORM_OUTBOX_BROKER_TOKEN,\n useFactory: async (...args: any[]) => {\n const config = mergeModuleOptions(\n TypeormOutboxRegisterCronModuleOptions,\n await options.useFactory?.(...args),\n );\n return ClientProxyFactory.create(config?.brokerConfig ?? {});\n },\n inject: options.inject || [],\n});\n\n@Module({})\nexport class TypeormOutboxModule {\n static forRoot(options: TypeormOutboxModuleOptions = {}): DynamicModule {\n const providers = [\n moduleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature(options.typeOrmConnectionName)],\n providers,\n exports: providers,\n };\n }\n\n static forRootAsync(options: TypeormOutboxModuleAsyncOptions): DynamicModule {\n const providers = [\n asyncModuleConfigProvider(options),\n serviceProvider(),\n brokerProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers,\n exports: providers,\n };\n }\n\n static registerCronAsync(\n options: TypeormOutboxRegisterCronAsyncOptions,\n ): DynamicModule {\n const providers = [\n cronConfigProvider(options),\n cronBrokerProvider(options),\n serviceProvider(),\n ];\n return {\n module: TypeormOutboxModule,\n global: true,\n imports: [typeOrmFeature()],\n providers: [TypeormOutboxCronService, ...providers],\n exports: providers,\n };\n }\n}\n"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@globalart/nestjs-typeorm-outbox",
|
|
3
3
|
"description": "TypeORM Outbox integration for NestJS",
|
|
4
|
-
"version": "1.7.
|
|
4
|
+
"version": "1.7.4",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.mjs",
|
|
7
7
|
"module": "dist/index.mjs",
|
|
@@ -49,6 +49,7 @@
|
|
|
49
49
|
"cron": "^4.4.0",
|
|
50
50
|
"kafkajs": "^2.2.4",
|
|
51
51
|
"lodash": "^4.17.23",
|
|
52
|
+
"@globalart/platformatic-kafka": "^1.0.0",
|
|
52
53
|
"rxjs": "^7.8.2"
|
|
53
54
|
},
|
|
54
55
|
"peerDependencies": {
|
|
@@ -59,11 +60,11 @@
|
|
|
59
60
|
"typeorm": "^0.3.0"
|
|
60
61
|
},
|
|
61
62
|
"devDependencies": {
|
|
62
|
-
"@types/node": "25.
|
|
63
|
+
"@types/node": "25.6.0",
|
|
63
64
|
"prettier": "^3.8.1",
|
|
64
65
|
"reflect-metadata": "^0.2.2",
|
|
65
|
-
"release-it": "
|
|
66
|
-
"tsdown": "0.21.
|
|
66
|
+
"release-it": "20.0.0",
|
|
67
|
+
"tsdown": "0.21.9",
|
|
67
68
|
"typescript": "^6.0.2"
|
|
68
69
|
}
|
|
69
70
|
}
|