ts-patch-mongoose 2.9.6 → 3.0.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.
package/README.md CHANGED
@@ -23,8 +23,8 @@ I need to track changes of mongoose models and save them as patch history (audit
23
23
 
24
24
  ```json
25
25
  {
26
- "node": "18.x || 20.x || 22.x",
27
- "mongoose": ">=6.6.x || 7.x || 8.x",
26
+ "node": "20.x || 22.x || 24.x",
27
+ "mongoose": ">=6.6.x || 7.x || 8.x || 9.x",
28
28
  }
29
29
  ```
30
30
 
@@ -40,37 +40,19 @@ I need to track changes of mongoose models and save them as patch history (audit
40
40
 
41
41
  ## Installation
42
42
 
43
- - Locally inside your project
43
+ `mongoose` is a peer dependency — install it alongside `ts-patch-mongoose`.
44
44
 
45
45
  ```bash
46
- npm install ts-patch-mongoose
47
- pnpm add ts-patch-mongoose
48
- yarn add ts-patch-mongoose
49
- bun add ts-patch-mongoose
50
- ```
51
-
52
- - This plugin requires mongoose `>=6.6.x || 7.x || 8.x` to be installed as a peer dependency
53
-
54
- ```bash
55
- # For latest mongoose 6
56
- npm install mongoose@6
57
- pnpm add mongoose@6
58
- yarn add mongoose@6
59
- bun add mongoose@6
60
- # For latest mongoose 7
61
- npm install mongoose@7
62
- pnpm add mongoose@7
63
- yarn add mongoose@7
64
- bun add mongoose@7
65
- # For latest mongoose 8
66
- npm install mongoose@8
67
- pnpm add mongoose@8
68
- yarn add mongoose@8
69
- bun add mongoose@8
46
+ npm install ts-patch-mongoose mongoose
47
+ pnpm add ts-patch-mongoose mongoose
48
+ yarn add ts-patch-mongoose mongoose
49
+ bun add ts-patch-mongoose mongoose
70
50
  ```
71
51
 
72
52
  ## Example
73
53
 
54
+ Works with any Node.js framework — Express, Fastify, Koa, Hono, Nest, etc.
55
+ \
74
56
  How to use it with express [ts-express-tsx](https://github.com/ilovepixelart/ts-express-tsx)
75
57
 
76
58
  Create your event constants `events.ts`
@@ -213,6 +195,39 @@ patchEventEmitter.on(BOOK_DELETED, ({ oldDoc }) => {
213
195
  })
214
196
  ```
215
197
 
198
+ ## NestJS
199
+
200
+ ```typescript
201
+ import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'
202
+ import { patchHistoryPlugin } from 'ts-patch-mongoose'
203
+
204
+ @Schema({ timestamps: true })
205
+ export class Book {
206
+ @Prop({ type: String, required: true })
207
+ title!: string
208
+
209
+ @Prop({ type: String })
210
+ description?: string
211
+ }
212
+
213
+ export const BookSchema = SchemaFactory.createForClass(Book)
214
+
215
+ BookSchema.plugin(patchHistoryPlugin, {
216
+ eventCreated: 'book-created',
217
+ eventUpdated: 'book-updated',
218
+ eventDeleted: 'book-deleted',
219
+ omit: ['__v', 'createdAt', 'updatedAt'],
220
+ })
221
+ ```
222
+
223
+ ## Contributing
224
+
225
+ Check [CONTRIBUTING.md](CONTRIBUTING.md)
226
+
227
+ ## License
228
+
229
+ This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details
230
+
216
231
  ## Check my other projects
217
232
 
218
233
  - [ts-migrate-mongoose](https://github.com/ilovepixelart/ts-migrate-mongoose) - Migration framework for mongoose
package/biome.json CHANGED
@@ -1,5 +1,5 @@
1
1
  {
2
- "$schema": "https://biomejs.dev/schemas/2.4.4/schema.json",
2
+ "$schema": "https://biomejs.dev/schemas/2.4.7/schema.json",
3
3
  "vcs": { "enabled": false, "clientKind": "git", "useIgnoreFile": false },
4
4
  "files": {
5
5
  "ignoreUnknown": false,
package/dist/index.cjs CHANGED
@@ -1,20 +1,9 @@
1
1
  'use strict';
2
2
 
3
- var isEmpty = require('lodash/isEmpty.js');
4
- var ms = require('ms');
5
3
  var mongoose = require('mongoose');
6
- var isArray = require('lodash/isArray.js');
7
4
  var jsonpatch = require('fast-json-patch');
8
- var chunk = require('lodash/chunk.js');
9
- var isFunction = require('lodash/isFunction.js');
10
- var omit = require('omit-deep');
11
5
  var EventEmitter = require('node:events');
12
- var cloneDeep = require('lodash/cloneDeep.js');
13
- var forEach = require('lodash/forEach.js');
14
- var isObjectLike = require('lodash/isObjectLike.js');
15
- var keys = require('lodash/keys.js');
16
6
  var powerAssign = require('power-assign');
17
- var semver = require('semver');
18
7
 
19
8
  const HistorySchema = new mongoose.Schema(
20
9
  {
@@ -61,6 +50,156 @@ HistorySchema.index({ collectionId: 1, version: -1 });
61
50
  HistorySchema.index({ op: 1, modelName: 1, collectionName: 1, collectionId: 1, reason: 1, version: 1 });
62
51
  const HistoryModel = mongoose.model("History", HistorySchema, "history");
63
52
 
53
+ const s = 1e3;
54
+ const m = s * 60;
55
+ const h = m * 60;
56
+ const d = h * 24;
57
+ const w = d * 7;
58
+ const y = d * 365.25;
59
+ const mo = y / 12;
60
+ const UNITS = {
61
+ milliseconds: 1,
62
+ millisecond: 1,
63
+ msecs: 1,
64
+ msec: 1,
65
+ ms: 1,
66
+ seconds: s,
67
+ second: s,
68
+ secs: s,
69
+ sec: s,
70
+ s,
71
+ minutes: m,
72
+ minute: m,
73
+ mins: m,
74
+ min: m,
75
+ m,
76
+ hours: h,
77
+ hour: h,
78
+ hrs: h,
79
+ hr: h,
80
+ h,
81
+ days: d,
82
+ day: d,
83
+ d,
84
+ weeks: w,
85
+ week: w,
86
+ w,
87
+ months: mo,
88
+ month: mo,
89
+ mo,
90
+ years: y,
91
+ year: y,
92
+ yrs: y,
93
+ yr: y,
94
+ y
95
+ };
96
+ const unitPattern = Object.keys(UNITS).sort((a, b) => b.length - a.length).join("|");
97
+ const RE = new RegExp(String.raw`^(-?(?:\d+)?\.?\d+)\s*(${unitPattern})?$`, "i");
98
+ const ms = (val) => {
99
+ const str = String(val);
100
+ if (str.length > 100) return Number.NaN;
101
+ const match = RE.exec(str);
102
+ if (!match) return Number.NaN;
103
+ const n = Number.parseFloat(match[1] ?? "");
104
+ const type = (match[2] ?? "ms").toLowerCase();
105
+ return n * (UNITS[type] ?? 0);
106
+ };
107
+
108
+ const isArray = Array.isArray;
109
+ const isEmpty = (value) => {
110
+ if (value == null) return true;
111
+ if (Array.isArray(value) || typeof value === "string") return value.length === 0;
112
+ if (value instanceof Map || value instanceof Set) return value.size === 0;
113
+ if (typeof value === "object") {
114
+ for (const key in value) {
115
+ if (Object.hasOwn(value, key)) return false;
116
+ }
117
+ return true;
118
+ }
119
+ return true;
120
+ };
121
+ const isFunction = (value) => {
122
+ return typeof value === "function";
123
+ };
124
+ const isObjectLike = (value) => {
125
+ return typeof value === "object" && value !== null;
126
+ };
127
+ const cloneArrayBuffer = (arrayBuffer) => {
128
+ const result = new ArrayBuffer(arrayBuffer.byteLength);
129
+ new Uint8Array(result).set(new Uint8Array(arrayBuffer));
130
+ return result;
131
+ };
132
+ const cloneImmutable = (value) => {
133
+ const tag = Object.prototype.toString.call(value);
134
+ switch (tag) {
135
+ case "[object Date]":
136
+ return /* @__PURE__ */ new Date(+value);
137
+ case "[object RegExp]": {
138
+ const re = value;
139
+ const cloned = new RegExp(re.source, re.flags);
140
+ cloned.lastIndex = re.lastIndex;
141
+ return cloned;
142
+ }
143
+ case "[object ArrayBuffer]":
144
+ return cloneArrayBuffer(value);
145
+ case "[object DataView]": {
146
+ const dv = value;
147
+ const buffer = cloneArrayBuffer(dv.buffer);
148
+ return new DataView(buffer, dv.byteOffset, dv.byteLength);
149
+ }
150
+ }
151
+ if (ArrayBuffer.isView(value)) {
152
+ const ta = value;
153
+ const buffer = cloneArrayBuffer(ta.buffer);
154
+ return new value.constructor(buffer, ta.byteOffset, ta.length);
155
+ }
156
+ return void 0;
157
+ };
158
+ const cloneCollection = (value, seen) => {
159
+ if (value instanceof Map) {
160
+ const map = /* @__PURE__ */ new Map();
161
+ seen.set(value, map);
162
+ for (const [k, v] of value) map.set(k, cloneDeep(v, seen));
163
+ return map;
164
+ }
165
+ if (value instanceof Set) {
166
+ const set = /* @__PURE__ */ new Set();
167
+ seen.set(value, set);
168
+ for (const v of value) set.add(cloneDeep(v, seen));
169
+ return set;
170
+ }
171
+ if (Array.isArray(value)) {
172
+ const arr = new Array(value.length);
173
+ seen.set(value, arr);
174
+ for (let i = 0; i < value.length; i++) {
175
+ arr[i] = cloneDeep(value[i], seen);
176
+ }
177
+ return arr;
178
+ }
179
+ const result = typeof value.constructor === "function" ? Object.create(Object.getPrototypeOf(value)) : {};
180
+ seen.set(value, result);
181
+ for (const key of Object.keys(value)) {
182
+ result[key] = cloneDeep(value[key], seen);
183
+ }
184
+ return result;
185
+ };
186
+ const cloneDeep = (value, seen = /* @__PURE__ */ new WeakMap()) => {
187
+ if (value === null || typeof value !== "object") return value;
188
+ if (seen.has(value)) return seen.get(value);
189
+ const immutable = cloneImmutable(value);
190
+ if (immutable !== void 0) return immutable;
191
+ if ("toJSON" in value && typeof value.toJSON === "function") {
192
+ return JSON.parse(JSON.stringify(value));
193
+ }
194
+ return cloneCollection(value, seen);
195
+ };
196
+ const chunk = (array, size) => {
197
+ const result = [];
198
+ for (let i = 0; i < array.length; i += size) {
199
+ result.push(array.slice(i, i + size));
200
+ }
201
+ return result;
202
+ };
64
203
  const isHookIgnored = (options) => {
65
204
  return options.ignoreHook === true || options.ignoreEvent === true && options.ignorePatchHistory === true;
66
205
  };
@@ -77,7 +216,7 @@ const setPatchHistoryTTL = async (ttl) => {
77
216
  await HistoryModel.collection.dropIndex(name);
78
217
  return;
79
218
  }
80
- const milliseconds = typeof ttl === "string" ? ms(ttl) : ttl;
219
+ const milliseconds = ms(ttl);
81
220
  if (milliseconds < 1e3 && existingIndex) {
82
221
  await HistoryModel.collection.dropIndex(name);
83
222
  return;
@@ -99,63 +238,144 @@ class PatchEventEmitter extends EventEmitter {
99
238
  }
100
239
  const em = new PatchEventEmitter();
101
240
 
102
- function isPatchHistoryEnabled(opts, context) {
241
+ const isPlainObject = (val) => {
242
+ if (Object.prototype.toString.call(val) !== "[object Object]") return false;
243
+ const prot = Object.getPrototypeOf(val);
244
+ return prot === null || prot === Object.prototype;
245
+ };
246
+ const isUnsafeKey = (key) => {
247
+ return key === "__proto__" || key === "constructor" || key === "prototype";
248
+ };
249
+ const getValue$1 = (obj, path) => {
250
+ const segs = path.split(".");
251
+ let current = obj;
252
+ for (const seg of segs) {
253
+ if (current == null || typeof current !== "object") return void 0;
254
+ current = current[seg];
255
+ }
256
+ return current;
257
+ };
258
+ const hasValue = (val) => {
259
+ if (val == null) return false;
260
+ if (typeof val === "boolean" || typeof val === "number" || typeof val === "function") return true;
261
+ if (typeof val === "string") return val.length !== 0;
262
+ if (Array.isArray(val)) return val.length !== 0;
263
+ if (val instanceof RegExp) return val.source !== "(?:)" && val.source !== "";
264
+ if (val instanceof Error) return val.message !== "";
265
+ if (val instanceof Map || val instanceof Set) return val.size !== 0;
266
+ if (typeof val === "object") {
267
+ for (const key of Object.keys(val)) {
268
+ if (hasValue(val[key])) return true;
269
+ }
270
+ return false;
271
+ }
272
+ return true;
273
+ };
274
+ const has = (obj, path) => {
275
+ if (obj != null && typeof obj === "object" && typeof path === "string") {
276
+ return hasValue(getValue$1(obj, path));
277
+ }
278
+ return false;
279
+ };
280
+ const unset = (obj, prop) => {
281
+ if (typeof obj !== "object" || obj === null) return false;
282
+ if (Object.hasOwn(obj, prop)) {
283
+ delete obj[prop];
284
+ return true;
285
+ }
286
+ if (has(obj, prop)) {
287
+ const segs = prop.split(".");
288
+ let last = segs.pop();
289
+ while (segs.length && segs.at(-1)?.slice(-1) === "\\") {
290
+ last = `${segs.pop().slice(0, -1)}.${last}`;
291
+ }
292
+ let target = obj;
293
+ while (segs.length) {
294
+ const seg = segs.shift();
295
+ if (isUnsafeKey(seg)) return false;
296
+ target = target[seg];
297
+ }
298
+ return delete target[last ?? ""];
299
+ }
300
+ return true;
301
+ };
302
+ const omitDeep = (value, keys) => {
303
+ if (value === void 0) return {};
304
+ if (Array.isArray(value)) {
305
+ for (let i = 0; i < value.length; i++) {
306
+ value[i] = omitDeep(value[i], keys);
307
+ }
308
+ return value;
309
+ }
310
+ if (!isPlainObject(value)) return value;
311
+ const omitKeys = typeof keys === "string" ? [keys] : keys;
312
+ if (!Array.isArray(omitKeys)) return value;
313
+ for (const key of omitKeys) {
314
+ unset(value, key);
315
+ }
316
+ for (const key of Object.keys(value)) {
317
+ value[key] = omitDeep(value[key], omitKeys);
318
+ }
319
+ return value;
320
+ };
321
+
322
+ const isPatchHistoryEnabled = (opts, context) => {
103
323
  return !opts.patchHistoryDisabled && !context.ignorePatchHistory;
104
- }
105
- function getJsonOmit(opts, doc) {
324
+ };
325
+ const getJsonOmit = (opts, doc) => {
106
326
  const object = JSON.parse(JSON.stringify(doc));
107
327
  if (opts.omit) {
108
- return omit(object, opts.omit);
328
+ return omitDeep(object, opts.omit);
109
329
  }
110
330
  return object;
111
- }
112
- function getObjectOmit(opts, doc) {
331
+ };
332
+ const getObjectOmit = (opts, doc) => {
113
333
  if (opts.omit) {
114
- return omit(isFunction(doc?.toObject) ? doc.toObject() : doc, opts.omit);
334
+ return omitDeep(isFunction(doc?.toObject) ? doc.toObject() : doc, opts.omit);
115
335
  }
116
336
  return doc;
117
- }
118
- async function getUser(opts, doc) {
337
+ };
338
+ const getUser = async (opts, doc) => {
119
339
  if (isFunction(opts.getUser)) {
120
340
  return await opts.getUser(doc);
121
341
  }
122
342
  return void 0;
123
- }
124
- async function getReason(opts, doc) {
343
+ };
344
+ const getReason = async (opts, doc) => {
125
345
  if (isFunction(opts.getReason)) {
126
346
  return await opts.getReason(doc);
127
347
  }
128
348
  return void 0;
129
- }
130
- async function getMetadata(opts, doc) {
349
+ };
350
+ const getMetadata = async (opts, doc) => {
131
351
  if (isFunction(opts.getMetadata)) {
132
352
  return await opts.getMetadata(doc);
133
353
  }
134
354
  return void 0;
135
- }
136
- function getValue(item) {
355
+ };
356
+ const getValue = (item) => {
137
357
  return item.status === "fulfilled" ? item.value : void 0;
138
- }
139
- async function getData(opts, doc) {
358
+ };
359
+ const getData = async (opts, doc) => {
140
360
  return Promise.allSettled([getUser(opts, doc), getReason(opts, doc), getMetadata(opts, doc)]).then(([user, reason, metadata]) => {
141
361
  return [getValue(user), getValue(reason), getValue(metadata)];
142
362
  });
143
- }
144
- function emitEvent(context, event, data) {
363
+ };
364
+ const emitEvent = (context, event, data) => {
145
365
  if (event && !context.ignoreEvent) {
146
366
  em.emit(event, data);
147
367
  }
148
- }
149
- async function bulkPatch(opts, context, eventKey, docsKey) {
368
+ };
369
+ const bulkPatch = async (opts, context, eventKey, docsKey) => {
150
370
  const history = isPatchHistoryEnabled(opts, context);
151
371
  const event = opts[eventKey];
152
372
  const docs = context[docsKey];
153
373
  const key = eventKey === "eventCreated" ? "doc" : "oldDoc";
154
- if (isEmpty(docs) || !event && !history) return;
374
+ if (isEmpty(docs) || !docs || !event && !history) return;
155
375
  const chunks = chunk(docs, 1e3);
156
- for (const chunk2 of chunks) {
376
+ for (const batch of chunks) {
157
377
  const bulk = [];
158
- for (const doc of chunk2) {
378
+ for (const doc of batch) {
159
379
  emitEvent(context, event, { [key]: doc });
160
380
  if (history) {
161
381
  const [user, reason, metadata] = await getData(opts, doc);
@@ -182,11 +402,11 @@ async function bulkPatch(opts, context, eventKey, docsKey) {
182
402
  });
183
403
  }
184
404
  }
185
- }
186
- async function createPatch(opts, context) {
405
+ };
406
+ const createPatch = async (opts, context) => {
187
407
  await bulkPatch(opts, context, "eventCreated", "createdDocs");
188
- }
189
- async function updatePatch(opts, context, current, original) {
408
+ };
409
+ const updatePatch = async (opts, context, current, original) => {
190
410
  const history = isPatchHistoryEnabled(opts, context);
191
411
  const currentObject = getJsonOmit(opts, current);
192
412
  const originalObject = getJsonOmit(opts, original);
@@ -213,10 +433,10 @@ async function updatePatch(opts, context, current, original) {
213
433
  ...metadata !== void 0 && { metadata }
214
434
  });
215
435
  }
216
- }
217
- async function deletePatch(opts, context) {
436
+ };
437
+ const deletePatch = async (opts, context) => {
218
438
  await bulkPatch(opts, context, "eventDeleted", "deletedDocs");
219
- }
439
+ };
220
440
 
221
441
  const deleteMethods = ["remove", "findOneAndDelete", "findOneAndRemove", "findByIdAndDelete", "findByIdAndRemove", "deleteOne", "deleteMany"];
222
442
  const deleteHooksInitialize = (schema, opts) => {
@@ -279,12 +499,12 @@ const saveHooksInitialize = (schema, opts) => {
279
499
  const updateMethods = ["update", "updateOne", "replaceOne", "updateMany", "findOneAndUpdate", "findOneAndReplace", "findByIdAndUpdate"];
280
500
  const assignUpdate = (document, update, commands) => {
281
501
  let updated = powerAssign.assign(document.toObject(toObjectOptions), update);
282
- forEach(commands, (command) => {
502
+ for (const command of commands) {
283
503
  try {
284
504
  updated = powerAssign.assign(updated, command);
285
505
  } catch {
286
506
  }
287
- });
507
+ }
288
508
  const doc = document.set(updated).toObject(toObjectOptions);
289
509
  if (update.createdAt) doc.createdAt = update.createdAt;
290
510
  return doc;
@@ -294,12 +514,12 @@ const splitUpdateAndCommands = (updateQuery) => {
294
514
  const commands = [];
295
515
  if (!isEmpty(updateQuery) && !isArray(updateQuery) && isObjectLike(updateQuery)) {
296
516
  update = cloneDeep(updateQuery);
297
- const keysWithDollarSign = keys(update).filter((key) => key.startsWith("$"));
517
+ const keysWithDollarSign = Object.keys(update).filter((key) => key.startsWith("$"));
298
518
  if (!isEmpty(keysWithDollarSign)) {
299
- forEach(keysWithDollarSign, (key) => {
519
+ for (const key of keysWithDollarSign) {
300
520
  commands.push({ [key]: update[key] });
301
521
  delete update[key];
302
- });
522
+ }
303
523
  }
304
524
  }
305
525
  return { update, commands };
@@ -344,7 +564,6 @@ const updateHooksInitialize = (schema, opts) => {
344
564
  current = await model.findOne(combined).sort("desc").lean().exec();
345
565
  }
346
566
  if (!isEmpty(filter) && !current) {
347
- console.log("filter", filter);
348
567
  current = await model.findOne(filter).sort("desc").lean().exec();
349
568
  }
350
569
  if (current) {
@@ -354,15 +573,16 @@ const updateHooksInitialize = (schema, opts) => {
354
573
  });
355
574
  };
356
575
 
357
- const isMongooseLessThan8 = semver.satisfies(mongoose.version, "<8");
358
- const isMongooseLessThan7 = semver.satisfies(mongoose.version, "<7");
359
- const isMongoose6 = semver.satisfies(mongoose.version, "6");
576
+ const major = Number.parseInt(mongoose.version, 10);
577
+ const isMongooseLessThan8 = major < 8;
578
+ const isMongooseLessThan7 = major < 7;
579
+ const isMongoose6 = major === 6;
360
580
  if (isMongoose6) {
361
581
  mongoose.set("strictQuery", false);
362
582
  }
363
583
 
364
584
  const remove = isMongooseLessThan7 ? "remove" : "deleteOne";
365
- const patchHistoryPlugin = function plugin(schema, opts) {
585
+ const patchHistoryPlugin = (schema, opts) => {
366
586
  saveHooksInitialize(schema, opts);
367
587
  updateHooksInitialize(schema, opts);
368
588
  deleteHooksInitialize(schema, opts);
package/dist/index.d.cts CHANGED
@@ -1,7 +1,6 @@
1
1
  import { Types, Query, HydratedDocument, Schema } from 'mongoose';
2
2
  import { Operation } from 'fast-json-patch';
3
3
  import EventEmitter from 'node:events';
4
- import ms from 'ms';
5
4
 
6
5
  interface History {
7
6
  op: string;
@@ -54,10 +53,49 @@ declare class PatchEventEmitter extends EventEmitter {
54
53
  }
55
54
  declare const em: PatchEventEmitter;
56
55
 
57
- declare const setPatchHistoryTTL: (ttl: number | ms.StringValue) => Promise<void>;
56
+ declare const UNITS: {
57
+ readonly milliseconds: 1;
58
+ readonly millisecond: 1;
59
+ readonly msecs: 1;
60
+ readonly msec: 1;
61
+ readonly ms: 1;
62
+ readonly seconds: 1000;
63
+ readonly second: 1000;
64
+ readonly secs: 1000;
65
+ readonly sec: 1000;
66
+ readonly s: 1000;
67
+ readonly minutes: number;
68
+ readonly minute: number;
69
+ readonly mins: number;
70
+ readonly min: number;
71
+ readonly m: number;
72
+ readonly hours: number;
73
+ readonly hour: number;
74
+ readonly hrs: number;
75
+ readonly hr: number;
76
+ readonly h: number;
77
+ readonly days: number;
78
+ readonly day: number;
79
+ readonly d: number;
80
+ readonly weeks: number;
81
+ readonly week: number;
82
+ readonly w: number;
83
+ readonly months: number;
84
+ readonly month: number;
85
+ readonly mo: number;
86
+ readonly years: number;
87
+ readonly year: number;
88
+ readonly yrs: number;
89
+ readonly yr: number;
90
+ readonly y: number;
91
+ };
92
+ type Unit = keyof typeof UNITS;
93
+ type Duration = number | `${number}` | `${number}${Unit}` | `${number} ${Unit}`;
94
+
95
+ declare const setPatchHistoryTTL: (ttl: Duration) => Promise<void>;
58
96
 
59
97
  declare const patchHistoryPlugin: <T>(schema: Schema<T>, opts: PluginOptions<T>) => void;
60
98
 
61
99
  export { em as patchEventEmitter, patchHistoryPlugin, setPatchHistoryTTL };
62
- export type { History, HookContext, Metadata, PatchContext, PatchEvent, PluginOptions, User };
100
+ export type { Duration, History, HookContext, Metadata, PatchContext, PatchEvent, PluginOptions, User };
63
101
  //# sourceMappingURL=index.d.cts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.cts","sources":["../src/types.ts","../src/em.ts","../src/helpers.ts","../src/index.ts"],"mappings":";;;;;AAGM,UAAW,OAAO;;;;kBAIR,KAAK,CAAC,QAAQ;;;;;;YAMpB,SAAS;;AAGb,UAAW,UAAU;aAChB,gBAAgB;UACnB,gBAAgB;YACd,SAAS;;AAGb,UAAW,YAAY;;;;;kBAKb,gBAAgB;kBAChB,gBAAgB;;;;AAK1B,KAAM,WAAW,MAAM,KAAK;;cAAiC,YAAY;;AAEzE,KAAM,IAAI,GAAG,MAAM;AAEnB,KAAM,QAAQ,GAAG,MAAM;AAEvB,UAAW,aAAa;;;;;;oBAMZ,gBAAgB,QAAQ,OAAO,CAAC,IAAI,IAAI,IAAI;sBAC1C,gBAAgB,QAAQ,OAAO;wBAC7B,gBAAgB,QAAQ,OAAO,CAAC,QAAQ,IAAI,QAAQ;;;uBAGrD,gBAAgB,UAAU,OAAO;;;AChDtD,cAAM,iBAAkB,SAAQ,YAAY;;AAC5C,cAAM,EAAE,mBAA0B;;ACWlC,cAAa,kBAAkB,iBAAwB,EAAE,CAAC,WAAW,KAAG,OAAO;;ACiB/E,cAAa,kBAAkB,cAA8B,MAAM,WAAW,aAAa","names":[]}
1
+ {"version":3,"file":"index.d.cts","sources":["../src/types.ts","../src/em.ts","../src/ms.ts","../src/helpers.ts","../src/index.ts"],"mappings":";;;;AAGM,UAAW,OAAO;;;;kBAIR,KAAK,CAAC,QAAQ;;;;;;YAMpB,SAAS;;AAGb,UAAW,UAAU;aAChB,gBAAgB;UACnB,gBAAgB;YACd,SAAS;;AAGb,UAAW,YAAY;;;;;kBAKb,gBAAgB;kBAChB,gBAAgB;;;;AAK1B,KAAM,WAAW,MAAM,KAAK;;cAAiC,YAAY;;AAEzE,KAAM,IAAI,GAAG,MAAM;AAEnB,KAAM,QAAQ,GAAG,MAAM;AAEvB,UAAW,aAAa;;;;;;oBAMZ,gBAAgB,QAAQ,OAAO,CAAC,IAAI,IAAI,IAAI;sBAC1C,gBAAgB,QAAQ,OAAO;wBAC7B,gBAAgB,QAAQ,OAAO,CAAC,QAAQ,IAAI,QAAQ;;;uBAGrD,gBAAgB,UAAU,OAAO;;;AChDtD,cAAM,iBAAkB,SAAQ,YAAY;;AAC5C,cAAM,EAAE,mBAA0B;;ACKlC,cAAa,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAqCZ,KAAM,IAAI,gBAAgB,KAAK;AAE/B,KAAM,QAAQ,sCAAsC,IAAI,kBAAkB,IAAI;;ACiFpF,cAAa,kBAAkB,QAAe,QAAQ,KAAG,OAAO;;AC9GhE,cAAa,kBAAkB,cAAe,MAAM,WAAW,aAAa","names":[]}
package/dist/index.d.mts CHANGED
@@ -1,7 +1,6 @@
1
1
  import { Types, Query, HydratedDocument, Schema } from 'mongoose';
2
2
  import { Operation } from 'fast-json-patch';
3
3
  import EventEmitter from 'node:events';
4
- import ms from 'ms';
5
4
 
6
5
  interface History {
7
6
  op: string;
@@ -54,10 +53,49 @@ declare class PatchEventEmitter extends EventEmitter {
54
53
  }
55
54
  declare const em: PatchEventEmitter;
56
55
 
57
- declare const setPatchHistoryTTL: (ttl: number | ms.StringValue) => Promise<void>;
56
+ declare const UNITS: {
57
+ readonly milliseconds: 1;
58
+ readonly millisecond: 1;
59
+ readonly msecs: 1;
60
+ readonly msec: 1;
61
+ readonly ms: 1;
62
+ readonly seconds: 1000;
63
+ readonly second: 1000;
64
+ readonly secs: 1000;
65
+ readonly sec: 1000;
66
+ readonly s: 1000;
67
+ readonly minutes: number;
68
+ readonly minute: number;
69
+ readonly mins: number;
70
+ readonly min: number;
71
+ readonly m: number;
72
+ readonly hours: number;
73
+ readonly hour: number;
74
+ readonly hrs: number;
75
+ readonly hr: number;
76
+ readonly h: number;
77
+ readonly days: number;
78
+ readonly day: number;
79
+ readonly d: number;
80
+ readonly weeks: number;
81
+ readonly week: number;
82
+ readonly w: number;
83
+ readonly months: number;
84
+ readonly month: number;
85
+ readonly mo: number;
86
+ readonly years: number;
87
+ readonly year: number;
88
+ readonly yrs: number;
89
+ readonly yr: number;
90
+ readonly y: number;
91
+ };
92
+ type Unit = keyof typeof UNITS;
93
+ type Duration = number | `${number}` | `${number}${Unit}` | `${number} ${Unit}`;
94
+
95
+ declare const setPatchHistoryTTL: (ttl: Duration) => Promise<void>;
58
96
 
59
97
  declare const patchHistoryPlugin: <T>(schema: Schema<T>, opts: PluginOptions<T>) => void;
60
98
 
61
99
  export { em as patchEventEmitter, patchHistoryPlugin, setPatchHistoryTTL };
62
- export type { History, HookContext, Metadata, PatchContext, PatchEvent, PluginOptions, User };
100
+ export type { Duration, History, HookContext, Metadata, PatchContext, PatchEvent, PluginOptions, User };
63
101
  //# sourceMappingURL=index.d.mts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.mts","sources":["../src/types.ts","../src/em.ts","../src/helpers.ts","../src/index.ts"],"mappings":";;;;;AAGM,UAAW,OAAO;;;;kBAIR,KAAK,CAAC,QAAQ;;;;;;YAMpB,SAAS;;AAGb,UAAW,UAAU;aAChB,gBAAgB;UACnB,gBAAgB;YACd,SAAS;;AAGb,UAAW,YAAY;;;;;kBAKb,gBAAgB;kBAChB,gBAAgB;;;;AAK1B,KAAM,WAAW,MAAM,KAAK;;cAAiC,YAAY;;AAEzE,KAAM,IAAI,GAAG,MAAM;AAEnB,KAAM,QAAQ,GAAG,MAAM;AAEvB,UAAW,aAAa;;;;;;oBAMZ,gBAAgB,QAAQ,OAAO,CAAC,IAAI,IAAI,IAAI;sBAC1C,gBAAgB,QAAQ,OAAO;wBAC7B,gBAAgB,QAAQ,OAAO,CAAC,QAAQ,IAAI,QAAQ;;;uBAGrD,gBAAgB,UAAU,OAAO;;;AChDtD,cAAM,iBAAkB,SAAQ,YAAY;;AAC5C,cAAM,EAAE,mBAA0B;;ACWlC,cAAa,kBAAkB,iBAAwB,EAAE,CAAC,WAAW,KAAG,OAAO;;ACiB/E,cAAa,kBAAkB,cAA8B,MAAM,WAAW,aAAa","names":[]}
1
+ {"version":3,"file":"index.d.mts","sources":["../src/types.ts","../src/em.ts","../src/ms.ts","../src/helpers.ts","../src/index.ts"],"mappings":";;;;AAGM,UAAW,OAAO;;;;kBAIR,KAAK,CAAC,QAAQ;;;;;;YAMpB,SAAS;;AAGb,UAAW,UAAU;aAChB,gBAAgB;UACnB,gBAAgB;YACd,SAAS;;AAGb,UAAW,YAAY;;;;;kBAKb,gBAAgB;kBAChB,gBAAgB;;;;AAK1B,KAAM,WAAW,MAAM,KAAK;;cAAiC,YAAY;;AAEzE,KAAM,IAAI,GAAG,MAAM;AAEnB,KAAM,QAAQ,GAAG,MAAM;AAEvB,UAAW,aAAa;;;;;;oBAMZ,gBAAgB,QAAQ,OAAO,CAAC,IAAI,IAAI,IAAI;sBAC1C,gBAAgB,QAAQ,OAAO;wBAC7B,gBAAgB,QAAQ,OAAO,CAAC,QAAQ,IAAI,QAAQ;;;uBAGrD,gBAAgB,UAAU,OAAO;;;AChDtD,cAAM,iBAAkB,SAAQ,YAAY;;AAC5C,cAAM,EAAE,mBAA0B;;ACKlC,cAAa,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAqCZ,KAAM,IAAI,gBAAgB,KAAK;AAE/B,KAAM,QAAQ,sCAAsC,IAAI,kBAAkB,IAAI;;ACiFpF,cAAa,kBAAkB,QAAe,QAAQ,KAAG,OAAO;;AC9GhE,cAAa,kBAAkB,cAAe,MAAM,WAAW,aAAa","names":[]}