diff --git a/src/clients/Wyam/App.config b/src/clients/Wyam/App.config index a9da260dd..7c7483e7f 100644 --- a/src/clients/Wyam/App.config +++ b/src/clients/Wyam/App.config @@ -81,6 +81,18 @@ + + + + + + + + + + + + diff --git a/src/clients/Wyam/PreviewServer.cs b/src/clients/Wyam/PreviewServer.cs index bb39ccda5..461fc7324 100644 --- a/src/clients/Wyam/PreviewServer.cs +++ b/src/clients/Wyam/PreviewServer.cs @@ -1,15 +1,16 @@ using System; using System.Collections.Generic; -using System.IO; + using Microsoft.Owin; using Microsoft.Owin.FileSystems; -using Microsoft.Owin.Hosting; -using Microsoft.Owin.Hosting.Tracing; using Microsoft.Owin.StaticFiles; + using Owin; + using Wyam.Common.IO; using Wyam.Common.Tracing; using Wyam.Owin; +using Wyam.Server; namespace Wyam { @@ -17,57 +18,11 @@ internal static class PreviewServer { public static IDisposable Start(DirectoryPath path, int port, bool forceExtension, DirectoryPath virtualDirectory) { - IDisposable server; + HttpServer server; try { - StartOptions options = new StartOptions("http://localhost:" + port); - - // Disable built-in owin tracing by using a null trace output - // http://stackoverflow.com/questions/17948363/tracelistener-in-owin-self-hosting - options.Settings.Add(typeof(ITraceOutputFactory).FullName, typeof(NullTraceOutputFactory).AssemblyQualifiedName); - - server = WebApp.Start(options, app => - { - Microsoft.Owin.FileSystems.IFileSystem outputFolder = new PhysicalFileSystem(path.FullPath); - - // Support for virtual directory - if (virtualDirectory != null) - { - app.UseVirtualDirectory(virtualDirectory.FullPath); - } - - // Disable caching - app.Use((c, t) => - { - c.Response.Headers.Append("Cache-Control", "no-cache, no-store, must-revalidate"); - c.Response.Headers.Append("Pragma", "no-cache"); - c.Response.Headers.Append("Expires", "0"); - return t(); - }); - - // Support for extensionless URLs - if (!forceExtension) - { - app.UseExtensionlessUrls(new ExtensionlessUrlsOptions - { - FileSystem = outputFolder - }); - } - - // Serve up all static files - app.UseDefaultFiles(new DefaultFilesOptions - { - RequestPath = PathString.Empty, - FileSystem = outputFolder, - DefaultFileNames = new List { "index.html", "index.htm", "home.html", "home.htm", "default.html", "default.html" } - }); - app.UseStaticFiles(new StaticFileOptions - { - RequestPath = PathString.Empty, - FileSystem = outputFolder, - ServeUnknownFileTypes = true - }); - }); + server = new HttpServer(); + server.StartServer(port, app => ConfigureOwin(app, path, forceExtension, virtualDirectory)); } catch (Exception ex) { @@ -76,16 +31,51 @@ public static IDisposable Start(DirectoryPath path, int port, bool forceExtensio } Trace.Information($"Preview server listening on port {port} and serving from path {path}" - + (virtualDirectory == null ? string.Empty : $" with virtual directory {virtualDirectory.FullPath}")); + + (virtualDirectory == null ? string.Empty : $" with virtual directory {virtualDirectory.FullPath}")); return server; } - private class NullTraceOutputFactory : ITraceOutputFactory + internal static void ConfigureOwin(IAppBuilder app, DirectoryPath path, bool forceExtension, DirectoryPath virtualDirectory) { - public TextWriter Create(string outputFile) + Microsoft.Owin.FileSystems.IFileSystem outputFolder = new PhysicalFileSystem(path.FullPath); + + // Support for virtual directory + if (virtualDirectory != null) { - return StreamWriter.Null; + app.UseVirtualDirectory(virtualDirectory.FullPath); } + + // Disable caching + app.Use((c, t) => + { + c.Response.Headers.Append("Cache-Control", "no-cache, no-store, must-revalidate"); + c.Response.Headers.Append("Pragma", "no-cache"); + c.Response.Headers.Append("Expires", "0"); + return t(); + }); + + // Support for extensionless URLs + if (!forceExtension) + { + app.UseExtensionlessUrls(new ExtensionlessUrlsOptions + { + FileSystem = outputFolder + }); + } + + // Serve up all static files + app.UseDefaultFiles(new DefaultFilesOptions + { + RequestPath = PathString.Empty, + FileSystem = outputFolder, + DefaultFileNames = new List {"index.html", "index.htm", "home.html", "home.htm", "default.html", "default.html"} + }); + app.UseStaticFiles(new StaticFileOptions + { + RequestPath = PathString.Empty, + FileSystem = outputFolder, + ServeUnknownFileTypes = true + }); } } } \ No newline at end of file diff --git a/src/clients/Wyam/Program.cs b/src/clients/Wyam/Program.cs index 5e9c77cb8..3e16bf685 100644 --- a/src/clients/Wyam/Program.cs +++ b/src/clients/Wyam/Program.cs @@ -8,8 +8,6 @@ using System.Threading; using Microsoft.Owin; using Microsoft.Owin.FileSystems; -using Microsoft.Owin.Hosting; -using Microsoft.Owin.Hosting.Tracing; using Microsoft.Owin.StaticFiles; using Owin; using Wyam.Commands; @@ -45,7 +43,7 @@ private static void UnhandledExceptionEvent(object sender, UnhandledExceptionEve private int Run(string[] args) { // Add a default trace listener - Trace.AddListener(new SimpleColorConsoleTraceListener { TraceOutputOptions = System.Diagnostics.TraceOptions.None }); + Trace.AddListener(new SimpleColorConsoleTraceListener { TraceOutputOptions = TraceOptions.None }); // Output version info Trace.Information($"Wyam version {Engine.Version}"); diff --git a/src/clients/Wyam/Server/ApplicationBuilderExtensions.cs b/src/clients/Wyam/Server/ApplicationBuilderExtensions.cs new file mode 100644 index 000000000..269c36cb2 --- /dev/null +++ b/src/clients/Wyam/Server/ApplicationBuilderExtensions.cs @@ -0,0 +1,36 @@ +using System; +using System.Collections.Generic; +using System.Threading.Tasks; + +using Microsoft.AspNetCore.Builder; +using Microsoft.Owin.Builder; + +using Owin; + +namespace Wyam.Server +{ + internal static class ApplicationBuilderExtensions + { + // http://stackoverflow.com/a/30742029/2001966 + + public static void UseOwinBuilder(this IApplicationBuilder app, Action owinConfiguration) + { + app.UseOwin( + addToPipeline => + { + addToPipeline( + next => + { + AppBuilder builder = new AppBuilder(); + owinConfiguration(builder); + builder.Run(ctx => next(ctx.Environment)); + + // ReSharper disable once SuggestVarOrType_Elsewhere + var appFunc = (Func, Task>) builder.Build(typeof(Func, Task>)); + + return appFunc; + }); + }); + } + } +} \ No newline at end of file diff --git a/src/clients/Wyam/Server/HttpServer.cs b/src/clients/Wyam/Server/HttpServer.cs new file mode 100644 index 000000000..9be7c340f --- /dev/null +++ b/src/clients/Wyam/Server/HttpServer.cs @@ -0,0 +1,36 @@ +using System; + +using Microsoft.AspNetCore.Builder; +using Microsoft.AspNetCore.Hosting; + +using Owin; + +namespace Wyam.Server +{ + internal class HttpServer : IDisposable + { + private IWebHost _host; + + public void StartServer(int port, Action owinConfiguration) + { + _host = new WebHostBuilder() + .UseKestrel() + .UseUrls($"http://localhost:{port}") + .Configure(builder => + { + // Enable websocket support + builder.UseWebSockets(); + + // Support drop-in replacement + builder.UseOwinBuilder(owinConfiguration); + }) + .Build(); + _host.Start(); + } + + public void Dispose() + { + _host?.Dispose(); + } + } +} \ No newline at end of file diff --git a/src/clients/Wyam/Wyam.csproj b/src/clients/Wyam/Wyam.csproj index 79f71d0a3..7506e77f9 100644 --- a/src/clients/Wyam/Wyam.csproj +++ b/src/clients/Wyam/Wyam.csproj @@ -49,6 +49,84 @@ 4 + + ..\..\..\packages\Microsoft.AspNetCore.Hosting.1.1.0\lib\net451\Microsoft.AspNetCore.Hosting.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Hosting.Abstractions.1.1.0\lib\net451\Microsoft.AspNetCore.Hosting.Abstractions.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Hosting.Server.Abstractions.1.1.0\lib\net451\Microsoft.AspNetCore.Hosting.Server.Abstractions.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Http.1.1.0\lib\net451\Microsoft.AspNetCore.Http.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Http.Abstractions.1.1.0\lib\net451\Microsoft.AspNetCore.Http.Abstractions.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Http.Extensions.1.1.0\lib\net451\Microsoft.AspNetCore.Http.Extensions.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Http.Features.1.1.0\lib\net451\Microsoft.AspNetCore.Http.Features.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Owin.1.1.0\lib\net451\Microsoft.AspNetCore.Owin.dll + + + ..\..\..\packages\Microsoft.AspNetCore.Server.Kestrel.1.1.0\lib\net451\Microsoft.AspNetCore.Server.Kestrel.dll + + + ..\..\..\packages\Microsoft.AspNetCore.WebSockets.1.0.0\lib\net451\Microsoft.AspNetCore.WebSockets.dll + + + ..\..\..\packages\Microsoft.AspNetCore.WebUtilities.1.1.0\lib\net451\Microsoft.AspNetCore.WebUtilities.dll + + + ..\..\..\packages\Microsoft.Extensions.Configuration.1.1.0\lib\netstandard1.1\Microsoft.Extensions.Configuration.dll + + + ..\..\..\packages\Microsoft.Extensions.Configuration.Abstractions.1.1.0\lib\netstandard1.0\Microsoft.Extensions.Configuration.Abstractions.dll + + + ..\..\..\packages\Microsoft.Extensions.Configuration.EnvironmentVariables.1.1.0\lib\net451\Microsoft.Extensions.Configuration.EnvironmentVariables.dll + + + ..\..\..\packages\Microsoft.Extensions.DependencyInjection.1.1.0\lib\netstandard1.1\Microsoft.Extensions.DependencyInjection.dll + + + ..\..\..\packages\Microsoft.Extensions.DependencyInjection.Abstractions.1.1.0\lib\netstandard1.0\Microsoft.Extensions.DependencyInjection.Abstractions.dll + + + ..\..\..\packages\Microsoft.Extensions.FileProviders.Abstractions.1.1.0\lib\netstandard1.0\Microsoft.Extensions.FileProviders.Abstractions.dll + + + ..\..\..\packages\Microsoft.Extensions.FileProviders.Physical.1.1.0\lib\net451\Microsoft.Extensions.FileProviders.Physical.dll + + + ..\..\..\packages\Microsoft.Extensions.FileSystemGlobbing.1.1.0\lib\net45\Microsoft.Extensions.FileSystemGlobbing.dll + + + ..\..\..\packages\Microsoft.Extensions.Logging.1.1.0\lib\netstandard1.1\Microsoft.Extensions.Logging.dll + + + ..\..\..\packages\Microsoft.Extensions.Logging.Abstractions.1.1.0\lib\netstandard1.1\Microsoft.Extensions.Logging.Abstractions.dll + + + ..\..\..\packages\Microsoft.Extensions.ObjectPool.1.1.0\lib\net451\Microsoft.Extensions.ObjectPool.dll + + + ..\..\..\packages\Microsoft.Extensions.Options.1.1.0\lib\netstandard1.0\Microsoft.Extensions.Options.dll + + + ..\..\..\packages\Microsoft.Extensions.PlatformAbstractions.1.1.0\lib\net451\Microsoft.Extensions.PlatformAbstractions.dll + + + ..\..\..\packages\Microsoft.Extensions.Primitives.1.1.0\lib\netstandard1.0\Microsoft.Extensions.Primitives.dll + + + ..\..\..\packages\Microsoft.Net.Http.Headers.1.1.0\lib\netstandard1.1\Microsoft.Net.Http.Headers.dll + ..\..\..\packages\Microsoft.Owin.3.0.1\lib\net45\Microsoft.Owin.dll True @@ -57,23 +135,24 @@ ..\..\..\packages\Microsoft.Owin.FileSystems.3.0.1\lib\net45\Microsoft.Owin.FileSystems.dll True - - ..\..\..\packages\Microsoft.Owin.Host.HttpListener.3.0.1\lib\net45\Microsoft.Owin.Host.HttpListener.dll - True - - - ..\..\..\packages\Microsoft.Owin.Hosting.3.0.1\lib\net45\Microsoft.Owin.Hosting.dll - True - ..\..\..\packages\Microsoft.Owin.StaticFiles.3.0.1\lib\net45\Microsoft.Owin.StaticFiles.dll True + + ..\..\..\packages\Microsoft.Win32.Primitives.4.3.0\lib\net46\Microsoft.Win32.Primitives.dll + ..\..\..\packages\Owin.1.0\lib\net40\Owin.dll True + + ..\..\..\packages\System.AppContext.4.3.0\lib\net46\System.AppContext.dll + + + ..\..\..\packages\System.Buffers.4.3.0\lib\netstandard1.1\System.Buffers.dll + ..\..\..\packages\System.Collections.Immutable.1.3.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll True @@ -88,23 +167,91 @@ True + + ..\..\..\packages\System.Diagnostics.DiagnosticSource.4.3.0\lib\net46\System.Diagnostics.DiagnosticSource.dll + + + ..\..\..\packages\System.Diagnostics.Tracing.4.3.0\lib\net462\System.Diagnostics.Tracing.dll + + + ..\..\..\packages\System.Globalization.Calendars.4.3.0\lib\net46\System.Globalization.Calendars.dll + ..\..\..\packages\System.IO.4.3.0\lib\net462\System.IO.dll True + + ..\..\..\packages\System.IO.Compression.4.3.0\lib\net46\System.IO.Compression.dll + + + + ..\..\..\packages\System.IO.Compression.ZipFile.4.3.0\lib\net46\System.IO.Compression.ZipFile.dll + + + ..\..\..\packages\System.IO.FileSystem.4.3.0\lib\net46\System.IO.FileSystem.dll + + + ..\..\..\packages\System.IO.FileSystem.Primitives.4.3.0\lib\net46\System.IO.FileSystem.Primitives.dll + + + ..\..\..\packages\System.Net.Http.4.3.0\lib\net46\System.Net.Http.dll + + + ..\..\..\packages\System.Net.Sockets.4.3.0\lib\net46\System.Net.Sockets.dll + + + + ..\..\..\packages\System.Numerics.Vectors.4.3.0\lib\net46\System.Numerics.Vectors.dll + + + ..\..\..\packages\System.Reflection.4.3.0\lib\net462\System.Reflection.dll + + + ..\..\..\packages\System.Reflection.Metadata.1.4.1\lib\portable-net45+win8\System.Reflection.Metadata.dll + ..\..\..\packages\System.Runtime.4.3.0\lib\net462\System.Runtime.dll True + + ..\..\..\packages\System.Runtime.CompilerServices.Unsafe.4.3.0\lib\netstandard1.0\System.Runtime.CompilerServices.Unsafe.dll + ..\..\..\packages\System.Runtime.Extensions.4.3.0\lib\net462\System.Runtime.Extensions.dll True + + ..\..\..\packages\System.Runtime.InteropServices.4.3.0\lib\net462\System.Runtime.InteropServices.dll + + + ..\..\..\packages\System.Runtime.InteropServices.RuntimeInformation.4.3.0\lib\net45\System.Runtime.InteropServices.RuntimeInformation.dll + + + ..\..\..\packages\System.Security.Cryptography.Algorithms.4.3.0\lib\net461\System.Security.Cryptography.Algorithms.dll + + + ..\..\..\packages\System.Security.Cryptography.Encoding.4.3.0\lib\net46\System.Security.Cryptography.Encoding.dll + + + ..\..\..\packages\System.Security.Cryptography.Primitives.4.3.0\lib\net46\System.Security.Cryptography.Primitives.dll + + + ..\..\..\packages\System.Security.Cryptography.X509Certificates.4.3.0\lib\net461\System.Security.Cryptography.X509Certificates.dll + + + ..\..\..\packages\System.Text.Encodings.Web.4.3.0\lib\netstandard1.0\System.Text.Encodings.Web.dll + + + ..\..\..\packages\System.Threading.Tasks.Extensions.4.3.0\lib\portable-net45+win8+wp8+wpa81\System.Threading.Tasks.Extensions.dll + + + ..\..\..\packages\System.Xml.ReaderWriter.4.3.0\lib\net46\System.Xml.ReaderWriter.dll + @@ -113,6 +260,7 @@ + @@ -130,6 +278,7 @@ Properties\SolutionInfo.cs + @@ -138,6 +287,14 @@ + + + + libuv.dll + Always + False + + {43ccbef4-c940-457e-b6d7-4d2675532926} diff --git a/src/clients/Wyam/packages.config b/src/clients/Wyam/packages.config index 4c59e3649..c906e3012 100644 --- a/src/clients/Wyam/packages.config +++ b/src/clients/Wyam/packages.config @@ -1,20 +1,89 @@  + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/tests/clients/Wyam.Tests/app.config b/tests/clients/Wyam.Tests/app.config index 0c0173a27..032984c30 100644 --- a/tests/clients/Wyam.Tests/app.config +++ b/tests/clients/Wyam.Tests/app.config @@ -62,6 +62,18 @@ + + + + + + + + + + + + diff --git a/tests/integration/Wyam.Examples.Tests/app.config b/tests/integration/Wyam.Examples.Tests/app.config index f6eba8b39..0cdff5c29 100644 --- a/tests/integration/Wyam.Examples.Tests/app.config +++ b/tests/integration/Wyam.Examples.Tests/app.config @@ -90,6 +90,18 @@ + + + + + + + + + + + +