Skip to content

Commit

Permalink
Modify file path mapping so that it works on windows
Browse files Browse the repository at this point in the history
  • Loading branch information
dibarbet committed Sep 24, 2022
1 parent f3c35eb commit e8a86d3
Show file tree
Hide file tree
Showing 5 changed files with 108 additions and 14 deletions.
52 changes: 50 additions & 2 deletions src/OmniSharp.WebAssembly/CompilerLoggerPathRemapper.cs
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
using System;
using System.Composition;

using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;


namespace OmniSharp.WebAssembly;

[Export(typeof(IPathRemapper)), Shared]
internal class CompilerLoggerPathRemapper : IPathRemapper
public class CompilerLoggerPathRemapper : IPathRemapper
{
private readonly string _compilerLogBasePath;
private readonly string _workspaceBasePath;
Expand All @@ -24,6 +26,52 @@ public CompilerLoggerPathRemapper(IServiceProvider serviceProvider)

public string Remap(string path)
{
return path.Replace(_workspaceBasePath, _compilerLogBasePath);
return Remap(path, _workspaceBasePath, _compilerLogBasePath);
}

public static string Remap(string path, string workspacePath, string compilerLogBasePath)
{
var inputPathParts = GetPathParts(path);
var workspacePathParts = GetPathParts(workspacePath);

for (var i = 0; i < workspacePathParts.Length; i++)
{
if (i > inputPathParts.Length)
{
// input path is shorter than the base workspace path.
return path;
}

// VSCode gives paths on windows like 'c:\workspace\file.txt' while the input path to the workspace
// will usually be uppercase drive letter. We don't know what platform we're on, so we just do a
// case insensitive comparison and hope for the best.
if (!string.Equals(workspacePathParts[i], inputPathParts[i], StringComparison.OrdinalIgnoreCase))
{
// input path doesn't match workspace path.
return path;
}
}

var startingIndex = workspacePathParts.Length;

// If the input path has no more parts remaining its the same and we can just return it.
if (startingIndex > inputPathParts.Length - 1)
{
return path;
}

var remaining = inputPathParts[workspacePathParts.Length..];
// input path begins with workspace base path.
// combine the compilerLogBasePath with the remaining input path parts.
// Note that the compiler log could have been generated on a different platform with
// different directory separators, so use whatever it uses as thats what we need to match to in the workspace.
var directorySeparator = compilerLogBasePath.Contains(@"\") ? @"\" : @"/";
var remapped = $"{compilerLogBasePath}{directorySeparator}{string.Join(directorySeparator, remaining)}";
return remapped;
}

private static string[] GetPathParts(string path)
{
return path.Split(new string[] { @"\", @"/" }, StringSplitOptions.RemoveEmptyEntries);
}
}
2 changes: 2 additions & 0 deletions src/OmniSharp.WebAssembly/Host.cs
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,8 @@ public static async Task<string> InitializeAsync(byte[] compilerLogBytes, string
CompilerLoggerProjectSystem.CompilerLogBytes = compilerLogBytes;
var configurationResult = new ConfigurationBuilder(environment).Build((builder) =>
{
// Json serialization thinks backslashes in windows file paths are escapes so we need to escape them.
workspaceBasePath = workspaceBasePath.Replace(@"\", @"\\");
var jsonOptions =
$@"{{
""CompilerLogger"": {{
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
using System.ComponentModel.DataAnnotations;

using Microsoft.AspNetCore.Components.Forms;

namespace TestWithWebAssembly.Client;

public class InitializationOptions
{
[Required]
public string? WorkspacePath { get; set; }

[Required]
public IBrowserFile? CompilerLog { get; set; }
}
51 changes: 39 additions & 12 deletions tests/WebAssembly/TestWithWebAssembly/Pages/Index.razor
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,36 @@

<PageTitle>Index</PageTitle>

<h1>Hello, world!</h1>
<h2><u>Initialize Server</u></h2>

<InputFile OnChange="@LoadFiles" multiple />
<EditForm Model="@initializationOptions" OnValidSubmit="@HandleValidInitializeAsync">
<DataAnnotationsValidator />
<ValidationSummary />

<EditForm Model="@inputText" OnValidSubmit="@HandleValidSubmit">
<DataAnnotationsValidator />
<ValidationSummary />
Choose compiler log<br />
<InputFile accept=".compilerlog" OnChange="@LoadFiles" />
<br />
<InputText id="workspacePath" placeholder="Workspace path" @bind-Value="initializationOptions.WorkspacePath" />
<br />
<br />
<button type="submit" disabled="@(IsServerRunning)">@(IsServerRunning ? "Already started" : "Initialize server")</button>
</EditForm>
<br />

<InputText id="requestJson" @bind-Value="inputText.RequestJson" />
<h2><u>Send Request</u></h2>

<button type="submit" disabled="@(!IsServerRunning)">@(!IsServerRunning ? "Waiting for start..." : "Run request")</button>
</EditForm>
<EditForm Model="@inputText" OnValidSubmit="@HandleSubmitRequest">
<DataAnnotationsValidator />
<ValidationSummary />

<InputText id="requestJson" placeholder="Request json" @bind-Value="inputText.RequestJson" />
<br />
<br />
<button type="submit" disabled="@(!IsServerRunning)">@(!IsServerRunning ? "Waiting for start..." : "Run request")</button>
</EditForm>
<br />

<h2><u>Server Logs</u></h2>

<p>
@foreach (var line in Text)
Expand All @@ -31,6 +49,8 @@

@code
{
private InitializationOptions initializationOptions = new();

private InputJsonRequest inputText = new();

public bool IsServerRunning = false;
Expand All @@ -46,20 +66,27 @@
return Task.CompletedTask;
}

private async Task LoadFiles(InputFileChangeEventArgs e)
private Task LoadFiles(InputFileChangeEventArgs e)
{
initializationOptions.CompilerLog = e.File;
return Task.CompletedTask;
}

private async Task HandleValidInitializeAsync()
{
_logger.LogInformation("Initializing server...");
var memoryStream = new MemoryStream();
var stream = e.File.OpenReadStream(maxAllowedSize: 2147483648);
var stream = initializationOptions.CompilerLog!.OpenReadStream(maxAllowedSize: 2147483648);
await stream.CopyToAsync(memoryStream);
var response = await OmniSharp.WebAssembly.Program.InitializeAsync(memoryStream.ToArray(), "/home/fred/git/wasm-test", new StreamReader(new MemoryStream()), new RazorLogger(this, "Output"), _loggerProvider!);
var response = await OmniSharp.WebAssembly.Program.InitializeAsync(memoryStream.ToArray(), initializationOptions.WorkspacePath!, new StreamReader(new MemoryStream()), new RazorLogger(this, "Output"), _loggerProvider!);
if (response == "done")
{
IsServerRunning = true;
}
new RazorLogger(this, "Result").LogInformation(response);
}

private Task HandleValidSubmit()
private Task HandleSubmitRequest()
{
_logger.LogInformation("Submitting request");
return OmniSharp.WebAssembly.Program.InvokeRequestAsync(inputText.RequestJson!);
Expand Down
3 changes: 3 additions & 0 deletions tests/WebAssembly/TestWithoutWebAssembly/Program.cs
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
using OmniSharp.Services;
using OmniSharp.WebAssembly;

namespace TestWebAssemblyDriver;

internal class Program
{
static async Task Main(string[] args)
{
var result = CompilerLoggerPathRemapper.Remap(@"c:\workspace\a\b\test.txt", @"C:\workspace\", @"/home/workspace");

var compilerLogBytes = File.ReadAllBytes(@"/home/fred/Downloads/msbuild.compilerlog");
var response = await OmniSharp.WebAssembly.Program.InitializeAsync(compilerLogBytes, "/home/fred/git/wasm-test", Console.In, new SharedTextWriter(Console.Out));
Console.WriteLine(response);
Expand Down

0 comments on commit e8a86d3

Please sign in to comment.