@memberjunction/scheduling-engine-base 2.107.0

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.
@@ -0,0 +1,73 @@
1
+ /**
2
+ * @fileoverview Extended ScheduledJob entity with helper methods
3
+ * @module @memberjunction/scheduling-engine-base
4
+ */
5
+ import { ScheduledJobEntity } from '@memberjunction/core-entities';
6
+ /**
7
+ * Extended ScheduledJob entity with scheduling helper methods
8
+ *
9
+ * Provides utilities for:
10
+ * - Calculating next run times
11
+ * - Determining minimum intervals
12
+ * - Validating cron expressions
13
+ */
14
+ export declare class ScheduledJobEntityExtended extends ScheduledJobEntity {
15
+ /**
16
+ * Calculate time in milliseconds until next execution
17
+ * Note: Requires cron-parser, which is not available in base-engine
18
+ * This method is a placeholder for server-side implementation
19
+ */
20
+ GetTimeUntilNextRun(): number;
21
+ /**
22
+ * Check if this job is currently locked by an execution
23
+ */
24
+ get IsLocked(): boolean;
25
+ /**
26
+ * Check if lock is potentially stale
27
+ */
28
+ get IsLockStale(): boolean;
29
+ /**
30
+ * Get the server instance that holds the current lock
31
+ */
32
+ get CurrentLockHolder(): string | null;
33
+ /**
34
+ * Check if job allows concurrent runs
35
+ */
36
+ get AllowsConcurrent(): boolean;
37
+ /**
38
+ * Check if job queues overlapping runs
39
+ */
40
+ get QueuesOverlappingRuns(): boolean;
41
+ /**
42
+ * Check if job skips overlapping runs
43
+ */
44
+ get SkipsOverlappingRuns(): boolean;
45
+ /**
46
+ * Get success rate as percentage (0-100)
47
+ */
48
+ get SuccessRate(): number;
49
+ /**
50
+ * Get failure rate as percentage (0-100)
51
+ */
52
+ get FailureRate(): number;
53
+ /**
54
+ * Override Save to update polling interval cache after saving
55
+ */
56
+ Save(options?: any): Promise<boolean>;
57
+ /**
58
+ * Override Delete to update polling interval cache after deletion
59
+ */
60
+ Delete(): Promise<boolean>;
61
+ /**
62
+ * Notify the scheduling engine about job changes
63
+ * This method reloads job metadata and restarts polling if needed
64
+ * @private
65
+ */
66
+ private notifyEngineOfChange;
67
+ }
68
+ /**
69
+ * Loader function to ensure this class is registered
70
+ * Prevents tree-shaking from removing the class
71
+ */
72
+ export declare function LoadScheduledJobEntityExtended(): void;
73
+ //# sourceMappingURL=ScheduledJobEntityExtended.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ScheduledJobEntityExtended.d.ts","sourceRoot":"","sources":["../src/ScheduledJobEntityExtended.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,kBAAkB,EAAE,MAAM,+BAA+B,CAAC;AAInE;;;;;;;GAOG;AACH,qBACa,0BAA2B,SAAQ,kBAAkB;IAC9D;;;;OAIG;IACI,mBAAmB,IAAI,MAAM;IAOpC;;OAEG;IACH,IAAW,QAAQ,IAAI,OAAO,CAE7B;IAED;;OAEG;IACH,IAAW,WAAW,IAAI,OAAO,CAKhC;IAED;;OAEG;IACH,IAAW,iBAAiB,IAAI,MAAM,GAAG,IAAI,CAE5C;IAED;;OAEG;IACH,IAAW,gBAAgB,IAAI,OAAO,CAErC;IAED;;OAEG;IACH,IAAW,qBAAqB,IAAI,OAAO,CAE1C;IAED;;OAEG;IACH,IAAW,oBAAoB,IAAI,OAAO,CAEzC;IAED;;OAEG;IACH,IAAW,WAAW,IAAI,MAAM,CAK/B;IAED;;OAEG;IACH,IAAW,WAAW,IAAI,MAAM,CAK/B;IAED;;OAEG;IACmB,IAAI,CAAC,OAAO,CAAC,EAAE,GAAG,GAAG,OAAO,CAAC,OAAO,CAAC;IAgB3D;;OAEG;IACmB,MAAM,IAAI,OAAO,CAAC,OAAO,CAAC;IAgBhD;;;;OAIG;YACW,oBAAoB;CASrC;AAED;;;GAGG;AACH,wBAAgB,8BAA8B,IAAI,IAAI,CAErD"}
@@ -0,0 +1,153 @@
1
+ "use strict";
2
+ /**
3
+ * @fileoverview Extended ScheduledJob entity with helper methods
4
+ * @module @memberjunction/scheduling-engine-base
5
+ */
6
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
7
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
8
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
9
+ 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;
10
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
11
+ };
12
+ Object.defineProperty(exports, "__esModule", { value: true });
13
+ exports.LoadScheduledJobEntityExtended = exports.ScheduledJobEntityExtended = void 0;
14
+ const core_entities_1 = require("@memberjunction/core-entities");
15
+ const global_1 = require("@memberjunction/global");
16
+ const SchedulingEngineBase_1 = require("./SchedulingEngineBase");
17
+ /**
18
+ * Extended ScheduledJob entity with scheduling helper methods
19
+ *
20
+ * Provides utilities for:
21
+ * - Calculating next run times
22
+ * - Determining minimum intervals
23
+ * - Validating cron expressions
24
+ */
25
+ let ScheduledJobEntityExtended = class ScheduledJobEntityExtended extends core_entities_1.ScheduledJobEntity {
26
+ /**
27
+ * Calculate time in milliseconds until next execution
28
+ * Note: Requires cron-parser, which is not available in base-engine
29
+ * This method is a placeholder for server-side implementation
30
+ */
31
+ GetTimeUntilNextRun() {
32
+ if (this.NextRunAt) {
33
+ return Math.max(0, this.NextRunAt.getTime() - Date.now());
34
+ }
35
+ return 0;
36
+ }
37
+ /**
38
+ * Check if this job is currently locked by an execution
39
+ */
40
+ get IsLocked() {
41
+ return this.LockToken != null;
42
+ }
43
+ /**
44
+ * Check if lock is potentially stale
45
+ */
46
+ get IsLockStale() {
47
+ if (!this.IsLocked || !this.ExpectedCompletionAt) {
48
+ return false;
49
+ }
50
+ return new Date() > this.ExpectedCompletionAt;
51
+ }
52
+ /**
53
+ * Get the server instance that holds the current lock
54
+ */
55
+ get CurrentLockHolder() {
56
+ return this.LockedByInstance;
57
+ }
58
+ /**
59
+ * Check if job allows concurrent runs
60
+ */
61
+ get AllowsConcurrent() {
62
+ return this.ConcurrencyMode === 'Concurrent';
63
+ }
64
+ /**
65
+ * Check if job queues overlapping runs
66
+ */
67
+ get QueuesOverlappingRuns() {
68
+ return this.ConcurrencyMode === 'Queue';
69
+ }
70
+ /**
71
+ * Check if job skips overlapping runs
72
+ */
73
+ get SkipsOverlappingRuns() {
74
+ return this.ConcurrencyMode === 'Skip';
75
+ }
76
+ /**
77
+ * Get success rate as percentage (0-100)
78
+ */
79
+ get SuccessRate() {
80
+ if (this.RunCount === 0) {
81
+ return 0;
82
+ }
83
+ return (this.SuccessCount / this.RunCount) * 100;
84
+ }
85
+ /**
86
+ * Get failure rate as percentage (0-100)
87
+ */
88
+ get FailureRate() {
89
+ if (this.RunCount === 0) {
90
+ return 0;
91
+ }
92
+ return (this.FailureCount / this.RunCount) * 100;
93
+ }
94
+ /**
95
+ * Override Save to update polling interval cache after saving
96
+ */
97
+ async Save(options) {
98
+ const result = await super.Save(options);
99
+ if (result) {
100
+ // Notify the scheduling engine about the change
101
+ try {
102
+ await this.notifyEngineOfChange();
103
+ }
104
+ catch (error) {
105
+ // Log but don't fail the save operation
106
+ console.error('Failed to notify engine after save:', error);
107
+ }
108
+ }
109
+ return result;
110
+ }
111
+ /**
112
+ * Override Delete to update polling interval cache after deletion
113
+ */
114
+ async Delete() {
115
+ const result = await super.Delete();
116
+ if (result) {
117
+ // Notify the scheduling engine about the change
118
+ try {
119
+ await this.notifyEngineOfChange();
120
+ }
121
+ catch (error) {
122
+ // Log but don't fail the delete operation
123
+ console.error('Failed to notify engine after delete:', error);
124
+ }
125
+ }
126
+ return result;
127
+ }
128
+ /**
129
+ * Notify the scheduling engine about job changes
130
+ * This method reloads job metadata and restarts polling if needed
131
+ * @private
132
+ */
133
+ async notifyEngineOfChange() {
134
+ const engine = SchedulingEngineBase_1.SchedulingEngineBase.Instance;
135
+ // Force reload of job metadata
136
+ await engine.Config(true, this.ContextCurrentUser);
137
+ // Recalculate polling interval (will set to null if no jobs)
138
+ engine.UpdatePollingInterval();
139
+ }
140
+ };
141
+ exports.ScheduledJobEntityExtended = ScheduledJobEntityExtended;
142
+ exports.ScheduledJobEntityExtended = ScheduledJobEntityExtended = __decorate([
143
+ (0, global_1.RegisterClass)(core_entities_1.ScheduledJobEntity, 'ScheduledJobEntityExtended')
144
+ ], ScheduledJobEntityExtended);
145
+ /**
146
+ * Loader function to ensure this class is registered
147
+ * Prevents tree-shaking from removing the class
148
+ */
149
+ function LoadScheduledJobEntityExtended() {
150
+ // No-op function, just ensures class is loaded
151
+ }
152
+ exports.LoadScheduledJobEntityExtended = LoadScheduledJobEntityExtended;
153
+ //# sourceMappingURL=ScheduledJobEntityExtended.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ScheduledJobEntityExtended.js","sourceRoot":"","sources":["../src/ScheduledJobEntityExtended.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,76 @@
1
+ /**
2
+ * @fileoverview Base scheduling engine with metadata caching
3
+ * @module @memberjunction/scheduling-engine-base
4
+ */
5
+ import { BaseEngine, IMetadataProvider, UserInfo } from '@memberjunction/core';
6
+ import { ScheduledJobEntity, ScheduledJobTypeEntity, ScheduledJobRunEntity } from '@memberjunction/core-entities';
7
+ /**
8
+ * Base engine for scheduling system with metadata caching
9
+ *
10
+ * This engine loads and caches scheduling metadata including:
11
+ * - Scheduled job types (plugin registry)
12
+ * - Active scheduled jobs
13
+ * - Recent job runs (optional)
14
+ *
15
+ * Can be used anywhere (client or server) for accessing scheduling metadata.
16
+ * For actual job execution, use SchedulingEngine from @memberjunction/scheduling-engine.
17
+ */
18
+ export declare class SchedulingEngineBase extends BaseEngine<SchedulingEngineBase> {
19
+ private _scheduledJobTypes;
20
+ private _scheduledJobs;
21
+ private _scheduledJobRuns;
22
+ private _activePollingInterval;
23
+ /**
24
+ * Configure the engine by loading metadata
25
+ *
26
+ * @param forceRefresh - Whether to force reload from database
27
+ * @param contextUser - User context for data access
28
+ * @param provider - Optional metadata provider
29
+ * @param includeRuns - Whether to load recent job runs (default: false)
30
+ * @param includeAllJobs - Whether to load all jobs regardless of status (default: false, only loads Active)
31
+ */
32
+ Config(forceRefresh?: boolean, contextUser?: UserInfo, provider?: IMetadataProvider, includeRuns?: boolean, includeAllJobs?: boolean): Promise<boolean>;
33
+ /**
34
+ * Get all scheduled job types
35
+ */
36
+ get ScheduledJobTypes(): ScheduledJobTypeEntity[];
37
+ /**
38
+ * Get scheduled jobs (active only by default, unless includeAllJobs was set in Config)
39
+ */
40
+ get ScheduledJobs(): ScheduledJobEntity[];
41
+ /**
42
+ * Get recent scheduled job runs (only populated if includeRuns was set in Config)
43
+ */
44
+ get ScheduledJobRuns(): ScheduledJobRunEntity[];
45
+ /**
46
+ * Find a job type by name
47
+ */
48
+ GetJobTypeByName(name: string): ScheduledJobTypeEntity | undefined;
49
+ /**
50
+ * Find a job type by driver class
51
+ */
52
+ GetJobTypeByDriverClass(driverClass: string): ScheduledJobTypeEntity | undefined;
53
+ /**
54
+ * Get all jobs of a specific type
55
+ */
56
+ GetJobsByType(jobTypeId: string): ScheduledJobEntity[];
57
+ /**
58
+ * Get runs for a specific job
59
+ */
60
+ GetRunsForJob(jobId: string): ScheduledJobRunEntity[];
61
+ /**
62
+ * Get the current active polling interval in milliseconds
63
+ * Returns null if no jobs are active (polling should be stopped)
64
+ */
65
+ get ActivePollingInterval(): number | null;
66
+ /**
67
+ * Calculate and update the active polling interval based on scheduled jobs
68
+ * This should be called whenever jobs are added, modified, or deleted
69
+ */
70
+ UpdatePollingInterval(): void;
71
+ /**
72
+ * Get singleton instance
73
+ */
74
+ static get Instance(): SchedulingEngineBase;
75
+ }
76
+ //# sourceMappingURL=SchedulingEngineBase.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SchedulingEngineBase.d.ts","sourceRoot":"","sources":["../src/SchedulingEngineBase.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,UAAU,EAA4B,iBAAiB,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AACzG,OAAO,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AAElH;;;;;;;;;;GAUG;AACH,qBAAa,oBAAqB,SAAQ,UAAU,CAAC,oBAAoB,CAAC;IACtE,OAAO,CAAC,kBAAkB,CAAgC;IAC1D,OAAO,CAAC,cAAc,CAA4B;IAClD,OAAO,CAAC,iBAAiB,CAA+B;IACxD,OAAO,CAAC,sBAAsB,CAAwB;IAEtD;;;;;;;;OAQG;IACU,MAAM,CACf,YAAY,CAAC,EAAE,OAAO,EACtB,WAAW,CAAC,EAAE,QAAQ,EACtB,QAAQ,CAAC,EAAE,iBAAiB,EAC5B,WAAW,GAAE,OAAe,EAC5B,cAAc,GAAE,OAAe,GAChC,OAAO,CAAC,OAAO,CAAC;IAqCnB;;OAEG;IACH,IAAW,iBAAiB,IAAI,sBAAsB,EAAE,CAEvD;IAED;;OAEG;IACH,IAAW,aAAa,IAAI,kBAAkB,EAAE,CAE/C;IAED;;OAEG;IACH,IAAW,gBAAgB,IAAI,qBAAqB,EAAE,CAErD;IAED;;OAEG;IACI,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,sBAAsB,GAAG,SAAS;IAIzE;;OAEG;IACI,uBAAuB,CAAC,WAAW,EAAE,MAAM,GAAG,sBAAsB,GAAG,SAAS;IAIvF;;OAEG;IACI,aAAa,CAAC,SAAS,EAAE,MAAM,GAAG,kBAAkB,EAAE;IAI7D;;OAEG;IACI,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,qBAAqB,EAAE;IAI5D;;;OAGG;IACH,IAAW,qBAAqB,IAAI,MAAM,GAAG,IAAI,CAEhD;IAED;;;OAGG;IACI,qBAAqB,IAAI,IAAI;IAgCpC;;OAEG;IACH,WAAkB,QAAQ,IAAI,oBAAoB,CAEjD;CACJ"}
@@ -0,0 +1,157 @@
1
+ "use strict";
2
+ /**
3
+ * @fileoverview Base scheduling engine with metadata caching
4
+ * @module @memberjunction/scheduling-engine-base
5
+ */
6
+ Object.defineProperty(exports, "__esModule", { value: true });
7
+ exports.SchedulingEngineBase = void 0;
8
+ const core_1 = require("@memberjunction/core");
9
+ /**
10
+ * Base engine for scheduling system with metadata caching
11
+ *
12
+ * This engine loads and caches scheduling metadata including:
13
+ * - Scheduled job types (plugin registry)
14
+ * - Active scheduled jobs
15
+ * - Recent job runs (optional)
16
+ *
17
+ * Can be used anywhere (client or server) for accessing scheduling metadata.
18
+ * For actual job execution, use SchedulingEngine from @memberjunction/scheduling-engine.
19
+ */
20
+ class SchedulingEngineBase extends core_1.BaseEngine {
21
+ constructor() {
22
+ super(...arguments);
23
+ this._scheduledJobTypes = [];
24
+ this._scheduledJobs = [];
25
+ this._scheduledJobRuns = [];
26
+ this._activePollingInterval = 60000; // Default 1 minute, null when no jobs
27
+ }
28
+ /**
29
+ * Configure the engine by loading metadata
30
+ *
31
+ * @param forceRefresh - Whether to force reload from database
32
+ * @param contextUser - User context for data access
33
+ * @param provider - Optional metadata provider
34
+ * @param includeRuns - Whether to load recent job runs (default: false)
35
+ * @param includeAllJobs - Whether to load all jobs regardless of status (default: false, only loads Active)
36
+ */
37
+ async Config(forceRefresh, contextUser, provider, includeRuns = false, includeAllJobs = false) {
38
+ const configs = [
39
+ {
40
+ EntityName: 'MJ: Scheduled Job Types',
41
+ PropertyName: '_scheduledJobTypes'
42
+ },
43
+ {
44
+ EntityName: 'MJ: Scheduled Jobs',
45
+ PropertyName: '_scheduledJobs'
46
+ }
47
+ ];
48
+ // Optionally load recent runs
49
+ if (includeRuns) {
50
+ configs.push({
51
+ EntityName: 'MJ: Scheduled Job Runs',
52
+ PropertyName: '_scheduledJobRuns'
53
+ });
54
+ }
55
+ await this.Load(configs, provider, forceRefresh, contextUser);
56
+ // Filter jobs to only active if requested
57
+ if (!includeAllJobs) {
58
+ this._scheduledJobs = this._scheduledJobs.filter(j => j.Status === 'Active');
59
+ }
60
+ // Filter runs to last 7 days if loaded
61
+ if (includeRuns) {
62
+ const sevenDaysAgo = new Date();
63
+ sevenDaysAgo.setDate(sevenDaysAgo.getDate() - 7);
64
+ this._scheduledJobRuns = this._scheduledJobRuns.filter(r => r.StartedAt >= sevenDaysAgo);
65
+ }
66
+ return true;
67
+ }
68
+ /**
69
+ * Get all scheduled job types
70
+ */
71
+ get ScheduledJobTypes() {
72
+ return this._scheduledJobTypes;
73
+ }
74
+ /**
75
+ * Get scheduled jobs (active only by default, unless includeAllJobs was set in Config)
76
+ */
77
+ get ScheduledJobs() {
78
+ return this._scheduledJobs;
79
+ }
80
+ /**
81
+ * Get recent scheduled job runs (only populated if includeRuns was set in Config)
82
+ */
83
+ get ScheduledJobRuns() {
84
+ return this._scheduledJobRuns;
85
+ }
86
+ /**
87
+ * Find a job type by name
88
+ */
89
+ GetJobTypeByName(name) {
90
+ return this._scheduledJobTypes.find(jt => jt.Name === name);
91
+ }
92
+ /**
93
+ * Find a job type by driver class
94
+ */
95
+ GetJobTypeByDriverClass(driverClass) {
96
+ return this._scheduledJobTypes.find(jt => jt.DriverClass === driverClass);
97
+ }
98
+ /**
99
+ * Get all jobs of a specific type
100
+ */
101
+ GetJobsByType(jobTypeId) {
102
+ return this._scheduledJobs.filter(j => j.JobTypeID === jobTypeId);
103
+ }
104
+ /**
105
+ * Get runs for a specific job
106
+ */
107
+ GetRunsForJob(jobId) {
108
+ return this._scheduledJobRuns.filter(r => r.ScheduledJobID === jobId);
109
+ }
110
+ /**
111
+ * Get the current active polling interval in milliseconds
112
+ * Returns null if no jobs are active (polling should be stopped)
113
+ */
114
+ get ActivePollingInterval() {
115
+ return this._activePollingInterval;
116
+ }
117
+ /**
118
+ * Calculate and update the active polling interval based on scheduled jobs
119
+ * This should be called whenever jobs are added, modified, or deleted
120
+ */
121
+ UpdatePollingInterval() {
122
+ if (this._scheduledJobs.length === 0) {
123
+ // No active jobs, stop polling
124
+ this._activePollingInterval = null;
125
+ return;
126
+ }
127
+ // Find the minimum time until next run across all active jobs
128
+ let minInterval = Number.MAX_SAFE_INTEGER;
129
+ const now = Date.now();
130
+ for (const job of this._scheduledJobs) {
131
+ if (job.Status !== 'Active' || !job.NextRunAt) {
132
+ continue;
133
+ }
134
+ const timeUntilNext = Math.max(0, job.NextRunAt.getTime() - now);
135
+ if (timeUntilNext < minInterval) {
136
+ minInterval = timeUntilNext;
137
+ }
138
+ }
139
+ // Set polling interval to half the minimum interval, with bounds
140
+ // Min: 1 minute (60000ms), Max: 1 week (604800000ms)
141
+ if (minInterval === Number.MAX_SAFE_INTEGER) {
142
+ this._activePollingInterval = 60000; // Default 1 minute
143
+ }
144
+ else {
145
+ const halfInterval = Math.floor(minInterval / 2);
146
+ this._activePollingInterval = Math.max(60000, Math.min(604800000, halfInterval));
147
+ }
148
+ }
149
+ /**
150
+ * Get singleton instance
151
+ */
152
+ static get Instance() {
153
+ return super.getInstance();
154
+ }
155
+ }
156
+ exports.SchedulingEngineBase = SchedulingEngineBase;
157
+ //# sourceMappingURL=SchedulingEngineBase.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SchedulingEngineBase.js","sourceRoot":"","sources":["../src/SchedulingEngineBase.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,11 @@
1
+ /**
2
+ * @fileoverview Main export for Scheduling Engine Base
3
+ * @module @memberjunction/scheduling-engine-base
4
+ */
5
+ export * from './SchedulingEngineBase';
6
+ export * from './ScheduledJobEntityExtended';
7
+ /**
8
+ * Loader function to ensure all extended classes are registered
9
+ */
10
+ export declare function LoadBaseSchedulingEngine(): void;
11
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,cAAc,wBAAwB,CAAC;AACvC,cAAc,8BAA8B,CAAC;AAE7C;;GAEG;AACH,wBAAgB,wBAAwB,IAAI,IAAI,CAE/C"}
package/dist/index.js ADDED
@@ -0,0 +1,32 @@
1
+ "use strict";
2
+ /**
3
+ * @fileoverview Main export for Scheduling Engine Base
4
+ * @module @memberjunction/scheduling-engine-base
5
+ */
6
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
7
+ if (k2 === undefined) k2 = k;
8
+ var desc = Object.getOwnPropertyDescriptor(m, k);
9
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
10
+ desc = { enumerable: true, get: function() { return m[k]; } };
11
+ }
12
+ Object.defineProperty(o, k2, desc);
13
+ }) : (function(o, m, k, k2) {
14
+ if (k2 === undefined) k2 = k;
15
+ o[k2] = m[k];
16
+ }));
17
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
18
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
19
+ };
20
+ Object.defineProperty(exports, "__esModule", { value: true });
21
+ exports.LoadBaseSchedulingEngine = void 0;
22
+ const ScheduledJobEntityExtended_1 = require("./ScheduledJobEntityExtended");
23
+ __exportStar(require("./SchedulingEngineBase"), exports);
24
+ __exportStar(require("./ScheduledJobEntityExtended"), exports);
25
+ /**
26
+ * Loader function to ensure all extended classes are registered
27
+ */
28
+ function LoadBaseSchedulingEngine() {
29
+ (0, ScheduledJobEntityExtended_1.LoadScheduledJobEntityExtended)();
30
+ }
31
+ exports.LoadBaseSchedulingEngine = LoadBaseSchedulingEngine;
32
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA;;;GAGG;;;;;;;;;;;;;;;;;AAEH,6EAA8E;AAE9E,yDAAuC;AACvC,+DAA6C;AAE7C;;GAEG;AACH,SAAgB,wBAAwB;IACpC,IAAA,2DAA8B,GAAE,CAAC;AACrC,CAAC;AAFD,4DAEC"}
package/package.json ADDED
@@ -0,0 +1,26 @@
1
+ {
2
+ "name": "@memberjunction/scheduling-engine-base",
3
+ "version": "2.107.0",
4
+ "description": "MemberJunction: Base Scheduling Engine Package - extended entity types and metadata caching, can be used anywhere.",
5
+ "main": "dist/index.js",
6
+ "types": "dist/index.d.ts",
7
+ "files": [
8
+ "/dist"
9
+ ],
10
+ "scripts": {
11
+ "build": "tsc",
12
+ "watch": "tsc --watch"
13
+ },
14
+ "author": "MemberJunction.com",
15
+ "license": "ISC",
16
+ "dependencies": {
17
+ "@memberjunction/core": "2.100.3",
18
+ "@memberjunction/global": "2.100.3",
19
+ "@memberjunction/core-entities": "2.107.0",
20
+ "@memberjunction/scheduling-base-types": "2.107.0"
21
+ },
22
+ "devDependencies": {
23
+ "@types/node": "20.14.2",
24
+ "typescript": "^5.4.5"
25
+ }
26
+ }