Skip to content

Commit fb8bd8e

Browse files
committed
Tryhosting isfs folder-level settings on server
1 parent f127027 commit fb8bd8e

File tree

3 files changed

+89
-18
lines changed

3 files changed

+89
-18
lines changed

src/commands/compile.ts

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -251,18 +251,22 @@ export async function importAndCompile(askFlags = false, document?: vscode.TextD
251251
// console.error(error);
252252
throw error;
253253
})
254-
.then(() => compile([file], flags));
254+
.then(() => {
255+
if (!file.fileName.startsWith("\\.vscode\\")) {
256+
compile([file], flags);
257+
}
258+
});
255259
}
256260

257261
// Compiles all files types in the namespace
258-
export async function namespaceCompile(askFLags = false): Promise<any> {
262+
export async function namespaceCompile(askFlags = false): Promise<any> {
259263
const api = new AtelierAPI();
260264
const fileTypes = ["*.CLS", "*.MAC", "*.INC", "*.BAS"];
261265
if (!config("conn").active) {
262266
throw new Error(`No Active Connection`);
263267
}
264268
const defaultFlags = config().compileFlags;
265-
const flags = askFLags ? await compileFlags() : defaultFlags;
269+
const flags = askFlags ? await compileFlags() : defaultFlags;
266270
if (flags === undefined) {
267271
// User cancelled
268272
return;

src/providers/FileSystemPovider/FileSystemProvider.ts

Lines changed: 51 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import { Directory } from "./Directory";
66
import { File } from "./File";
77
import { fireOtherStudioAction, OtherStudioAction } from "../../commands/studio";
88
import { StudioOpenDialog } from "../../queries";
9+
import { redirectDotvscodeRoot } from "../../utils/index";
910

1011
declare function setTimeout(callback: (...args: any[]) => void, ms: number, ...args: any[]): NodeJS.Timeout;
1112

@@ -61,7 +62,13 @@ export class FileSystemProvider implements vscode.FileSystemProvider {
6162
} else {
6263
filter = "*.cls,*.inc,*.mac,*.int";
6364
}
64-
const folder = csp ? (uri.path.endsWith("/") ? uri.path : uri.path + "/") : uri.path.replace(/\//g, ".");
65+
const folder = !csp
66+
? uri.path.replace(/\//g, ".")
67+
: uri.path === "/"
68+
? ""
69+
: uri.path.endsWith("/")
70+
? uri.path
71+
: uri.path + "/";
6572
const spec = csp ? folder + filter : folder.length > 1 ? folder.slice(1) + "/" + filter : filter;
6673
const dir = "1";
6774
const orderBy = "1";
@@ -72,18 +79,48 @@ export class FileSystemProvider implements vscode.FileSystemProvider {
7279
return api
7380
.actionQuery(sql, [spec, dir, orderBy, system, flat, notStudio, generated])
7481
.then((data) => data.result.content || [])
75-
.then((data) =>
76-
data.map((item: StudioOpenDialog) => {
77-
const name = item.Name;
82+
.then((data) => {
83+
const results = data.map((item: StudioOpenDialog) => {
84+
// Handle how query returns web apps
85+
const name = item.Name.split("/")[0];
7886
const fullName = folder === "" ? name : folder + "/" + name;
7987
if (item.Type === "10" || item.Type === "9") {
8088
parent.entries.set(name, new Directory(name, fullName));
8189
return [name, vscode.FileType.Directory];
8290
} else {
8391
return [name, vscode.FileType.File];
8492
}
85-
})
86-
)
93+
});
94+
if (!csp || results.length) {
95+
return results;
96+
}
97+
//TODO further request(s) to get the next level in CSP app names
98+
// e.g. folder root is isfs://server/?ns=USER&csp
99+
// and USER namespace is the home of /csp/app1 and /csp/app2
100+
// Initial expand showed the csp folder.
101+
// Expand of that came here and asked Studio dialog query for /csp/*
102+
// but this doesn't return app1 and app2 folders.
103+
return api
104+
.actionQuery(sql, ["/*.CSPALL", dir, orderBy, system, flat, notStudio, generated])
105+
.then((data) => data.result.content || [])
106+
.then((data) => {
107+
return results;
108+
/*
109+
const results = data.map((item: StudioOpenDialog) => {
110+
// Handle how query returns web apps
111+
const name = item.Name.split("/")[0];
112+
const fullName = folder === "" ? name : folder + "/" + name;
113+
if (item.Type === "10" || item.Type === "9") {
114+
parent.entries.set(name, new Directory(name, fullName));
115+
return [name, vscode.FileType.Directory];
116+
} else {
117+
return [name, vscode.FileType.File];
118+
}
119+
});
120+
return results;
121+
*/
122+
});
123+
})
87124
.catch((error) => {
88125
error && console.error(error);
89126
});
@@ -138,16 +175,17 @@ export class FileSystemProvider implements vscode.FileSystemProvider {
138175
overwrite: boolean;
139176
}
140177
): void | Thenable<void> {
141-
if (uri.path.match(/\/\.[^/]*\//)) {
178+
uri = redirectDotvscodeRoot(uri);
179+
if (uri.path.startsWith("/.")) {
142180
throw vscode.FileSystemError.NoPermissions("dot-folders not supported by server");
143181
}
182+
const api = new AtelierAPI(uri);
144183
const { query } = url.parse(decodeURIComponent(uri.toString()), true);
145184
const csp = query.csp === "" || query.csp === "1";
146185
const fileName = csp ? uri.path : uri.path.slice(1).replace(/\//g, ".");
147186
if (fileName.startsWith(".")) {
148187
return;
149188
}
150-
const api = new AtelierAPI(uri);
151189
return this._lookupAsFile(uri).then(
152190
() => {
153191
// Weirdly, if the file exists on the server we don't actually write its content here.
@@ -274,15 +312,16 @@ export class FileSystemProvider implements vscode.FileSystemProvider {
274312

275313
// Fetch from server and cache it
276314
private async _lookupAsFile(uri: vscode.Uri): Promise<File> {
277-
// Reject attempts to access files in .-folders such as .vscode and .git
278-
if (uri.path.match(/\/\.[^/]*\//)) {
279-
throw vscode.FileSystemError.FileNotFound("dot-folders not supported by server");
315+
uri = redirectDotvscodeRoot(uri);
316+
if (uri.path.startsWith("/.")) {
317+
throw vscode.FileSystemError.NoPermissions("dot-folders not supported by server");
280318
}
319+
320+
const api = new AtelierAPI(uri);
281321
const { query } = url.parse(decodeURIComponent(uri.toString()), true);
282322
const csp = query.csp === "" || query.csp === "1";
283323
const fileName = csp ? uri.path : uri.path.slice(1).replace(/\//g, ".");
284324
const name = path.basename(uri.path);
285-
const api = new AtelierAPI(uri);
286325
return api
287326
.getDoc(fileName)
288327
.then((data) => data.result)

src/utils/index.ts

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -72,19 +72,20 @@ export function currentFile(document?: vscode.TextDocument): CurrentFile {
7272
!document.fileName ||
7373
!document.languageId ||
7474
!document.languageId.startsWith("objectscript") ||
75-
fileExt.match(/(csp)/i)) // Skip CSP for now, yet
75+
fileExt.match(/(csp)/i)) // Skip local CSPs for now
7676
) {
7777
return null;
7878
}
7979
const eol = document.eol || vscode.EndOfLine.LF;
80-
const uri = document.uri;
80+
const uri = redirectDotvscodeRoot(document.uri);
8181
const content = document.getText();
8282
let name = "";
8383
let ext = "";
8484
const { query } = url.parse(decodeURIComponent(uri.toString()), true);
8585
const csp = query.csp === "" || query.csp === "1";
8686
if (csp) {
87-
name = fileName.replace("\\", "/");
87+
//name = fileName.replace("\\", "/");
88+
name = uri.path;
8889
} else if (fileExt === "cls") {
8990
const match = content.match(/^Class (%?\w+(?:\.\w+)+)/im);
9091
if (match) {
@@ -333,3 +334,30 @@ export async function terminalWithDocker(): Promise<vscode.Terminal> {
333334
terminal.show(true);
334335
return terminal;
335336
}
337+
338+
/**
339+
* Alter isfs-type uri.path of /.vscode/* files or subdirectories.
340+
* Rewrite `/.vscode/path/to/file` as `/_vscode/XYZ/path/to/file`
341+
* where XYZ comes from the `ns` queryparam of uri.
342+
* Also alter query to specify `ns=%SYS&csp=1`
343+
*
344+
* @returns uri, altered if necessary.
345+
* @throws if `ns` queryparam is missing but required.
346+
*/
347+
export function redirectDotvscodeRoot(uri: vscode.Uri): vscode.Uri {
348+
if (!schemas.includes(uri.scheme)) {
349+
return uri;
350+
}
351+
const dotMatch = uri.path.match(/^\/(\.[^/]*)\/(.*)$/);
352+
if (dotMatch && dotMatch[1] === ".vscode") {
353+
const nsMatch = `&${uri.query}&`.match(/&ns=(.+)&/);
354+
if (!nsMatch) {
355+
throw new Error("No 'ns' query parameter on uri");
356+
}
357+
const namespace = nsMatch[1];
358+
const newQueryString = (("&" + uri.query).replace(`ns=${namespace}`, "ns=%SYS") + "&csp=1").slice(1);
359+
return uri.with({ path: `/_vscode/${namespace}/${dotMatch[2]}`, query: newQueryString });
360+
} else {
361+
return uri;
362+
}
363+
}

0 commit comments

Comments
 (0)