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

Modify file path mapping so that it works on windows #12

Open
wants to merge 1 commit into
base: feature/webassembly
Choose a base branch
from
Open
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
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)
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

haven't really tested on unix (or done a lot of validation on this). Might not be right, but hopeuflly describes the problems well

{
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