Skip to content

Commit

Permalink
refactor: Make error handling for readdir and stat more explicit.
Browse files Browse the repository at this point in the history
  • Loading branch information
Jackson Dean committed Nov 6, 2019
1 parent e1d1c2d commit fdf985e
Show file tree
Hide file tree
Showing 2 changed files with 51 additions and 20 deletions.
7 changes: 5 additions & 2 deletions packages/@css-blocks/language-server/package.json
Expand Up @@ -6,7 +6,7 @@
"author": "LinkedIn Corporation",
"license": "BSD-2-Clause",
"engines": {
"node": "*"
"node": "10.11.0"
},
"repository": {
"type": "git",
Expand All @@ -33,5 +33,8 @@
"test": "mocha dist/test --opts src/test/mocha.opts",
"test:runner": "mocha dist/test",
"watch": "watch 'yarn run test' './src' --wait=3"
},
"volta": {
"node": "10.11.0"
}
}
}
64 changes: 46 additions & 18 deletions packages/@css-blocks/language-server/src/util/blockUtils.ts
Expand Up @@ -52,12 +52,16 @@ interface PathCompletionCandidateInfo {
stats: fs.Stats;
}

/**
* We only return folders/directories or block files as completion items.
*/
function maybeCompletionItem(completionCandidateInfo: PathCompletionCandidateInfo): CompletionItem | null {
let completionKind: CompletionItemKind | undefined;
let isBlockFile = (candidate: PathCompletionCandidateInfo) => candidate.pathName.indexOf(".block.") >= 0;

if (completionCandidateInfo.stats.isDirectory()) {
completionKind = CompletionItemKind.Folder;
} else if (completionCandidateInfo.stats.isFile() && completionCandidateInfo.pathName.indexOf(".block.") >= 0) {
} else if (completionCandidateInfo.stats.isFile() && isBlockFile(completionCandidateInfo)) {
completionKind = CompletionItemKind.File;
}

Expand All @@ -71,6 +75,30 @@ function maybeCompletionItem(completionCandidateInfo: PathCompletionCandidateInf
return null;
}

async function getFilesInDirectory(directoryPath: string): Promise<string[]> {
try {
return await new Promise((resolve, reject) => {
fs.readdir(directoryPath, (error, fileNames) => {
error ? reject(error) : resolve(fileNames);
});
});
} catch (e) {
return [];
}
}

async function getStatsForFile(filePath: string): Promise<fs.Stats | null> {
try {
return await new Promise((resolve, reject) => {
fs.stat(filePath, (error, stats) => {
error ? reject(error) : resolve(stats);
});
});
} catch (e) {
return null;
}
}

async function getImportPathCompletions(documentUri: string, relativeImportPath: string): Promise<CompletionItem[]> {
let completionItems: CompletionItem[] = [];

Expand All @@ -83,26 +111,26 @@ async function getImportPathCompletions(documentUri: string, relativeImportPath:
let relativeScanDir = relativeImportPath.endsWith(path.sep) ? relativeImportPath : relativeImportPath.substring(0, relativeImportPath.lastIndexOf(path.sep) + 1);
let absoluteScanDir = path.resolve(blockDirPath, relativeScanDir);
let blockFsPath = URI.parse(documentUri).fsPath;
let pathNames: string[] = await new Promise(r => {
fs.readdir(absoluteScanDir, (_, paths) => r(paths || []));
});

let fileInfos: (PathCompletionCandidateInfo | null)[] = await Promise.all(pathNames.map(pathName => {
return new Promise(r => {
let absolutePath = `${absoluteScanDir}/${pathName}`;
fs.stat(absolutePath, (_, stats) => r(
stats ? { pathName: absolutePath, stats } : null,
));
});
}));

return fileInfos.reduce(
(completionItems: CompletionItem[], fileInfo) => {
if (!fileInfo || fileInfo.pathName === blockFsPath) {
let fileNames: string[] = await getFilesInDirectory(absoluteScanDir);

let completionCandidates: (PathCompletionCandidateInfo | null)[] = await Promise.all(
fileNames.map(async (fileName): Promise<PathCompletionCandidateInfo | null> => {
let absolutePath = `${absoluteScanDir}/${fileName}`;
let stats: fs.Stats | null = await getStatsForFile(absolutePath);

return stats ? {
pathName: absolutePath,
stats,
} : null;
}));

return completionCandidates.reduce(
(completionItems: CompletionItem[], candidate) => {
if (!candidate || candidate.pathName === blockFsPath) {
return completionItems;
}

let completionItem = maybeCompletionItem(fileInfo);
let completionItem = maybeCompletionItem(candidate);

if (completionItem) {
completionItems.push(completionItem);
Expand Down

0 comments on commit fdf985e

Please sign in to comment.