-
Notifications
You must be signed in to change notification settings - Fork 796
/
Copy pathgoRename.ts
97 lines (88 loc) · 3.41 KB
/
goRename.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
/* eslint-disable @typescript-eslint/no-explicit-any */
/*---------------------------------------------------------
* Copyright (C) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See LICENSE in the project root for license information.
*--------------------------------------------------------*/
'use strict';
import cp = require('child_process');
import vscode = require('vscode');
import { getGoConfig } from '../../config';
import { Edit, FilePatch, getEditsFromUnifiedDiffStr, isDiffToolAvailable } from '../../diffUtils';
import { toolExecutionEnvironment } from '../../goEnv';
import { promptForMissingTool } from '../../goInstallTools';
import { outputChannel } from '../../goStatus';
import { byteOffsetAt, canonicalizeGOPATHPrefix, getBinPath } from '../../util';
import { killProcessTree } from '../../utils/processUtils';
import { logVerbose } from '../../goLogging';
import { logWarn } from '../../goLogging';
export class GoRenameProvider implements vscode.RenameProvider {
public provideRenameEdits(
document: vscode.TextDocument,
position: vscode.Position,
newName: string,
token: vscode.CancellationToken
): Thenable<vscode.WorkspaceEdit> {
return vscode.workspace.saveAll(false).then(() => {
return this.doRename(document, position, newName, token);
});
}
private doRename(
document: vscode.TextDocument,
position: vscode.Position,
newName: string,
token: vscode.CancellationToken
): Thenable<vscode.WorkspaceEdit> {
return new Promise<vscode.WorkspaceEdit>((resolve, reject) => {
const filename = canonicalizeGOPATHPrefix(document.fileName);
const range = document.getWordRangeAtPosition(position);
const pos = range ? range.start : position;
const offset = byteOffsetAt(document, pos);
const env = toolExecutionEnvironment();
const gorename = getBinPath('gorename');
const buildTags = getGoConfig(document.uri)['buildTags'];
const gorenameArgs = ['-offset', filename + ':#' + offset, '-to', newName];
if (buildTags) {
gorenameArgs.push('-tags', buildTags);
}
const canRenameToolUseDiff = isDiffToolAvailable();
if (canRenameToolUseDiff) {
gorenameArgs.push('-d');
}
// eslint-disable-next-line prefer-const
let p: cp.ChildProcess;
if (token) {
token.onCancellationRequested(() => killProcessTree(p));
}
logWarn(`Support for ${gorename} is deprecated in favor of gopls and will be removed in a future version.`)
logVerbose(`$ ${gorename} ${gorenameArgs} (cwd: ${opts.cwd})`);
p = cp.execFile(gorename, gorenameArgs, { env }, (err, stdout, stderr) => {
try {
if (err && (<any>err).code === 'ENOENT') {
promptForMissingTool('gorename');
return reject('Could not find gorename tool.');
}
if (err) {
const errMsg = stderr ? 'Rename failed: ' + stderr.replace(/\n/g, ' ') : 'Rename failed';
console.log(errMsg);
outputChannel.appendLine(errMsg);
outputChannel.show();
return reject();
}
const result = new vscode.WorkspaceEdit();
if (canRenameToolUseDiff) {
const filePatches = getEditsFromUnifiedDiffStr(stdout);
filePatches.forEach((filePatch: FilePatch) => {
const fileUri = vscode.Uri.file(filePatch.fileName);
filePatch.edits.forEach((edit: Edit) => {
edit.applyUsingWorkspaceEdit(result, fileUri);
});
});
}
return resolve(result);
} catch (e) {
reject(e);
}
});
});
}
}