diff --git a/.archivist/config.json b/.archivist/config.json
new file mode 100644
index 000000000..ab1ddae63
--- /dev/null
+++ b/.archivist/config.json
@@ -0,0 +1,22 @@
+{
+ "projectId": "b4228f2e-a928-445e-83d8-6bc7a05c420e",
+ "ignoredFiles": [
+ ".DS_Store",
+ ".env",
+ ".archivist/",
+ ".idea/",
+ ".vscode/",
+ "env/",
+ "venv/",
+ ".git/",
+ ".gitignore",
+ "__pycache__/",
+ "__init__.py",
+ "dist/",
+ "node_modules/",
+ "package-lock.json",
+ "yarn.lock",
+ "*.config.js",
+ ".next/"
+ ]
+}
\ No newline at end of file
diff --git a/.changeset/config.json b/.changeset/config.json
index d86fcec82..2396f0ca7 100644
--- a/.changeset/config.json
+++ b/.changeset/config.json
@@ -6,7 +6,6 @@
"linked": [],
"access": "public",
"baseBranch": "master",
- "ignore": ["@asyncapi/nunjucks-filters"],
"updateInternalDependencies": "patch",
"privatePackages": {
"version": true,
diff --git a/.changeset/proud-brooms-accept.md b/.changeset/proud-brooms-accept.md
deleted file mode 100644
index 8a8feff94..000000000
--- a/.changeset/proud-brooms-accept.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-"@asyncapi/generator": patch
----
-
-Updated the method for importing the Nunjucks filter dependency
\ No newline at end of file
diff --git a/.github/workflows/release-docker.yml b/.github/workflows/release-docker.yml
index 93f6615eb..82366d8a8 100644
--- a/.github/workflows/release-docker.yml
+++ b/.github/workflows/release-docker.yml
@@ -47,11 +47,15 @@ jobs:
platforms: linux/amd64,linux/arm64
cache-from: type=gha
cache-to: type=gha
-
+
+ - name: Check out the repository
+ uses: actions/checkout@v4
+
- name: Update Docker Hub Readme
uses: meeDamian/sync-readme@v1.0.6
with:
user: ${{ secrets.DOCKER_USERNAME }}
pass: ${{ secrets.DOCKER_PASSWORD }}
slug: asyncapi/generator
+ readme: ./apps/generator/README.md
description: Use your AsyncAPI definition to generate literally anything. Markdown documentation, Node.js code, HTML documentation, anything!
diff --git a/.gitignore b/.gitignore
index ecb69486e..a53c05bd1 100644
--- a/.gitignore
+++ b/.gitignore
@@ -14,3 +14,4 @@ coverage
# Turbo
.turbo
+/.idea
diff --git a/apps/generator/CHANGELOG.md b/apps/generator/CHANGELOG.md
index ea79756ba..d83655139 100644
--- a/apps/generator/CHANGELOG.md
+++ b/apps/generator/CHANGELOG.md
@@ -1,5 +1,23 @@
# @asyncapi/generator
+## 2.3.0
+
+### Minor Changes
+
+- 44fcc33: ts-node is registered only when it's actually needed
+
+## 2.2.0
+
+### Minor Changes
+
+- 81dfd0c: Enable `noOverwriteGlobs` option for templates based on react rendering engine.
+
+## 2.1.3
+
+### Patch Changes
+
+- 93fb8e8: Updated the method for importing the Nunjucks filter dependency
+
## 2.1.2
### Patch Changes
diff --git a/apps/generator/README.md b/apps/generator/README.md
new file mode 100644
index 000000000..13f9ba7b3
--- /dev/null
+++ b/apps/generator/README.md
@@ -0,0 +1,28 @@
+Generator is a tool that you can use to generate whatever you want basing on the AsyncAPI specification file as an input. For more information [read the docs](https://www.asyncapi.com/docs/tools/generator).
+
+There is a large number of templates that are ready to use and are officially supported by the AsyncAPI Initiative.
+
+## List of official generator templates
+
+
+
+
+| Template Name | Description | Source code |
+| --------------------------------------------- | --------------------------------------------------------------- | --------------------------------------------------------------------------- |
+| `@asyncapi/nodejs-template` | Generates Nodejs service that uses Hermes package | [click here](https://github.com/asyncapi/nodejs-template) |
+| `@asyncapi/nodejs-ws-template` | Generates Nodejs service that supports WebSockets protocol only | [click here](https://github.com/asyncapi/nodejs-ws-template) |
+| `@asyncapi/java-template` | Generates Java JMS application | [click here](https://github.com/asyncapi/java-template) |
+| `@asyncapi/java-spring-template` | Generates Java Spring service | [click here](https://github.com/asyncapi/java-spring-template) |
+| `@asyncapi/java-spring-cloud-stream-template` | Generates Java Spring Cloud Stream service | [click here](https://github.com/asyncapi/java-spring-cloud-stream-template) |
+| `@asyncapi/python-paho-template` | Generates Python service that uses Paho library | [click here](https://github.com/asyncapi/python-paho-template) |
+| `@asyncapi/html-template` | Generates HTML documentation site | [click here](https://github.com/asyncapi/html-template) |
+| `@asyncapi/markdown-template` | Generates documentation in Markdown file | [click here](https://github.com/asyncapi/markdown-template) |
+| `@asyncapi/ts-nats-template` | Generates TypeScript NATS client | [click here](https://github.com/asyncapi/ts-nats-template/) |
+| `@asyncapi/go-watermill-template` | Generates Go client using Watermill | [click here](https://github.com/asyncapi/go-watermill-template) |
+| `@asyncapi/dotnet-nats-template` | Generates .NET C# client using NATS | [click here](https://github.com/asyncapi/dotnet-nats-template) |
+| `@asyncapi/php-template` | Generates PHP client using RabbitMQ | [click here](https://github.com/asyncapi/php-template) |
+| `@asyncapi/dotnet-rabbitmq-template` | Generates .NET C# client using RabbitMQ | [click here](https://github.com/asyncapi/dotnet-rabbitmq-template) |
+
+
+
+You can find above templates and the ones provided by the community in **[this list](https://github.com/search?q=topic%3Aasyncapi+topic%3Agenerator+topic%3Atemplate)**
diff --git a/apps/generator/docs/depreciate-nunjucks.md b/apps/generator/docs/depreciate-nunjucks.md
new file mode 100644
index 000000000..ab06950ee
--- /dev/null
+++ b/apps/generator/docs/depreciate-nunjucks.md
@@ -0,0 +1,121 @@
+---
+title: "Depreciation of nunjucks render engine"
+weight: 170
+---
+
+# Migration Guide from nunjucks render engine to react render engine
+
+## Introduction
+
+AsyncAPI Generator is moving away from Nunjucks templates in favor of React templates. This guide will help you migrate your existing Nunjucks templates to React.
+
+## Step-by-Step Migration Guide
+
+### 1. Update package.json
+
+Change your template configuration in `package.json`:
+
+```json
+{
+"generator": {
+"renderer": "react"
+}
+}
+```
+
+### 2. Install Dependencies
+
+Install the necessary React dependencies:
+
+```bash
+npm install @asyncapi/generator-react-sdk
+```
+
+### 3. Basic Template Structure
+
+Nunjucks:
+```jsx
+
{{ asyncapi.info().title() }}
+{{ asyncapi.info().description() }}
+```
+
+React:
+```jsx
+import { File } from '@asyncapi/generator-react-sdk';
+
+export default function({ asyncapi }) {
+ return (
+
+ {asyncapi.info().title()}
+ {asyncapi.info().description()}
+
+ );
+}
+```
+
+### 4. Macros
+
+Replace macros with React components:
+
+Nunjucks:
+```jsx
+{% macro renderChannel(channel) %}
+
+
{{ channel.address() }}
+
{{ channel.description() }}
+
+{% endmacro %}
+
+{{ renderChannel(someChannel) }}
+```
+
+React:
+```jsx
+// components/Channel.js
+import { Text } from '@asyncapi/generator-react-sdk';
+
+export function Channel({ channel }) {
+ return (
+
+
+
{channel.address()}
+
{channel.description()}
+
+
+ );
+}
+
+// Main template
+import { File, Text } from '@asyncapi/generator-react-sdk';
+import { Channel } from './components/Channel';
+
+export default function({ asyncapi }) {
+ return (
+
+
+ Channels
+
+ {asyncapi.channels().map(channel => (
+
+ ))}
+
+ );
+}
+```
+
+### 5. File template
+
+//TODO: we can add a link to Florence docs once it is merged
+
+## Testing Your Migration
+
+After migrating, test your template thoroughly:
+
+1. Run the generator with your new React template
+2. Compare the output with the previous Nunjucks template output
+3. Check for any missing or incorrectly rendered content
+
+## Conclusion
+
+Migrating from Nunjucks to React templates may require some initial effort, but it will result in more maintainable. You can read why we introduced react render engine [here](https://www.asyncapi.com/blog/react-as-generator-engine)
+
diff --git a/apps/generator/hello.js b/apps/generator/hello.js
new file mode 100644
index 000000000..831276c55
--- /dev/null
+++ b/apps/generator/hello.js
@@ -0,0 +1,50 @@
+const path = require("path");
+const Generator = require("./lib/generator");
+const { promises: fsPromise } = require("fs");
+const reactTemplate = 'test/test-templates/react-template';
+
+// const reactTemplate = path.resolve(__dirname, "./test/test-templates/react-template");
+// console.log("reactTemplate", reactTemplate);
+const dummySpecPath = path.resolve(__dirname, './test/docs/dummy.yml');
+
+async function main() {
+ const outputDir = path.resolve(__dirname, "test/hello");
+ console.log("outputDir", outputDir);
+ // await fsPromise.mkdir(outputDir, { recursive: true });
+
+ // Create temp.md.js file dynamically
+ const tempJsContent = `
+ import { File, Text } from '@asyncapi/generator-react-sdk';
+
+ export default function() {
+ return (
+
+ Test
+
+ );
+}
+`;
+// const reactTemplate = path.resolve(__dirname, "./test/test-templates/react-template");
+console.log("reactTemplate", reactTemplate);
+ const transpiledPath = path.join(reactTemplate, '__transpiled');
+
+ // await fsPromise.unlink(path.join(transpiledPath, 'temp.md.js'))
+ // await fsPromise.unlink(path.join(transpiledPath, 'temp.md.js.map'))
+
+ const tempJsPath = path.join(reactTemplate, "template","temp.md.js");
+ await fsPromise.writeFile(tempJsPath, tempJsContent);
+ console.log("tempJsPath", tempJsPath);
+
+ const generator = new Generator(reactTemplate, outputDir, {
+ forceWrite: true,
+ debug: true,
+ compile: false,
+ });
+ await generator.generateFromFile(dummySpecPath);
+
+ // Check if temp.md is created in the output directory
+ const tempMdPath = path.join(outputDir, "temp.md");
+ console.log("tempMdPath", tempMdPath);
+}
+
+main()
\ No newline at end of file
diff --git a/apps/generator/lib/filtersRegistry.js b/apps/generator/lib/filtersRegistry.js
index 4c90aed31..6659960ed 100644
--- a/apps/generator/lib/filtersRegistry.js
+++ b/apps/generator/lib/filtersRegistry.js
@@ -1,7 +1,7 @@
const path = require('path');
const fs = require('fs');
const xfs = require('fs.extra');
-const { isAsyncFunction } = require('./utils');
+const { isAsyncFunction, registerTypeScript } = require('./utils');
const nunjucksFilters = require('@asyncapi/nunjucks-filters');
/**
@@ -38,7 +38,12 @@ function registerLocalFilters(nunjucks, templateDir, filtersDir) {
walker.on('file', async (root, stats, next) => {
try {
- const filePath = path.resolve(templateDir, path.resolve(root, stats.name));
+ const filePath = path.resolve(
+ templateDir,
+ path.resolve(root, stats.name)
+ );
+
+ registerTypeScript(filePath);
// If it's a module constructor, inject dependencies to ensure consistent usage in remote templates in other projects or plain directories.
delete require.cache[require.resolve(filePath)];
const mod = require(filePath);
diff --git a/apps/generator/lib/generator.js b/apps/generator/lib/generator.js
index 837414c7c..edbaa9f07 100644
--- a/apps/generator/lib/generator.js
+++ b/apps/generator/lib/generator.js
@@ -28,7 +28,6 @@ const {
isReactTemplate,
isJsFile,
registerSourceMap,
- registerTypeScript,
getTemplateDetails,
convertCollectionToObject,
} = require('./utils');
@@ -59,7 +58,6 @@ const shouldIgnoreDir = dirPath =>
|| dirPath.startsWith(`.git${path.sep}`);
registerSourceMap();
-registerTypeScript();
class Generator {
/**
@@ -854,7 +852,7 @@ class Generator {
if (renderContent === undefined) {
return;
} else if (isReactTemplate(this.templateConfig)) {
- await saveRenderedReactContent(renderContent, outputpath);
+ await saveRenderedReactContent(renderContent, outputpath, this.noOverwriteGlobs);
} else {
await writeFile(outputpath, renderContent);
}
@@ -933,9 +931,11 @@ class Generator {
async renderFile(asyncapiDocument, filePath, extraTemplateData = {}) {
if (isReactTemplate(this.templateConfig)) {
return await renderReact(asyncapiDocument, filePath, extraTemplateData, this.templateDir, this.templateContentDir, TRANSPILED_TEMPLATE_LOCATION, this.templateParams, this.debug, this.originalAsyncAPI);
+ } else {
+ console.warn('Deprecation Warning: Nunjucks templates are deprecated. Please migrate to React templates.');
+ const templateString = await readFile(filePath, 'utf8');
+ return renderNunjucks(asyncapiDocument, templateString, filePath, extraTemplateData, this.templateParams, this.originalAsyncAPI, this.nunjucks);
}
- const templateString = await readFile(filePath, 'utf8');
- return renderNunjucks(asyncapiDocument, templateString, filePath, extraTemplateData, this.templateParams, this.originalAsyncAPI, this.nunjucks);
}
/**
diff --git a/apps/generator/lib/hooksRegistry.js b/apps/generator/lib/hooksRegistry.js
index bde5c919c..2c21389fb 100644
--- a/apps/generator/lib/hooksRegistry.js
+++ b/apps/generator/lib/hooksRegistry.js
@@ -1,6 +1,6 @@
const path = require('path');
const xfs = require('fs.extra');
-const { exists } = require('./utils');
+const { exists, registerTypeScript } = require('./utils');
/**
* Registers all template hooks.
@@ -37,6 +37,9 @@ async function registerLocalHooks(hooks, templateDir, hooksDir) {
walker.on('file', async (root, stats, next) => {
try {
const filePath = path.resolve(templateDir, path.resolve(root, stats.name));
+
+ registerTypeScript(filePath);
+
delete require.cache[require.resolve(filePath)];
const mod = require(filePath);
diff --git a/apps/generator/lib/logMessages.js b/apps/generator/lib/logMessages.js
index 13ac04c7e..5d28bf8f0 100644
--- a/apps/generator/lib/logMessages.js
+++ b/apps/generator/lib/logMessages.js
@@ -6,22 +6,22 @@ const NODE_MODULES_INSTALL ='Remember that your local template must have its own
const NPM_INSTALL_TRIGGER = 'Installation of template located on disk technically means symlink creation betweed node_modules of the generator and template sources. Your local template must have its own node_modules, "npm install" is not triggered.';
-function templateVersion(ver) {
+function templateVersion(ver) {
return `Version of used template is ${ver}.`;
-}
+}
function templateSource(localHtmlTemplate) {
return `Template sources taken from ${localHtmlTemplate}.`;
-}
+}
function templateNotFound(templateName) {
return `${templateName} not found in local dependencies but found it installed as a global package.`;
-}
+}
function packageNotAvailable(packageDetails) {
if (packageDetails && packageDetails.pkgPath) {
return `Unable to resolve template location at ${packageDetails.pkgPath}. Package is not available locally.`;
- }
+ }
return `Template is not available locally and expected location is undefined. Known details are: ${JSON.stringify(packageDetails, null, 2)}`;
}
@@ -38,6 +38,10 @@ function relativeSourceFileNotGenerated(relativeSourceFile , subject) {
return `${relativeSourceFile} was not generated because ${subject} specified in template configuration in conditionalFiles was not found in provided AsyncAPI specification file.`;
}
+function skipOverwrite(testFilePath) {
+ return `Skipping overwrite for: ${testFilePath}`;
+}
+
function conditionalFilesMatched(relativeSourceFile) {
return `${relativeSourceFile} was not generated because condition specified for this file in template configuration in conditionalFiles matched.`;
}
@@ -59,5 +63,7 @@ module.exports = {
templateSuccessfullyInstalled,
relativeSourceFileNotGenerated,
conditionalFilesMatched,
- compileEnabled
-};
\ No newline at end of file
+ compileEnabled,
+ compileEnabled,
+ skipOverwrite
+};
diff --git a/apps/generator/lib/renderer/nunjucks.js b/apps/generator/lib/renderer/nunjucks.js
index 410b8d945..7b2a0f51c 100644
--- a/apps/generator/lib/renderer/nunjucks.js
+++ b/apps/generator/lib/renderer/nunjucks.js
@@ -9,6 +9,7 @@ const nunjucksExport = module.exports;
* @param {string} templateDir path
*/
nunjucksExport.configureNunjucks = (debug, templateDir) => {
+ console.warn('Deprecation Warning: Nunjucks support is being phased out. Please migrate to React templates.');
const config = {};
if (debug) config.dev = true;
diff --git a/apps/generator/lib/renderer/react.js b/apps/generator/lib/renderer/react.js
index 4aad213fc..19d176719 100644
--- a/apps/generator/lib/renderer/react.js
+++ b/apps/generator/lib/renderer/react.js
@@ -1,16 +1,17 @@
const path = require('path');
-const AsyncReactSDK = require('@asyncapi/generator-react-sdk');
+const AsyncReactSDK = require('../../../../../generator-react-sdk/lib/index.js');
+const minimatch = require('minimatch');
+const logMessage = require('../logMessages.js');
+const log = require('loglevel');
const {
writeFile
} = require('../utils');
-const logMessage = require('../logMessages');
-const log = require('loglevel');
const reactExport = module.exports;
/**
* Configures React templating system, this handles all the transpilation work.
- *
+ *
* @private
* @param {string} templateLocation located for thetemplate
* @param {string} templateContentDir where the template content are located
@@ -27,9 +28,9 @@ reactExport.configureReact = async (templateLocation, templateContentDir, transp
/**
* Renders the template with react and returns the content and meta data for the file.
- *
+ *
* @private
- * @param {AsyncAPIDocument} asyncapiDocument
+ * @param {AsyncAPIDocument} asyncapiDocument
* @param {string} filePath path to the template file
* @param {Object} extraTemplateData Extra data to pass to the template.
* @param {string} templateLocation located for thetemplate
@@ -37,34 +38,41 @@ reactExport.configureReact = async (templateLocation, templateContentDir, transp
* @param {string} transpiledTemplateLocation folder for the transpiled code
* @param {Object} templateParams provided template parameters
* @param {boolean} debug flag
- * @param {string} originalAsyncAPI
+ * @param {string} originalAsyncAPI
* @return {Promise}
*/
-reactExport.renderReact = async (asyncapiDocument, filePath, extraTemplateData, templateLocation, templateContentDir, transpiledTemplateLocation, templateParams, debug, originalAsyncAPI) => {
+reactExport.renderReact = async (asyncapiDocument, filePath, extraTemplateData, templateLocation, templateContentDir, transpiledTemplateLocation, templateParams, debug, originalAsyncAPI, compile) => {
extraTemplateData = extraTemplateData || {};
+ let fileToRender;
+ if (compile) {
+ fileToRender = filePath.replace(templateContentDir, path.resolve(templateLocation, transpiledTemplateLocation));
+ } else {
+ fileToRender = filePath;
+ }
+ console.log('Attempting to render file:', fileToRender);
filePath = filePath.replace(templateContentDir, path.resolve(templateLocation, transpiledTemplateLocation));
return await AsyncReactSDK.renderTemplate(
- filePath,
+ filePath,
{
asyncapi: asyncapiDocument,
params: templateParams,
originalAsyncAPI,
...extraTemplateData
- },
+ },
debug
);
};
/**
* Save the single rendered react content based on the meta data available.
- *
+ *
* @private
* @param {TemplateRenderResult} renderedContent the react content rendered
* @param {String} outputPath Path to the file being rendered.
*/
-const saveContentToFile = async (renderedContent, outputPath) => {
+const saveContentToFile = async (renderedContent, outputPath, noOverwriteGlobs = []) => {
let filePath = outputPath;
- // Might be the same as in the `fs` package, but is an active choice for our default file permission for any rendered files.
+ // Might be the same as in the `fs` package, but is an active choice for our default file permission for any rendered files.
let permissions = 0o666;
const content = renderedContent.content;
@@ -82,21 +90,32 @@ const saveContentToFile = async (renderedContent, outputPath) => {
}
}
- await writeFile(filePath, content, {
- mode: permissions
- });
+ // get the final file name of the file
+ const finalFileName = path.basename(filePath);
+ // check whether the filename should be ignored based on user's inputs
+ const shouldOverwrite = !noOverwriteGlobs.some(globExp => minimatch(finalFileName, globExp));
+
+ // Write the file only if it should not be skipped
+ if (shouldOverwrite) {
+ await writeFile(filePath, content, {
+ mode: permissions
+ });
+ } else {
+ await log.debug(logMessage.skipOverwrite(filePath));
+ }
};
/**
* Save the rendered react content based on the meta data available.
- *
+ *
* @private
* @param {TemplateRenderResult[] | TemplateRenderResult} renderedContent the react content rendered
* @param {String} outputPath Path to the file being rendered.
+ * @param noOverwriteGlobs Array of globs to skip overwriting files.
*/
-reactExport.saveRenderedReactContent = async (renderedContent, outputPath) => {
+reactExport.saveRenderedReactContent = async (renderedContent, outputPath, noOverwriteGlobs = []) => {
if (Array.isArray(renderedContent)) {
- return Promise.all(renderedContent.map(content => saveContentToFile(content, outputPath)));
+ return Promise.all(renderedContent.map(content => saveContentToFile(content, outputPath, noOverwriteGlobs)));
}
- return saveContentToFile(renderedContent, outputPath);
+ return await saveContentToFile(renderedContent, outputPath, noOverwriteGlobs);
};
diff --git a/apps/generator/lib/utils.js b/apps/generator/lib/utils.js
index f7026b166..27e26de0f 100644
--- a/apps/generator/lib/utils.js
+++ b/apps/generator/lib/utils.js
@@ -149,7 +149,13 @@ utils.registerSourceMap = () => {
*
* @private
*/
-utils.registerTypeScript = () => {
+utils.registerTypeScript = (filePath) => {
+ const isTypescriptFile = filePath.endsWith('.ts');
+
+ if (!isTypescriptFile) {
+ return;
+ }
+
const { REGISTER_INSTANCE, register } = require('ts-node');
// if the ts-node has already been registered before, do not register it again.
// Check the env. TS_NODE_ENV if ts-node started via ts-node-dev package
diff --git a/apps/generator/package.json b/apps/generator/package.json
index 19aacaa8b..b83e72ffd 100644
--- a/apps/generator/package.json
+++ b/apps/generator/package.json
@@ -1,6 +1,6 @@
{
"name": "@asyncapi/generator",
- "version": "2.1.2",
+ "version": "2.3.0",
"description": "The AsyncAPI generator. It can generate documentation, code, anything!",
"main": "./lib/generator.js",
"bin": {
@@ -15,8 +15,8 @@
"test": "npm run test:unit && npm run test:integration && npm run test:cli",
"test:unit": "jest --coverage --testPathIgnorePatterns=integration --testPathIgnorePatterns=test-project",
"test:dev": "npm run test:unit -- --watchAll",
- "test:integration": "npm run test:cleanup && jest --testPathPattern=integration --modulePathIgnorePatterns='./__mocks__'",
- "test:integration:update": "jest --updateSnapshot --testPathPattern=integration --modulePathIgnorePatterns='./__mocks__'",
+ "test:integration": "npm run test:cleanup && jest --testPathPattern=integration --modulePathIgnorePatterns='./__mocks__(?!\\/loglevel\\.js$)'",
+ "test:integration:update": "jest --updateSnapshot --testPathPattern=integration --modulePathIgnorePatterns='./__mocks__(?!\\/loglevel\\.js$)'",
"test:cli": "node cli.js ./test/docs/dummy.yml ./test/test-templates/react-template -o test/output --force-write --debug && test -e test/output/test-file.md",
"test:cleanup": "rimraf \"test/temp\"",
"docs": "jsdoc2md --partial docs/jsdoc2md-handlebars/custom-sig-name.hbs docs/jsdoc2md-handlebars/main.hbs docs/jsdoc2md-handlebars/docs.hbs docs/jsdoc2md-handlebars/header.hbs docs/jsdoc2md-handlebars/defaultvalue.hbs docs/jsdoc2md-handlebars/link.hbs docs/jsdoc2md-handlebars/params-table.hbs --files lib/generator.js > docs/api.md",
diff --git a/apps/generator/test/integration.test.js b/apps/generator/test/integration.test.js
index b4f86499e..949253a96 100644
--- a/apps/generator/test/integration.test.js
+++ b/apps/generator/test/integration.test.js
@@ -3,7 +3,7 @@
*/
const path = require('path');
-const { readFile, writeFile, access } = require('fs').promises;
+const { readFile, writeFile, access, unlink, mkdir } = require('fs').promises;
const Generator = require('../lib/generator');
const dummySpecPath = path.resolve(__dirname, './docs/dummy.yml');
const refSpecPath = path.resolve(__dirname, './docs/apiwithref.json');
@@ -22,9 +22,21 @@ describe('Integration testing generateFromFile() to make sure the result of the
jest.setTimeout(100000);
const testOutputFile = 'test-file.md';
+ const tempJsContent = `
+ import { File, Text } from '@asyncapi/generator-react-sdk';
+
+ export default function() {
+ return (
+
+ Test
+
+ );
+ }
+ `;
+
it('generated using Nunjucks template', async () => {
const outputDir = generateFolderName();
- const generator = new Generator(nunjucksTemplate, outputDir, {
+ const generator = new Generator(nunjucksTemplate, outputDir, {
forceWrite: true,
templateParams: { version: 'v1', mode: 'production' }
});
@@ -35,7 +47,7 @@ describe('Integration testing generateFromFile() to make sure the result of the
it('generate using React template', async () => {
const outputDir = generateFolderName();
- const generator = new Generator(reactTemplate, outputDir, {
+ const generator = new Generator(reactTemplate, outputDir, {
forceWrite: true ,
templateParams: { version: 'v1', mode: 'production' }
});
@@ -60,17 +72,6 @@ describe('Integration testing generateFromFile() to make sure the result of the
const outputDir = generateFolderName();
// Create temp.md.js file dynamically
- const tempJsContent = `
- import { File, Text } from '@asyncapi/generator-react-sdk';
-
- export default function() {
- return (
-
- Test
-
- );
- }
- `;
const tempJsPath = path.join(reactTemplate, 'template/temp.md.js');
await writeFile(tempJsPath, tempJsContent);
@@ -90,19 +91,13 @@ describe('Integration testing generateFromFile() to make sure the result of the
it('check if the temp.md file is not created when compile option is false', async () => {
const outputDir = generateFolderName();
-
+
+ // first we need to do cleanup of the react template `__transpiled` folder as from previous test it will have the transpiled files
+ const transpiledPath = path.join(reactTemplate, '__transpiled');
+ await unlink(path.join(transpiledPath, 'temp.md.js'));
+ await unlink(path.join(transpiledPath, 'temp.md.js.map'));
+
// Create temp.md.js file dynamically
- const tempJsContent = `
- import { File, Text } from '@asyncapi/generator-react-sdk';
-
- export default function() {
- return (
-
- Test
-
- );
- }
- `;
const tempJsPath = path.join(reactTemplate, 'template/temp.md.js');
await writeFile(tempJsPath, tempJsContent);
@@ -118,4 +113,33 @@ describe('Integration testing generateFromFile() to make sure the result of the
const tempMdExists = await access(tempMdPath).then(() => true).catch(() => false);
expect(tempMdExists).toBe(false);
});
+
+ it('should ignore specified files with noOverwriteGlobs', async () => {
+ const outputDir = generateFolderName();
+ // Manually create a file to test if it's not overwritten
+ await mkdir(outputDir, { recursive: true });
+ // Create a variable to store the file content
+ const testContent = '';
+ // eslint-disable-next-line sonarjs/no-duplicate-string
+ const testFilePath = path.normalize(path.resolve(outputDir, testOutputFile));
+ await writeFile(testFilePath, testContent);
+
+ // Manually create an output first, before generation, with additional custom file to validate if later it is still there, not overwritten
+ const generator = new Generator(reactTemplate, outputDir, {
+ forceWrite: true,
+ noOverwriteGlobs: [`**/${testOutputFile}`],
+ debug: true,
+ });
+
+ await generator.generateFromFile(dummySpecPath);
+
+ // Read the file to confirm it was not overwritten
+ const fileContent = await readFile(testFilePath, 'utf8');
+ // Check if the files have been overwritten
+ expect(fileContent).toBe(testContent);
+ // Check if the log debug message was printed
+ /*TODO:
+ Include log message test in the future to ensure that the log.debug for skipping overwrite is called
+ */
+ });
});
diff --git a/apps/generator/test/test-templates/react-template/template/temp.md.js b/apps/generator/test/test-templates/react-template/template/temp.md.js
new file mode 100644
index 000000000..911686c2a
--- /dev/null
+++ b/apps/generator/test/test-templates/react-template/template/temp.md.js
@@ -0,0 +1,10 @@
+
+ import { File, Text } from '@asyncapi/generator-react-sdk';
+
+ export default function() {
+ return (
+
+ Test
+
+ );
+}
diff --git a/package-lock.json b/package-lock.json
index 5f3b1b082..b2eac8b6f 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -20,7 +20,7 @@
},
"apps/generator": {
"name": "@asyncapi/generator",
- "version": "2.1.2",
+ "version": "2.3.0",
"license": "Apache-2.0",
"dependencies": {
"@asyncapi/generator-react-sdk": "^1.0.18",