Make Virtual document tracking apply to specific scheme.

This cherry-pick`s commit fcdad6b673 from master

Details of the original fix:
- Also fixed issue where we'd attempt to initialize virtual documents before the project world was ready. This is an issue because virtual documents don't exist as part of the MSBuild piece of the project and therefore would more-often than not get put into the miscellaneous project on the server; resulting in bad IntelliSense.
- Fixed the diagnostic provider to also obey the new `virtualCSharp-*` scheme requirement
- Changed the default change forwarder to ignore virtual documents to ensure that it doesn't try and trigger any changes for them until the server is ready.

OmniSharp/omnisharp-vscode##2538
aspnet/Razor.VSCode#105
This commit is contained in:
Gregg Miskelly 2018-10-02 17:08:16 -07:00
Родитель b708aa160a
Коммит cfc3346306
3 изменённых файлов: 85 добавлений и 26 удалений

Просмотреть файл

@ -15,7 +15,7 @@ function forwardDocumentChanges(server: OmniSharpServer): IDisposable {
return workspace.onDidChangeTextDocument(event => {
let {document} = event;
if (document.isUntitled || document.languageId !== 'csharp') {
if (document.isUntitled || document.languageId !== 'csharp' || document.uri.scheme !== 'file') {
return;
}

Просмотреть файл

@ -11,6 +11,8 @@ import { toRange } from '../omnisharp/typeConvertion';
import * as vscode from 'vscode';
import CompositeDisposable from '../CompositeDisposable';
import { IDisposable } from '../Disposable';
import { isVirtualCSharpDocument } from './virtualDocumentTracker';
import { TextDocument } from '../vscodeAdapter';
export class Advisor {
@ -140,9 +142,11 @@ class DiagnosticsProvider extends AbstractSupport {
// Go ahead and check for diagnostics in the currently visible editors.
for (let editor of vscode.window.visibleTextEditors) {
let document = editor.document;
if (document.languageId === 'csharp') {
this._validateDocument(document);
if (this.shouldIgnoreDocument(document)) {
continue;
}
this._validateDocument(document);
}
}
@ -158,6 +162,19 @@ class DiagnosticsProvider extends AbstractSupport {
this._disposable.dispose();
}
private shouldIgnoreDocument(document: TextDocument) {
if (document.languageId !== 'csharp') {
return true;
}
if (document.uri.scheme !== 'file' &&
!isVirtualCSharpDocument(document)) {
return true;
}
return false;
}
private _OnDidChangeWindowState(windowState: vscode.WindowState): void {
if (windowState.focused === true) {
this._onDidChangeActiveTextEditor(vscode.window.activeTextEditor);
@ -166,16 +183,18 @@ class DiagnosticsProvider extends AbstractSupport {
private _onDidChangeActiveTextEditor(textEditor: vscode.TextEditor): void {
// active text editor can be undefined.
if (textEditor != undefined && textEditor.document != null) {
if (textEditor != undefined && textEditor.document != null) {
this._onDocumentAddOrChange(textEditor.document);
}
}
private _onDocumentAddOrChange(document: vscode.TextDocument): void {
if (document.languageId === 'csharp') {
this._validateDocument(document);
this._validateProject();
if (this.shouldIgnoreDocument(document)) {
return;
}
this._validateDocument(document);
this._validateProject();
}
private _onDocumentRemove(document: vscode.TextDocument): void {

Просмотреть файл

@ -3,8 +3,8 @@
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import {workspace, TextDocument, Uri} from 'vscode';
import {OmniSharpServer} from '../omnisharp/server';
import { workspace, TextDocument, Uri } from 'vscode';
import { OmniSharpServer } from '../omnisharp/server';
import * as serverUtils from '../omnisharp/utils';
import { FileChangeType } from '../omnisharp/protocol';
import { IDisposable } from '../Disposable';
@ -12,18 +12,30 @@ import CompositeDisposable from '../CompositeDisposable';
import { EventStream } from '../EventStream';
import { DocumentSynchronizationFailure } from '../omnisharp/loggingEvents';
function trackCurrentVirtualDocuments(server: OmniSharpServer, eventStream: EventStream) {
let registration = server.onProjectAdded(async () => {
registration.dispose();
async function trackCurrentVirtualDocuments(server: OmniSharpServer, eventStream: EventStream) {
for (let i = 0; i < workspace.textDocuments.length; i++) {
let document = workspace.textDocuments[i];
for (let i = 0; i < workspace.textDocuments.length; i++) {
let document = workspace.textDocuments[i];
if (!shouldIgnoreDocument(document, server)) {
await openVirtualDocument(document, server, eventStream);
}
if (!shouldIgnoreDocument(document, server)) {
await openVirtualDocument(document, server, eventStream);
}
});
}
}
export function isVirtualCSharpDocument(document: TextDocument) {
if (document.languageId !== 'csharp') {
return false;
}
if (document.uri.scheme === 'virtualCSharp-') {
return false;
}
if (!document.uri.scheme.startsWith('virtualCSharp-')) {
return false;
}
return true;
}
function trackFutureVirtualDocuments(server: OmniSharpServer, eventStream: EventStream): IDisposable {
@ -35,6 +47,16 @@ function trackFutureVirtualDocuments(server: OmniSharpServer, eventStream: Event
await openVirtualDocument(document, server, eventStream);
});
let onTextDocumentChange = workspace.onDidChangeTextDocument(async changeEvent => {
const document = changeEvent.document;
if (shouldIgnoreDocument(document, server)) {
return;
}
await changeVirtualDocument(document, server, eventStream);
});
let onTextDocumentClose = workspace.onDidCloseTextDocument(async document => {
if (shouldIgnoreDocument(document, server)) {
return;
@ -42,15 +64,16 @@ function trackFutureVirtualDocuments(server: OmniSharpServer, eventStream: Event
await closeVirtualDocument(document, server, eventStream);
});
// We already track text document changes for virtual documents in our change forwarder.
return new CompositeDisposable(
onTextDocumentOpen,
onTextDocumentClose);
onTextDocumentClose,
onTextDocumentChange);
}
function shouldIgnoreDocument(document: TextDocument, server: OmniSharpServer): boolean {
if (document.uri.scheme === 'file' || document.languageId !== 'csharp') {
if (!isVirtualCSharpDocument(document)) {
// We're only interested in non-physical CSharp documents.
return true;
}
@ -68,10 +91,27 @@ async function openVirtualDocument(document: TextDocument, server: OmniSharpServ
if (!path) {
path = document.uri.path;
}
let req = { FileName: path, changeType: FileChangeType.Create };
try {
await serverUtils.filesChanged(server, [req]);
// Trigger a change for the opening so we can get content refreshed.
await changeVirtualDocument(document, server, eventStream);
}
catch (error) {
logSynchronizationFailure(document.uri, error, server, eventStream);
}
}
async function changeVirtualDocument(document: TextDocument, server: OmniSharpServer, eventStream: EventStream) {
let path = document.uri.fsPath;
if (!path) {
path = document.uri.path;
}
try {
await serverUtils.updateBuffer(server, { Buffer: document.getText(), FileName: document.fileName });
}
catch (error) {
@ -85,7 +125,7 @@ async function closeVirtualDocument(document: TextDocument, server: OmniSharpSer
if (!path) {
path = document.uri.path;
}
let req = { FileName: path, changeType: FileChangeType.Delete };
try {
await serverUtils.filesChanged(server, [req]);
@ -103,7 +143,7 @@ function logSynchronizationFailure(uri: Uri, error: any, server: OmniSharpServer
export default function trackVirtualDocuments(server: OmniSharpServer, eventStream: EventStream): IDisposable {
trackCurrentVirtualDocuments(server, eventStream);
let disposable = trackFutureVirtualDocuments(server, eventStream);
const disposable = trackFutureVirtualDocuments(server, eventStream);
return disposable;
}