提交 f8ad8453 编写于 作者: J Johannes Rieken

Allow executeCodeActionProvider API command to set the number of items to...

Allow executeCodeActionProvider API command to set the number of items to resolve, unit test to check that and the whole resolve machinery
上级 136cc276
......@@ -225,7 +225,7 @@ function getDocumentation(
}
registerLanguageCommand('_executeCodeActionProvider', async function (accessor, args): Promise<ReadonlyArray<modes.CodeAction>> {
const { resource, rangeOrSelection, kind } = args;
const { resource, rangeOrSelection, kind, itemResolveCount } = args;
if (!(resource instanceof URI)) {
throw illegalArgument();
}
......@@ -252,6 +252,17 @@ registerLanguageCommand('_executeCodeActionProvider', async function (accessor,
Progress.None,
CancellationToken.None);
setTimeout(() => codeActionSet.dispose(), 100);
return codeActionSet.validActions.map(item => item.action);
const resolving: Promise<any>[] = [];
const resolveCount = Math.min(codeActionSet.validActions.length, typeof itemResolveCount === 'number' ? itemResolveCount : 0);
for (let i = 0; i < resolveCount; i++) {
resolving.push(codeActionSet.validActions[i].resolve(CancellationToken.None));
}
try {
await Promise.all(resolving);
return codeActionSet.validActions.map(item => item.action);
} finally {
setTimeout(() => codeActionSet.dispose(), 100);
}
});
......@@ -282,6 +282,8 @@ export class ExtHostApiCommands {
{ name: 'uri', description: 'Uri of a text document', constraint: URI },
{ name: 'rangeOrSelection', description: 'Range in a text document. Some refactoring provider requires Selection object.', constraint: types.Range },
{ name: 'kind', description: '(optional) Code action kind to return code actions for', constraint: (value: any) => !value || typeof value.value === 'string' },
{ name: 'itemResolveCount', description: '(optional) Number of code actions to resolve (too large numbers slow down code actions)', constraint: (value: any) => value === undefined || typeof value === 'number' }
],
returns: 'A promise that resolves to an array of Command-instances.'
});
......@@ -436,13 +438,14 @@ export class ExtHostApiCommands {
}
private _executeCodeActionProvider(resource: URI, rangeOrSelection: types.Range | types.Selection, kind?: string): Promise<(vscode.CodeAction | vscode.Command | undefined)[] | undefined> {
private _executeCodeActionProvider(resource: URI, rangeOrSelection: types.Range | types.Selection, kind?: string, itemResolveCount?: number): Promise<(vscode.CodeAction | vscode.Command | undefined)[] | undefined> {
const args = {
resource,
rangeOrSelection: types.Selection.isSelection(rangeOrSelection)
? typeConverters.Selection.from(rangeOrSelection)
: typeConverters.Range.from(rangeOrSelection),
kind
kind,
itemResolveCount,
};
return this._commands.executeCommand<CustomCodeAction[]>('_executeCodeActionProvider', args)
.then(tryMapWith(codeAction => {
......
......@@ -1612,7 +1612,7 @@ export class ExtHostLanguageFeatures implements extHostProtocol.ExtHostLanguageF
kind: x.kind.value,
command: this._commands.converter.toInternal(x.command, store),
}))
}, ExtHostLanguageFeatures._extLabel(extension), Boolean(extension.enableProposedApi && provider.resolveCodeAction));
}, ExtHostLanguageFeatures._extLabel(extension), Boolean(provider.resolveCodeAction));
store.add(this._createDisposable(handle));
return store;
}
......
......@@ -925,6 +925,38 @@ suite('ExtHostLanguageFeatureCommands', function () {
});
});
test('resolving code action', async function () {
let didCallResolve = 0;
class MyAction extends types.CodeAction { }
disposables.push(extHost.registerCodeActionProvider(nullExtensionDescription, defaultSelector, {
provideCodeActions(document, rangeOrSelection): vscode.CodeAction[] {
return [new MyAction('title', types.CodeActionKind.Empty.append('foo'))];
},
resolveCodeAction(action): vscode.CodeAction {
assert.ok(action instanceof MyAction);
didCallResolve += 1;
action.title = 'resolved title';
action.edit = new types.WorkspaceEdit();
return action;
}
}));
const selection = new types.Selection(0, 0, 1, 1);
await rpcProtocol.sync();
const value = await commands.executeCommand<vscode.CodeAction[]>('vscode.executeCodeActionProvider', model.uri, selection, undefined, 1000);
assert.equal(didCallResolve, 1);
assert.equal(value.length, 1);
const [first] = value;
assert.equal(first.title, 'title'); // does NOT change
assert.ok(first.edit); // is set
});
// --- code lens
test('CodeLens, back and forth', function () {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册