Skip to content

Commit 3186ac4

Browse files
committed
feat: add simple filepath validation to all ini files
Add a new FileServer service. It provides lists of all valid filepaths in open the workspace directories. Populate this list on activation of the Language Server. Register new change watcher and file sync for all valid file types. Add `vscode-uri` as a dependency to resolve paths.
1 parent e5be6a8 commit 3186ac4

File tree

6 files changed

+103
-28
lines changed

6 files changed

+103
-28
lines changed

package-lock.json

Lines changed: 9 additions & 3 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@
5252
"type": "string",
5353
"default": ".",
5454
"description": "The path to the Cortex Command game directory. Required if developing the mod outside the game directory.",
55-
"format": "uri"
55+
"format": "string"
5656
}
5757
}
5858
},
@@ -140,6 +140,7 @@
140140
"vscode-languageclient": "^7.0.0",
141141
"vscode-languageserver": "^7.0.0",
142142
"vscode-languageserver-textdocument": "^1.0.8",
143-
"vscode-test": "^1.6.1"
143+
"vscode-test": "^1.6.1",
144+
"vscode-uri": "^3.0.7"
144145
}
145146
}

packages/client/src/extension.ts

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
'use strict';
66

77
import * as path from 'path';
8-
import { ExtensionContext, window as Window } from 'vscode';
8+
import { ExtensionContext, window as Window, workspace } from 'vscode';
99
import {
1010
LanguageClient,
1111
LanguageClientOptions,
@@ -35,7 +35,11 @@ export function activate(context: ExtensionContext): void {
3535
documentSelector: [{ scheme: 'file', language: 'ccini' }],
3636
revealOutputChannelOn: RevealOutputChannelOn.Error,
3737
progressOnInitialization: true,
38-
38+
synchronize: {
39+
fileEvents: workspace.createFileSystemWatcher(
40+
'**/*.{ini,txt,lua,cfg,bmp,png,jpg,jpeg,wav,ogg,mp3,flac}'
41+
),
42+
},
3943
};
4044

4145
let client: LanguageClient;

packages/server/src/sampleServer.ts

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import {
1212
Diagnostic,
1313
DiagnosticSeverity,
1414
DidChangeConfigurationNotification,
15+
DidChangeWatchedFilesNotification,
1516
InitializeParams,
1617
InitializeResult,
1718
Position,
@@ -29,6 +30,7 @@ import {
2930
CortexCommandLanguageSupportConfiguration,
3031
} from './services/configuration.service';
3132
import { validateFilePaths } from './validations/validateFilePath';
33+
import { fileSystemService } from './services/fs.service';
3234

3335
const connection = createConnection(ProposedFeatures.all);
3436

@@ -66,6 +68,13 @@ connection.onInitialize((params: InitializeParams): InitializeResult => {
6668
},
6769
};
6870

71+
if (configService.hasWorkspaceFolderCapability && params.workspaceFolders) {
72+
fileSystemService.registerWorkspaces(params.workspaceFolders);
73+
fileSystemService.fileList.forEach((file) => {
74+
connection.console.log(file);
75+
});
76+
}
77+
6978
if (configService.hasWorkspaceFolderCapability) {
7079
result.capabilities.workspace = {
7180
workspaceFolders: {
@@ -85,6 +94,9 @@ connection.onInitialized(() => {
8594
undefined
8695
);
8796
}
97+
98+
connection.client.register(DidChangeWatchedFilesNotification.type);
99+
88100
if (configService.hasWorkspaceFolderCapability) {
89101
connection.workspace.onDidChangeWorkspaceFolders((_event) => {
90102
connection.console.log('Workspace folder change event received.');
@@ -106,6 +118,12 @@ connection.onDidChangeConfiguration((change) => {
106118
documents.all().forEach(validate);
107119
});
108120

121+
connection.onDidChangeWatchedFiles((change) => {
122+
change.changes.forEach((change) => {
123+
connection.console.log(change.type.toString() + change.uri);
124+
});
125+
});
126+
109127
function validate(document: TextDocument): void {
110128
const diagnostics = validateFilePaths(document);
111129

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
import { readdirSync, statSync } from 'fs';
2+
import { join, relative } from 'path';
3+
import { WorkspaceFolder } from 'vscode-languageserver';
4+
import { URI } from 'vscode-uri';
5+
6+
class FileSystemService {
7+
public fileList: string[] = [];
8+
9+
public registerWorkspaces(workspaces: WorkspaceFolder[]) {
10+
workspaces.forEach((folder) => {
11+
const workspacePath = URI.parse(folder.uri).fsPath;
12+
const workspaceFileList = this.getAllFiles(workspacePath);
13+
14+
for (const file of workspaceFileList) {
15+
this.fileList.push(relative(workspacePath, file));
16+
}
17+
});
18+
}
19+
20+
// public init(rootUri: URI): void {
21+
// this.fileList = this.getAllFiles(rootUri);
22+
// }
23+
24+
private getAllFiles(dirPath: string): string[] {
25+
const files = readdirSync(dirPath);
26+
27+
const fileList: string[] = [];
28+
29+
files.forEach((file) => {
30+
if (statSync(dirPath + '/' + file).isDirectory()) {
31+
fileList.push(...this.getAllFiles(join(dirPath, file)));
32+
} else {
33+
fileList.push(join(dirPath, file));
34+
}
35+
});
36+
37+
return fileList;
38+
}
39+
}
40+
41+
export const fileSystemService: FileSystemService = new FileSystemService();

packages/server/src/validations/validateFilePath.ts

Lines changed: 26 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
1+
import { normalize } from 'path';
12
import { Diagnostic, DiagnosticSeverity } from 'vscode-languageserver';
23
import { TextDocument } from 'vscode-languageserver-textdocument';
34
import { configService } from '../services/configuration.service';
5+
import { fileSystemService } from '../services/fs.service';
46

57
export function validateFilePaths(textDocument: TextDocument): Diagnostic[] {
68
// In this simple example we get the settings for every validate run.
@@ -18,29 +20,32 @@ export function validateFilePaths(textDocument: TextDocument): Diagnostic[] {
1820
(m = pattern.exec(text)) &&
1921
problems < configService.globalSettings.maxNumberOfProblems
2022
) {
21-
problems++;
22-
const diagnostic: Diagnostic = {
23-
severity: DiagnosticSeverity.Error,
24-
range: {
25-
start: textDocument.positionAt(m.index + m[1].length),
26-
end: textDocument.positionAt(m.index + m[0].length),
27-
},
28-
message: `Cannot find the file ${m[2]}`,
29-
source: 'CC Language Features',
30-
};
31-
if (configService.hasDiagnosticRelatedInformationCapability) {
32-
diagnostic.relatedInformation = [
33-
{
34-
location: {
35-
uri: textDocument.uri,
36-
range: Object.assign({}, diagnostic.range),
37-
},
38-
message:
39-
'This may be due to a bad file extension/path, or incorrect capitalization.',
23+
const normalizedPath = normalize(m[2]);
24+
if (!fileSystemService.fileList.includes(normalizedPath)) {
25+
problems++;
26+
const diagnostic: Diagnostic = {
27+
severity: DiagnosticSeverity.Error,
28+
range: {
29+
start: textDocument.positionAt(m.index + m[1].length),
30+
end: textDocument.positionAt(m.index + m[0].length),
4031
},
41-
];
32+
message: `Cannot find the file ${m[2]}`,
33+
source: 'CC Language Features',
34+
};
35+
if (configService.hasDiagnosticRelatedInformationCapability) {
36+
diagnostic.relatedInformation = [
37+
{
38+
location: {
39+
uri: textDocument.uri,
40+
range: Object.assign({}, diagnostic.range),
41+
},
42+
message:
43+
'This may be due to a bad file extension/path, or incorrect capitalization.',
44+
},
45+
];
46+
}
47+
diagnostics.push(diagnostic);
4248
}
43-
diagnostics.push(diagnostic);
4449
}
4550

4651
// Send the computed diagnostics to VSCode.

0 commit comments

Comments
 (0)