blob: 132ce12f890996d9e43d8bc28ea46a76bcf1933c (
plain)
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
|
import * as vscode from 'vscode';
import SuggestedFix from './SuggestedFix';
/**
* Collection of suggested fixes across multiple documents
*
* This stores `SuggestedFix` model objects and returns them via the
* `vscode.CodeActionProvider` interface.
*/
export default class SuggestedFixCollection
implements vscode.CodeActionProvider {
public static PROVIDED_CODE_ACTION_KINDS = [vscode.CodeActionKind.QuickFix];
/**
* Map of document URI strings to suggested fixes
*/
private suggestedFixes: Map<string, SuggestedFix[]>;
constructor() {
this.suggestedFixes = new Map();
}
/**
* Clears all suggested fixes across all documents
*/
public clear(): void {
this.suggestedFixes = new Map();
}
/**
* Adds a suggested fix for the given diagnostic
*
* Some suggested fixes will appear in multiple diagnostics. For example,
* forgetting a `mut` on a variable will suggest changing the delaration on
* every mutable usage site. If the suggested fix has already been added
* this method will instead associate the existing fix with the new
* diagnostic.
*/
public addSuggestedFixForDiagnostic(
suggestedFix: SuggestedFix,
diagnostic: vscode.Diagnostic
): void {
const fileUriString = suggestedFix.location.uri.toString();
const fileSuggestions = this.suggestedFixes.get(fileUriString) || [];
const existingSuggestion = fileSuggestions.find(s =>
s.isEqual(suggestedFix)
);
if (existingSuggestion) {
// The existing suggestion also applies to this new diagnostic
existingSuggestion.diagnostics.push(diagnostic);
} else {
// We haven't seen this suggestion before
suggestedFix.diagnostics.push(diagnostic);
fileSuggestions.push(suggestedFix);
}
this.suggestedFixes.set(fileUriString, fileSuggestions);
}
/**
* Filters suggested fixes by their document and range and converts them to
* code actions
*/
public provideCodeActions(
document: vscode.TextDocument,
range: vscode.Range
): vscode.CodeAction[] {
const documentUriString = document.uri.toString();
const suggestedFixes = this.suggestedFixes.get(documentUriString);
return (suggestedFixes || [])
.filter(({ location }) => location.range.intersection(range))
.map(suggestedEdit => suggestedEdit.toCodeAction());
}
}
|