Skip to content

Commit bbd4f73

Browse files
author
WebFreak001
committed
Added dfmt checks (fix #20, fix #21)
1 parent 24d1246 commit bbd4f73

File tree

4 files changed

+104
-26
lines changed

4 files changed

+104
-26
lines changed

src/dfmt-check.ts

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
import * as vscode from "vscode"
2+
3+
function getMatchIndices(regex: RegExp, str: string) {
4+
let result: number[] = [];
5+
let match: RegExpExecArray;
6+
while (match = regex.exec(str))
7+
result.push(match.index);
8+
return result;
9+
}
10+
11+
let validDfmt = /\/\/dfmt (off|on)(\n|\s+|$)/;
12+
13+
export function lintDfmt(doc: vscode.TextDocument, code: string) {
14+
let locations = getMatchIndices(/\/\/dfmt/g, code);
15+
let issues: vscode.Diagnostic[] = [];
16+
let isOn: boolean = true;
17+
locations.forEach(location => {
18+
let part = code.substr(location, 11);
19+
let match = validDfmt.exec(part);
20+
if (!match) {
21+
let pos = doc ? doc.positionAt(location) : new vscode.Position(0, 0);
22+
issues.push(new vscode.Diagnostic(new vscode.Range(pos, pos.translate(0, 100)), "Not a valid dfmt command (try //dfmt off or //dfmt on instead)", vscode.DiagnosticSeverity.Warning));
23+
} else {
24+
if (match[1] == "off") {
25+
if (!isOn) {
26+
let pos = doc ? doc.positionAt(location) : new vscode.Position(0, 0);
27+
issues.push(new vscode.Diagnostic(new vscode.Range(pos, pos.translate(0, 10)), "Redundant //dfmt off", vscode.DiagnosticSeverity.Information));
28+
}
29+
isOn = false;
30+
} else {
31+
if (isOn) {
32+
let pos = doc ? doc.positionAt(location) : new vscode.Position(0, 0);
33+
issues.push(new vscode.Diagnostic(new vscode.Range(pos, pos.translate(0, 9)), "Redundant //dfmt on", vscode.DiagnosticSeverity.Information));
34+
}
35+
isOn = true;
36+
}
37+
}
38+
});
39+
return issues;
40+
}

src/extension.ts

Lines changed: 34 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import { uploadCode } from "./util"
66
import * as statusbar from "./statusbar"
77
import * as path from "path"
88
import { DlangUIHandler } from "./dlangui"
9+
import { lintDfmt } from "./dfmt-check"
910

1011
let diagnosticCollection: vscode.DiagnosticCollection;
1112

@@ -21,7 +22,7 @@ export function activate(context: vscode.ExtensionContext) {
2122

2223
let workspaced = new WorkspaceD(vscode.workspace.rootPath);
2324
context.subscriptions.push(vscode.languages.registerCompletionItemProvider(DML_MODE, workspaced.getDlangUI()));
24-
25+
2526
context.subscriptions.push(vscode.languages.registerCompletionItemProvider(D_MODE, workspaced, "."));
2627
context.subscriptions.push(vscode.languages.registerSignatureHelpProvider(D_MODE, workspaced, "(", ","));
2728
context.subscriptions.push(vscode.languages.registerDocumentSymbolProvider(D_MODE, workspaced));
@@ -79,7 +80,7 @@ export function activate(context: vscode.ExtensionContext) {
7980
decreaseIndentPattern: /\}/,
8081
increaseIndentPattern: /\{/
8182
},
82-
83+
8384
wordPattern: /[a-zA-Z_][a-zA-Z0-9_]*/g,
8485

8586
brackets: [
@@ -95,7 +96,34 @@ export function activate(context: vscode.ExtensionContext) {
9596
context.subscriptions.push(diagnosticCollection);
9697

9798
let version;
98-
let oldLint = [[], []];
99+
let writeTimeout;
100+
let oldLint: [vscode.Uri, vscode.Diagnostic[]][][] = [[], [], []];
101+
context.subscriptions.push(vscode.workspace.onDidChangeTextDocument(event => {
102+
clearTimeout(writeTimeout);
103+
writeTimeout = setTimeout(function() {
104+
let document = event.document;
105+
if (document.languageId != "d")
106+
return;
107+
version = document.version;
108+
let target = version;
109+
if (config().get("enableLinting", true)) {
110+
let allErrors: [vscode.Uri, vscode.Diagnostic[]][] = [];
111+
112+
let fresh = true;
113+
let buildErrors = () => {
114+
allErrors = [];
115+
oldLint.forEach(errors => {
116+
allErrors.push.apply(allErrors, errors);
117+
});
118+
diagnosticCollection.set(allErrors);
119+
};
120+
121+
oldLint[2] = [[document.uri, lintDfmt(document, document.getText())]];
122+
buildErrors();
123+
}
124+
}, 500);
125+
}));
126+
99127
context.subscriptions.push(vscode.workspace.onDidSaveTextDocument(document => {
100128
if (document.languageId != "d")
101129
return;
@@ -113,6 +141,8 @@ export function activate(context: vscode.ExtensionContext) {
113141
diagnosticCollection.set(allErrors);
114142
};
115143

144+
oldLint[2] = [[document.uri, lintDfmt(document, document.getText())]];
145+
buildErrors();
116146
workspaced.lint(document).then((errors: [vscode.Uri, vscode.Diagnostic[]][]) => {
117147
if (target == version) {
118148
oldLint[0] = errors;
@@ -196,7 +226,7 @@ export function activate(context: vscode.ExtensionContext) {
196226
vscode.window.showErrorMessage("Could not update imports. dub might not be initialized yet!");
197227
});
198228
}));
199-
229+
200230
context.subscriptions.push(vscode.commands.registerCommand("code-d.insertDscanner", () => {
201231
vscode.window.activeTextEditor.edit((bld) => {
202232
bld.insert(vscode.window.activeTextEditor.selection.start, `; Configurue which static analysis checks are enabled

test/dfmt-check.test.ts

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import * as assert from 'assert';
2+
import * as vscode from 'vscode';
3+
import { lintDfmt } from '../src/dfmt-check';
4+
5+
// Defines a Mocha test suite to group tests of similar kind together
6+
suite("dfmt lint", () => {
7+
test("misspelling on/off", () => {
8+
let linted = lintDfmt(undefined, `void foo() {
9+
//dfmt offs
10+
int i = 5;
11+
//dfmt onf
12+
}`);
13+
assert.strictEqual(linted.length, 2);
14+
assert.strictEqual(linted[0].severity, vscode.DiagnosticSeverity.Warning);
15+
assert.strictEqual(linted[1].severity, vscode.DiagnosticSeverity.Warning);
16+
});
17+
test("redundant on/off", () => {
18+
let linted = lintDfmt(undefined, `void foo() {
19+
//dfmt on
20+
//dfmt off
21+
int i = 5;
22+
//dfmt off
23+
//dfmt ons
24+
}`);
25+
assert.strictEqual(linted.length, 3);
26+
assert.strictEqual(linted[0].severity, vscode.DiagnosticSeverity.Information);
27+
assert.strictEqual(linted[1].severity, vscode.DiagnosticSeverity.Information);
28+
assert.strictEqual(linted[2].severity, vscode.DiagnosticSeverity.Warning);
29+
});
30+
});

test/extension.test.ts

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

0 commit comments

Comments
 (0)