Skip to content

Commit

Permalink
Merge pull request #262 from HPInc/feat/improve-edge-compatibility
Browse files Browse the repository at this point in the history
feat: improve edge compatibility
  • Loading branch information
pierissimo authored Sep 5, 2023
2 parents 22d8b7a + 4608473 commit 57cadb5
Show file tree
Hide file tree
Showing 6 changed files with 62 additions and 16 deletions.
9 changes: 7 additions & 2 deletions packages/http-server/src/HttpServerModule.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import {
Module,
omit
} from '@davinci/core';
import pathUtils from 'path';
import pino from 'pino';
import { ClassReflection, ClassType, DecoratorId, MethodReflection } from '@davinci/reflector';
import type { InjectOptions } from 'light-my-request';
Expand Down Expand Up @@ -130,7 +129,7 @@ export abstract class HttpServerModule<
options: { path }
} = methodDecoratorMetadata;

let fullPath = pathUtils.join(basePath, path);
let fullPath = this.joinPaths(basePath, path);
if (fullPath.length > 1 && fullPath[fullPath.length - 1] === '/') {
fullPath = fullPath.slice(0, -1);
}
Expand Down Expand Up @@ -565,6 +564,12 @@ export abstract class HttpServerModule<
}
}

private joinPaths(...args: Array<string>) {
const path = args.join('/').replace(/\/+/g, '/'); // replace multiple slashes with one

return path === '/' ? '/' : path.replace(/\/$/, ''); // remove trailing slash only if it's not '/'
}

/* abstract render(response, view: string, options: unknown);
abstract useStaticAssets(...args: unknown[]);
abstract setViewEngine(engine: string);
Expand Down
3 changes: 2 additions & 1 deletion packages/openapi/.mocharc.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,5 +14,6 @@ module.exports = {
bail: true,
checkLeaks: true,
require: ['ts-node/register', 'source-map-support/register'],
spec: 'test/**/*.{js,ts}'
spec: 'test/**/*.{js,ts}',
globals: ['EdgeRuntime']
};
40 changes: 30 additions & 10 deletions packages/openapi/src/OpenAPIModule.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,6 @@ import pino, { Level } from 'pino';
import { OpenAPIV3 } from 'openapi-types';
import createDeepMerge from '@fastify/deepmerge';
import { ClassType, PartialDeep, TypeValue } from '@davinci/reflector';
import { promises as fs } from 'fs';
import { join as joinPaths } from 'path';
import * as process from 'process';
import { generateSwaggerUiHtml } from './swaggerUi';

const deepMerge = createDeepMerge();
Expand Down Expand Up @@ -133,19 +130,40 @@ export class OpenAPIModule extends Module {

const relativeOutputPath = this.moduleOptions.document?.output?.path;
if (relativeOutputPath) {
await this.writeOpenAPIDocument(relativeOutputPath);
}
}

public getOpenAPIDocument(): PartialDeep<OpenAPIV3.Document> {
return this.openAPIDoc;
}

public async writeOpenAPIDocument(relativeOutputPath: string) {
/**
This block will be dead-code-eliminated on Edge
@see https://vercel.com/docs/functions/edge-functions/edge-runtime#check-if-you're-running-on-the-edge-runtime
*/
// @ts-expect-error
if (typeof EdgeRuntime === 'string') {
throw new Error('Write operation not available in Edge Runtime');
} else {
const stringifyOptions = this.moduleOptions.document?.output.stringifyOptions;
const stringifiedDocument = JSON.stringify(
this.openAPIDoc,
stringifyOptions?.replacer,
stringifyOptions?.space
);
const outputPath = joinPaths(process.cwd(), relativeOutputPath);

const fs = await import('fs').then(m => m.promises);
const process = await import('process');

const outputPath = this.joinPaths(process.cwd(), relativeOutputPath);
await fs.writeFile(outputPath, stringifiedDocument);
this.logger.debug(`The OpenAPI document has been written to the local file system at path: ${outputPath}`);
}
}

async createPathAndSchema(route: Route<unknown>): Promise<void> {
private async createPathAndSchema(route: Route<unknown>): Promise<void> {
const {
path: origPath,
verb,
Expand Down Expand Up @@ -359,7 +377,7 @@ export class OpenAPIModule extends Module {
});
}

async registerOpenapiRoutes() {
private async registerOpenapiRoutes() {
const documentEnabled = this.moduleOptions.document?.enabled;
const explorerEnabled = this.moduleOptions.explorer?.enabled;

Expand All @@ -384,10 +402,6 @@ export class OpenAPIModule extends Module {
}
}

getOpenAPIDocument(): PartialDeep<OpenAPIV3.Document> {
return this.openAPIDoc;
}

private createJsonSchema(entityJsonSchema: EntityDefinitionJSONSchema): Partial<JSONSchema> {
return transformEntityDefinitionSchema(entityJsonSchema, args => {
if (args.pointerPath === '') {
Expand Down Expand Up @@ -458,4 +472,10 @@ export class OpenAPIModule extends Module {

return jsonSchema;
}

private joinPaths(...args: Array<string>) {
const path = args.join('/').replace(/\/+/g, '/'); // replace multiple slashes with one

return path === '/' ? '/' : path.replace(/\/$/, ''); // remove trailing slash only if it's not '/'
}
}
23 changes: 22 additions & 1 deletion packages/openapi/test/unit/OpenAPIModule.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ describe('OpenAPIModule', () => {
}
}
const openApiModule = new OpenAPIModule(openapiModuleOpts);
const app = new App({ logger: { level: 'error' } });
const app = new App({ logger: { level: 'silent' } });
await app.registerController(CustomerController).registerModule(new FastifyHttpServer(), openApiModule);

await app.init();
Expand Down Expand Up @@ -1149,5 +1149,26 @@ describe('OpenAPIModule', () => {
expect(writeFileStub.args[0][0]).to.match(/path\/to\/local\/file\.json$/);
expect(writeFileStub.args[0][1]).to.contain('"openapi": "3.0.0"');
});

it('should throw an error when trying to output in a Edge environment', async () => {
const origValue = globalThis.EdgeRuntime;
globalThis.EdgeRuntime = 'edge';

await expect(
initApp({
document: {
output: { path: 'path/to/local/file.json', stringifyOptions: { space: 2 } },
spec: { info: { title: '', version: '' } }
}
})
).to.rejectedWith('Write operation not available in Edge Runtime');

// eslint-disable-next-line require-atomic-updates
globalThis.EdgeRuntime = origValue;

/* expect(writeFileStub.called).to.be.true;
expect(writeFileStub.args[0][0]).to.match(/path\/to\/local\/file\.json$/);
expect(writeFileStub.args[0][1]).to.contain('"openapi": "3.0.0"'); */
});
});
});
1 change: 0 additions & 1 deletion packages/openapi/tsconfig.cjs.release.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
"extends": "../../tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"module": "commonjs",
"outDir": "./build-cjs",
"strictNullChecks": false
},
Expand Down
2 changes: 1 addition & 1 deletion packages/openapi/tsconfig.esm.release.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"extends": "../../tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"module": "ES6",
"module": "ES2020",
"outDir": "./build-esm",
"strictNullChecks": false
},
Expand Down

0 comments on commit 57cadb5

Please sign in to comment.