mirror of
https://github.com/mermaid-js/mermaid.git
synced 2025-09-16 22:09:57 +02:00
feat(parser): create info
parser with exporting parser internals
This commit is contained in:
@@ -3,3 +3,4 @@ export * from './generated/grammar.js';
|
||||
export * from './generated/module.js';
|
||||
|
||||
export * from './common/index.js';
|
||||
export * from './info/index.js';
|
||||
|
1
packages/parser/src/language/info/index.ts
Normal file
1
packages/parser/src/language/info/index.ts
Normal file
@@ -0,0 +1 @@
|
||||
export * from './infoModule.js';
|
9
packages/parser/src/language/info/info.langium
Normal file
9
packages/parser/src/language/info/info.langium
Normal file
@@ -0,0 +1,9 @@
|
||||
grammar Info
|
||||
import "../common/common";
|
||||
|
||||
entry Info:
|
||||
NEWLINE*
|
||||
"info" NEWLINE*
|
||||
("showInfo" NEWLINE*)?
|
||||
TitleAndAccessibilities?
|
||||
;
|
72
packages/parser/src/language/info/infoModule.ts
Normal file
72
packages/parser/src/language/info/infoModule.ts
Normal file
@@ -0,0 +1,72 @@
|
||||
import type {
|
||||
DefaultSharedModuleContext,
|
||||
LangiumServices,
|
||||
LangiumSharedServices,
|
||||
Module,
|
||||
PartialLangiumServices,
|
||||
} from 'langium';
|
||||
import { EmptyFileSystem, createDefaultModule, createDefaultSharedModule, inject } from 'langium';
|
||||
|
||||
import { MermaidGeneratedSharedModule, InfoGeneratedModule } from '../generated/module.js';
|
||||
import { CommonLexer } from '../common/commonLexer.js';
|
||||
import { CommonValueConverter } from '../common/commonValueConverters.js';
|
||||
import { InfoTokenBuilder } from './infoTokenBuilder.js';
|
||||
|
||||
/**
|
||||
* Declaration of `Info` services.
|
||||
*/
|
||||
type InfoAddedServices = {
|
||||
parser: {
|
||||
Lexer: CommonLexer;
|
||||
TokenBuilder: InfoTokenBuilder;
|
||||
ValueConverter: CommonValueConverter;
|
||||
};
|
||||
};
|
||||
|
||||
/**
|
||||
* Union of Langium default services and `Info` services.
|
||||
*/
|
||||
export type InfoServices = LangiumServices & InfoAddedServices;
|
||||
|
||||
/**
|
||||
* Dependency injection module that overrides Langium default services and
|
||||
* contributes the declared `Info` services.
|
||||
*/
|
||||
const InfoModule: Module<InfoServices, PartialLangiumServices & InfoAddedServices> = {
|
||||
parser: {
|
||||
Lexer: (services) => new CommonLexer(services),
|
||||
TokenBuilder: () => new InfoTokenBuilder(),
|
||||
ValueConverter: () => new CommonValueConverter(),
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* Create the full set of services required by Langium.
|
||||
*
|
||||
* First inject the shared services by merging two modules:
|
||||
* - Langium default shared services
|
||||
* - Services generated by langium-cli
|
||||
*
|
||||
* Then inject the language-specific services by merging three modules:
|
||||
* - Langium default language-specific services
|
||||
* - Services generated by langium-cli
|
||||
* - Services specified in this file
|
||||
* @param context - Optional module context with the LSP connection
|
||||
* @returns An object wrapping the shared services and the language-specific services
|
||||
*/
|
||||
export function createInfoServices(context: DefaultSharedModuleContext = EmptyFileSystem): {
|
||||
shared: LangiumSharedServices;
|
||||
Info: InfoServices;
|
||||
} {
|
||||
const shared: LangiumSharedServices = inject(
|
||||
createDefaultSharedModule(context),
|
||||
MermaidGeneratedSharedModule
|
||||
);
|
||||
const Info: InfoServices = inject(
|
||||
createDefaultModule({ shared }),
|
||||
InfoGeneratedModule,
|
||||
InfoModule
|
||||
);
|
||||
shared.ServiceRegistry.register(Info);
|
||||
return { shared, Info };
|
||||
}
|
24
packages/parser/src/language/info/infoTokenBuilder.ts
Normal file
24
packages/parser/src/language/info/infoTokenBuilder.ts
Normal file
@@ -0,0 +1,24 @@
|
||||
import type { GrammarAST, Stream, TokenBuilderOptions } from 'langium';
|
||||
import { DefaultTokenBuilder } from 'langium';
|
||||
|
||||
import type { TokenType } from '../chevrotainWrapper.js';
|
||||
|
||||
export class InfoTokenBuilder extends DefaultTokenBuilder {
|
||||
protected override buildKeywordTokens(
|
||||
rules: Stream<GrammarAST.AbstractRule>,
|
||||
terminalTokens: TokenType[],
|
||||
options?: TokenBuilderOptions
|
||||
): TokenType[] {
|
||||
const tokenTypes: TokenType[] = super.buildKeywordTokens(rules, terminalTokens, options);
|
||||
// to restrict users, they mustn't have any non-whitespace characters after the keyword.
|
||||
tokenTypes.forEach((tokenType: TokenType): void => {
|
||||
if (
|
||||
(tokenType.name === 'info' || tokenType.name === 'showInfo') &&
|
||||
tokenType.PATTERN !== undefined
|
||||
) {
|
||||
tokenType.PATTERN = new RegExp(tokenType.PATTERN.toString() + '(?!\\S)');
|
||||
}
|
||||
});
|
||||
return tokenTypes;
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user