diff --git a/apps/velo-external-db/test/drivers/index_api_rest_matchers.ts b/apps/velo-external-db/test/drivers/index_api_rest_matchers.ts index 4c04ce0be..d85de9f60 100644 --- a/apps/velo-external-db/test/drivers/index_api_rest_matchers.ts +++ b/apps/velo-external-db/test/drivers/index_api_rest_matchers.ts @@ -1,9 +1,10 @@ -import { IndexFieldOrder, IndexStatus, Index } from "libs/velo-external-db-core/src/spi-model/indexing"; +import { indexSpi } from '@wix-velo/velo-external-db-core' +const { IndexFieldOrder, IndexStatus } = indexSpi const responseWith = (matcher: any) => expect.objectContaining({ data: matcher }) -const indexWith = (index: Index, extraProps: Partial) => ({ +const indexWith = (index: indexSpi.Index, extraProps: Partial) => ({ ...index, fields: index.fields.map(field => ({ ...field, @@ -17,9 +18,9 @@ const indexWith = (index: Index, extraProps: Partial) => ({ export const listIndexResponseWithDefaultIndex = () => expect.arrayContaining([toHaveDefaultIndex()]) -export const listIndexResponseWith = (indexes: Index[]) => +export const listIndexResponseWith = (indexes: indexSpi.Index[]) => expect.arrayContaining( - [...indexes.map((index: Index) => indexWith(index, { status: IndexStatus.ACTIVE }))] + [...indexes.map((index: indexSpi.Index) => indexWith(index, { status: IndexStatus.ACTIVE }))] ) export const toHaveDefaultIndex = () => ({ @@ -36,10 +37,10 @@ export const toHaveDefaultIndex = () => ({ }) -export const createIndexResponseWith = (index: Index) => responseWith(({ index: indexWith(index, { status: IndexStatus.BUILDING }) })) +export const createIndexResponseWith = (index: indexSpi.Index) => responseWith(({ index: indexWith(index, { status: IndexStatus.BUILDING }) })) export const removeIndexResponse = () => responseWith(({})) -export const listIndexResponseWithFailedIndex = (index: Index) => { +export const listIndexResponseWithFailedIndex = (index: indexSpi.Index) => { return expect.arrayContaining([indexWith(index, { status: IndexStatus.FAILED })]) } diff --git a/apps/velo-external-db/test/drivers/index_api_rest_test_support.ts b/apps/velo-external-db/test/drivers/index_api_rest_test_support.ts index 691bdb471..6a7020884 100644 --- a/apps/velo-external-db/test/drivers/index_api_rest_test_support.ts +++ b/apps/velo-external-db/test/drivers/index_api_rest_test_support.ts @@ -1,25 +1,24 @@ -import { authOwner } from "@wix-velo/external-db-testkit" -import { streamToArray } from "@wix-velo/test-commons" -import waitUntil from "async-wait-until" -import { CreateIndexRequest, Index, ListIndexesRequest } from "libs/velo-external-db-core/src/spi-model/indexing" +import { streamToArray } from '@wix-velo/test-commons' +import waitUntil from 'async-wait-until' +import { indexSpi } from '@wix-velo/velo-external-db-core' const axios = require('axios').create({ baseURL: 'http://localhost:8080' }) -export const givenIndexes = async (collectionName: string, indexes: Index[], auth: any) => { +export const givenIndexes = async(collectionName: string, indexes: indexSpi.Index[], auth: any) => { for (const index of indexes) { - await axios.post('/indexes/create', { dataCollectionId: collectionName, index } as CreateIndexRequest, auth) + await axios.post('/indexes/create', { dataCollectionId: collectionName, index } as indexSpi.CreateIndexRequest, auth) } await Promise.all(indexes.map(index => indexCreated(collectionName, index.name, auth))) } -const indexCreated = async (collectionName: string, indexName: string, auth: any) => { - await waitUntil(async () => { - const indexes = await retrieveIndexesFor(collectionName) as Index[] +const indexCreated = async(collectionName: string, indexName: string, auth: any) => { + await waitUntil(async() => { + const indexes = await retrieveIndexesFor(collectionName, auth) as indexSpi.Index[] return indexes.some(index => index.name === indexName) }) } -export const retrieveIndexesFor = async (collectionName: string) => axios.post('/indexes/list', { dataCollectionId: collectionName }, {responseType: 'stream', ...authOwner}) - .then(response => streamToArray(response.data)) \ No newline at end of file +export const retrieveIndexesFor = async(collectionName: string, auth: any) => axios.post('/indexes/list', { dataCollectionId: collectionName }, { responseType: 'stream', ...auth }) + .then(response => streamToArray(response.data)) diff --git a/apps/velo-external-db/test/e2e/app_index.e2e.spec.ts b/apps/velo-external-db/test/e2e/app_index.e2e.spec.ts index 40684e6a9..2ead4c9ce 100644 --- a/apps/velo-external-db/test/e2e/app_index.e2e.spec.ts +++ b/apps/velo-external-db/test/e2e/app_index.e2e.spec.ts @@ -1,5 +1,5 @@ import Chance = require('chance') -import { Uninitialized } from '@wix-velo/test-commons'; +import { Uninitialized } from '@wix-velo/test-commons' import { authOwner } from '@wix-velo/external-db-testkit' import { initApp, teardownApp, dbTeardown, setupDb, currentDbImplementationName } from '../resources/e2e_resources' import * as schema from '../drivers/schema_api_rest_test_support' @@ -16,29 +16,29 @@ const axiosServer = axios.create({ describe(`Velo External DB Index API: ${currentDbImplementationName()}`, () => { - beforeAll(async () => { + beforeAll(async() => { await setupDb() await initApp() }) - afterAll(async () => { + afterAll(async() => { await dbTeardown() }, 20000) - test('list', async () => { + test('list', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) - expect(index.retrieveIndexesFor(ctx.collectionName)).resolves.toEqual(matchers.listIndexResponseWithDefaultIndex()) + await expect(index.retrieveIndexesFor(ctx.collectionName, authOwner)).resolves.toEqual(matchers.listIndexResponseWithDefaultIndex()) }) - test('list with multiple indexes', async () => { + test('list with multiple indexes', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) await index.givenIndexes(ctx.collectionName, [ctx.index], authOwner) - await expect(index.retrieveIndexesFor(ctx.collectionName)).resolves.toEqual(matchers.listIndexResponseWith([ctx.index])) + await expect(index.retrieveIndexesFor(ctx.collectionName, authOwner)).resolves.toEqual(matchers.listIndexResponseWith([ctx.index])) }) - test('create', async () => { + test('create', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) // in-progress @@ -48,12 +48,12 @@ describe(`Velo External DB Index API: ${currentDbImplementationName()}`, () => { }, authOwner)).resolves.toEqual(matchers.createIndexResponseWith(ctx.index)) // active - await eventually(async () => - await expect(index.retrieveIndexesFor(ctx.collectionName)).resolves.toEqual(matchers.listIndexResponseWith([ctx.index])) + await eventually(async() => + await expect(index.retrieveIndexesFor(ctx.collectionName, authOwner)).resolves.toEqual(matchers.listIndexResponseWith([ctx.index])) ) }) - test('create with existing index', async () => { + test('create with existing index', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) await index.givenIndexes(ctx.collectionName, [ctx.index], authOwner) @@ -63,7 +63,7 @@ describe(`Velo External DB Index API: ${currentDbImplementationName()}`, () => { }, authOwner)).rejects.toThrow() }) - test('remove', async () => { + test('remove', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) await index.givenIndexes(ctx.collectionName, [ctx.index], authOwner) @@ -72,25 +72,25 @@ describe(`Velo External DB Index API: ${currentDbImplementationName()}`, () => { indexName: ctx.index.name }, authOwner)).resolves.toEqual(matchers.removeIndexResponse()).catch() - await expect(index.retrieveIndexesFor(ctx.collectionName)).resolves.not.toEqual(matchers.listIndexResponseWith([ctx.index])) + await expect(index.retrieveIndexesFor(ctx.collectionName, authOwner)).resolves.not.toEqual(matchers.listIndexResponseWith([ctx.index])) }) - test('get failed indexes', async () => { + test('get failed indexes', async() => { await schema.givenCollection(ctx.collectionName, [ctx.column], authOwner) await axiosServer.post('/indexes/create', { dataCollectionId: ctx.collectionName, index: ctx.invalidIndex - }, authOwner).catch(e=>{}) + }, authOwner).catch(_e => {}) - await eventually(async () => - await expect(index.retrieveIndexesFor(ctx.collectionName)).resolves.toEqual(matchers.listIndexResponseWithFailedIndex(ctx.invalidIndex)) + await eventually(async() => + await expect(index.retrieveIndexesFor(ctx.collectionName, authOwner)).resolves.toEqual(matchers.listIndexResponseWithFailedIndex(ctx.invalidIndex)) ) }) - afterAll(async () => { + afterAll(async() => { await teardownApp() }) @@ -107,4 +107,4 @@ describe(`Velo External DB Index API: ${currentDbImplementationName()}`, () => { ctx.index = gen.spiIndexFor(ctx.collectionName, [ctx.column.name]) ctx.invalidIndex = gen.spiIndexFor(ctx.collectionName, ['wrongColumn']) }) -}); \ No newline at end of file +}) diff --git a/apps/velo-external-db/test/gen.ts b/apps/velo-external-db/test/gen.ts index e2c875646..2db06642c 100644 --- a/apps/velo-external-db/test/gen.ts +++ b/apps/velo-external-db/test/gen.ts @@ -1,7 +1,8 @@ import { SystemFields } from '@wix-velo/velo-external-db-commons' import { InputField } from '@wix-velo/velo-external-db-types' import * as Chance from 'chance' -import { Index as spiIndex, IndexFieldOrder } from 'libs/velo-external-db-core/src/spi-model/indexing' +import { indexSpi } from '@wix-velo/velo-external-db-core' +const { IndexFieldOrder } = indexSpi const chance = Chance() @@ -106,11 +107,11 @@ export const randomMatchesValueWithDashes = () => { return arr.join('-') } -export const spiIndexFor = (collectionName: string, columns: string[]): spiIndex => { +export const spiIndexFor = (_collectionName: string, columns: string[]): indexSpi.Index => { return { name: chance.word(), - fields: columns.map((column: string) => ({ path: column, order: chance.pickone([IndexFieldOrder.ASC, IndexFieldOrder.DESC])})), + fields: columns.map((column: string) => ({ path: column, order: chance.pickone([IndexFieldOrder.ASC, IndexFieldOrder.DESC]) })), unique: chance.bool(), caseInsensitive: chance.bool(), } -} \ No newline at end of file +} diff --git a/apps/velo-external-db/test/utils/eventually.ts b/apps/velo-external-db/test/utils/eventually.ts index e1613778f..2125a35f0 100644 --- a/apps/velo-external-db/test/utils/eventually.ts +++ b/apps/velo-external-db/test/utils/eventually.ts @@ -5,7 +5,7 @@ const defaults = { interval: 200 } -export const eventually = async (fn: any, opts?: { timeout?: number; interval?: number }) => { +export const eventually = async(fn: any, opts?: { timeout?: number; interval?: number }) => { return Promise.resolve().then(() => { let error = null const action = () => Promise.resolve().then(fn).catch(err => { diff --git a/libs/external-db-mysql/src/mysql_index_provider.ts b/libs/external-db-mysql/src/mysql_index_provider.ts index 60d602bf7..95f3fd755 100644 --- a/libs/external-db-mysql/src/mysql_index_provider.ts +++ b/libs/external-db-mysql/src/mysql_index_provider.ts @@ -59,22 +59,22 @@ export default class IndexProvider implements IIndexProvider { } private async getInProgressIndexesFor(collectionName: string): Promise<{ [x: string]: DomainIndex }> { - const databaseName = this.pool.config.connectionConfig.database; - const inProgressIndexes = await this.query(`SELECT * FROM information_schema.processlist WHERE db = ? AND info LIKE 'CREATE%INDEX%'`, [databaseName]) - const domainIndexesForCollection = inProgressIndexes.map((r: any) => this.extractIndexFromQueryForCollection(collectionName, r.INFO)).filter(Boolean) as DomainIndex[]; + const databaseName = this.pool.config.connectionConfig.database + const inProgressIndexes = await this.query('SELECT * FROM information_schema.processlist WHERE db = ? AND info LIKE \'CREATE%INDEX%\'', [databaseName]) + const domainIndexesForCollection = inProgressIndexes.map((r: any) => this.extractIndexFromQueryForCollection(collectionName, r.INFO)).filter(Boolean) as DomainIndex[] return domainIndexesForCollection.reduce((acc, index) => { - acc[index.name] = index; - return acc; - }, {} as { [x: string]: DomainIndex }); + acc[index.name] = index + return acc + }, {} as { [x: string]: DomainIndex }) } private extractIndexFromQueryForCollection(collectionName: string, createIndexQuery: string): DomainIndex | undefined { - const regex = /CREATE\s+(UNIQUE)?\s?INDEX\s+`(\w+)`\s+ON\s+`(\w+)`\s+\(([\w\s`,]+)\)/; - const match = createIndexQuery.match(regex); + const regex = /CREATE\s+(UNIQUE)?\s?INDEX\s+`(\w+)`\s+ON\s+`(\w+)`\s+\(([\w\s`,]+)\)/ + const match = createIndexQuery.match(regex) if (match) { - const [, isUnique, name, collection, columnsString] = match; + const [, isUnique, name, collection, columnsString] = match if (collection === collectionName) { - const columns = columnsString.replace(/`/g, '').split(',').map((column) => column.trim()); + const columns = columnsString.replace(/`/g, '').split(',').map((column) => column.trim()) return { name, columns, @@ -82,16 +82,16 @@ export default class IndexProvider implements IIndexProvider { caseInsensitive: true, order: 'ASC', status: DomainIndexStatus.BUILDING - }; + } } } - return; + return } private async returnStatusAfterXSeconds(x: number, promise: Promise, index: DomainIndex): Promise { return new Promise((resolve, reject) => { promise.catch((e: any) => { - console.log('failed to create index', e); + console.log('failed to create index', e) this.failedIndexes[index.name] = ({ ...index, status: DomainIndexStatus.FAILED, error: this.translateErrorCodes(e) }) reject(this.translateErrorCodes(e)) }) @@ -115,4 +115,4 @@ export default class IndexProvider implements IIndexProvider { return new errors.UnrecognizedError(`Error while creating index: ${e.sqlMessage}`) } } -} \ No newline at end of file +} diff --git a/libs/velo-external-db-commons/src/libs/errors.ts b/libs/velo-external-db-commons/src/libs/errors.ts index cc9b0cded..62ff68fea 100644 --- a/libs/velo-external-db-commons/src/libs/errors.ts +++ b/libs/velo-external-db-commons/src/libs/errors.ts @@ -99,4 +99,4 @@ export class IndexDoesNotExist extends BaseHttpError { constructor(message: string) { super(message, 404) } -} \ No newline at end of file +} diff --git a/libs/velo-external-db-core/src/index.ts b/libs/velo-external-db-core/src/index.ts index 1dc8eccce..106d4f626 100644 --- a/libs/velo-external-db-core/src/index.ts +++ b/libs/velo-external-db-core/src/index.ts @@ -71,5 +71,6 @@ export class ExternalDbRouter { } } -export * as dataSpi from './spi-model/data_source' +export * as dataSpi from './spi-model/data_source' +export * as indexSpi from './spi-model/indexing' export { DataService, SchemaService, OperationService, CacheableSchemaInformation, FilterTransformer, AggregationTransformer, QueryValidator, SchemaAwareDataService, ItemTransformer, Hooks, ServiceContext, CollectionCapability, decodeBase64 } diff --git a/libs/velo-external-db-core/src/router.ts b/libs/velo-external-db-core/src/router.ts index 9476a3de2..bc82d7555 100644 --- a/libs/velo-external-db-core/src/router.ts +++ b/libs/velo-external-db-core/src/router.ts @@ -26,10 +26,8 @@ import { JwtAuthenticator } from './web/jwt-auth-middleware' import * as dataSource from './spi-model/data_source' import * as capabilities from './spi-model/capabilities' import { WixDataFacade } from './web/wix_data_facade' -import { json } from 'stream/consumers'; -import DataService from './service/data'; -import IndexService from './service/indexing'; -import { CreateIndexRequest, ListIndexesRequest, RemoveIndexRequest } from './spi-model/indexing'; +import IndexService from './service/indexing' +import { CreateIndexRequest, ListIndexesRequest, RemoveIndexRequest } from './spi-model/indexing' const { InvalidRequest } = errors @@ -365,7 +363,7 @@ export const createRouter = () => { // *************** Indexes API ********************** - router.post('/indexes/list', async (req, res, next) => { + router.post('/indexes/list', async(req, res, next) => { try { const { dataCollectionId: collectionId } = req.body as ListIndexesRequest const indexes = await indexService.list(collectionId) @@ -375,7 +373,7 @@ export const createRouter = () => { } }) - router.post('/indexes/create', async (req, res, next) => { + router.post('/indexes/create', async(req, res, next) => { try { const { dataCollectionId: collectionId, index } = req.body as CreateIndexRequest const createdIndex = await indexService.create(collectionId, index) @@ -387,7 +385,7 @@ export const createRouter = () => { } }) - router.post('/indexes/remove', async (req, res, next) => { + router.post('/indexes/remove', async(req, res, next) => { try { const { dataCollectionId: collectionId, indexName } = req.body as RemoveIndexRequest await indexService.remove(collectionId, indexName) diff --git a/libs/velo-external-db-core/src/service/indexing.ts b/libs/velo-external-db-core/src/service/indexing.ts index 749adf384..1b3fb0c61 100644 --- a/libs/velo-external-db-core/src/service/indexing.ts +++ b/libs/velo-external-db-core/src/service/indexing.ts @@ -42,4 +42,4 @@ export default class IndexService { order: spiIndex.fields[0].order, } } -} \ No newline at end of file +} diff --git a/libs/velo-external-db-core/src/spi-model/indexing.ts b/libs/velo-external-db-core/src/spi-model/indexing.ts index 3a168ad3b..f118a0e03 100644 --- a/libs/velo-external-db-core/src/spi-model/indexing.ts +++ b/libs/velo-external-db-core/src/spi-model/indexing.ts @@ -92,4 +92,4 @@ export interface RemoveIndexRequest { indexName: string; } -export interface RemoveIndexResponse {} \ No newline at end of file +export interface RemoveIndexResponse {} diff --git a/libs/velo-external-db-core/test/drivers/index_provider_test_support.ts b/libs/velo-external-db-core/test/drivers/index_provider_test_support.ts index 0c0a82ad3..9cbaad021 100644 --- a/libs/velo-external-db-core/test/drivers/index_provider_test_support.ts +++ b/libs/velo-external-db-core/test/drivers/index_provider_test_support.ts @@ -12,7 +12,7 @@ export const givenListResult = (indexes: DomainIndex[], collectionName: string) } export const givenCreateResult = (index: DomainIndex, collectionName: string) => { - const {status, ...indexWithoutStatus} = index + const { status, ...indexWithoutStatus } = index when(indexProvider.create).calledWith(collectionName, indexWithoutStatus).mockResolvedValue(index) } diff --git a/libs/velo-external-db-types/src/index.ts b/libs/velo-external-db-types/src/index.ts index d82e7b2fb..832dace0b 100644 --- a/libs/velo-external-db-types/src/index.ts +++ b/libs/velo-external-db-types/src/index.ts @@ -270,4 +270,4 @@ export enum DomainIndexStatus { ACTIVE = 'ACTIVE', BUILDING = 'BUILDING', FAILED = 'FAILED' -} \ No newline at end of file +}