@nocobase/database 0.7.6-alpha.2 → 0.8.0-alpha.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.
Files changed (61) hide show
  1. package/lib/collection.d.ts +1 -1
  2. package/lib/collection.js +1 -0
  3. package/lib/database.d.ts +17 -2
  4. package/lib/database.js +53 -41
  5. package/lib/features/ReferencesMap.d.ts +15 -0
  6. package/lib/features/ReferencesMap.js +60 -0
  7. package/lib/features/referential-integrity-check.d.ts +8 -0
  8. package/lib/features/referential-integrity-check.js +89 -0
  9. package/lib/fields/belongs-to-field.d.ts +2 -0
  10. package/lib/fields/belongs-to-field.js +16 -2
  11. package/lib/fields/belongs-to-many-field.d.ts +1 -0
  12. package/lib/fields/belongs-to-many-field.js +8 -2
  13. package/lib/fields/context-field.d.ts +2 -1
  14. package/lib/fields/context-field.js +12 -8
  15. package/lib/fields/field.d.ts +2 -1
  16. package/lib/fields/field.js +1 -0
  17. package/lib/fields/formula-field.js +1 -1
  18. package/lib/fields/has-many-field.d.ts +2 -0
  19. package/lib/fields/has-many-field.js +19 -1
  20. package/lib/fields/has-one-field.d.ts +2 -0
  21. package/lib/fields/has-one-field.js +16 -2
  22. package/lib/filter-parser.js +5 -3
  23. package/lib/model.d.ts +1 -0
  24. package/lib/options-parser.js +3 -2
  25. package/lib/relation-repository/belongs-to-many-repository.d.ts +3 -3
  26. package/lib/relation-repository/hasmany-repository.d.ts +2 -2
  27. package/lib/relation-repository/hasone-repository.d.ts +2 -4
  28. package/lib/relation-repository/multiple-relation-repository.d.ts +2 -5
  29. package/lib/relation-repository/relation-repository.js +2 -2
  30. package/lib/relation-repository/single-relation-repository.d.ts +1 -1
  31. package/lib/repository.d.ts +25 -15
  32. package/lib/repository.js +3 -1
  33. package/lib/types.d.ts +43 -0
  34. package/lib/types.js +5 -0
  35. package/package.json +3 -3
  36. package/src/__tests__/fields/belongs-to-field.test.ts +112 -4
  37. package/src/__tests__/fields/has-many-field.test.ts +83 -0
  38. package/src/__tests__/relation-repository/hasone-repository.test.ts +3 -3
  39. package/src/__tests__/repository/find.test.ts +10 -0
  40. package/src/collection.ts +3 -1
  41. package/src/database.ts +64 -15
  42. package/src/features/ReferencesMap.ts +64 -0
  43. package/src/features/referential-integrity-check.ts +61 -0
  44. package/src/fields/belongs-to-field.ts +21 -1
  45. package/src/fields/belongs-to-many-field.ts +6 -0
  46. package/src/fields/context-field.ts +5 -7
  47. package/src/fields/field.ts +4 -3
  48. package/src/fields/formula-field.ts +4 -4
  49. package/src/fields/has-many-field.ts +25 -2
  50. package/src/fields/has-one-field.ts +22 -2
  51. package/src/filter-parser.ts +5 -1
  52. package/src/model.ts +1 -0
  53. package/src/options-parser.ts +4 -2
  54. package/src/relation-repository/belongs-to-many-repository.ts +3 -3
  55. package/src/relation-repository/hasmany-repository.ts +8 -5
  56. package/src/relation-repository/hasone-repository.ts +2 -4
  57. package/src/relation-repository/multiple-relation-repository.ts +3 -4
  58. package/src/relation-repository/relation-repository.ts +1 -1
  59. package/src/relation-repository/single-relation-repository.ts +1 -1
  60. package/src/repository.ts +41 -19
  61. package/src/types.ts +64 -0
@@ -5,11 +5,12 @@ import {
5
5
  ForeignKeyOptions,
6
6
  HasOneOptions,
7
7
  HasOneOptions as SequelizeHasOneOptions,
8
- Utils
8
+ Utils,
9
9
  } from 'sequelize';
10
10
  import { Collection } from '../collection';
11
11
  import { checkIdentifier } from '../utils';
12
12
  import { BaseRelationFieldOptions, RelationField } from './relation-field';
13
+ import { Reference } from '../features/ReferencesMap';
13
14
 
14
15
  export interface HasOneFieldOptions extends HasOneOptions {
15
16
  /**
@@ -86,9 +87,22 @@ export class HasOneField extends RelationField {
86
87
  return Utils.camelize([model.options.name.singular, model.primaryKeyAttribute].join('_'));
87
88
  }
88
89
 
90
+ reference(association): Reference {
91
+ const sourceKey = association.sourceKey;
92
+
93
+ return {
94
+ sourceCollectionName: this.database.modelCollection.get(association.target).name,
95
+ sourceField: association.foreignKey,
96
+ targetField: sourceKey,
97
+ targetCollectionName: this.database.modelCollection.get(association.source).name,
98
+ onDelete: this.options.onDelete,
99
+ };
100
+ }
101
+
89
102
  bind() {
90
103
  const { database, collection } = this.context;
91
104
  const Target = this.TargetModel;
105
+
92
106
  if (!Target) {
93
107
  database.addPendingField(this);
94
108
  return false;
@@ -96,7 +110,7 @@ export class HasOneField extends RelationField {
96
110
 
97
111
  const association = collection.model.hasOne(Target, {
98
112
  constraints: false,
99
- ...omit(this.options, ['name', 'type', 'target']),
113
+ ...omit(this.options, ['name', 'type', 'target', 'onDelete']),
100
114
  as: this.name,
101
115
  foreignKey: this.foreignKey,
102
116
  });
@@ -129,6 +143,8 @@ export class HasOneField extends RelationField {
129
143
  if (tcoll) {
130
144
  tcoll.addIndex([this.options.foreignKey]);
131
145
  }
146
+
147
+ this.database.referenceMap.addReference(this.reference(association));
132
148
  return true;
133
149
  }
134
150
 
@@ -148,6 +164,10 @@ export class HasOneField extends RelationField {
148
164
  if (!field) {
149
165
  tcoll.model.removeAttribute(foreignKey);
150
166
  }
167
+
168
+ const association = collection.model.associations[this.name];
169
+ this.database.referenceMap.removeReference(this.reference(association));
170
+
151
171
  // 删掉 model 的关联字段
152
172
  delete collection.model.associations[this.name];
153
173
  // @ts-ignore
@@ -78,7 +78,6 @@ export default class FilterParser {
78
78
 
79
79
  const include = {};
80
80
  const where = {};
81
- const filter2 = lodash.cloneDeep(flattenedFilter);
82
81
 
83
82
  let skipPrefix = null;
84
83
  const associations = model.associations;
@@ -91,6 +90,11 @@ export default class FilterParser {
91
90
  continue;
92
91
  }
93
92
 
93
+ // skip empty logic operator value
94
+ if ((key == '$or' || key == '$and') && Array.isArray(value) && value.length == 0) {
95
+ continue;
96
+ }
97
+
94
98
  debug('handle filter key "%s: "%s"', key, value);
95
99
  let keys = key.split('.');
96
100
 
package/src/model.ts CHANGED
@@ -23,6 +23,7 @@ export class Model<TModelAttributes extends {} = any, TCreationAttributes extend
23
23
  public static database: Database;
24
24
  public static collection: Collection;
25
25
 
26
+ [key: string]: any;
26
27
  protected _changedWithAssociations = new Set();
27
28
  protected _previousDataValuesWithAssociations = {};
28
29
 
@@ -70,6 +70,7 @@ export class OptionsParser {
70
70
  if (typeof sort === 'string') {
71
71
  sort = sort.split(',');
72
72
  }
73
+
73
74
  const orderParams = [];
74
75
  for (const sortKey of sort) {
75
76
  let direction = sortKey.startsWith('-') ? 'DESC' : 'ASC';
@@ -191,8 +192,9 @@ export class OptionsParser {
191
192
 
192
193
  /**
193
194
  * set include params
194
- * @param includeRoot
195
- * @param appends
195
+ * @param model
196
+ * @param queryParams
197
+ * @param append
196
198
  */
197
199
  const setInclude = (model: ModelCtor<any>, queryParams: any, append: string) => {
198
200
  const appendFields = append.split('.');
@@ -1,9 +1,9 @@
1
1
  import lodash from 'lodash';
2
2
  import { BelongsToMany, Op, Transaction } from 'sequelize';
3
3
  import { Model } from '../model';
4
- import { CreateOptions, DestroyOptions, FindOptions, TargetKey, UpdateOptions } from '../repository';
4
+ import { CreateOptions, DestroyOptions, FindOneOptions, FindOptions, TargetKey, UpdateOptions } from '../repository';
5
5
  import { updateThroughTableValue } from '../update-associations';
6
- import { FindAndCountOptions, FindOneOptions, MultipleRelationRepository } from './multiple-relation-repository';
6
+ import { FindAndCountOptions, MultipleRelationRepository } from './multiple-relation-repository';
7
7
  import { transaction } from './relation-repository';
8
8
  import { AssociatedOptions, PrimaryKeyWithThroughValues } from './types';
9
9
 
@@ -14,7 +14,7 @@ interface IBelongsToManyRepository<M extends Model> {
14
14
  findAndCount(options?: FindAndCountOptions): Promise<[M[], number]>;
15
15
  findOne(options?: FindOneOptions): Promise<M>;
16
16
  // 新增并关联,存在中间表数据
17
- create(options?: CreateBelongsToManyOptions): Promise<M>;
17
+ create(options?: CreateOptions): Promise<M>;
18
18
  // 更新,存在中间表数据
19
19
  update(options?: UpdateOptions): Promise<M>;
20
20
  // 删除
@@ -1,13 +1,16 @@
1
1
  import { omit } from 'lodash';
2
2
  import { HasMany, Op } from 'sequelize';
3
3
  import { Model } from '../model';
4
- import { CreateOptions, DestroyOptions, FindOptions, TargetKey, TK, UpdateOptions } from '../repository';
5
4
  import {
6
- AssociatedOptions,
7
- FindAndCountOptions,
5
+ CreateOptions,
6
+ DestroyOptions,
8
7
  FindOneOptions,
9
- MultipleRelationRepository
10
- } from './multiple-relation-repository';
8
+ FindOptions,
9
+ TargetKey,
10
+ TK,
11
+ UpdateOptions,
12
+ } from '../repository';
13
+ import { AssociatedOptions, FindAndCountOptions, MultipleRelationRepository } from './multiple-relation-repository';
11
14
  import { transaction } from './relation-repository';
12
15
 
13
16
  interface IHasManyRepository<M extends Model> {
@@ -2,12 +2,10 @@ import { Model } from '../model';
2
2
  import { CreateOptions } from '../repository';
3
3
  import { SingleRelationFindOption, SingleRelationRepository } from './single-relation-repository';
4
4
 
5
- interface HasOneFindOptions extends SingleRelationFindOption {}
6
-
7
5
  interface IHasOneRepository<M extends Model> {
8
6
  // 不需要 findOne,find 就是 findOne
9
- find(options?: HasOneFindOptions): Promise<M>;
10
- findOne(options?: HasOneFindOptions): Promise<M>;
7
+ find(options?: SingleRelationFindOption): Promise<M>;
8
+ findOne(options?: SingleRelationFindOption): Promise<M>;
11
9
  // 新增并关联,如果存在关联,解除之后,与新数据建立关联
12
10
  create(options?: CreateOptions): Promise<M>;
13
11
  // 更新
@@ -5,7 +5,7 @@ import {
5
5
  CountOptions,
6
6
  DestroyOptions,
7
7
  Filter,
8
- FilterByTk,
8
+ FindOneOptions,
9
9
  FindOptions,
10
10
  TargetKey,
11
11
  TK,
@@ -16,9 +16,7 @@ import { UpdateGuard } from '../update-guard';
16
16
  import { RelationRepository, transaction } from './relation-repository';
17
17
  import { handleAppendsQuery } from '../utils';
18
18
 
19
- export interface FindAndCountOptions extends CommonFindOptions {}
20
-
21
- export interface FindOneOptions extends CommonFindOptions, FilterByTk {}
19
+ export type FindAndCountOptions = CommonFindOptions;
22
20
 
23
21
  export interface AssociatedOptions extends Transactionable {
24
22
  tk?: TK;
@@ -88,6 +86,7 @@ export abstract class MultipleRelationRepository extends RelationRepository {
88
86
 
89
87
  async findAndCount(options?: FindAndCountOptions): Promise<[any[], number]> {
90
88
  const transaction = await this.getTransaction(options, false);
89
+
91
90
  return [
92
91
  await this.find({
93
92
  ...options,
@@ -2,12 +2,12 @@ import lodash from 'lodash';
2
2
  import { Association, BelongsTo, BelongsToMany, HasMany, HasOne, ModelCtor, Transaction } from 'sequelize';
3
3
  import { Collection } from '../collection';
4
4
  import Database from '../database';
5
+ import { transactionWrapperBuilder } from '../decorators/transaction-decorator';
5
6
  import { RelationField } from '../fields/relation-field';
6
7
  import FilterParser from '../filter-parser';
7
8
  import { Model } from '../model';
8
9
  import { OptionsParser } from '../options-parser';
9
10
  import { CreateOptions, Filter, FindOptions } from '../repository';
10
- import { transactionWrapperBuilder } from '../decorators/transaction-decorator';
11
11
  import { updateAssociations } from '../update-associations';
12
12
  import { UpdateGuard } from '../update-guard';
13
13
 
@@ -44,7 +44,7 @@ export abstract class SingleRelationRepository extends RelationRepository {
44
44
  });
45
45
  }
46
46
 
47
- async find(options?: SingleRelationFindOption): Promise<Model<any>> {
47
+ async find(options?: SingleRelationFindOption): Promise<Model<any> | null> {
48
48
  const transaction = await this.getTransaction(options);
49
49
 
50
50
  const findOptions = this.buildQueryOptions({
package/src/repository.ts CHANGED
@@ -2,6 +2,7 @@ import lodash, { omit } from 'lodash';
2
2
  import {
3
3
  Association,
4
4
  BulkCreateOptions,
5
+ CountOptions as SequelizeCountOptions,
5
6
  CreateOptions as SequelizeCreateOptions,
6
7
  DestroyOptions as SequelizeDestroyOptions,
7
8
  FindAndCountOptions as SequelizeAndCountOptions,
@@ -9,8 +10,9 @@ import {
9
10
  ModelCtor,
10
11
  Op,
11
12
  Transactionable,
12
- UpdateOptions as SequelizeUpdateOptions
13
+ UpdateOptions as SequelizeUpdateOptions,
13
14
  } from 'sequelize';
15
+ import { WhereOperators } from 'sequelize/types/lib/model';
14
16
  import { Collection } from './collection';
15
17
  import { Database } from './database';
16
18
  import mustHaveFilter from './decorators/must-have-filter-decorator';
@@ -18,6 +20,7 @@ import { transactionWrapperBuilder } from './decorators/transaction-decorator';
18
20
  import { RelationField } from './fields';
19
21
  import FilterParser from './filter-parser';
20
22
  import { Model } from './model';
23
+ import operators from './operators';
21
24
  import { OptionsParser } from './options-parser';
22
25
  import { BelongsToManyRepository } from './relation-repository/belongs-to-many-repository';
23
26
  import { BelongsToRepository } from './relation-repository/belongs-to-repository';
@@ -45,7 +48,32 @@ export interface FilterAble {
45
48
  export type TargetKey = string | number;
46
49
  export type TK = TargetKey | TargetKey[];
47
50
 
48
- export type Filter = any;
51
+ type FieldValue = string | number | bigint | boolean | Date | Buffer | null | FieldValue[] | FilterWithOperator;
52
+
53
+ type Operators = keyof typeof operators & keyof WhereOperators;
54
+
55
+ export type FilterWithOperator = {
56
+ [key: string]:
57
+ | {
58
+ [K in Operators]: FieldValue;
59
+ }
60
+ | FieldValue;
61
+ };
62
+
63
+ export type FilterWithValue = {
64
+ [key: string]: FieldValue;
65
+ };
66
+
67
+ type FilterAnd = {
68
+ $and: Filter[];
69
+ };
70
+
71
+ type FilterOr = {
72
+ $or: Filter[];
73
+ };
74
+
75
+ export type Filter = FilterWithOperator | FilterWithValue | FilterAnd | FilterOr;
76
+
49
77
  export type Appends = string[];
50
78
  export type Except = string[];
51
79
  export type Fields = string[];
@@ -53,12 +81,12 @@ export type Sort = string[] | string;
53
81
 
54
82
  export type WhiteList = string[];
55
83
  export type BlackList = string[];
84
+
56
85
  export type AssociationKeysToBeUpdate = string[];
57
86
 
58
87
  export type Values = any;
59
88
 
60
- export interface CountOptions extends Omit<SequelizeCreateOptions, 'distinct' | 'where' | 'include'>, Transactionable {
61
- fields?: Fields;
89
+ export interface CountOptions extends Omit<SequelizeCountOptions, 'distinct' | 'where' | 'include'>, Transactionable {
62
90
  filter?: Filter;
63
91
  context?: any;
64
92
  }
@@ -67,7 +95,7 @@ export interface FilterByTk {
67
95
  filterByTk?: TargetKey;
68
96
  }
69
97
 
70
- export interface FindOptions extends SequelizeFindOptions, CommonFindOptions, FilterByTk {}
98
+ export type FindOptions = SequelizeFindOptions & CommonFindOptions & FilterByTk;
71
99
 
72
100
  export interface CommonFindOptions extends Transactionable {
73
101
  filter?: Filter;
@@ -78,7 +106,7 @@ export interface CommonFindOptions extends Transactionable {
78
106
  context?: any;
79
107
  }
80
108
 
81
- interface FindOneOptions extends FindOptions {}
109
+ export type FindOneOptions = Omit<FindOptions, 'limit'>;
82
110
 
83
111
  export interface DestroyOptions extends SequelizeDestroyOptions {
84
112
  filter?: Filter;
@@ -87,18 +115,7 @@ export interface DestroyOptions extends SequelizeDestroyOptions {
87
115
  context?: any;
88
116
  }
89
117
 
90
- interface FindAndCountOptions extends Omit<SequelizeAndCountOptions, 'where' | 'include' | 'order'> {
91
- // 数据过滤
92
- filter?: Filter;
93
- // 输出结果显示哪些字段
94
- fields?: Fields;
95
- // 输出结果不显示哪些字段
96
- except?: Except;
97
- // 附加字段,用于控制关系字段的输出
98
- appends?: Appends;
99
- // 排序,字段前面加上 “-” 表示降序
100
- sort?: Sort;
101
- }
118
+ type FindAndCountOptions = Omit<SequelizeAndCountOptions, 'where' | 'include' | 'order'> & CommonFindOptions;
102
119
 
103
120
  export interface CreateOptions extends SequelizeCreateOptions {
104
121
  values?: Values | Values[];
@@ -275,7 +292,10 @@ export class Repository<TModelAttributes extends {} = any, TCreationAttributes e
275
292
  transaction,
276
293
  };
277
294
 
278
- return [await this.find(options), await this.count(options)];
295
+ const count = await this.count(options);
296
+ const results = count ? await this.find(options) : [];
297
+
298
+ return [results, count];
279
299
  }
280
300
 
281
301
  /**
@@ -318,6 +338,7 @@ export class Repository<TModelAttributes extends {} = any, TCreationAttributes e
318
338
  const guard = UpdateGuard.fromOptions(this.model, { ...options, action: 'create' });
319
339
  const values = guard.sanitize(options.values || {});
320
340
 
341
+
321
342
  const instance = await this.model.create<any>(values, {
322
343
  ...options,
323
344
  transaction,
@@ -358,6 +379,7 @@ export class Repository<TModelAttributes extends {} = any, TCreationAttributes e
358
379
  const transaction = await this.getTransaction(options);
359
380
  const { records } = options;
360
381
  const instances = [];
382
+
361
383
  for (const values of records) {
362
384
  const instance = await this.create({ values, transaction });
363
385
  instances.push(instance);
package/src/types.ts ADDED
@@ -0,0 +1,64 @@
1
+ import type { Model } from './model';
2
+ import type { ValidationOptions } from 'sequelize/types/lib/instance-validator';
3
+ import type { HookReturn } from 'sequelize/types/lib/hooks';
4
+ import type { CreateOptions, DestroyOptions, SaveOptions, SyncOptions, UpdateOptions } from 'sequelize/types';
5
+ import { Collection, CollectionOptions } from './collection';
6
+
7
+ export type CollectionNameType = string;
8
+
9
+ export type ModelSyncEventType = 'beforeSync' | 'afterSync';
10
+ export type ModelValidateEventType = 'beforeValidate' | 'afterValidate';
11
+ export type ModelCreateEventType = 'beforeCreate' | 'afterCreate';
12
+ export type ModelUpdateEventType = 'beforeUpdate' | 'afterUpdate';
13
+ export type ModelSaveEventType = 'beforeSave' | 'afterSave';
14
+ export type ModelDestroyEventType = 'beforeDestroy' | 'afterDestroy';
15
+ export type ModelCreateWithAssociationsEventType = 'afterCreateWithAssociations';
16
+ export type ModelUpdateWithAssociationsEventType = 'afterUpdateWithAssociations';
17
+ export type ModelSaveWithAssociationsEventType = 'afterSaveWithAssociations';
18
+
19
+ export type ModelValidateEventTypes = ModelValidateEventType | `${CollectionNameType}.${ModelValidateEventType}`;
20
+ export type ModelCreateEventTypes = ModelCreateEventType | `${CollectionNameType}.${ModelCreateEventType}`;
21
+ export type ModelUpdateEventTypes = ModelUpdateEventType | `${CollectionNameType}.${ModelUpdateEventType}`;
22
+ export type ModelSaveEventTypes = ModelSaveEventType | `${CollectionNameType}.${ModelSaveEventType}`;
23
+ export type ModelDestroyEventTypes = ModelDestroyEventType | `${CollectionNameType}.${ModelDestroyEventType}`;
24
+ export type ModelCreateWithAssociationsEventTypes = ModelCreateWithAssociationsEventType | `${CollectionNameType}.${ModelCreateWithAssociationsEventType}`;
25
+ export type ModelUpdateWithAssociationsEventTypes = ModelUpdateWithAssociationsEventType | `${CollectionNameType}.${ModelUpdateWithAssociationsEventType}`;
26
+ export type ModelSaveWithAssociationsEventTypes = ModelSaveWithAssociationsEventType | `${CollectionNameType}.${ModelSaveWithAssociationsEventType}`;
27
+
28
+ export type ModelEventTypes = ModelSyncEventType
29
+ | ModelValidateEventTypes
30
+ | ModelCreateEventTypes
31
+ | ModelUpdateEventTypes
32
+ | ModelSaveEventTypes
33
+ | ModelDestroyEventTypes
34
+ | ModelCreateWithAssociationsEventTypes
35
+ | ModelUpdateWithAssociationsEventTypes
36
+ | ModelSaveWithAssociationsEventTypes;
37
+
38
+ export type DatabaseBeforeDefineCollectionEventType = 'beforeDefineCollection';
39
+ export type DatabaseAfterDefineCollectionEventType = 'afterDefineCollection';
40
+ export type DatabaseBeforeRemoveCollectionEventType = 'beforeRemoveCollection';
41
+ export type DatabaseAfterRemoveCollectionEventType = 'afterRemoveCollection';
42
+
43
+ export type DatabaseEventTypes = DatabaseBeforeDefineCollectionEventType
44
+ | DatabaseAfterDefineCollectionEventType
45
+ | DatabaseBeforeRemoveCollectionEventType
46
+ | DatabaseAfterRemoveCollectionEventType;
47
+
48
+ export type EventType = ModelEventTypes | DatabaseEventTypes | string;
49
+
50
+ export type { HookReturn };
51
+
52
+ export type SyncListener = (options?: SyncOptions) => HookReturn;
53
+ export type ValidateListener = (model: Model, options?: ValidationOptions) => HookReturn;
54
+ export type CreateListener = (model: Model, options?: CreateOptions) => HookReturn;
55
+ export type UpdateListener = (model: Model, options?: UpdateOptions) => HookReturn;
56
+ export type SaveListener = (model: Model, options?: SaveOptions) => HookReturn;
57
+ export type DestroyListener = (model: Model, options?: DestroyOptions) => HookReturn;
58
+ export type CreateWithAssociationsListener = (model: Model, options?: CreateOptions) => HookReturn;
59
+ export type UpdateWithAssociationsListener = (model: Model, options?: UpdateOptions) => HookReturn;
60
+ export type SaveWithAssociationsListener = (model: Model, options?: SaveOptions) => HookReturn;
61
+
62
+ export type BeforeDefineCollectionListener = (options: CollectionOptions) => void;
63
+ export type AfterDefineCollectionListener = (collection: Collection) => void;
64
+ export type RemoveCollectionListener = (collection: Collection) => void;