Skip to content

Commit 47d629c

Browse files
Improve generated ast.ts regarding multiple languages (#1979)
* split the content inside the ast.ts for multiple-language-projects * added validations to make names of grammars unique regarding: other grammar's names, names of types/rules * mix and sort type definitions derived from unions and interfaces
1 parent 16899fd commit 47d629c

File tree

22 files changed

+2087
-253
lines changed

22 files changed

+2087
-253
lines changed

examples/arithmetics/src/language-server/generated/ast.ts

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -43,26 +43,6 @@ export function isAbstractDefinition(item: unknown): item is AbstractDefinition
4343
return reflection.isInstance(item, AbstractDefinition.$type);
4444
}
4545

46-
export type Expression = BinaryExpression | FunctionCall | NumberLiteral;
47-
48-
export const Expression = {
49-
$type: 'Expression'
50-
} as const;
51-
52-
export function isExpression(item: unknown): item is Expression {
53-
return reflection.isInstance(item, Expression.$type);
54-
}
55-
56-
export type Statement = Definition | Evaluation;
57-
58-
export const Statement = {
59-
$type: 'Statement'
60-
} as const;
61-
62-
export function isStatement(item: unknown): item is Statement {
63-
return reflection.isInstance(item, Statement.$type);
64-
}
65-
6646
export interface BinaryExpression extends langium.AstNode {
6747
readonly $container: BinaryExpression | Definition | Evaluation | FunctionCall;
6848
readonly $type: 'BinaryExpression';
@@ -131,6 +111,16 @@ export function isEvaluation(item: unknown): item is Evaluation {
131111
return reflection.isInstance(item, Evaluation.$type);
132112
}
133113

114+
export type Expression = BinaryExpression | FunctionCall | NumberLiteral;
115+
116+
export const Expression = {
117+
$type: 'Expression'
118+
} as const;
119+
120+
export function isExpression(item: unknown): item is Expression {
121+
return reflection.isInstance(item, Expression.$type);
122+
}
123+
134124
export interface FunctionCall extends langium.AstNode {
135125
readonly $container: BinaryExpression | Definition | Evaluation | FunctionCall;
136126
readonly $type: 'FunctionCall';
@@ -179,6 +169,16 @@ export function isNumberLiteral(item: unknown): item is NumberLiteral {
179169
return reflection.isInstance(item, NumberLiteral.$type);
180170
}
181171

172+
export type Statement = Definition | Evaluation;
173+
174+
export const Statement = {
175+
$type: 'Statement'
176+
} as const;
177+
178+
export function isStatement(item: unknown): item is Statement {
179+
return reflection.isInstance(item, Statement.$type);
180+
}
181+
182182
export type ArithmeticsAstType = {
183183
AbstractDefinition: AbstractDefinition
184184
BinaryExpression: BinaryExpression

examples/domainmodel/src/language-server/generated/ast.ts

Lines changed: 16 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -38,22 +38,6 @@ export function isAbstractElement(item: unknown): item is AbstractElement {
3838
return reflection.isInstance(item, AbstractElement.$type);
3939
}
4040

41-
export type QualifiedName = string;
42-
43-
export function isQualifiedName(item: unknown): item is QualifiedName {
44-
return typeof item === 'string';
45-
}
46-
47-
export type Type = DataType | Entity;
48-
49-
export const Type = {
50-
$type: 'Type'
51-
} as const;
52-
53-
export function isType(item: unknown): item is Type {
54-
return reflection.isInstance(item, Type.$type);
55-
}
56-
5741
export interface DataType extends langium.AstNode {
5842
readonly $container: Domainmodel | PackageDeclaration;
5943
readonly $type: 'DataType';
@@ -138,6 +122,22 @@ export function isPackageDeclaration(item: unknown): item is PackageDeclaration
138122
return reflection.isInstance(item, PackageDeclaration.$type);
139123
}
140124

125+
export type QualifiedName = string;
126+
127+
export function isQualifiedName(item: unknown): item is QualifiedName {
128+
return typeof item === 'string';
129+
}
130+
131+
export type Type = DataType | Entity;
132+
133+
export const Type = {
134+
$type: 'Type'
135+
} as const;
136+
137+
export function isType(item: unknown): item is Type {
138+
return reflection.isInstance(item, Type.$type);
139+
}
140+
141141
export type DomainModelAstType = {
142142
AbstractElement: AbstractElement
143143
DataType: DataType

examples/requirements/src/language-server/generated/ast.ts

Lines changed: 81 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -6,31 +6,95 @@
66
/* eslint-disable */
77
import * as langium from 'langium';
88

9+
/** Contains the reachable terminals & keywords and all available types of the 'Requirements' language. */
10+
export namespace Requirements {
11+
12+
export const Terminals = {
13+
WS: /\s+/,
14+
ID: /[_a-zA-Z][\w_]*/,
15+
STRING: /"(\\.|[^"\\])*"|'(\\.|[^'\\])*'/,
16+
ML_COMMENT: /\/\*[\s\S]*?\*\//,
17+
SL_COMMENT: /\/\/[^\n\r]*/,
18+
};
19+
20+
export type TerminalNames = keyof typeof Terminals;
21+
22+
export type KeywordNames =
23+
| ","
24+
| ":"
25+
| "applicable"
26+
| "contact"
27+
| "environment"
28+
| "for"
29+
| "req";
30+
31+
export type TokenNames = TerminalNames | KeywordNames;
32+
33+
export type AstType = {
34+
Contact: Contact
35+
Environment: Environment
36+
Requirement: Requirement
37+
RequirementModel: RequirementModel
38+
}
39+
40+
}
41+
42+
/** Contains the reachable terminals & keywords and all available types of the 'Tests' language. */
43+
export namespace Tests {
44+
45+
export const Terminals = {
46+
WS: /\s+/,
47+
ID: /[_a-zA-Z][\w_]*/,
48+
STRING: /"(\\.|[^"\\])*"|'(\\.|[^'\\])*'/,
49+
ML_COMMENT: /\/\*[\s\S]*?\*\//,
50+
SL_COMMENT: /\/\/[^\n\r]*/,
51+
};
52+
53+
export type TerminalNames = keyof typeof Terminals;
54+
55+
export type KeywordNames =
56+
| ","
57+
| ":"
58+
| "="
59+
| "applicable"
60+
| "contact"
61+
| "for"
62+
| "testFile"
63+
| "tests"
64+
| "tst";
65+
66+
export type TokenNames = TerminalNames | KeywordNames;
67+
68+
export type AstType = {
69+
Contact: Contact
70+
Environment: Environment
71+
Requirement: Requirement
72+
RequirementModel: RequirementModel
73+
Test: Test
74+
TestModel: TestModel
75+
}
76+
77+
}
78+
79+
80+
// the terminals, keywords and types of the whole 'RequirementsAndTests' project
81+
982
export const RequirementsAndTestsTerminals = {
10-
WS: /\s+/,
11-
ID: /[_a-zA-Z][\w_]*/,
12-
STRING: /"(\\.|[^"\\])*"|'(\\.|[^'\\])*'/,
13-
ML_COMMENT: /\/\*[\s\S]*?\*\//,
14-
SL_COMMENT: /\/\/[^\n\r]*/,
83+
...Requirements.Terminals,
84+
...Tests.Terminals,
1585
};
1686

1787
export type RequirementsAndTestsTerminalNames = keyof typeof RequirementsAndTestsTerminals;
1888

19-
export type RequirementsAndTestsKeywordNames =
20-
| ","
21-
| ":"
22-
| "="
23-
| "applicable"
24-
| "contact"
25-
| "environment"
26-
| "for"
27-
| "req"
28-
| "testFile"
29-
| "tests"
30-
| "tst";
89+
export type RequirementsAndTestsKeywordNames = Requirements.KeywordNames | Tests.KeywordNames;
3190

3291
export type RequirementsAndTestsTokenNames = RequirementsAndTestsTerminalNames | RequirementsAndTestsKeywordNames;
3392

93+
export type RequirementsAndTestsAstType = Requirements.AstType & Tests.AstType
94+
95+
96+
// all type definitions of the the whole 'RequirementsAndTests' project
97+
3498
export interface Contact extends langium.AstNode {
3599
readonly $container: RequirementModel | TestModel;
36100
readonly $type: 'Contact';
@@ -137,15 +201,6 @@ export function isTestModel(item: unknown): item is TestModel {
137201
return reflection.isInstance(item, TestModel.$type);
138202
}
139203

140-
export type RequirementsAndTestsAstType = {
141-
Contact: Contact
142-
Environment: Environment
143-
Requirement: Requirement
144-
RequirementModel: RequirementModel
145-
Test: Test
146-
TestModel: TestModel
147-
}
148-
149204
export class RequirementsAndTestsAstReflection extends langium.AbstractAstReflection {
150205
override readonly types = {
151206
Contact: {

examples/statemachine/src/cli/cli.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import chalk from 'chalk';
88
import { Command } from 'commander';
99
import { NodeFileSystem } from 'langium/node';
1010
import type { Statemachine } from '../language-server/generated/ast.js';
11-
import { StatemachineLanguageMetaData } from '../language-server/generated/module.js';
11+
import { StatemachineModelLanguageMetaData } from '../language-server/generated/module.js';
1212
import { createStatemachineServices } from '../language-server/statemachine-module.js';
1313
import { extractAstNode } from './cli-util.js';
1414
import { generateCpp } from './generator.js';
@@ -18,7 +18,7 @@ import * as path from 'node:path';
1818

1919
export const generateAction = async (fileName: string, opts: GenerateOptions): Promise<void> => {
2020
const services = createStatemachineServices(NodeFileSystem).statemachine;
21-
const statemachine = await extractAstNode<Statemachine>(fileName, StatemachineLanguageMetaData.fileExtensions, services);
21+
const statemachine = await extractAstNode<Statemachine>(fileName, StatemachineModelLanguageMetaData.fileExtensions, services);
2222
const generatedFilePath = generateCpp(statemachine, fileName, opts.destination);
2323
console.log(chalk.green(`C++ code generated successfully: ${generatedFilePath}`));
2424
};
@@ -38,9 +38,9 @@ program.version(JSON.parse(packageContent).version);
3838

3939
program
4040
.command('generate')
41-
.argument('<file>', `possible file extensions: ${StatemachineLanguageMetaData.fileExtensions.join(', ')}`)
41+
.argument('<file>', `possible file extensions: ${StatemachineModelLanguageMetaData.fileExtensions.join(', ')}`)
4242
.option('-d, --destination <dir>', 'destination directory of generating')
4343
.description('generates a C++ CLI to walk over states')
4444
.action(generateAction);
4545

46-
program.parse(process.argv);
46+
program.parse(process.argv);

examples/statemachine/src/language-server/generated/grammar.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,11 @@
66
import type { Grammar } from 'langium';
77
import { loadGrammarFromJson } from 'langium';
88

9-
let loadedStatemachineGrammar: Grammar | undefined;
10-
export const StatemachineGrammar = (): Grammar => loadedStatemachineGrammar ?? (loadedStatemachineGrammar = loadGrammarFromJson(`{
9+
let loadedStatemachineModelGrammar: Grammar | undefined;
10+
export const StatemachineModelGrammar = (): Grammar => loadedStatemachineModelGrammar ?? (loadedStatemachineModelGrammar = loadGrammarFromJson(`{
1111
"$type": "Grammar",
1212
"isDeclared": true,
13-
"name": "Statemachine",
13+
"name": "StatemachineModel",
1414
"rules": [
1515
{
1616
"$type": "ParserRule",

examples/statemachine/src/language-server/generated/module.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@
55

66
import type { LangiumSharedCoreServices, LangiumCoreServices, LangiumGeneratedCoreServices, LangiumGeneratedSharedCoreServices, LanguageMetaData, Module } from 'langium';
77
import { StatemachineAstReflection } from './ast.js';
8-
import { StatemachineGrammar } from './grammar.js';
8+
import { StatemachineModelGrammar } from './grammar.js';
99

10-
export const StatemachineLanguageMetaData = {
10+
export const StatemachineModelLanguageMetaData = {
1111
languageId: 'statemachine',
1212
fileExtensions: ['.statemachine'],
1313
caseInsensitive: false,
@@ -18,8 +18,8 @@ export const StatemachineGeneratedSharedModule: Module<LangiumSharedCoreServices
1818
AstReflection: () => new StatemachineAstReflection()
1919
};
2020

21-
export const StatemachineGeneratedModule: Module<LangiumCoreServices, LangiumGeneratedCoreServices> = {
22-
Grammar: () => StatemachineGrammar(),
23-
LanguageMetaData: () => StatemachineLanguageMetaData,
21+
export const StatemachineModelGeneratedModule: Module<LangiumCoreServices, LangiumGeneratedCoreServices> = {
22+
Grammar: () => StatemachineModelGrammar(),
23+
LanguageMetaData: () => StatemachineModelLanguageMetaData,
2424
parser: {}
2525
};

examples/statemachine/src/language-server/statemachine-module.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
import { type Module, inject } from 'langium';
88
import type { LangiumServices, LangiumSharedServices, PartialLangiumServices } from 'langium/lsp';
99
import { createDefaultModule, createDefaultSharedModule, type DefaultSharedModuleContext } from 'langium/lsp';
10-
import { StatemachineGeneratedModule, StatemachineGeneratedSharedModule } from './generated/module.js';
10+
import { StatemachineGeneratedSharedModule, StatemachineModelGeneratedModule } from './generated/module.js';
1111
import { StatemachineValidator, registerValidationChecks } from './statemachine-validator.js';
1212

1313
/**
@@ -61,7 +61,7 @@ export function createStatemachineServices(context: DefaultSharedModuleContext):
6161
);
6262
const statemachine = inject(
6363
createDefaultModule({ shared }),
64-
StatemachineGeneratedModule,
64+
StatemachineModelGeneratedModule,
6565
StatemachineModule
6666
);
6767
shared.ServiceRegistry.register(statemachine);

examples/statemachine/src/language-server/statemachine.langium

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
grammar Statemachine
1+
grammar StatemachineModel
22

33
/** A textual representation of a state machine */
44
entry Statemachine:

0 commit comments

Comments
 (0)