Skip to content

Client-side improvements #1470

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 14 additions & 6 deletions src/commands/compile.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,16 @@ import {
exportedUris,
handleError,
isClassDeployed,
isClassOrRtn,
notIsfs,
notNull,
outputChannel,
RateLimiter,
routineNameTypeRegex,
throttleRequests,
} from "../utils";
import { StudioActions } from "./studio";
import { NodeBase, PackageNode, RootNode } from "../explorer/nodes";
import { updateIndexForDocument } from "../utils/documentIndex";

async function compileFlags(): Promise<string> {
const defaultFlags = config().compileFlags;
Expand Down Expand Up @@ -226,6 +228,10 @@ export async function loadChanges(files: (CurrentTextFile | CurrentBinaryFile)[]
file.uri,
Buffer.isBuffer(content) ? content : new TextEncoder().encode(content.join("\n"))
);
if (isClassOrRtn(file.uri)) {
// Update the document index
updateIndexForDocument(file.uri, undefined, undefined, content);
}
exportedUris.push(file.uri.toString());
} else if (filesystemSchemas.includes(file.uri.scheme)) {
fileSystemProvider.fireFileChanged(file.uri);
Expand Down Expand Up @@ -414,9 +420,10 @@ export async function namespaceCompile(askFlags = false): Promise<any> {

async function importFiles(files: vscode.Uri[], noCompile = false) {
const toCompile: CurrentFile[] = [];
const rateLimiter = new RateLimiter(50);
await Promise.allSettled<void>(
files.map(
throttleRequests((uri: vscode.Uri) => {
files.map((uri) =>
rateLimiter.call(async () => {
return vscode.workspace.fs
.readFile(uri)
.then((contentBytes) => {
Expand Down Expand Up @@ -661,7 +668,7 @@ export async function importLocalFilesToServerSideFolder(wsFolderUri: vscode.Uri
return;
}
// Filter out non-ISC files
uris = uris.filter((uri) => ["cls", "mac", "int", "inc"].includes(uri.path.split(".").pop().toLowerCase()));
uris = uris.filter(isClassOrRtn);
if (uris.length == 0) {
vscode.window.showErrorMessage("No classes or routines were selected.", "Dismiss");
return;
Expand Down Expand Up @@ -711,9 +718,10 @@ export async function importLocalFilesToServerSideFolder(wsFolderUri: vscode.Uri
docs.map((e) => e.name)
);
// Import the files
const rateLimiter = new RateLimiter(50);
return Promise.allSettled<string>(
docs.map(
throttleRequests((doc: { name: string; content: string; uri: vscode.Uri }) => {
docs.map((doc) =>
rateLimiter.call(async () => {
// Allow importing over deployed classes since the XML import
// command and SMP, terminal, and Studio imports allow it
return importFileFromContent(doc.name, doc.content, api, false, true).then(() => {
Expand Down
44 changes: 19 additions & 25 deletions src/commands/export.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,19 @@ import { AtelierAPI } from "../api";
import { config, explorerProvider, OBJECTSCRIPT_FILE_SCHEMA, schemas, workspaceState } from "../extension";
import {
currentFile,
currentFileFromContent,
exportedUris,
handleError,
isClassOrRtn,
notNull,
outputChannel,
RateLimiter,
stringifyError,
throttleRequests,
uriOfWorkspaceFolder,
workspaceFolderOfUri,
} from "../utils";
import { pickDocuments } from "../utils/documentPicker";
import { NodeBase } from "../explorer/nodes";
import { updateIndexForDocument } from "../utils/documentIndex";

export function getCategory(fileName: string, addCategory: any | boolean): string {
const fileExt = fileName.split(".").pop().toLowerCase();
Expand Down Expand Up @@ -99,28 +101,19 @@ async function exportFile(wsFolderUri: vscode.Uri, namespace: string, name: stri
throw new Error("Received malformed JSON object from server fetching document");
}
const content = data.result.content;

// Local function to update local record of mtime
const recordMtime = async () => {
const contentString = Buffer.isBuffer(content) ? "" : content.join("\n");
const file = currentFileFromContent(fileUri, contentString);
const serverTime = Number(new Date(data.result.ts + "Z"));
await workspaceState.update(`${file.uniqueId}:mtime`, serverTime);
};
if (Buffer.isBuffer(content)) {
// This is a binary file
await vscode.workspace.fs.writeFile(fileUri, content);
exportedUris.push(fileUri.toString());
await recordMtime();
log("Success");
} else {
// This is a text file
const joinedContent = content.join("\n");
await vscode.workspace.fs.writeFile(fileUri, new TextEncoder().encode(joinedContent));
exportedUris.push(fileUri.toString());
await recordMtime();
log("Success");
await vscode.workspace.fs.writeFile(
fileUri,
Buffer.isBuffer(content) ? content : new TextEncoder().encode(content.join("\n"))
);
if (isClassOrRtn(fileUri)) {
// Update the document index
updateIndexForDocument(fileUri, undefined, undefined, content);
}
exportedUris.push(fileUri.toString());
const ws = workspaceFolderOfUri(fileUri);
const mtime = Number(new Date(data.result.ts + "Z"));
if (ws) await workspaceState.update(`${ws}:${name}:mtime`, mtime > 0 ? mtime : undefined);
log("Success");
} catch (error) {
const errorStr = stringifyError(error);
log(errorStr == "" ? "ERROR" : errorStr);
Expand All @@ -146,6 +139,7 @@ export async function exportList(files: string[], workspaceFolder: string, names
const { atelier, folder, addCategory, map } = config("export", workspaceFolder);
const root = wsFolderUri.fsPath + (folder.length ? path.sep + folder : "");
outputChannel.show(true);
const rateLimiter = new RateLimiter(50);
return vscode.window.withProgress(
{
title: `Exporting ${files.length == 1 ? files[0] : files.length + " documents"}`,
Expand All @@ -154,8 +148,8 @@ export async function exportList(files: string[], workspaceFolder: string, names
},
() =>
Promise.allSettled<void>(
files.map(
throttleRequests((file: string) =>
files.map((file) =>
rateLimiter.call(() =>
exportFile(wsFolderUri, namespace, file, getFileName(root, file, atelier, addCategory, map))
)
)
Expand Down
3 changes: 2 additions & 1 deletion src/extension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,7 @@ import {
cspApps,
otherDocExts,
getWsServerConnection,
isClassOrRtn,
addWsServerRootFolderData,
} from "./utils";
import { ObjectScriptDiagnosticProvider } from "./providers/ObjectScriptDiagnosticProvider";
Expand Down Expand Up @@ -1220,7 +1221,7 @@ export async function activate(context: vscode.ExtensionContext): Promise<any> {
return Promise.all(
e.files
.filter(notIsfs)
.filter((uri) => ["cls", "inc", "int", "mac"].includes(uri.path.split(".").pop().toLowerCase()))
.filter(isClassOrRtn)
.map(async (uri) => {
// Determine the file name
const workspace = workspaceFolderOfUri(uri);
Expand Down
4 changes: 2 additions & 2 deletions src/providers/DocumentContentProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { AtelierAPI } from "../api";

import { getFileName } from "../commands/export";
import { config, FILESYSTEM_SCHEMA, FILESYSTEM_READONLY_SCHEMA, OBJECTSCRIPT_FILE_SCHEMA } from "../extension";
import { currentWorkspaceFolder, notIsfs, uriOfWorkspaceFolder } from "../utils";
import { currentWorkspaceFolder, isClassOrRtn, notIsfs, uriOfWorkspaceFolder } from "../utils";
import { getUrisForDocument } from "../utils/documentIndex";

export function compareConns(
Expand Down Expand Up @@ -52,7 +52,7 @@ export class DocumentContentProvider implements vscode.TextDocumentContentProvid
if (!notIsfs(wsFolder.uri)) return;
const conf = vscode.workspace.getConfiguration("objectscript.export", wsFolder);
const confFolder = conf.get("folder", "");
if (["cls", "mac", "int", "inc"].includes(name.split(".").pop().toLowerCase())) {
if (isClassOrRtn(name)) {
// Use the document index to find the local URI
const uris = getUrisForDocument(name, wsFolder);
switch (uris.length) {
Expand Down
13 changes: 7 additions & 6 deletions src/providers/FileSystemProvider/TextSearchProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { makeRe } from "minimatch";
import { AsyncSearchRequest, SearchResult, SearchMatch } from "../../api/atelier";
import { AtelierAPI } from "../../api";
import { DocumentContentProvider } from "../DocumentContentProvider";
import { handleError, notNull, outputChannel, throttleRequests } from "../../utils";
import { handleError, notNull, outputChannel, RateLimiter } from "../../utils";
import { config } from "../../extension";
import { fileSpecFromURI } from "../../utils/FileProviderUtil";

Expand Down Expand Up @@ -280,6 +280,7 @@ export class TextSearchProvider implements vscode.TextSearchProvider {
const api = new AtelierAPI(options.folder);
const params = new URLSearchParams(options.folder.query);
const decoder = new TextDecoder();
const rateLimiter = new RateLimiter(50);
let counter = 0;
if (!api.enabled) {
return {
Expand Down Expand Up @@ -470,7 +471,7 @@ export class TextSearchProvider implements vscode.TextSearchProvider {
return api.verifiedCancel(id, false);
}
// Process matches
filePromises.push(...pollResp.result.map(throttleRequests(reportMatchesForFile)));
filePromises.push(...pollResp.result.map((file) => rateLimiter.call(() => reportMatchesForFile(file))));
if (pollResp.retryafter) {
await new Promise((resolve) => {
setTimeout(resolve, 50);
Expand Down Expand Up @@ -524,8 +525,8 @@ export class TextSearchProvider implements vscode.TextSearchProvider {
requestGroups.push(group);
}
searchPromise = Promise.allSettled(
requestGroups.map(
throttleRequests((group: string[]) =>
requestGroups.map((group) =>
rateLimiter.call(() =>
api
.actionSearch({
query: pattern,
Expand Down Expand Up @@ -628,8 +629,8 @@ export class TextSearchProvider implements vscode.TextSearchProvider {
return;
}
const resultsPromise = Promise.allSettled(
files.map(
throttleRequests(async (file: SearchResult): Promise<void> => {
files.map((file) =>
rateLimiter.call(() => {
if (token.isCancellationRequested) {
return;
}
Expand Down
Loading