Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add dart generator. #658

Merged
merged 10 commits into from
Apr 27, 2022
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,10 @@ To see the complete feature list for each language, please click the individual
<td><a href="./docs/usage.md#generate-javascript-models">JavaScript</a></td>
<td>Class generation: <em>custom indentation type and size, etc</em></td>
</tr>
<tr>
<td><a href="./docs/usage.md#generate-dart-models">Dart</a></td>
<td>Class and enum generation: json_annotation</td>
</tr>
</table>

## Roadmap
Expand Down
16 changes: 16 additions & 0 deletions docs/languages/Dart.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# Dart
There are special use-cases that each language supports; this document pertains to **Dart models**.

<!-- toc is generated with GitHub Actions do not remove toc markers -->

<!-- toc -->

- [Include json_annotation for the class and enums](#include-json-annotation-for-the-class)

<!-- tocstop -->

## Include Json annotation for the class and enums

When you generate the models with json annotation, generated files include json_annotation package (https://pub.dev/packages/json_annotation/) and their syntax

Check out this [example for a live demonstration](../../examples/dart-generate-json-annotation).
5 changes: 5 additions & 0 deletions docs/usage.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ For more specific integration options, please check out the [integration documen
- [Generate Java models](#generate-java-models)
- [Generate TypeScript models](#generate-typescript-models)
- [Generate JavaScript models](#generate-javascript-models)
- [Generate Dart models](#generate-dart-models)

<!-- tocstop -->

Expand Down Expand Up @@ -98,3 +99,7 @@ TypeScript is one of the many output languages we support. Check out this [basic
## Generate JavaScript models

JavaScript is one of the many output languages we support. Check out this [basic example for a live demonstration](../examples/generate-javascript-models) and the following [JavaScript documentation for more advanced use-cases](./languages/JavaScript.md).

## Generate Dart models

Dart is one of the many output languages we support. Check out this [basic example for a live demonstration](../examples/generate-dart-models) and the following [Dart documentation for more advanced use-cases](./languages/Dart.md).
17 changes: 17 additions & 0 deletions examples/dart-generate-json-annotation/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Dart Data Models with json_annotation

A basic example of how to use Modelina and output a Go data model.

## How to run this example

Run this example using:

```sh
npm i && npm run start
```

If you are on Windows, use the `start:windows` script instead:

```sh
npm i && npm run start:windows
```
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`Should be able to render Dart Models and should log expected output to console 1`] = `
Array [
"class Root {
Object? email;

Root();

factory Root.fromJson(Map<String, dynamic> json) => _$RootFromJson(json);
Map<String, dynamic> toJson() => _$RootToJson(this);
}",
]
`;
13 changes: 13 additions & 0 deletions examples/dart-generate-json-annotation/index.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
const spy = jest.spyOn(global.console, 'log').mockImplementation(() => { return; });
import {generate} from './index';

describe('Should be able to render Dart Models', () => {
afterAll(() => {
jest.restoreAllMocks();
});
test('and should log expected output to console', async () => {
await generate();
expect(spy.mock.calls.length).toEqual(2);
expect(spy.mock.calls[1]).toMatchSnapshot();
});
});
24 changes: 24 additions & 0 deletions examples/dart-generate-json-annotation/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import {DART_JSON_PRESET, DartFileGenerator} from '../../src';

const jsonSchemaDraft7 = {
$schema: 'http://json-schema.org/draft-07/schema#',
type: 'object',
additionalProperties: true,
properties: {
email: {
type: 'string',
format: 'email'
}
}
};

const generator = new DartFileGenerator({ presets: [DART_JSON_PRESET] });

export async function generate() : Promise<void> {
const models = await generator.generate(jsonSchemaDraft7);
for (const model of models) {
console.log(model.result);
}
}
generate();

17 changes: 17 additions & 0 deletions examples/generate-dart-models/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Dart Data Models

A basic example of how to use Modelina and output a Go data model.

## How to run this example

Run this example using:

```sh
npm i && npm run start
```

If you are on Windows, use the `start:windows` script instead:

```sh
npm i && npm run start:windows
```
11 changes: 11 additions & 0 deletions examples/generate-dart-models/__snapshots__/index.spec.ts.snap
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`Should be able to render Dart Models and should log expected output to console 1`] = `
Array [
"class Root {
Object? email;

Root();
}",
]
`;
13 changes: 13 additions & 0 deletions examples/generate-dart-models/index.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
const spy = jest.spyOn(global.console, 'log').mockImplementation(() => { return; });
import {generate} from './index';

describe('Should be able to render Dart Models', () => {
afterAll(() => {
jest.restoreAllMocks();
});
test('and should log expected output to console', async () => {
await generate();
expect(spy.mock.calls.length).toEqual(2);
expect(spy.mock.calls[1]).toMatchSnapshot();
});
});
22 changes: 22 additions & 0 deletions examples/generate-dart-models/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import {DartGenerator} from '../../src';

const generator = new DartGenerator();
const jsonSchemaDraft7 = {
$schema: 'http://json-schema.org/draft-07/schema#',
type: 'object',
additionalProperties: false,
properties: {
email: {
type: 'string',
format: 'email'
}
}
};

export async function generate() : Promise<void> {
const models = await generator.generate(jsonSchemaDraft7);
for (const model of models) {
console.log(model.result);
}
}
generate();
10 changes: 10 additions & 0 deletions examples/generate-dart-models/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

12 changes: 12 additions & 0 deletions examples/generate-dart-models/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"config": {
"example_name": "generate-dart-models"
},
"scripts": {
"install": "cd ../.. && npm i",
"start": "../../node_modules/.bin/ts-node --cwd ../../ ./examples/$npm_package_config_example_name/index.ts",
"start:windows": "..\\..\\node_modules\\.bin\\ts-node --cwd ..\\..\\ .\\examples\\%npm_package_config_example_name%\\index.ts",
"test": "../../node_modules/.bin/jest --config=../../jest.config.js ./examples/$npm_package_config_example_name/index.spec.ts",
"test:windows": "..\\..\\node_modules\\.bin\\jest --config=..\\..\\jest.config.js examples/%npm_package_config_example_name%/index.spec.ts"
}
}
69 changes: 69 additions & 0 deletions src/generators/dart/Constants.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
export const RESERVED_DART_KEYWORDS = [
'abstract',
'as',
'assert',
'async',
'await',
'break',
'case',
'catch',
'class',
'const',
'continue',
'covariant',
'default',
'deferred',
'do',
'dynamic',
'else',
'enum',
'export',
'extends',
'extension',
'external',
'factory',
'false',
'final',
'for',
'Function',
'get',
'get',
'hide',
'if',
'implements',
'import',
'in',
'interface',
'is',
'late',
'library',
'mixin',
'new',
'null',
'on',
'operator',
'part',
'required',
'rethrow',
'return',
'set',
'show',
'static',
'super',
'switch',
'sync',
'this',
'throw',
'true',
'try',
'typedef',
'var',
'void',
'while',
'with',
'yield',
];

export function isReservedDartKeyword(word: string): boolean {
return RESERVED_DART_KEYWORDS.includes(word);
}
24 changes: 24 additions & 0 deletions src/generators/dart/DartFileGenerator.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import { DartGenerator, DartRenderCompleteModelOptions } from './';
import { CommonInputModel, OutputModel } from '../../models';
import * as path from 'path';
import { AbstractFileGenerator } from '../AbstractFileGenerator';
import { FileHelpers } from '../../helpers';

export class DartFileGenerator extends DartGenerator implements AbstractFileGenerator<DartRenderCompleteModelOptions> {
/**
* Generates all the models to an output directory each model with their own separate files.
*
* @param input
* @param outputDirectory where you want the models generated to
* @param options
*/
public async generateToFiles(input: Record<string, unknown> | CommonInputModel, outputDirectory: string, options: DartRenderCompleteModelOptions): Promise<OutputModel[]> {
let generatedModels = await this.generateCompleteModels(input, options);
generatedModels = generatedModels.filter((outputModel) => { return outputModel.modelName !== undefined; });
for (const outputModel of generatedModels) {
const filePath = path.resolve(outputDirectory, `${outputModel.modelName}.dart`);
await FileHelpers.writerToFileSystem(outputModel.result, filePath);
}
return generatedModels;
}
}
Loading