Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reload and update MSBuild projects in response to dotnet restore #1003

Merged
merged 11 commits into from
Nov 6, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
namespace OmniSharp.Models.FilesChanged
namespace OmniSharp.FileWatching
{
public enum FileChangeType
{
Expand Down
14 changes: 14 additions & 0 deletions src/OmniSharp.Abstractions/FileWatching/IFileSystemNotifier.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
using OmniSharp.Models.FilesChanged;

namespace OmniSharp.FileWatching
{
public interface IFileSystemNotifier
{
/// <summary>
/// Notifiers any relevant file system watchers when a file is created, changed, or deleted.
/// </summary>
/// <param name="filePath">The path to the file that was changed.</param>
/// <param name="changeType">The type of change. Hosts are not required to pass a change type.</param>
void Notify(string filePath, FileChangeType changeType = FileChangeType.Unspecified);
}
}
18 changes: 7 additions & 11 deletions src/OmniSharp.Abstractions/FileWatching/IFileSystemWatcher.cs
Original file line number Diff line number Diff line change
@@ -1,20 +1,16 @@
using System;
using OmniSharp.Models.FilesChanged;
using OmniSharp.Models.FilesChanged;

namespace OmniSharp.FileWatching
{
// TODO: Flesh out this API more
public delegate void FileSystemNotificationCallback(string filePath, FileChangeType changeType);

public interface IFileSystemWatcher
{
void Watch(string path, Action<string, FileChangeType> callback);

/// <summary>
/// Called when a file is created, changed, or deleted.
/// Call to watch a file or directory path for changes.
/// </summary>
/// <param name="path">The path to the file</param>
/// <param name="changeType">The type of change. Hosts are not required to pass a change type</param>
void TriggerChange(string path, FileChangeType changeType);

void WatchDirectory(string path, Action<string, FileChangeType> callback);
/// <param name="fileOrDirectoryPath">The file or directory path to watch.</param>
/// <param name="callback">The callback that will be invoked when a change occurs in the watched file or directory.</param>
void Watch(string fileOrDirectoryPath, FileSystemNotificationCallback callback);
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using System.Collections.Generic;
using OmniSharp.FileWatching;
using OmniSharp.Mef;

namespace OmniSharp.Models.FilesChanged
Expand Down
1 change: 1 addition & 0 deletions src/OmniSharp.Host/CompositionHostBuilder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ public CompositionHost Build()

config = config
.WithProvider(MefValueProvider.From(_serviceProvider))
.WithProvider(MefValueProvider.From<IFileSystemNotifier>(fileSystemWatcher))
.WithProvider(MefValueProvider.From<IFileSystemWatcher>(fileSystemWatcher))
.WithProvider(MefValueProvider.From(memoryCache))
.WithProvider(MefValueProvider.From(loggerFactory))
Expand Down
50 changes: 27 additions & 23 deletions src/OmniSharp.Host/FileWatching/ManualFileSystemWatcher.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,39 +5,43 @@

namespace OmniSharp.FileWatching
{
public class ManualFileSystemWatcher : IFileSystemWatcher
internal class ManualFileSystemWatcher : IFileSystemWatcher, IFileSystemNotifier
{
private readonly Dictionary<string, Action<string, FileChangeType>> _callbacks = new Dictionary<string, Action<string, FileChangeType>>();
private readonly Dictionary<string, Action<string, FileChangeType>> _directoryCallBacks = new Dictionary<string, Action<string, FileChangeType>>();
private readonly object _gate = new object();
private readonly Dictionary<string, FileSystemNotificationCallback> _callbacks;

public void TriggerChange(string path, FileChangeType changeType)
public ManualFileSystemWatcher()
{
if (_callbacks.TryGetValue(path, out var callback))
{
callback(path, changeType);
}

var directoryPath = Path.GetDirectoryName(path);
if (_directoryCallBacks.TryGetValue(directoryPath, out var fileCallback))
{
fileCallback(path, changeType);
}
_callbacks = new Dictionary<string, FileSystemNotificationCallback>(StringComparer.OrdinalIgnoreCase);
}

public void Watch(string path, Action<string, FileChangeType> callback)
public void Notify(string filePath, FileChangeType changeType = FileChangeType.Unspecified)
{
_callbacks[path] = callback;
lock (_gate)
{
if (_callbacks.TryGetValue(filePath, out var fileCallback))
{
fileCallback(filePath, changeType);
}

var directoryPath = Path.GetDirectoryName(filePath);
if (_callbacks.TryGetValue(directoryPath, out var directoryCallback))
{
directoryCallback(filePath, changeType);
}
}
}

public void WatchDirectory(string path, Action<string, FileChangeType> callback)
public void Watch(string fileOrDirectoryPath, FileSystemNotificationCallback callback)
{
if (_directoryCallBacks.TryGetValue(path, out var existingCallback))
lock (_gate)
{
_directoryCallBacks[path] = callback + existingCallback;
}
else
{
_directoryCallBacks[path] = callback;
if (_callbacks.TryGetValue(fileOrDirectoryPath, out var existingCallback))
{
callback = callback + existingCallback;
}

_callbacks[fileOrDirectoryPath] = callback;
}
}
}
Expand Down
43 changes: 43 additions & 0 deletions src/OmniSharp.MSBuild/Logging/MSBuildDiagnostic.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
namespace OmniSharp.MSBuild.Logging
{
public class MSBuildDiagnostic
{
public MSBuildDiagnosticSeverity Severity { get; }
public string Message { get; }
public string File { get; }
public string ProjectFile { get; }
public string Subcategory { get; }
public string Code { get; }
public int LineNumber { get; }
public int ColumnNumber { get; }
public int EndLineNumber { get; }
public int EndColumnNumber { get; }

private MSBuildDiagnostic(
MSBuildDiagnosticSeverity severity,
string message, string file, string projectFile, string subcategory, string code,
int lineNumber, int columnNumber, int endLineNumber, int endColumnNumber)
{
Severity = severity;
Message = message;
File = file;
ProjectFile = projectFile;
Subcategory = subcategory;
Code = code;
LineNumber = lineNumber;
ColumnNumber = columnNumber;
EndLineNumber = endLineNumber;
EndColumnNumber = endColumnNumber;
}

public static MSBuildDiagnostic CreateFrom(Microsoft.Build.Framework.BuildErrorEventArgs args)
=> new MSBuildDiagnostic(MSBuildDiagnosticSeverity.Error,
args.Message, args.File, args.ProjectFile, args.Subcategory, args.Code,
args.LineNumber, args.ColumnNumber, args.EndLineNumber, args.EndColumnNumber);

public static MSBuildDiagnostic CreateFrom(Microsoft.Build.Framework.BuildWarningEventArgs args)
=> new MSBuildDiagnostic(MSBuildDiagnosticSeverity.Error,
args.Message, args.File, args.ProjectFile, args.Subcategory, args.Code,
args.LineNumber, args.ColumnNumber, args.EndLineNumber, args.EndColumnNumber);
}
}
8 changes: 8 additions & 0 deletions src/OmniSharp.MSBuild/Logging/MSBuildDiagnosticSeverity.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
namespace OmniSharp.MSBuild.Logging
{
public enum MSBuildDiagnosticSeverity
{
Error,
Warning
}
}
39 changes: 39 additions & 0 deletions src/OmniSharp.MSBuild/Logging/MSBuildLogger.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
using System.Collections.Generic;
using System.Collections.Immutable;
using Microsoft.Extensions.Logging;

namespace OmniSharp.MSBuild.Logging
{
internal class MSBuildLogger : Microsoft.Build.Utilities.Logger
{
private readonly ILogger _logger;
private readonly List<MSBuildDiagnostic> _diagnostics;

public MSBuildLogger(ILogger logger)
{
_logger = logger;
_diagnostics = new List<MSBuildDiagnostic>();
}

public override void Initialize(Microsoft.Build.Framework.IEventSource eventSource)
{
eventSource.ErrorRaised += OnError;
eventSource.WarningRaised += OnWarning;
}

public ImmutableArray<MSBuildDiagnostic> GetDiagnostics() =>
_diagnostics.ToImmutableArray();

private void OnError(object sender, Microsoft.Build.Framework.BuildErrorEventArgs args)
{
_logger.LogError(args.Message);
_diagnostics.Add(MSBuildDiagnostic.CreateFrom(args));
}

private void OnWarning(object sender, Microsoft.Build.Framework.BuildWarningEventArgs args)
{
_logger.LogWarning(args.Message);
_diagnostics.Add(MSBuildDiagnostic.CreateFrom(args));
}
}
}
77 changes: 0 additions & 77 deletions src/OmniSharp.MSBuild/MSBuildLogForwarder.cs

This file was deleted.

Loading