ASP.NET Core MVC
The easiest way to enable #Script support in a .NET Core App is to register an empty ServiceStack AppHost with the SharpPagesFeature plugin enabled:
public class Startup
{
public void Configure(IApplicationBuilder app)
{
app.UseServiceStack(new AppHost());
}
}
public class MyServices : Service {}
public class AppHost : AppHostBase
{
public AppHost() : base("ServiceStack #Script Pages", typeof(MyServices).Assembly) { }
public override void Configure(Container container)
{
Plugins.Add(new SharpPagesFeature());
}
}
This let you use the #Script Pages and Sharp Code Pages features to build your entire .NET Core Web App with Templates without needing to use anything else in ServiceStack.
MVC PageResult
Just as you can use a ServiceStack Service as the Controller for a Sharp Page View, you can also use an MVC Controller which works the same way as a Service, but instead of returning the PageResult directly, you need to call ToMvcResult() extension method to wrap it in an MVC ActionResult, e.g:
public class HomeController : Controller
{
public ActionResult Index() =>
new PageResult(HostContext.TryResolve<ISharpPages>().GetPage("index")).ToMvcResult();
}
This has the same effect as it has in a ServiceStack Service where the PageResult sets the Content-Type HTTP Response Header and asynchronously writes the template to the Response OutputStream for maximum performance.
Sharing Dependencies
To resolve ISharpPages from ASP.NET Core you will need to register it in ASP.NET's IOC, the easiest way to do this is to use a Modular Startup where any dependencies registered in Configure(IServiceCollection) are available to both ASP.NET Core and ServiceStack, e.g:
public class Startup : ModularStartup
{
public Startup(IConfiguration configuration) : base(configuration){}
public void ConfigureServices(IServiceCollection services) {}
public void Configure(IApplicationBuilder app)
{
app.UseServiceStack(new AppHost {
AppSettings = new NetCoreAppSettings(Configuration)
});
}
}
public class MyServices : Service {}
public class AppHost : AppHostBase
{
public AppHost() : base("ServiceStack #Script Pages", typeof(MyServices).Assembly) {}
public override void Configure(IServiceCollection services)
{
var feature = new SharpPagesFeature();
services.AddSingleton(feature);
services.AddSingleton(feature.Pages);
}
public override void Configure(Container container)
{
Plugins.Add(container.Resolve<SharpPagesFeature>());
}
}
This will then let you access ISharpPages as a normal dependency in your MVC Controller:
public class HomeController : Controller
{
ISharpPages pages;
public HomeController(ISharpPages pages) => this.pages = pages;
public ActionResult Index() => new PageResult(pages.GetPage("index")).ToMvcResult();
}
Using #Script without a ServiceStack AppHost
If you don't need the #Script Pages support and would like to use Templates without a ServiceStack AppHost you can, just register a ScriptContext instance in .NET Core's IOC, replace its Virtual File System to point to the WebRootPath and you can start returning PageResult's as above:
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
var context = new ScriptContext();
services.AddSingleton(context);
services.AddSingleton(context.Pages);
}
public void Configure(IApplicationBuilder app)
{
var context = app.ApplicationServices.GetService<ScriptContext>();
context.VirtualFiles = new FileSystemVirtualFiles(env.WebRootPath);
context.Init();
}
}
public class HomeController : Controller
{
ISharpPages pages;
public HomeController(ISharpPages pages) => this.pages = pages;
public ActionResult Index() => new PageResult(pages.GetPage("index")).ToMvcResult();
}
Checkout the NetCoreApps/MvcTemplates repository for a stand-alone example of this, complete with a sidebar.html partial and a CustomScriptMethods.cs.
ASP.NET v4.5 Framework MVC
You can return a Sharp Page in a classic ASP.NET MVC similar to ASP.NET Core MVC Controller except that in order to work around the lack of being able to async in classic ASP.NET MVC Action Results you need to return a task, but because we can replace the IOC Controller Factory in ASP.NET MVC you can use Constructor Injection to access the ISharpPages dependency:
public class HomeController : Controller
{
ISharpPages pages;
public HomeController(ISharpPages pages) => this.pages = pages;
public Task<MvcPageResult> Index() =>
new PageResult(pages.GetPage("index")).ToMvcResultAsync();
}
ASP.NET MVC + Templates Demo
Checkout the ServiceStackApps/MvcTemplates repository for a stand-alone example, complete with a sidebar.html partial and a CustomScriptMethods.cs.
This demo was created from the ServiceStack ASP.NET MVC5 Empty VS.NET Template.