mirror of
https://github.com/strapi/strapi.git
synced 2025-12-29 08:04:51 +00:00
1st pass done
This commit is contained in:
parent
4761ec70c8
commit
22ea624841
@ -4,6 +4,10 @@ import type { ID } from '../typings';
|
||||
|
||||
type Params = Record<string, unknown>;
|
||||
type Data = Record<string, unknown>;
|
||||
type Entity = {
|
||||
id: ID;
|
||||
[key: string]: any;
|
||||
};
|
||||
|
||||
const withDefaultPagination = (params: Params) => {
|
||||
const { page = 1, pageSize = 10, ...rest } = params;
|
||||
@ -121,15 +125,15 @@ export const createRepository = (uid: string, db: Database) => {
|
||||
return db.entityManager.cloneRelations(uid, targetId, sourceId, params);
|
||||
},
|
||||
|
||||
populate(entity: Data, populate: unknown) {
|
||||
populate(entity: Entity, populate: unknown) {
|
||||
return db.entityManager.populate(uid, entity, populate);
|
||||
},
|
||||
|
||||
load(entity: Data, fields: string[], params: Params) {
|
||||
load(entity: Entity, fields: string[], params: Params) {
|
||||
return db.entityManager.load(uid, entity, fields, params);
|
||||
},
|
||||
|
||||
async loadPages(entity: Data, field: string[], params: Params) {
|
||||
async loadPages(entity: Entity, field: string[], params: Params) {
|
||||
if (!isString(field)) {
|
||||
throw new Error(`Invalid load. Expected ${field} to be a string`);
|
||||
}
|
||||
|
||||
@ -63,6 +63,11 @@ type Params = {
|
||||
orderBy?: any;
|
||||
_q?: string;
|
||||
data?: any;
|
||||
page?: number;
|
||||
pageSize?: number;
|
||||
limit?: number;
|
||||
offset?: number;
|
||||
count?: boolean;
|
||||
};
|
||||
|
||||
type Entity = {
|
||||
@ -574,9 +579,10 @@ export const createEntityManager = (db: Database) => {
|
||||
uid: string,
|
||||
id: ID,
|
||||
data: Record<string, any>,
|
||||
{ transaction: trx }: { transaction: Knex.Transaction }
|
||||
options?: { transaction?: Knex.Transaction }
|
||||
) {
|
||||
const { attributes } = db.metadata.get(uid);
|
||||
const { transaction: trx } = options ?? {};
|
||||
|
||||
for (const attributeName of Object.keys(attributes)) {
|
||||
const attribute = attributes[attributeName];
|
||||
@ -806,13 +812,10 @@ export const createEntityManager = (db: Database) => {
|
||||
uid: string,
|
||||
id: ID,
|
||||
data: any,
|
||||
{
|
||||
transaction: trx,
|
||||
}: {
|
||||
transaction: Knex.Transaction;
|
||||
}
|
||||
options?: { transaction?: Knex.Transaction }
|
||||
) {
|
||||
const { attributes } = db.metadata.get(uid);
|
||||
const { transaction: trx } = options ?? {};
|
||||
|
||||
for (const attributeName of Object.keys(attributes)) {
|
||||
const attribute = attributes[attributeName];
|
||||
@ -1233,13 +1236,12 @@ export const createEntityManager = (db: Database) => {
|
||||
async deleteRelations(
|
||||
uid: string,
|
||||
id: ID,
|
||||
{
|
||||
transaction: trx,
|
||||
}: {
|
||||
transaction: Knex.Transaction;
|
||||
options?: {
|
||||
transaction?: Knex.Transaction;
|
||||
}
|
||||
) {
|
||||
const { attributes } = db.metadata.get(uid);
|
||||
const { transaction: trx } = options ?? {};
|
||||
|
||||
for (const attributeName of Object.keys(attributes)) {
|
||||
const attribute = attributes[attributeName];
|
||||
@ -1367,15 +1369,13 @@ export const createEntityManager = (db: Database) => {
|
||||
targetId: ID,
|
||||
sourceId: ID,
|
||||
data: any,
|
||||
{
|
||||
cloneAttrs = [],
|
||||
transaction,
|
||||
}: {
|
||||
options?: {
|
||||
cloneAttrs?: string[];
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}
|
||||
) {
|
||||
const { attributes } = db.metadata.get(uid);
|
||||
const { cloneAttrs = [], transaction } = options ?? {};
|
||||
|
||||
if (!attributes) {
|
||||
return;
|
||||
|
||||
@ -48,7 +48,7 @@ export const deleteRelatedMorphOneRelationsAfterMorphToManyUpdate = async (
|
||||
attributeName: string;
|
||||
joinTable: MorphJoinTable;
|
||||
db: Database;
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}
|
||||
) => {
|
||||
const { morphColumn } = joinTable;
|
||||
|
||||
@ -1,3 +1,4 @@
|
||||
/* eslint-disable @typescript-eslint/no-namespace */
|
||||
import { randomBytes } from 'crypto';
|
||||
import { map, isEmpty } from 'lodash/fp';
|
||||
import type { Knex } from 'knex';
|
||||
@ -16,6 +17,14 @@ import type { Database } from '..';
|
||||
import type { ID } from '../typings';
|
||||
import type { Relation } from '../metadata/types';
|
||||
|
||||
declare module 'knex' {
|
||||
namespace Knex {
|
||||
interface ChainableInterface {
|
||||
transacting(trx?: Knex.Transaction): this;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* If some relations currently exist for this oneToX relation, on the one side, this function removes them and update the inverse order if needed.
|
||||
*/
|
||||
@ -30,7 +39,7 @@ const deletePreviousOneToAnyRelations = async ({
|
||||
attribute: Relation.Bidirectional;
|
||||
relIdsToadd: ID[];
|
||||
db: Database;
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
if (!(isBidirectional(attribute) && isOneToAny(attribute))) {
|
||||
throw new Error(
|
||||
@ -67,7 +76,7 @@ const deletePreviousAnyToOneRelations = async ({
|
||||
attribute: Relation.Bidirectional;
|
||||
relIdToadd: ID;
|
||||
db: Database;
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
const { joinTable } = attribute;
|
||||
const { joinColumn, inverseJoinColumn } = joinTable;
|
||||
@ -132,7 +141,7 @@ const deleteRelations = async ({
|
||||
db: Database;
|
||||
relIdsToNotDelete?: ID[];
|
||||
relIdsToDelete?: ID[] | 'all';
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
const { joinTable } = attribute;
|
||||
const { joinColumn, inverseJoinColumn } = joinTable;
|
||||
@ -203,7 +212,7 @@ const cleanOrderColumns = async ({
|
||||
attribute: Relation.Bidirectional;
|
||||
db: Database;
|
||||
inverseRelIds?: ID[];
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
if (
|
||||
!(hasOrderColumn(attribute) && id) &&
|
||||
@ -356,7 +365,7 @@ const cleanOrderColumnsForOldDatabases = async ({
|
||||
attribute: Relation.Bidirectional;
|
||||
db: Database;
|
||||
inverseRelIds: ID[];
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
const { joinTable } = attribute;
|
||||
const { joinColumn, inverseJoinColumn, orderColumnName, inverseOrderColumnName } = joinTable;
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
import type { Knex } from 'knex';
|
||||
import { Knex } from 'knex';
|
||||
|
||||
import { cleanInverseOrderColumn } from '../../regular-relations';
|
||||
import type { Relation } from '../../../metadata/types';
|
||||
@ -15,7 +15,7 @@ const replaceRegularRelations = async ({
|
||||
sourceId: ID;
|
||||
attribute: Relation.Bidirectional;
|
||||
omitIds: ID[];
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
const { joinTable } = attribute;
|
||||
|
||||
@ -42,7 +42,7 @@ const cloneRegularRelations = async ({
|
||||
targetId: ID;
|
||||
sourceId: ID;
|
||||
attribute: Relation.Bidirectional;
|
||||
transaction: Knex.Transaction;
|
||||
transaction?: Knex.Transaction;
|
||||
}) => {
|
||||
const { joinTable } = attribute;
|
||||
const { joinColumn, inverseJoinColumn, orderColumnName, inverseOrderColumnName } = joinTable;
|
||||
@ -92,7 +92,7 @@ const cloneRegularRelations = async ({
|
||||
await cleanInverseOrderColumn({
|
||||
id: targetId,
|
||||
attribute,
|
||||
trx,
|
||||
trx: trx as Knex.Transaction,
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
@ -116,6 +116,8 @@ export namespace Relation {
|
||||
export type OneToMany = BaseBidirectional & {
|
||||
relation: 'oneToMany';
|
||||
joinTable: OrderedJoinTable;
|
||||
joinColumn?: JoinColumn;
|
||||
owner?: boolean;
|
||||
};
|
||||
|
||||
export type ManyToOne = BaseBidirectional & {
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
import _ from 'lodash/fp';
|
||||
|
||||
import { fromRow } from '../transform';
|
||||
import { Rec, fromRow } from '../transform';
|
||||
import type { QueryBuilder } from '../../query-builder';
|
||||
import type { Database } from '../../..';
|
||||
import type { Meta, RelationalAttribute, Relation } from '../../../metadata/types';
|
||||
@ -15,8 +15,11 @@ type Context = {
|
||||
type Input<T extends RelationalAttribute = RelationalAttribute> = {
|
||||
attribute: T;
|
||||
attributeName: string;
|
||||
results: Record<string, unknown>[];
|
||||
populateValue: Record<string, unknown>;
|
||||
results: Row[];
|
||||
populateValue: {
|
||||
on?: Record<string, Record<string, unknown>>;
|
||||
} & Record<string, unknown>;
|
||||
|
||||
isCount: boolean;
|
||||
};
|
||||
|
||||
@ -24,7 +27,7 @@ type InputWithTarget<T extends RelationalAttribute = RelationalAttribute> = Inpu
|
||||
targetMeta: Meta;
|
||||
};
|
||||
|
||||
type MorphIdMap = Record<string, Record<ID, Record<string, unknown>[]>>;
|
||||
type MorphIdMap = Record<string, Record<ID, Row[]>>;
|
||||
|
||||
type Row = Record<string, unknown>;
|
||||
|
||||
@ -41,7 +44,12 @@ const XtoOne = async (
|
||||
const { attribute, attributeName, results, populateValue, targetMeta, isCount } = input;
|
||||
const { db, qb } = ctx;
|
||||
|
||||
const fromTargetRow = (rowOrRows: Row | Row[]) => fromRow(targetMeta, rowOrRows);
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
return fromRow(targetMeta, rowOrRows);
|
||||
};
|
||||
|
||||
if ('joinColumn' in attribute && attribute.joinColumn) {
|
||||
const { name: joinColumnName, referencedColumn: referencedColumnName } = attribute.joinColumn;
|
||||
@ -63,12 +71,12 @@ const XtoOne = async (
|
||||
.init(populateValue)
|
||||
.addSelect(`${qb.alias}.${referencedColumnName}`)
|
||||
.where({ [referencedColumnName]: referencedValues })
|
||||
.execute<Record<string, unknown>[]>({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy<ID>(referencedColumnName)(rows);
|
||||
const map = _.groupBy<Row[]>(referencedColumnName)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
result[attributeName] = fromTargetRow(_.first(map[result[joinColumnName]]));
|
||||
result[attributeName] = fromTargetRow(_.first(map[result[joinColumnName] as string]));
|
||||
});
|
||||
|
||||
return;
|
||||
@ -144,12 +152,12 @@ const XtoOne = async (
|
||||
})
|
||||
.addSelect(joinColAlias)
|
||||
.where({ [joinColAlias]: referencedValues })
|
||||
.execute({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(joinColumnName, rows);
|
||||
const map = _.groupBy<Row>(joinColumnName)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
result[attributeName] = fromTargetRow(_.first(map[result[referencedColumnName]]));
|
||||
result[attributeName] = fromTargetRow(_.first(map[result[referencedColumnName] as string]));
|
||||
});
|
||||
}
|
||||
};
|
||||
@ -158,7 +166,13 @@ const oneToMany = async (input: InputWithTarget<Relation.OneToMany>, ctx: Contex
|
||||
const { attribute, attributeName, results, populateValue, targetMeta, isCount } = input;
|
||||
const { db, qb } = ctx;
|
||||
|
||||
const fromTargetRow = (rowOrRows) => fromRow(targetMeta, rowOrRows);
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
|
||||
return fromRow(targetMeta, rowOrRows);
|
||||
};
|
||||
|
||||
if ('joinColumn' in attribute && attribute.joinColumn) {
|
||||
const { name: joinColumnName, referencedColumn: referencedColumnName } = attribute.joinColumn;
|
||||
@ -179,12 +193,12 @@ const oneToMany = async (input: InputWithTarget<Relation.OneToMany>, ctx: Contex
|
||||
.init(populateValue)
|
||||
.addSelect(`${qb.alias}.${referencedColumnName}`)
|
||||
.where({ [referencedColumnName]: referencedValues })
|
||||
.execute({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(referencedColumnName, rows);
|
||||
const map = _.groupBy<Row>(referencedColumnName)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
result[attributeName] = fromTargetRow(map[result[joinColumnName]] || []);
|
||||
result[attributeName] = fromTargetRow(map[result[joinColumnName] as string] || []);
|
||||
});
|
||||
|
||||
return;
|
||||
@ -259,12 +273,12 @@ const oneToMany = async (input: InputWithTarget<Relation.OneToMany>, ctx: Contex
|
||||
})
|
||||
.addSelect(joinColAlias)
|
||||
.where({ [joinColAlias]: referencedValues })
|
||||
.execute({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(joinColumnName, rows);
|
||||
const map = _.groupBy<Row>(joinColumnName)(rows);
|
||||
|
||||
results.forEach((r) => {
|
||||
r[attributeName] = fromTargetRow(map[r[referencedColumnName]] || []);
|
||||
r[attributeName] = fromTargetRow(map[r[referencedColumnName] as string] || []);
|
||||
});
|
||||
}
|
||||
};
|
||||
@ -273,7 +287,13 @@ const manyToMany = async (input: InputWithTarget<Relation.ManyToMany>, ctx: Cont
|
||||
const { attribute, attributeName, results, populateValue, targetMeta, isCount } = input;
|
||||
const { db } = ctx;
|
||||
|
||||
const fromTargetRow = (rowOrRows) => fromRow(targetMeta, rowOrRows);
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
|
||||
return fromRow(targetMeta, rowOrRows);
|
||||
};
|
||||
|
||||
const { joinTable } = attribute;
|
||||
|
||||
@ -342,9 +362,9 @@ const manyToMany = async (input: InputWithTarget<Relation.ManyToMany>, ctx: Cont
|
||||
})
|
||||
.addSelect(joinColAlias)
|
||||
.where({ [joinColAlias]: referencedValues })
|
||||
.execute<Record<string, unknown>[]>({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(joinColumnName)(rows);
|
||||
const map = _.groupBy<Row>(joinColumnName)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
result[attributeName] = fromTargetRow(map[result[referencedColumnName] as string] || []);
|
||||
@ -358,8 +378,13 @@ const morphX = async (
|
||||
const { attribute, attributeName, results, populateValue, targetMeta } = input;
|
||||
const { db, uid } = ctx;
|
||||
|
||||
const fromTargetRow = (rowOrRows: Record<string, unknown> | Record<string, unknown>[]) =>
|
||||
fromRow(targetMeta, rowOrRows);
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
|
||||
return fromRow(targetMeta, rowOrRows);
|
||||
};
|
||||
|
||||
const { target, morphBy } = attribute;
|
||||
|
||||
@ -385,12 +410,12 @@ const morphX = async (
|
||||
.init(populateValue)
|
||||
// .addSelect(`${qb.alias}.${idColumn.referencedColumn}`)
|
||||
.where({ [idColumn.name]: referencedValues, [typeColumn.name]: uid })
|
||||
.execute({ mapResults: false });
|
||||
.execute<Row>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(idColumn.name, rows);
|
||||
const map = _.groupBy<Row>(idColumn.name)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
const matchingRows = map[result[idColumn.referencedColumn]];
|
||||
const matchingRows = map[result[idColumn.referencedColumn] as string];
|
||||
|
||||
const matchingValue =
|
||||
attribute.relation === 'morphOne' ? _.first(matchingRows) : matchingRows;
|
||||
@ -440,12 +465,12 @@ const morphX = async (
|
||||
[`${alias}.${idColumn.name}`]: referencedValues,
|
||||
[`${alias}.${typeColumn.name}`]: uid,
|
||||
})
|
||||
.execute({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const map = _.groupBy(idColumn.name, rows);
|
||||
const map = _.groupBy<Row>(idColumn.name)(rows);
|
||||
|
||||
results.forEach((result) => {
|
||||
const matchingRows = map[result[idColumn.referencedColumn]];
|
||||
const matchingRows = map[result[idColumn.referencedColumn] as string];
|
||||
|
||||
const matchingValue =
|
||||
attribute.relation === 'morphOne' ? _.first(matchingRows) : matchingRows;
|
||||
@ -480,11 +505,11 @@ const morphToMany = async (input: Input<Relation.MorphToMany>, ctx: Context) =>
|
||||
// If the populateValue contains an "on" property,
|
||||
// only populate the types defined in it
|
||||
...('on' in populateValue
|
||||
? { [morphColumn.typeColumn.name]: Object.keys(populateValue.on) }
|
||||
? { [morphColumn.typeColumn.name]: Object.keys(populateValue.on ?? {}) }
|
||||
: {}),
|
||||
})
|
||||
.orderBy([joinColumn.name, 'order'])
|
||||
.execute<Array<Record<string, unknown>>>({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
const joinMap = _.groupBy(joinColumn.name, joinRows);
|
||||
|
||||
@ -524,19 +549,24 @@ const morphToMany = async (input: Input<Relation.MorphToMany>, ctx: Context) =>
|
||||
.init(on?.[type] ?? typePopulate)
|
||||
.addSelect(`${qb.alias}.${idColumn.referencedColumn}`)
|
||||
.where({ [idColumn.referencedColumn]: ids })
|
||||
.execute<Record<string, unknown>[]>({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
map[type] = _.groupBy<Record<string, unknown>>(idColumn.referencedColumn)(rows);
|
||||
map[type] = _.groupBy<Row>(idColumn.referencedColumn)(rows);
|
||||
}
|
||||
|
||||
results.forEach((result) => {
|
||||
const joinResults = joinMap[result[joinColumn.referencedColumn] as string] || [];
|
||||
|
||||
const matchingRows = joinResults.flatMap((joinResult) => {
|
||||
const id = joinResult[idColumn.name];
|
||||
const type = joinResult[typeColumn.name];
|
||||
const id = joinResult[idColumn.name] as ID;
|
||||
const type = joinResult[typeColumn.name] as string;
|
||||
|
||||
const fromTargetRow = (rowOrRows) => fromRow(db.metadata.get(type), rowOrRows);
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
return fromRow(db.metadata.get(type), rowOrRows);
|
||||
};
|
||||
|
||||
return (map[type][id] || []).map((row) => {
|
||||
return {
|
||||
@ -595,9 +625,9 @@ const morphToOne = async (input: Input<Relation.MorphToOne>, ctx: Context) => {
|
||||
.init(on?.[type] ?? typePopulate)
|
||||
.addSelect(`${qb.alias}.${idColumn.referencedColumn}`)
|
||||
.where({ [idColumn.referencedColumn]: ids })
|
||||
.execute<Record<string, unknown>[]>({ mapResults: false });
|
||||
.execute<Row[]>({ mapResults: false });
|
||||
|
||||
map[type] = _.groupBy<Record<string, unknown>>(idColumn.referencedColumn)(rows);
|
||||
map[type] = _.groupBy<Row>(idColumn.referencedColumn)(rows);
|
||||
}
|
||||
|
||||
results.forEach((result) => {
|
||||
@ -611,9 +641,7 @@ const morphToOne = async (input: Input<Relation.MorphToOne>, ctx: Context) => {
|
||||
|
||||
const matchingRows = map[type][id];
|
||||
|
||||
const fromTargetRow = (
|
||||
rowOrRows: Record<string, unknown> | Record<string, unknown>[] | undefined
|
||||
) => {
|
||||
const fromTargetRow = (rowOrRows: Row | Row[] | undefined) => {
|
||||
if (!rowOrRows) {
|
||||
return rowOrRows;
|
||||
}
|
||||
@ -645,11 +673,7 @@ const pickPopulateParams = (populate: Record<string, unknown>) => {
|
||||
return _.pick(fieldsToPick, populate);
|
||||
};
|
||||
|
||||
const applyPopulate = async (
|
||||
results: Record<string, unknown>[],
|
||||
populate: Record<string, any>,
|
||||
ctx: Context
|
||||
) => {
|
||||
const applyPopulate = async (results: Row[], populate: Record<string, any>, ctx: Context) => {
|
||||
const { db, uid, qb } = ctx;
|
||||
const meta = db.metadata.get(uid);
|
||||
|
||||
|
||||
@ -77,11 +77,11 @@ export interface QueryBuilder {
|
||||
shouldUseDistinct(): boolean;
|
||||
processSelect(): void;
|
||||
getKnexQuery(): Knex.QueryBuilder;
|
||||
execute<T>({ mapResults }?: { mapResults?: boolean }): Promise<T>;
|
||||
stream({ mapResults }?: { mapResults?: boolean }): helpers.ReadableQuery;
|
||||
execute<T>(options?: { mapResults?: boolean }): Promise<T>;
|
||||
stream(options?: { mapResults?: boolean }): helpers.ReadableQuery;
|
||||
}
|
||||
|
||||
const createQueryBuilder = <TResult>(
|
||||
const createQueryBuilder = (
|
||||
uid: string,
|
||||
db: Database,
|
||||
initialState: Partial<State> = {}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user