Skip to content

Commit cfd482d

Browse files
committed
Refactor and fix error highlighting
1 parent a33a303 commit cfd482d

31 files changed

+24725
-6472
lines changed

.vscode/settings.json

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"cSpell.words": ["ANTLR"]
3+
}

server/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
},
1010
"type": "module",
1111
"scripts": {
12-
"generate-core-dts": "rimraf src/parser/core/grammar/Bitloops*.ts && node --experimental-vm-modules node_modules/typescript/bin/tsc src/parser/core/grammar/Bitloops*js --declaration --emitDeclarationOnly --allowJs --outDir src/parser/core/grammar && node_modules/prettier/bin-prettier.js --config .prettierrc --write src/parser/core/grammar/*.d.ts",
12+
"generate-core-dts": "rimraf src/parser/grammar/Bitloops*.ts && node --experimental-vm-modules node_modules/typescript/bin/tsc src/parser/grammar/Bitloops*js --declaration --emitDeclarationOnly --allowJs --outDir src/parser/grammar && node_modules/prettier/bin-prettier.js --config .prettierrc --write src/parser/grammar/*.d.ts",
1313
"ant": "yarn antlr4 -listener -visitor -Dlanguage=JavaScript src/parser/grammar/BitloopsLexer.g4 && yarn antlr4 -listener -visitor -Dlanguage=JavaScript src/parser/grammar/BitloopsParser.g4 && yarn generate-core-dts",
1414
"antlr4": "java -jar /usr/local/lib/antlr-4.10.1-complete.jar"
1515
},

server/src/analyzer.ts

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@ import { components } from './types/keywords.js';
66
import { getMatchRange } from './utils/regex.js';
77

88
export interface IAnalyzer {
9+
/**
10+
* It analyzes the document and returns a list of diagnostics.
11+
*/
912
analyze(document: TextDocument): Diagnostic[];
1013
}
1114

@@ -29,7 +32,11 @@ export class RegexAnalyzer implements IAnalyzer {
2932
const pattern = new RegExp(`(${componentUnion})(?!\\s*\\w)`);
3033
const match = pattern.exec(document.getText());
3134
if (match) {
32-
const useCaseSyntacError = DiagnosticFactory.create(1, getMatchRange(document, match), EErrors.NoIdentifier);
35+
const useCaseSyntacError = DiagnosticFactory.create(
36+
1,
37+
getMatchRange(document, match),
38+
EErrors.NoIdentifier,
39+
);
3340
// console.log(useCaseSyntacError);
3441
return [useCaseSyntacError];
3542
}

server/src/completion.ts

Lines changed: 13 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,22 @@
1-
import { CompletionItem, CompletionItemKind, TextDocumentPositionParams } from 'vscode-languageserver/node.js';
1+
import {
2+
CompletionItem,
3+
CompletionItemKind,
4+
TextDocumentPositionParams,
5+
} from 'vscode-languageserver/node.js';
26
import { documentation } from './information/documentation.js';
37
import { details } from './information/details.js';
48
import { components } from './types/keywords.js';
59

6-
export class BitloopsCompletionItemProvider {
7-
// constructor(connection: Connection) {
8-
// super();
9-
// }
10+
export class CompletionItemProvider {
1011
public static onCompletion(_textDocumentPosition: TextDocumentPositionParams) {
11-
const keywords = BitloopsCompletionItemProvider.completeKeyword();
12-
return keywords;
12+
const keywordsList = Object.keys(components);
13+
return keywordsList.map((symbol) => ({
14+
label: symbol,
15+
kind: CompletionItemKind.Keyword,
16+
data: 1,
17+
}));
1318
}
19+
1420
public static onCompletionResolve(item: CompletionItem): CompletionItem {
1521
const label: string = item.label;
1622
if (documentation[item.label as keyof typeof documentation]) {
@@ -22,15 +28,4 @@ export class BitloopsCompletionItemProvider {
2228

2329
return item;
2430
}
25-
26-
private static completeKeyword(): CompletionItem[] {
27-
const keywordsList = Object.keys(components);
28-
return keywordsList.map((symbol) => {
29-
return {
30-
label: symbol,
31-
kind: CompletionItemKind.Keyword,
32-
data: 1,
33-
};
34-
});
35-
}
3631
}

server/src/diagnostic.ts

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,25 @@
11
import { Diagnostic, DiagnosticSeverity, Range, TextDocument } from 'vscode-languageserver/node.js';
22

3+
export enum LogLevel {
4+
Error = 1,
5+
Warn = 2,
6+
Info = 3,
7+
Log = 4,
8+
}
9+
310
export class DiagnosticFactory {
411
public static create(
5-
severity: 1 | 2 | 3 | 4,
12+
severity: LogLevel,
613
range: Range,
714
message: string,
8-
addRelatedInformation?: string[]
15+
addRelatedInformation?: string[],
916
): Diagnostic {
1017
message = this.prefixMessage(message, severity);
1118
const diagnostic: Diagnostic = {
12-
severity: severity,
13-
range: range,
14-
message: message,
15-
source: 'ex',
19+
severity,
20+
range,
21+
message,
22+
source: 'bl',
1623
};
1724
if (addRelatedInformation) {
1825
diagnostic.relatedInformation = [];
@@ -29,7 +36,7 @@ export class DiagnosticFactory {
2936
}
3037
return diagnostic;
3138
}
32-
public static prefixMessage(message: string, severity: 1 | 2 | 3 | 4) {
39+
public static prefixMessage(message: string, severity: LogLevel) {
3340
switch (severity) {
3441
case 1:
3542
return `Error: ${message}`;

server/src/index.ts

Lines changed: 2 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,3 @@
1-
import {
2-
createConnection,
3-
DidChangeConfigurationNotification,
4-
InitializeParams,
5-
InitializeResult,
6-
ProposedFeatures,
7-
TextDocumentSyncKind,
8-
} from 'vscode-languageserver/node.js';
9-
import { BitloopsServer } from './server.js';
10-
let hasConfigurationCapability = false;
11-
let hasWorkspaceFolderCapability = false;
12-
let hasDiagnosticRelatedInformationCapability = false;
1+
import { LspConnection } from './lsp-connection.js';
132

14-
const connection = createConnection(ProposedFeatures.all);
15-
connection.onInitialize(onInitialize);
16-
connection.onInitialized(onInitialized);
17-
const server = new BitloopsServer(
18-
connection,
19-
hasConfigurationCapability,
20-
hasWorkspaceFolderCapability,
21-
hasDiagnosticRelatedInformationCapability
22-
);
23-
server.register();
24-
25-
function onInitialize(params: InitializeParams): InitializeResult {
26-
const capabilities = params.capabilities;
27-
hasConfigurationCapability = !!(capabilities.workspace && !!capabilities.workspace.configuration);
28-
hasWorkspaceFolderCapability = !!(capabilities.workspace && !!capabilities.workspace.workspaceFolders);
29-
hasDiagnosticRelatedInformationCapability = !!(
30-
capabilities.textDocument &&
31-
capabilities.textDocument.publishDiagnostics &&
32-
capabilities.textDocument.publishDiagnostics.relatedInformation
33-
);
34-
35-
const result: InitializeResult = {
36-
capabilities: {
37-
textDocumentSync: TextDocumentSyncKind.Incremental,
38-
// Tell the client that this server supports code completion.
39-
completionProvider: {
40-
resolveProvider: true,
41-
},
42-
},
43-
};
44-
if (hasWorkspaceFolderCapability) {
45-
result.capabilities.workspace = {
46-
workspaceFolders: {
47-
supported: true,
48-
},
49-
};
50-
}
51-
return result;
52-
}
53-
function onInitialized() {
54-
if (hasConfigurationCapability) {
55-
// Register for all configuration changes.
56-
connection.client.register(DidChangeConfigurationNotification.type, undefined);
57-
}
58-
if (hasWorkspaceFolderCapability) {
59-
connection.workspace.onDidChangeWorkspaceFolders((_event) => {
60-
connection.console.log('Workspace folder change event received.');
61-
});
62-
}
63-
}
3+
new LspConnection().registerLspEvents().listen();

server/src/linter.ts

Lines changed: 0 additions & 26 deletions
This file was deleted.

server/src/lsp-client.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import * as lsp from 'vscode-languageserver';
2+
3+
export interface ILspClient {
4+
publishDiagnostics(args: lsp.PublishDiagnosticsParams): void;
5+
}
6+
7+
export class LspClientImpl implements ILspClient {
8+
constructor(protected connection: lsp.Connection) {}
9+
10+
publishDiagnostics(params: lsp.PublishDiagnosticsParams): void {
11+
this.connection.sendDiagnostics(params);
12+
}
13+
}

server/src/lsp-connection.ts

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
import {
2+
createConnection,
3+
TextDocuments,
4+
ProposedFeatures,
5+
_Connection,
6+
} from 'vscode-languageserver/node.js';
7+
8+
import { TextDocument } from 'vscode-languageserver-textdocument';
9+
import { LspClientImpl } from './lsp-client.js';
10+
import { BitloopsServer } from './server.js';
11+
12+
export class LspConnection {
13+
private connection: _Connection;
14+
private server: BitloopsServer;
15+
16+
protected documents: TextDocuments<TextDocument>;
17+
constructor() {
18+
this.documents = new TextDocuments(TextDocument);
19+
this.connection = createConnection(ProposedFeatures.all);
20+
const lspClient = new LspClientImpl(this.connection);
21+
22+
this.server = new BitloopsServer(lspClient, this.connection);
23+
}
24+
25+
public registerLspEvents() {
26+
const server = this.server;
27+
this.connection.onInitialize(server.onInitialize.bind(server));
28+
this.connection.onInitialized(server.onInitialized.bind(server));
29+
30+
this.documents.onDidClose(server.onDidClose.bind(server));
31+
this.documents.onDidChangeContent(server.onDidChangeContent.bind(server));
32+
this.connection.onCompletion(server.completion.bind(server));
33+
this.connection.onCompletionResolve(server.completionResolve.bind(server));
34+
return this;
35+
}
36+
37+
// Listen on the connection
38+
public listen() {
39+
this.documents.listen(this.connection);
40+
this.connection.listen();
41+
}
42+
}

server/src/parser/errorListener.ts

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
import antlr from 'antlr4';
2+
import Recognizer from 'antlr4/Recognizer.js';
3+
import { DiagnosticFactory } from '../diagnostic.js';
4+
import { ANTLR4Analyzer } from './index.js';
5+
// import { ErrorListener } from 'antlr4/error';
6+
7+
export class VerboseListener extends (antlr as any).error.ErrorListener {
8+
syntaxError = (
9+
_recognizer: Recognizer.default,
10+
offendingToken: any,
11+
line: number,
12+
column: number,
13+
msg: string,
14+
_e: any,
15+
) => {
16+
// const stack: any = recognizer.getTokenErrorDisplay(offendingSymbol);
17+
// console.log("rule stack: "+stack);
18+
console.log(`line: ${line}:${column}, offendingSymbol : ${offendingToken.text}, msg: ${msg}`);
19+
const start = offendingToken.start;
20+
const stop = offendingToken.stop;
21+
console.log(`start: ${start}, stop: ${stop}`);
22+
// let range = new Range(error.line - 1, error.startColumn, error.line - 1, error.endColumn);
23+
24+
const diagnostic = DiagnosticFactory.create(
25+
1,
26+
{
27+
start,
28+
end: stop,
29+
},
30+
`line: ${line}:${column}, offendingSymbol : ${offendingToken.text}, msg: ${msg}`,
31+
);
32+
ANTLR4Analyzer.diagnostics.push(diagnostic);
33+
};
34+
}

0 commit comments

Comments
 (0)