Skip to content

Commit

Permalink
Adds support for partial paths. Fixes #87
Browse files Browse the repository at this point in the history
  • Loading branch information
mihai-vlc committed Dec 20, 2020
1 parent cb1d6ec commit 256dfda
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 10 deletions.
13 changes: 13 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,18 @@
# Path Autocomplete Change Log

#### 1.17.0
Adds support for partial paths.
Previously the completions were only generated if the path inserted by the user
was a valid folder on the disk.
Starting with this version partial paths are suppored as well.
Examples:
```
./tmp/folder1/ -- generates suggetions
./tmp/fol -- generates suggetions for ./tmp/ and filters out items that don't start with fol
```
This feature fixes: #87


#### 1.16.0
Added new option `path-autocomplete.disableUpOneFolder`. Fixes #89
By default it's set to `true`.
Expand Down
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ Provides path completion for visual studio code.
- it supports absolute path to the workspace (starting with /)
- it supports absolute path to the file system (starts with: C:)
- it supports paths relative to the user folder (starts with ~)
- it supports parial paths (./tmp/fol will suggest ./tmp/folder1 if it exists)
- it supports items exclusions via the `path-autocomplete.excludedItems` option
- it supports npm packages (starting with a-z and not relative to disk)
- it supports automatic suggestion after selecting a folder
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"name": "path-autocomplete",
"displayName": "Path Autocomplete",
"description": "Provides path completion for visual studio code.",
"version": "1.16.0",
"version": "1.17.0",
"publisher": "ionutvmi",
"icon": "icon.png",
"repository": {
Expand Down
55 changes: 46 additions & 9 deletions src/features/PathAutocompleteProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
currentLine: string;
currentPosition: number;
insideString: boolean;
namePrefix: string;

provideCompletionItems(document: vs.TextDocument, position: vs.Position, token: vs.CancellationToken): Thenable<vs.CompletionItem[]> {
var currentLine = document.getText(document.lineAt(position).range);
Expand All @@ -28,6 +29,7 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
this.currentFile = document.fileName;
this.currentLine = currentLine;
this.currentPosition = position.character;
this.namePrefix = this.getNamePrefix();

if (!this.shouldProvide()) {
return Promise.resolve([]);
Expand All @@ -39,9 +41,10 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
return Promise.resolve([]);
}

var result = this.getFolderItems(foldersPath).then((items: FileInfo[]) => {
var folderItems = this.getFolderItems(foldersPath).then((items: FileInfo[]) => {
// build the list of the completion items
var result = items.filter(self.filter, self).map((file) => {

var completion = new vs.CompletionItem(file.getName());

completion.insertText = this.getInsertText(file);
Expand Down Expand Up @@ -77,6 +80,7 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
completion.kind = vs.CompletionItemKind.File;
}


// this is deprecated but still needed for the completion to work
// in json files
completion.textEdit = new vs.TextEdit(new vs.Range(position, position), completion.insertText);
Expand All @@ -92,7 +96,24 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
return Promise.resolve(result);
});

return result;
return folderItems;
}

/**
* Gets the name prefix for the completion item.
* This is used when the path that the user user typed so far
* contains part of the file/folder name
* Examples:
* /folder/Fi
* /folder/subfo
*/
getNamePrefix(): string {
var userPath = this.getUserPath(this.currentLine, this.currentPosition);
if (userPath.endsWith("/") || userPath.endsWith("\\")) {
return "";
}

return path.basename(userPath);
}

/**
Expand Down Expand Up @@ -138,6 +159,10 @@ export class PathAutocomplete implements vs.CompletionItemProvider {

});

if (this.namePrefix) {
insertText = insertText.substr(this.namePrefix.length);
}

return insertText;
}

Expand All @@ -152,23 +177,23 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
if (err) {
return reject(err);
}
var results = [];
var fileResults = [];

items.forEach(item => {
try {
results.push(new FileInfo(path.join(folderPath, item)));
fileResults.push(new FileInfo(path.join(folderPath, item)));
} catch (err) {
// silently ignore permissions errors
}
});

resolve(results);
resolve(fileResults);
});
});
});

return Promise.all(results).then(results => {
return results.reduce((all: string[], currentResults: string[]) => {
return Promise.all(results).then(allResults => {
return allResults.reduce((all: string[], currentResults: string[]) => {
return all.concat(currentResults);
}, []);
});
Expand Down Expand Up @@ -209,6 +234,13 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
.reduce((flat, toFlatten) => {
return flat.concat(toFlatten);
}, [])
// keep only folders
.map((folderPath: string) => {
if (folderPath.endsWith("/") || folderPath.endsWith("\\")) {
return folderPath;
}
return path.dirname(folderPath);
})
// keep only valid paths
.filter(folderPath => {
if (!fs.existsSync(folderPath) || !fs.lstatSync(folderPath).isDirectory()) {
Expand Down Expand Up @@ -265,7 +297,7 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
var rootPath = configuration.data.workspaceFolderPath;

while (currentDir != path.dirname(currentDir)) {
console.log(currentDir);

var candidatePath = path.join(currentDir, 'node_modules');
if (fs.existsSync(candidatePath)) {
return candidatePath;
Expand Down Expand Up @@ -463,6 +495,11 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
return true;
}

// keep only the records that match the name prefix inserted by the user
if (this.namePrefix && (suggestionFile.getName().indexOf(this.namePrefix) != 0)) {
return false;
}

var currentFile = this.currentFile;
var currentLine = this.currentLine;
var valid = true;
Expand All @@ -474,7 +511,7 @@ export class PathAutocomplete implements vs.CompletionItemProvider {
if (!minimatch(currentFile, exclusion.when)) {
return;
}

if (!minimatch(suggestionFile.getPath(), item)) {
return;
}
Expand Down

0 comments on commit 256dfda

Please sign in to comment.