I’m trying to create a simple vscode extension that will insert some default text into a newly created file. What I want is for the vscode.workspace.createFileSystemWatcher
to call a function that gets the activeTextEditor
and writes to the new file. Here is what I’ve tried:
import * as vscode from "vscode";
export function activate(context: vscode.ExtensionContext) {
let disposable = vscode.commands.registerCommand(
"default-text-generator.generate",
() => {
function _watcherChangeApplied(editor?: vscode.TextEditor) {
if (editor) {
editor.edit((editBuilder) => {
editBuilder.insert(editor.selection.active, "Hello World");
});
}
}
const editor = vscode.window.activeTextEditor;
let uri: vscode.Uri | undefined = editor?.document.uri;
if (uri) {
let watcher = vscode.workspace.createFileSystemWatcher(
new vscode.RelativePattern(
vscode.workspace.getWorkspaceFolder(uri)!,
"**/*.ts"
),
false,
false,
false
);
watcher.onDidCreate(() => _watcherChangeApplied(editor));
}
}
);
context.subscriptions.push(disposable);
}
// this method is called when your extension is deactivated
export function deactivate(): void {
//deactivate
}
Here’s what’s happening. The editor seems to insert the text, then immediately gets overwritten back to a blank page. I can’t seem to figure out why.
2
Answers
The problem happens because the
editor
you are referring to is not what you think to be. It is not the newly created editor but instead, the editor that you are focused/active when the new.ts
file is created.The
FileSystemWatcher.onDidCreate
event provides you aUri
to the newly created file inside your workspace, but not necessarily opened in VS Code. Try creating a file via terminal and you will see what I mean. The file is created, the event is fired, but no editor is opened in VS Code.So, you won’t be able to use the
editor.edit
API to manipulate the file. Instead, you should edit the file using RAW/Node functions. But, in this case, maybe/probably you will clash with the external tool that is creating the.ts
file (which may not be VS Code, if you use the FileWatcher). If only files created via VS Code must be detected, you should change to theworkspace.onDidCreateFiles
event instead. But yet, it also only provides you theUri
, not theEditor
.Hope this helps
This works:
The key point is that
watcher.onDidCreate()
will return the uri of the newly created file. You can pass that to your_watcherChangeApplied(uri)
function.In
_watcherChangeApplied(uri)
you can show the created file viaawait vscode.window.showTextDocument(uri)
and that function returns aneditor
that you can use with itsedit
functions.The code works whether you create the file within vscode (like the
New File...
icon button at the top of the explorer) or via the terminal (liketouch test.ts
).If you want to enable creating new files through the terminal, for example, and NOT open them, try this
_watcherChangeApplied(uri)
: