@sprucelabs/data-stores 25.2.3 → 25.3.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
@@ -12,7 +12,6 @@ Spruce XP Documentation
12
12
  <p align="center">
13
13
  <img align="center" width="80%" src="https://raw.githubusercontent.com/sprucelabsai/data-stores/master/docs/images/sprucebot-message.png">
14
14
  </p>
15
-
16
15
  <br />
17
16
 
18
17
  <p align="center">
@@ -6,8 +6,10 @@ export default class BatchCursorImpl<ResponseRecord> implements BatchCursor<Resp
6
6
  private store;
7
7
  private options?;
8
8
  private query?;
9
+ private nextResults?;
9
10
  private constructor();
10
11
  static Cursor<Response>(store: AbstractStore<Schema>, query?: Record<string, any>, options?: FindBatchOptions): BatchCursor<Response>;
12
+ setOnNextResults(cb: (results: ResponseRecord[]) => never[]): void;
11
13
  next(): Promise<ResponseRecord[] | null>;
12
14
  private bumpCursorPosition;
13
15
  }
@@ -15,5 +17,6 @@ export interface FindBatchOptions<IncludePrivateFields extends boolean = true, F
15
17
  batchSize?: number;
16
18
  }
17
19
  export interface BatchCursor<ResponseRecord> {
20
+ setOnNextResults(cb: (results: ResponseRecord[]) => never[]): void;
18
21
  next(): Promise<ResponseRecord[] | null>;
19
22
  }
@@ -20,9 +20,16 @@ class BatchCursorImpl {
20
20
  static Cursor(store, query, options) {
21
21
  return new this(store, query, options);
22
22
  }
23
+ setOnNextResults(cb) {
24
+ this.nextResults = cb;
25
+ }
23
26
  async next() {
24
27
  var _a;
25
28
  const _b = (_a = this.options) !== null && _a !== void 0 ? _a : {}, { batchSize = 10 } = _b, rest = __rest(_b, ["batchSize"]);
29
+ if (this.nextResults) {
30
+ //@ts-ignore
31
+ return this.nextResults();
32
+ }
26
33
  const matches = await this.store.find(Object.assign({}, this.query), {
27
34
  limit: batchSize,
28
35
  }, Object.assign({}, rest));
@@ -6,8 +6,10 @@ export default class BatchCursorImpl<ResponseRecord> implements BatchCursor<Resp
6
6
  private store;
7
7
  private options?;
8
8
  private query?;
9
+ private nextResults?;
9
10
  private constructor();
10
11
  static Cursor<Response>(store: AbstractStore<Schema>, query?: Record<string, any>, options?: FindBatchOptions): BatchCursor<Response>;
12
+ setOnNextResults(cb: (results: ResponseRecord[]) => never[]): void;
11
13
  next(): Promise<ResponseRecord[] | null>;
12
14
  private bumpCursorPosition;
13
15
  }
@@ -15,5 +17,6 @@ export interface FindBatchOptions<IncludePrivateFields extends boolean = true, F
15
17
  batchSize?: number;
16
18
  }
17
19
  export interface BatchCursor<ResponseRecord> {
20
+ setOnNextResults(cb: (results: ResponseRecord[]) => never[]): void;
18
21
  next(): Promise<ResponseRecord[] | null>;
19
22
  }
@@ -27,10 +27,17 @@ export default class BatchCursorImpl {
27
27
  static Cursor(store, query, options) {
28
28
  return new this(store, query, options);
29
29
  }
30
+ setOnNextResults(cb) {
31
+ this.nextResults = cb;
32
+ }
30
33
  next() {
31
34
  var _a;
32
35
  return __awaiter(this, void 0, void 0, function* () {
33
36
  const _b = (_a = this.options) !== null && _a !== void 0 ? _a : {}, { batchSize = 10 } = _b, rest = __rest(_b, ["batchSize"]);
37
+ if (this.nextResults) {
38
+ //@ts-ignore
39
+ return this.nextResults();
40
+ }
34
41
  const matches = yield this.store.find(Object.assign({}, this.query), {
35
42
  limit: batchSize,
36
43
  }, Object.assign({}, rest));
@@ -20,6 +20,10 @@ export { default as CursorPager } from './cursors/CursorPager';
20
20
  export * from './cursors/CursorPager';
21
21
  export { default as CursorPagerFaker } from './cursors/CursorPagerFaker';
22
22
  export * from './cursors/CursorPager';
23
+ /**
24
+ * @deprecated databaseAssertUtil -> databaseAssert
25
+ */
23
26
  export { default as databaseAssertUtil } from './tests/databaseAssertUtil';
27
+ export { default as databaseAssert } from './tests/databaseAssertUtil';
24
28
  export { default as BatchCursor } from './cursors/BatchCursor';
25
29
  export * from './cursors/BatchCursor';
@@ -20,6 +20,10 @@ export { default as CursorPager } from './cursors/CursorPager.js';
20
20
  export * from './cursors/CursorPager.js';
21
21
  export { default as CursorPagerFaker } from './cursors/CursorPagerFaker.js';
22
22
  export * from './cursors/CursorPager.js';
23
+ /**
24
+ * @deprecated databaseAssertUtil -> databaseAssert
25
+ */
23
26
  export { default as databaseAssertUtil } from './tests/databaseAssertUtil.js';
27
+ export { default as databaseAssert } from './tests/databaseAssertUtil.js';
24
28
  export { default as BatchCursor } from './cursors/BatchCursor.js';
25
29
  export * from './cursors/BatchCursor.js';
@@ -16,6 +16,7 @@ export default abstract class AbstractStore<FullSchema extends Schema, CreateSch
16
16
  protected scrambleFields?: string[];
17
17
  protected db: Database;
18
18
  protected primaryFieldNames: string[];
19
+ protected shouldMapLowerCaseToCamelCase: boolean;
19
20
  initialize?(): Promise<void>;
20
21
  protected prepareRecord?<IncludePrivateFields extends boolean, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>>(record: DatabaseRecord, options?: PrepareOptions<IncludePrivateFields, FullSchema, F>): Promise<PrepareResults<FullSchema, IncludePrivateFields>>;
21
22
  protected willCreate?(values: CreateRecord): Promise<Omit<DatabaseRecord, 'id'>>;
@@ -27,8 +28,10 @@ export default abstract class AbstractStore<FullSchema extends Schema, CreateSch
27
28
  }): Promise<Partial<DatabaseRecord>>;
28
29
  protected constructor(db: Database, collectionName?: string);
29
30
  protected setCollectionName(name: string): void;
31
+ getDb(): Database;
30
32
  getCollectionName(): string;
31
33
  protected prepareAndNormalizeRecord<IncludePrivateFields extends boolean = true, CreateEntityInstances extends boolean = false, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>, PF extends SchemaPublicFieldNames<FullSchema> = SchemaPublicFieldNames<FullSchema>>(record: any, options?: PrepareOptions<IncludePrivateFields, FullSchema, F>): Promise<Response<FullSchema, CreateEntityInstances, IncludePrivateFields, PF, F>>;
34
+ private mapCasing;
32
35
  create<IncludePrivateFields extends boolean = true, CreateEntityInstances extends boolean = false, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>, PF extends SchemaPublicFieldNames<FullSchema> = SchemaPublicFieldNames<FullSchema>>(values: CreateRecord[], options?: PrepareOptions<CreateEntityInstances, FullSchema, F>): Promise<Response<FullSchema, CreateEntityInstances, IncludePrivateFields, PF, F>[]>;
33
36
  createOne<CreateEntityInstances extends boolean, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>>(values: CreateRecord, options?: PrepareOptions<CreateEntityInstances, FullSchema, F>): Promise<SchemaValues<FullSchema, false, CreateEntityInstances, false, F, SchemaPublicFieldNames<FullSchema>>>;
34
37
  private get primaryFieldName();
@@ -29,6 +29,7 @@ export default class AbstractStore extends AbstractMutexer {
29
29
  constructor(db, collectionName) {
30
30
  super();
31
31
  this.primaryFieldNames = ['id'];
32
+ this.shouldMapLowerCaseToCamelCase = false;
32
33
  this.db = db;
33
34
  if (collectionName) {
34
35
  this.setCollectionName(collectionName);
@@ -37,6 +38,9 @@ export default class AbstractStore extends AbstractMutexer {
37
38
  setCollectionName(name) {
38
39
  this.collectionName = name;
39
40
  }
41
+ getDb() {
42
+ return this.db;
43
+ }
40
44
  getCollectionName() {
41
45
  return this.collectionName;
42
46
  }
@@ -49,9 +53,23 @@ export default class AbstractStore extends AbstractMutexer {
49
53
  if (isScrambled) {
50
54
  return preparedRecord;
51
55
  }
56
+ if (this.shouldMapLowerCaseToCamelCase) {
57
+ this.mapCasing(preparedRecord);
58
+ }
52
59
  return normalizeSchemaValues(this.fullSchema, preparedRecord, Object.assign(Object.assign({}, options), { fields: options.includeFields, shouldIncludePrivateFields: options.shouldIncludePrivateFields === true, shouldCreateEntityInstances: false, shouldIncludeNullAndUndefinedFields: false }));
53
60
  });
54
61
  }
62
+ mapCasing(preparedRecord) {
63
+ var _a;
64
+ const fields = (_a = this.fullSchema.fields) !== null && _a !== void 0 ? _a : {};
65
+ Object.keys(fields).forEach((f) => {
66
+ const lowerF = f.toLowerCase();
67
+ if (lowerF !== f && lowerF in preparedRecord) {
68
+ preparedRecord[f] = preparedRecord[lowerF];
69
+ delete preparedRecord[lowerF];
70
+ }
71
+ });
72
+ }
55
73
  create(values, options) {
56
74
  return __awaiter(this, void 0, void 0, function* () {
57
75
  try {
@@ -1,3 +1,4 @@
1
+ import AbstractStore from '../stores/AbstractStore';
1
2
  import { Database, Index, TestConnect, UniqueIndex } from '../types/database.types';
2
3
  declare const databaseAssertUtil: {
3
4
  collectionName: string;
@@ -78,5 +79,6 @@ declare const databaseAssertUtil: {
78
79
  _assertThrowsExpectedNotFoundOnUpdateOne(db: Database, query: Record<string, any>): Promise<void>;
79
80
  _assert$orReturnsExpectedTotalRecords(db: Database, $or: Record<string, any>[], expected: number): Promise<void>;
80
81
  _assertCanCreateMultiFieldIndex(connect: TestConnect, fields: string[]): Promise<void>;
82
+ assertHasLowerCaseToCamelCaseMappingEnabled(store: AbstractStore<any>): void;
81
83
  };
82
84
  export default databaseAssertUtil;
@@ -1696,6 +1696,11 @@ const databaseAssertUtil = {
1696
1696
  yield this.shutdown(db);
1697
1697
  });
1698
1698
  },
1699
+ assertHasLowerCaseToCamelCaseMappingEnabled(store) {
1700
+ assert.isTrue(
1701
+ //@ts-ignore
1702
+ store.shouldMapLowerCaseToCamelCase, `Your data store is not mapping lower case to camel case field names! To make that work, add protected shouldMapLowerCaseToCamelCase = true to your store.`);
1703
+ },
1699
1704
  };
1700
1705
  export default databaseAssertUtil;
1701
1706
  function assertCantCreateUniqueIndexTwice(db, collectionName, fields, expectedTotalUniqueIndexes) {
@@ -1,2 +1,2 @@
1
1
  import databaseAssertUtil from './databaseAssertUtil';
2
- export default function pluckAssertionMethods(util: typeof databaseAssertUtil): ("collectionName" | "assertThrowsWithInvalidConnectionString" | "assertThrowsWhenCantConnect" | "assertThrowsWithBadDatabaseName" | "assertEmptyDatabaseReturnsEmptyArray" | "assertKnowsIfConnectionClosed" | "assertFindOneOnEmptyDatabaseReturnsNull" | "assertCanSortDesc" | "assertCanSortAsc" | "assertCanSortById" | "assertCanQueryWithOr" | "generateIdDifferentEachTime" | "assertInsertingGeneratesId" | "assertCanCreateMany" | "assertCanLimitResults" | "assertCanCreateWithObjectField" | "assertCanCountOnId" | "assertCanCount" | "assertThrowsWhenUpdatingRecordNotFound" | "assertCanUpdate" | "assertCanUpdateMany" | "assertCanPushOntoArrayValue" | "assertCanUpdateWithObjectField" | "assertCanUpdateFieldInObjectFieldWithTargettedWhere" | "assertCanSaveAndGetNullAndUndefined" | "assertCanUpsertOne" | "assertCanUpsertNull" | "assertCanPushToArrayOnUpsert" | "assertCanLimitResultsToZero" | "assertCanFindWithBooleanField" | "assertCanQueryByGtLtGteLteNe" | "assertCanQueryPathWithDotSyntax" | "assertCanReturnOnlySelectFields" | "assertCanSearchByRegex" | "assertCanFindWithNe" | "assertCanFindWithIn" | "assertCanDeleteRecord" | "assertCanDeleteOne" | "assertHasNoUniqueIndexToStart" | "assertCanCreateUniqueIndex" | "assertCanCreateMultiFieldUniqueIndex" | "assertCantCreateUniqueIndexTwice" | "assertCanDropUniqueIndex" | "assertCanDropCompoundUniqueIndex" | "assertCantDropUniqueIndexThatDoesntExist" | "assertCantDropIndexWhenNoIndexExists" | "assertCantDropCompoundUniqueIndexThatDoesntExist" | "assertSyncingUniqueIndexsAddsMissingIndexes" | "assertSyncingUniqueIndexsSkipsExistingIndexs" | "assertSyncingUniqueIndexesRemovesExtraIndexes" | "assertSyncingUniqueIndexesIsRaceProof" | "assertSyncingIndexesDoesNotAddAndRemove" | "assertUniqueIndexBlocksDuplicates" | "assertDuplicateKeyThrowsOnInsert" | "assertSettingUniqueIndexViolationThrowsSpruceError" | "assertCanCreateUniqueIndexOnNestedField" | "assertUpsertWithUniqueIndex" | "assertNestedFieldIndexUpdates" | "assertHasNoIndexToStart" | "assertCanCreateIndex" | "assertCantCreateSameIndexTwice" | "assertCanCreateMultiFieldIndex" | "assertCanDropIndex" | "assertCanDropCompoundIndex" | "assertCantDropCompoundIndexThatDoesNotExist" | "assertSyncIndexesSkipsExisting" | "assertSyncIndexesRemovesExtraIndexes" | "assertSyncIndexesHandlesRaceConditions" | "assertSyncIndexesDoesNotRemoveExisting" | "assertDuplicateFieldsWithMultipleUniqueIndexesWorkAsExpected" | "runSuite" | "_getFilteredIndexes" | "_filterIdIndex" | "_assertUpdateUpdatedRightNumberOfRecords" | "shutdown" | "_assertThrowsExpectedNotFoundOnUpdateOne" | "_assert$orReturnsExpectedTotalRecords" | "_assertCanCreateMultiFieldIndex")[];
2
+ export default function pluckAssertionMethods(util: typeof databaseAssertUtil): ("collectionName" | "assertThrowsWithInvalidConnectionString" | "assertThrowsWhenCantConnect" | "assertThrowsWithBadDatabaseName" | "assertEmptyDatabaseReturnsEmptyArray" | "assertKnowsIfConnectionClosed" | "assertFindOneOnEmptyDatabaseReturnsNull" | "assertCanSortDesc" | "assertCanSortAsc" | "assertCanSortById" | "assertCanQueryWithOr" | "generateIdDifferentEachTime" | "assertInsertingGeneratesId" | "assertCanCreateMany" | "assertCanLimitResults" | "assertCanCreateWithObjectField" | "assertCanCountOnId" | "assertCanCount" | "assertThrowsWhenUpdatingRecordNotFound" | "assertCanUpdate" | "assertCanUpdateMany" | "assertCanPushOntoArrayValue" | "assertCanUpdateWithObjectField" | "assertCanUpdateFieldInObjectFieldWithTargettedWhere" | "assertCanSaveAndGetNullAndUndefined" | "assertCanUpsertOne" | "assertCanUpsertNull" | "assertCanPushToArrayOnUpsert" | "assertCanLimitResultsToZero" | "assertCanFindWithBooleanField" | "assertCanQueryByGtLtGteLteNe" | "assertCanQueryPathWithDotSyntax" | "assertCanReturnOnlySelectFields" | "assertCanSearchByRegex" | "assertCanFindWithNe" | "assertCanFindWithIn" | "assertCanDeleteRecord" | "assertCanDeleteOne" | "assertHasNoUniqueIndexToStart" | "assertCanCreateUniqueIndex" | "assertCanCreateMultiFieldUniqueIndex" | "assertCantCreateUniqueIndexTwice" | "assertCanDropUniqueIndex" | "assertCanDropCompoundUniqueIndex" | "assertCantDropUniqueIndexThatDoesntExist" | "assertCantDropIndexWhenNoIndexExists" | "assertCantDropCompoundUniqueIndexThatDoesntExist" | "assertSyncingUniqueIndexsAddsMissingIndexes" | "assertSyncingUniqueIndexsSkipsExistingIndexs" | "assertSyncingUniqueIndexesRemovesExtraIndexes" | "assertSyncingUniqueIndexesIsRaceProof" | "assertSyncingIndexesDoesNotAddAndRemove" | "assertUniqueIndexBlocksDuplicates" | "assertDuplicateKeyThrowsOnInsert" | "assertSettingUniqueIndexViolationThrowsSpruceError" | "assertCanCreateUniqueIndexOnNestedField" | "assertUpsertWithUniqueIndex" | "assertNestedFieldIndexUpdates" | "assertHasNoIndexToStart" | "assertCanCreateIndex" | "assertCantCreateSameIndexTwice" | "assertCanCreateMultiFieldIndex" | "assertCanDropIndex" | "assertCanDropCompoundIndex" | "assertCantDropCompoundIndexThatDoesNotExist" | "assertSyncIndexesSkipsExisting" | "assertSyncIndexesRemovesExtraIndexes" | "assertSyncIndexesHandlesRaceConditions" | "assertSyncIndexesDoesNotRemoveExisting" | "assertDuplicateFieldsWithMultipleUniqueIndexesWorkAsExpected" | "runSuite" | "_getFilteredIndexes" | "_filterIdIndex" | "_assertUpdateUpdatedRightNumberOfRecords" | "shutdown" | "_assertThrowsExpectedNotFoundOnUpdateOne" | "_assert$orReturnsExpectedTotalRecords" | "_assertCanCreateMultiFieldIndex" | "assertHasLowerCaseToCamelCaseMappingEnabled")[];
package/build/index.d.ts CHANGED
@@ -20,6 +20,10 @@ export { default as CursorPager } from './cursors/CursorPager';
20
20
  export * from './cursors/CursorPager';
21
21
  export { default as CursorPagerFaker } from './cursors/CursorPagerFaker';
22
22
  export * from './cursors/CursorPager';
23
+ /**
24
+ * @deprecated databaseAssertUtil -> databaseAssert
25
+ */
23
26
  export { default as databaseAssertUtil } from './tests/databaseAssertUtil';
27
+ export { default as databaseAssert } from './tests/databaseAssertUtil';
24
28
  export { default as BatchCursor } from './cursors/BatchCursor';
25
29
  export * from './cursors/BatchCursor';
package/build/index.js CHANGED
@@ -17,7 +17,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
17
17
  return (mod && mod.__esModule) ? mod : { "default": mod };
18
18
  };
19
19
  Object.defineProperty(exports, "__esModule", { value: true });
20
- exports.BatchCursor = exports.databaseAssertUtil = exports.CursorPagerFaker = exports.CursorPager = exports.generateId = exports.DataStoresError = exports.mongoUtil = exports.NeDbDatabase = exports.MongoDatabase = exports.StoreLoader = exports.DatabaseFactory = exports.StoreFactory = exports.AbstractStore = exports.DatabaseFixture = exports.AbstractDatabaseTest = void 0;
20
+ exports.BatchCursor = exports.databaseAssert = exports.databaseAssertUtil = exports.CursorPagerFaker = exports.CursorPager = exports.generateId = exports.DataStoresError = exports.mongoUtil = exports.NeDbDatabase = exports.MongoDatabase = exports.StoreLoader = exports.DatabaseFactory = exports.StoreFactory = exports.AbstractStore = exports.DatabaseFixture = exports.AbstractDatabaseTest = void 0;
21
21
  var AbstractDatabaseTest_1 = require("./tests/AbstractDatabaseTest");
22
22
  Object.defineProperty(exports, "AbstractDatabaseTest", { enumerable: true, get: function () { return __importDefault(AbstractDatabaseTest_1).default; } });
23
23
  var DatabaseFixture_1 = require("./fixtures/DatabaseFixture");
@@ -53,8 +53,13 @@ __exportStar(require("./cursors/CursorPager"), exports);
53
53
  var CursorPagerFaker_1 = require("./cursors/CursorPagerFaker");
54
54
  Object.defineProperty(exports, "CursorPagerFaker", { enumerable: true, get: function () { return __importDefault(CursorPagerFaker_1).default; } });
55
55
  __exportStar(require("./cursors/CursorPager"), exports);
56
+ /**
57
+ * @deprecated databaseAssertUtil -> databaseAssert
58
+ */
56
59
  var databaseAssertUtil_1 = require("./tests/databaseAssertUtil");
57
60
  Object.defineProperty(exports, "databaseAssertUtil", { enumerable: true, get: function () { return __importDefault(databaseAssertUtil_1).default; } });
61
+ var databaseAssertUtil_2 = require("./tests/databaseAssertUtil");
62
+ Object.defineProperty(exports, "databaseAssert", { enumerable: true, get: function () { return __importDefault(databaseAssertUtil_2).default; } });
58
63
  var BatchCursor_1 = require("./cursors/BatchCursor");
59
64
  Object.defineProperty(exports, "BatchCursor", { enumerable: true, get: function () { return __importDefault(BatchCursor_1).default; } });
60
65
  __exportStar(require("./cursors/BatchCursor"), exports);
@@ -16,6 +16,7 @@ export default abstract class AbstractStore<FullSchema extends Schema, CreateSch
16
16
  protected scrambleFields?: string[];
17
17
  protected db: Database;
18
18
  protected primaryFieldNames: string[];
19
+ protected shouldMapLowerCaseToCamelCase: boolean;
19
20
  initialize?(): Promise<void>;
20
21
  protected prepareRecord?<IncludePrivateFields extends boolean, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>>(record: DatabaseRecord, options?: PrepareOptions<IncludePrivateFields, FullSchema, F>): Promise<PrepareResults<FullSchema, IncludePrivateFields>>;
21
22
  protected willCreate?(values: CreateRecord): Promise<Omit<DatabaseRecord, 'id'>>;
@@ -27,8 +28,10 @@ export default abstract class AbstractStore<FullSchema extends Schema, CreateSch
27
28
  }): Promise<Partial<DatabaseRecord>>;
28
29
  protected constructor(db: Database, collectionName?: string);
29
30
  protected setCollectionName(name: string): void;
31
+ getDb(): Database;
30
32
  getCollectionName(): string;
31
33
  protected prepareAndNormalizeRecord<IncludePrivateFields extends boolean = true, CreateEntityInstances extends boolean = false, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>, PF extends SchemaPublicFieldNames<FullSchema> = SchemaPublicFieldNames<FullSchema>>(record: any, options?: PrepareOptions<IncludePrivateFields, FullSchema, F>): Promise<Response<FullSchema, CreateEntityInstances, IncludePrivateFields, PF, F>>;
34
+ private mapCasing;
32
35
  create<IncludePrivateFields extends boolean = true, CreateEntityInstances extends boolean = false, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>, PF extends SchemaPublicFieldNames<FullSchema> = SchemaPublicFieldNames<FullSchema>>(values: CreateRecord[], options?: PrepareOptions<CreateEntityInstances, FullSchema, F>): Promise<Response<FullSchema, CreateEntityInstances, IncludePrivateFields, PF, F>[]>;
33
36
  createOne<CreateEntityInstances extends boolean, F extends SchemaFieldNames<FullSchema> = SchemaFieldNames<FullSchema>>(values: CreateRecord, options?: PrepareOptions<CreateEntityInstances, FullSchema, F>): Promise<SchemaValues<FullSchema, false, CreateEntityInstances, false, F, SchemaPublicFieldNames<FullSchema>>>;
34
37
  private get primaryFieldName();
@@ -48,6 +48,7 @@ class AbstractStore extends AbstractMutexer_1.default {
48
48
  constructor(db, collectionName) {
49
49
  super();
50
50
  this.primaryFieldNames = ['id'];
51
+ this.shouldMapLowerCaseToCamelCase = false;
51
52
  this.db = db;
52
53
  if (collectionName) {
53
54
  this.setCollectionName(collectionName);
@@ -56,6 +57,9 @@ class AbstractStore extends AbstractMutexer_1.default {
56
57
  setCollectionName(name) {
57
58
  this.collectionName = name;
58
59
  }
60
+ getDb() {
61
+ return this.db;
62
+ }
59
63
  getCollectionName() {
60
64
  return this.collectionName;
61
65
  }
@@ -67,8 +71,22 @@ class AbstractStore extends AbstractMutexer_1.default {
67
71
  if (isScrambled) {
68
72
  return preparedRecord;
69
73
  }
74
+ if (this.shouldMapLowerCaseToCamelCase) {
75
+ this.mapCasing(preparedRecord);
76
+ }
70
77
  return (0, schema_1.normalizeSchemaValues)(this.fullSchema, preparedRecord, Object.assign(Object.assign({}, options), { fields: options.includeFields, shouldIncludePrivateFields: options.shouldIncludePrivateFields === true, shouldCreateEntityInstances: false, shouldIncludeNullAndUndefinedFields: false }));
71
78
  }
79
+ mapCasing(preparedRecord) {
80
+ var _a;
81
+ const fields = (_a = this.fullSchema.fields) !== null && _a !== void 0 ? _a : {};
82
+ Object.keys(fields).forEach((f) => {
83
+ const lowerF = f.toLowerCase();
84
+ if (lowerF !== f && lowerF in preparedRecord) {
85
+ preparedRecord[f] = preparedRecord[lowerF];
86
+ delete preparedRecord[lowerF];
87
+ }
88
+ });
89
+ }
72
90
  async create(values, options) {
73
91
  try {
74
92
  //@ts-ignore
@@ -1,3 +1,4 @@
1
+ import AbstractStore from '../stores/AbstractStore';
1
2
  import { Database, Index, TestConnect, UniqueIndex } from '../types/database.types';
2
3
  declare const databaseAssertUtil: {
3
4
  collectionName: string;
@@ -78,5 +79,6 @@ declare const databaseAssertUtil: {
78
79
  _assertThrowsExpectedNotFoundOnUpdateOne(db: Database, query: Record<string, any>): Promise<void>;
79
80
  _assert$orReturnsExpectedTotalRecords(db: Database, $or: Record<string, any>[], expected: number): Promise<void>;
80
81
  _assertCanCreateMultiFieldIndex(connect: TestConnect, fields: string[]): Promise<void>;
82
+ assertHasLowerCaseToCamelCaseMappingEnabled(store: AbstractStore<any>): void;
81
83
  };
82
84
  export default databaseAssertUtil;
@@ -1540,6 +1540,11 @@ const databaseAssertUtil = {
1540
1540
  test_utils_1.assert.isEqualDeep(indexes[0].map((i) => i.toLowerCase()), fields.map((f) => f.toLowerCase()));
1541
1541
  await this.shutdown(db);
1542
1542
  },
1543
+ assertHasLowerCaseToCamelCaseMappingEnabled(store) {
1544
+ test_utils_1.assert.isTrue(
1545
+ //@ts-ignore
1546
+ store.shouldMapLowerCaseToCamelCase, `Your data store is not mapping lower case to camel case field names! To make that work, add protected shouldMapLowerCaseToCamelCase = true to your store.`);
1547
+ },
1543
1548
  };
1544
1549
  exports.default = databaseAssertUtil;
1545
1550
  async function assertCantCreateUniqueIndexTwice(db, collectionName, fields, expectedTotalUniqueIndexes) {
@@ -1,2 +1,2 @@
1
1
  import databaseAssertUtil from './databaseAssertUtil';
2
- export default function pluckAssertionMethods(util: typeof databaseAssertUtil): ("collectionName" | "assertThrowsWithInvalidConnectionString" | "assertThrowsWhenCantConnect" | "assertThrowsWithBadDatabaseName" | "assertEmptyDatabaseReturnsEmptyArray" | "assertKnowsIfConnectionClosed" | "assertFindOneOnEmptyDatabaseReturnsNull" | "assertCanSortDesc" | "assertCanSortAsc" | "assertCanSortById" | "assertCanQueryWithOr" | "generateIdDifferentEachTime" | "assertInsertingGeneratesId" | "assertCanCreateMany" | "assertCanLimitResults" | "assertCanCreateWithObjectField" | "assertCanCountOnId" | "assertCanCount" | "assertThrowsWhenUpdatingRecordNotFound" | "assertCanUpdate" | "assertCanUpdateMany" | "assertCanPushOntoArrayValue" | "assertCanUpdateWithObjectField" | "assertCanUpdateFieldInObjectFieldWithTargettedWhere" | "assertCanSaveAndGetNullAndUndefined" | "assertCanUpsertOne" | "assertCanUpsertNull" | "assertCanPushToArrayOnUpsert" | "assertCanLimitResultsToZero" | "assertCanFindWithBooleanField" | "assertCanQueryByGtLtGteLteNe" | "assertCanQueryPathWithDotSyntax" | "assertCanReturnOnlySelectFields" | "assertCanSearchByRegex" | "assertCanFindWithNe" | "assertCanFindWithIn" | "assertCanDeleteRecord" | "assertCanDeleteOne" | "assertHasNoUniqueIndexToStart" | "assertCanCreateUniqueIndex" | "assertCanCreateMultiFieldUniqueIndex" | "assertCantCreateUniqueIndexTwice" | "assertCanDropUniqueIndex" | "assertCanDropCompoundUniqueIndex" | "assertCantDropUniqueIndexThatDoesntExist" | "assertCantDropIndexWhenNoIndexExists" | "assertCantDropCompoundUniqueIndexThatDoesntExist" | "assertSyncingUniqueIndexsAddsMissingIndexes" | "assertSyncingUniqueIndexsSkipsExistingIndexs" | "assertSyncingUniqueIndexesRemovesExtraIndexes" | "assertSyncingUniqueIndexesIsRaceProof" | "assertSyncingIndexesDoesNotAddAndRemove" | "assertUniqueIndexBlocksDuplicates" | "assertDuplicateKeyThrowsOnInsert" | "assertSettingUniqueIndexViolationThrowsSpruceError" | "assertCanCreateUniqueIndexOnNestedField" | "assertUpsertWithUniqueIndex" | "assertNestedFieldIndexUpdates" | "assertHasNoIndexToStart" | "assertCanCreateIndex" | "assertCantCreateSameIndexTwice" | "assertCanCreateMultiFieldIndex" | "assertCanDropIndex" | "assertCanDropCompoundIndex" | "assertCantDropCompoundIndexThatDoesNotExist" | "assertSyncIndexesSkipsExisting" | "assertSyncIndexesRemovesExtraIndexes" | "assertSyncIndexesHandlesRaceConditions" | "assertSyncIndexesDoesNotRemoveExisting" | "assertDuplicateFieldsWithMultipleUniqueIndexesWorkAsExpected" | "runSuite" | "_getFilteredIndexes" | "_filterIdIndex" | "_assertUpdateUpdatedRightNumberOfRecords" | "shutdown" | "_assertThrowsExpectedNotFoundOnUpdateOne" | "_assert$orReturnsExpectedTotalRecords" | "_assertCanCreateMultiFieldIndex")[];
2
+ export default function pluckAssertionMethods(util: typeof databaseAssertUtil): ("collectionName" | "assertThrowsWithInvalidConnectionString" | "assertThrowsWhenCantConnect" | "assertThrowsWithBadDatabaseName" | "assertEmptyDatabaseReturnsEmptyArray" | "assertKnowsIfConnectionClosed" | "assertFindOneOnEmptyDatabaseReturnsNull" | "assertCanSortDesc" | "assertCanSortAsc" | "assertCanSortById" | "assertCanQueryWithOr" | "generateIdDifferentEachTime" | "assertInsertingGeneratesId" | "assertCanCreateMany" | "assertCanLimitResults" | "assertCanCreateWithObjectField" | "assertCanCountOnId" | "assertCanCount" | "assertThrowsWhenUpdatingRecordNotFound" | "assertCanUpdate" | "assertCanUpdateMany" | "assertCanPushOntoArrayValue" | "assertCanUpdateWithObjectField" | "assertCanUpdateFieldInObjectFieldWithTargettedWhere" | "assertCanSaveAndGetNullAndUndefined" | "assertCanUpsertOne" | "assertCanUpsertNull" | "assertCanPushToArrayOnUpsert" | "assertCanLimitResultsToZero" | "assertCanFindWithBooleanField" | "assertCanQueryByGtLtGteLteNe" | "assertCanQueryPathWithDotSyntax" | "assertCanReturnOnlySelectFields" | "assertCanSearchByRegex" | "assertCanFindWithNe" | "assertCanFindWithIn" | "assertCanDeleteRecord" | "assertCanDeleteOne" | "assertHasNoUniqueIndexToStart" | "assertCanCreateUniqueIndex" | "assertCanCreateMultiFieldUniqueIndex" | "assertCantCreateUniqueIndexTwice" | "assertCanDropUniqueIndex" | "assertCanDropCompoundUniqueIndex" | "assertCantDropUniqueIndexThatDoesntExist" | "assertCantDropIndexWhenNoIndexExists" | "assertCantDropCompoundUniqueIndexThatDoesntExist" | "assertSyncingUniqueIndexsAddsMissingIndexes" | "assertSyncingUniqueIndexsSkipsExistingIndexs" | "assertSyncingUniqueIndexesRemovesExtraIndexes" | "assertSyncingUniqueIndexesIsRaceProof" | "assertSyncingIndexesDoesNotAddAndRemove" | "assertUniqueIndexBlocksDuplicates" | "assertDuplicateKeyThrowsOnInsert" | "assertSettingUniqueIndexViolationThrowsSpruceError" | "assertCanCreateUniqueIndexOnNestedField" | "assertUpsertWithUniqueIndex" | "assertNestedFieldIndexUpdates" | "assertHasNoIndexToStart" | "assertCanCreateIndex" | "assertCantCreateSameIndexTwice" | "assertCanCreateMultiFieldIndex" | "assertCanDropIndex" | "assertCanDropCompoundIndex" | "assertCantDropCompoundIndexThatDoesNotExist" | "assertSyncIndexesSkipsExisting" | "assertSyncIndexesRemovesExtraIndexes" | "assertSyncIndexesHandlesRaceConditions" | "assertSyncIndexesDoesNotRemoveExisting" | "assertDuplicateFieldsWithMultipleUniqueIndexesWorkAsExpected" | "runSuite" | "_getFilteredIndexes" | "_filterIdIndex" | "_assertUpdateUpdatedRightNumberOfRecords" | "shutdown" | "_assertThrowsExpectedNotFoundOnUpdateOne" | "_assert$orReturnsExpectedTotalRecords" | "_assertCanCreateMultiFieldIndex" | "assertHasLowerCaseToCamelCaseMappingEnabled")[];
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "publishConfig": {
4
4
  "access": "public"
5
5
  },
6
- "version": "25.2.3",
6
+ "version": "25.3.0",
7
7
  "files": [
8
8
  "build/**/*",
9
9
  "!build/__tests__",