From 683dae27182d5ae7a8d1f4e9f75c64711e107d1d Mon Sep 17 00:00:00 2001 From: aramissennyeydd Date: Tue, 19 Mar 2024 10:21:09 +0100 Subject: [PATCH] starting watch command Signed-off-by: aramissennyeydd --- .../src/generated/.openapi-generator-ignore | 24 ++++++++++++ .../src/generated/apis/DefaultApi.client.ts | 9 +++-- packages/repo-tools/package.json | 1 + packages/repo-tools/src/commands/index.ts | 2 + .../package/schema/openapi/generate/client.ts | 14 +++++-- .../package/schema/openapi/generate/index.ts | 39 ++++++++++++++++--- .../package/schema/openapi/generate/server.ts | 17 +++++--- yarn.lock | 1 + 8 files changed, 91 insertions(+), 16 deletions(-) create mode 100644 packages/catalog-client/src/generated/.openapi-generator-ignore diff --git a/packages/catalog-client/src/generated/.openapi-generator-ignore b/packages/catalog-client/src/generated/.openapi-generator-ignore new file mode 100644 index 0000000000..bd8a6eec07 --- /dev/null +++ b/packages/catalog-client/src/generated/.openapi-generator-ignore @@ -0,0 +1,24 @@ +*.md +*.mustache +apis/baseapi.ts +apis/exception.ts +auth/* +http/* +middleware.ts +servers.ts +util.ts +configuration.ts +rxjsStub.ts +.gitignore +apis/*.ts +!apis/*.client.ts +models/*.ts +!models/*.model.ts +!index.ts +!**/index.ts +types/ObjectParamAPI.ts +types/ObservableAPI.ts +types/PromiseAPI.ts +git_push.sh +package.json +tsconfig.json \ No newline at end of file diff --git a/packages/catalog-client/src/generated/apis/DefaultApi.client.ts b/packages/catalog-client/src/generated/apis/DefaultApi.client.ts index 1f1c54d6f8..598d9c706f 100644 --- a/packages/catalog-client/src/generated/apis/DefaultApi.client.ts +++ b/packages/catalog-client/src/generated/apis/DefaultApi.client.ts @@ -276,13 +276,14 @@ export class DefaultApiClient { /** * Get a batch set of entities given an array of entityRefs. + * @param filter Filter for just the entities defined by this filter. * @param getEntitiesByRefsRequest */ public async getEntitiesByRefs( // @ts-ignore request: { body: GetEntitiesByRefsRequest; - query?: { + query: { filter?: Array; }; }, @@ -290,9 +291,11 @@ export class DefaultApiClient { ): Promise> { const baseUrl = await this.discoveryApi.getBaseUrl(pluginId); - const uriTemplate = `/entities/by-refs/{?filter*}`; + const uriTemplate = `/entities/by-refs{?filter*}`; - const uri = parser.parse(uriTemplate).expand({ ...request.query }); + const uri = parser.parse(uriTemplate).expand({ + ...request.query, + }); return await this.fetchApi.fetch(`${baseUrl}${uri}`, { headers: { diff --git a/packages/repo-tools/package.json b/packages/repo-tools/package.json index f4b5133b30..a8fef81b63 100644 --- a/packages/repo-tools/package.json +++ b/packages/repo-tools/package.json @@ -62,6 +62,7 @@ "@stoplight/types": "^14.0.0", "@useoptic/openapi-utilities": "^0.55.0", "chalk": "^4.0.0", + "chokidar": "^3.6.0", "codeowners-utils": "^1.0.2", "command-exists": "^1.2.9", "commander": "^12.0.0", diff --git a/packages/repo-tools/src/commands/index.ts b/packages/repo-tools/src/commands/index.ts index 5a69a74ff3..abe55356ef 100644 --- a/packages/repo-tools/src/commands/index.ts +++ b/packages/repo-tools/src/commands/index.ts @@ -58,6 +58,8 @@ function registerPackageCommand(program: Command) { .description( 'Additional properties that can be passed to @openapitools/openapi-generator-cli', ) + .option('--watch') + .description('Watch the OpenAPI spec for changes and regenerate on save.') .action( lazy(() => import('./package/schema/openapi/generate').then(m => m.command), diff --git a/packages/repo-tools/src/commands/package/schema/openapi/generate/client.ts b/packages/repo-tools/src/commands/package/schema/openapi/generate/client.ts index b843cd27ec..61be02979e 100644 --- a/packages/repo-tools/src/commands/package/schema/openapi/generate/client.ts +++ b/packages/repo-tools/src/commands/package/schema/openapi/generate/client.ts @@ -30,6 +30,7 @@ import { getPathToCurrentOpenApiSpec } from '../../../../../lib/openapi/helpers' async function generate( outputDirectory: string, clientAdditionalProperties?: string, + abortSignal?: AbortController, ) { const resolvedOpenapiPath = await getPathToCurrentOpenApiSpec(); const resolvedOutputDirectory = cliPaths.resolveTargetRoot( @@ -69,6 +70,7 @@ async function generate( additionalProperties, ], { + signal: abortSignal?.signal, maxBuffer: Number.MAX_VALUE, cwd: resolvePackagePath('@backstage/repo-tools'), env: { @@ -83,7 +85,9 @@ async function generate( const prettier = cliPaths.resolveTargetRoot('node_modules/.bin/prettier'); if (prettier) { - await exec(`${prettier} --write ${resolvedOutputDirectory}`); + await exec(`${prettier} --write ${resolvedOutputDirectory}`, [], { + signal: abortSignal?.signal, + }); } fs.removeSync(resolve(resolvedOutputDirectory, '.openapi-generator-ignore')); @@ -97,14 +101,18 @@ async function generate( export async function command( outputPackage: string, clientAdditionalProperties?: string, + abortSignal?: AbortController, ): Promise { try { - await generate(outputPackage, clientAdditionalProperties); + await generate(outputPackage, clientAdditionalProperties, abortSignal); console.log( chalk.green(`Generated client in ${outputPackage}/${OUTPUT_PATH}`), ); } catch (err) { - console.log(); + if (err.name === 'AbortError') { + console.debug('Server generation aborted.'); + return; + } console.log(chalk.red(`Client generation failed:`)); console.log(err); diff --git a/packages/repo-tools/src/commands/package/schema/openapi/generate/index.ts b/packages/repo-tools/src/commands/package/schema/openapi/generate/index.ts index 41884e2e90..9227b67ba8 100644 --- a/packages/repo-tools/src/commands/package/schema/openapi/generate/index.ts +++ b/packages/repo-tools/src/commands/package/schema/openapi/generate/index.ts @@ -17,6 +17,8 @@ import chalk from 'chalk'; import { OptionValues } from 'commander'; import { command as generateClient } from './client'; import { command as generateServer } from './server'; +import chokidar from 'chokidar'; +import { getPathToCurrentOpenApiSpec } from '../../../../../lib/openapi/helpers'; export async function command(opts: OptionValues) { if (!opts.clientPackage && !opts.server) { @@ -25,10 +27,37 @@ export async function command(opts: OptionValues) { ); process.exit(1); } - if (opts.clientPackage) { - await generateClient(opts.clientPackage, opts.clientAdditionalProperties); - } - if (opts.server) { - await generateServer(); + + const sharedCommand = async (abortSignal?: AbortController) => { + if (opts.clientPackage) { + await generateClient( + opts.clientPackage, + opts.clientAdditionalProperties, + abortSignal, + ); + } + if (opts.server) { + await generateServer(abortSignal); + } + }; + + if (opts.watch) { + try { + const resolvedOpenapiPath = await getPathToCurrentOpenApiSpec(); + let abortController = new AbortController(); + chokidar.watch(resolvedOpenapiPath).on('change', async () => { + console.log('detected changes'); + abortController.abort(); + await sharedCommand(abortController); + abortController = new AbortController(); + }); + await sharedCommand(); + await new Promise(() => {}); + } catch (err) { + console.error(chalk.red('Error: ', err)); + process.exit(1); + } + } else { + await sharedCommand(); } } diff --git a/packages/repo-tools/src/commands/package/schema/openapi/generate/server.ts b/packages/repo-tools/src/commands/package/schema/openapi/generate/server.ts index e6c56c3122..317c17f96d 100644 --- a/packages/repo-tools/src/commands/package/schema/openapi/generate/server.ts +++ b/packages/repo-tools/src/commands/package/schema/openapi/generate/server.ts @@ -25,7 +25,7 @@ import { getPathToCurrentOpenApiSpec } from '../../../../../lib/openapi/helpers' const exec = promisify(execCb); -async function generate() { +async function generate(abortSignal?: AbortController) { const openapiPath = await getPathToCurrentOpenApiSpec(); const yaml = YAML.load(await fs.readFile(openapiPath, 'utf8')); @@ -50,19 +50,26 @@ export const createOpenApiRouter = async ( `, ); - await exec(`yarn backstage-cli package lint --fix ${tsPath}`); + await exec(`yarn backstage-cli package lint --fix ${tsPath}`, { + signal: abortSignal?.signal, + }); if (await cliPaths.resolveTargetRoot('node_modules/.bin/prettier')) { await exec(`yarn prettier --write ${tsPath}`, { cwd: cliPaths.targetRoot, + signal: abortSignal?.signal, }); } } -export async function command(): Promise { +export async function command(abortSignal?: AbortController): Promise { try { - await generate(); - console.log(chalk.green('Generated all files.')); + await generate(abortSignal); + console.log(chalk.green('Generated server files.')); } catch (err) { + if (err.name === 'AbortError') { + console.debug('Server generation aborted.'); + return; + } console.log(chalk.red(`OpenAPI server stub generation failed.`)); console.log(err.message); process.exit(1); diff --git a/yarn.lock b/yarn.lock index d8070957c2..eba469581e 100644 --- a/yarn.lock +++ b/yarn.lock @@ -8309,6 +8309,7 @@ __metadata: "@types/prettier": ^2.0.0 "@useoptic/openapi-utilities": ^0.55.0 chalk: ^4.0.0 + chokidar: ^3.6.0 codeowners-utils: ^1.0.2 command-exists: ^1.2.9 commander: ^12.0.0