I wanna Render View To Stream.
this is my code:
var httpContext = new DefaultHttpContext { RequestServices = _serviceProvider };
var actionContext = new ActionContext(httpContext, new
RouteData(), new ActionDescriptor());
var viewEngineResult = _viewEngine.FindView(actionContext,
viewName, false);
this code worked before. but after update to core6 doesn't work.
net core 6 does not create view.dll
my razor view is in Views/Shared location. and i set it as content
Compiler no longer produces a Views assembly
The Razor compiler no longer produces a separate Views.dll file that
contains the CSHTML views defined in an application.
Both views and application types are included in a single
AppName.dll assembly. View types have the accessibility modifiers
internal and sealed, by default, and are included under the
AspNetCoreGeneratedDocument namespace.
So, If your method is doing something by View.dll, It is not work in .Net 6
Refer to this doc to learn more.
Related
After I managed to get multiple Database Context working in asp.net boilerplate (with some help here ASP.NET Boilerplate multiple databases and DbContexts), I ran into another problem. In the unit tests, when I use one of the additional database contexts like so:
using (var uow = this.UnitOfWorkManager.Begin())
{
var r = this.SlipLineRepository.GetAll().ToList();
}
I get this error:
Abp.AbpException : Could not resolve DbContextOptions for SlipStreamAPI.SlipStreamDB.miSlipLiveContext, SlipStreamAPI.EntityFrameworkCore, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null.
So my questions are:
1) Is it possible to test against in memory DB contexts, if they are the second, third, etc context?
2) If it is, what should I do to make it work?
You should register DbContextOptions in ServiceCollectionRegistrar.cs:
public static void Register(IIocManager iocManager)
{
// ...
var builder = new DbContextOptionsBuilder<miSlipLiveContext>();
builder.UseInMemoryDatabase(Guid.NewGuid().ToString()).UseInternalServiceProvider(serviceProvider);
iocManager.IocContainer.Register(
Component
.For<DbContextOptions<miSlipLiveContext>>()
.Instance(builder.Options)
.LifestyleSingleton()
);
}
I'm working at a middleware for aspnetcore2.0 where I want to execute some razor view.
Actually I need a error handling middleware which would show nice pages from razor views. I know that it's possible to do with UseStatusCodePagesWithReExecute based on status codes. But I need a more general approach - handle an exception in my middleware to delegate (in some cases) it to an error view.
I realized that DeveloperExceptionPageMiddleware does something similar to what I need. But I can't understand how it works even after digging into its sources.
Here is the place where that middleware returns a view - https://github.com/aspnet/Diagnostics/blob/dev/src/Microsoft.AspNetCore.Diagnostics/DeveloperExceptionPage/DeveloperExceptionPageMiddleware.cs#L206
But I can't understand what kind of view it is. It's nor a razor page (as it has no #page directive) neither an mvc view (but i'm not sure).
In the project there're two files for that view: ErrorPage.cshtml and ErrorPage.Designer.cs. How that Designer.cs was created? It looks like a generated file. But thanks to it there's a normal class in the project (ErrorPage) which can be used explicitly. It inherits Microsoft.Extensions.RazorViews.BaseView class from Microsoft.Extensions.RazorViews.Sources package.
So the middleware just execute that view:
var errorPage = new ErrorPage(model);
return errorPage.ExecuteAsync(context);
How can it be achieved in my project?
UPDATE [2018.06]: Please note that the post was written for .NET Core 2.0 times, there're breaking changes for RazorEngine in .NET Core 2.1.
It turned out that it's pretty easy to do.
Aspnet prjoect has an internal tool called RazorPageGenerator (see https://github.com/aspnet/Razor/tree/dev/src/RazorPageGenerator) which can be used to compile views. After compilation with this tool we'll get normal classes which can be used in middlewares.
But before we need to get RazorPageGenerator and slightly customize it.
1.Create a new console project
dotnet new console -o MyRazorGenerator
2.put NuGet.config inside this folder
<configuration>
<config>
<add key="globalPackagesFolder" value="./packages" />
</config>
<packageSources>
<add key="aspnetcore-dev" value="https://dotnet.myget.org/F/aspnetcore-dev/api/v3/index.json " />
</packageSources>
</configuration>
3.Add the following in csprj (as dotnet add package doesn't support installing pre-prelease packages)
<ItemGroup>
<PackageReference Include="RazorPageGenerator" Version="2.1.0-*" />
<PackageReference Include="Microsoft.AspNetCore.Mvc.Razor.Extensions" Version="2.1.0-*" />
<PackageReference Include="Microsoft.AspNetCore.Razor.Language" Version="2.1.0-*" />
</ItemGroup>
4.restore dotnet restore to check you got RazorPageGenerator
5.add into Program.cs:
public static int Main(string[] args)
{
if (args == null || args.Length < 1)
{
Console.WriteLine("Invalid argument(s).");
return 1;
}
var rootNamespace = args[0];
var targetProjectDirectory = args.Length > 1 ? args[1] : Directory.GetCurrentDirectory();
var razorEngine = RazorPageGenerator.Program.CreateRazorEngine(rootNamespace, builder => {
FunctionsDirective.Register(builder);
InheritsDirective.Register(builder);
SectionDirective.Register(builder);
});
var results = RazorPageGenerator.Program.MainCore(razorEngine, targetProjectDirectory);
foreach (var result in results)
{
File.WriteAllText(result.FilePath, result.GeneratedCode);
}
Console.WriteLine();
Console.WriteLine($"{results.Count} files successfully generated.");
Console.WriteLine();
return 0;
}
6.Now we have our own generator and can compile views
7.Create a Razor View (.cshtml)
8.run our generator to compile view:
dotnet run --project .\MyRazorPageGenerator\MyRazorPageGenerator.csproj Croc.XFW3.Web .\Middleware
here I assume that the view is inside Middleware\Views folder.
9.Generator creates a file like ErrorPage.Designer.cs (if view was ErrorPage.cshtml) which we can use:
public async Task Invoke(HttpContext context)
{
try
{
await _next.Invoke(context);
if (context.Response.StatusCode == StatusCodes.Status404NotFound)
{
var statusCodeFeature = context.Features.Get<IStatusCodePagesFeature>();
if (statusCodeFeature == null || !statusCodeFeature.Enabled)
{
if (!context.Response.HasStarted)
{
var view = new ErrorPage(new ErrorPageModel());
await view.ExecuteAsync(context);
}
}
}
}
}
Here we're returning our view in case of 404 error and absense of StatusCodePagesMiddleware. Can be useful for embedded UI in libs.
The generated code uses staff which should be added into your project. To get it we need to acquire nuget package Microsoft.Extensions.RazorViews.Sources. Again it’s not on nuget.org so we need to install it from https://dotnet.myget.org/feed/aspnetcore-dev/package/nuget/Microsoft.Extensions.RazorViews.Sources.
I am doing a development to integrate a non Java OMS system with QuickFIX/J to send buy/sell orders to multiple brokerage systems .
I have written the belog logic to send the messages
I have written this under main function which is in the same class created by implementing Application "public class Initiator implements Application"
InputStream inp = InitiatorSocket.class.getResourceAsStream("test.cfg");
SessionSettings sessionSetting = new SessionSettings(inp);
Application myApp = new Initiator();
FileStoreFactory factory = new FileStoreFactory(sessionSetting);
ScreenLogFactory sfactory = new ScreenLogFactory(sessionSetting);
DefaultMessageFactory defaultMsgFactory = new DefaultMessageFactory();
initiator = new SocketInitiator(myApp, factory, sessionSetting,sfactory,defaultMsgFactory);
initiator.start();
SessionID sessionId = initiator.getSessions().get(0);
I am using the below code to send messages after continuously listening a directory using while Loop.
while(true)
{
readFilefromSrcDirectory();
prepareFixMessage();
Session.sendToTarget(fixMessage, sessionId);
}
My above code is getting executed while debugging but when I run it normally, the Session.sendToTarget(fixMessage, sessionId); and other file read related logic which is next to initiator.start(); is not getting executed.
Kindly note that the same above code is getting executed if we add some console print statements such as System.out.print("Test");
Please help me.
Are your test.cfg settings between debug and run different? I would add console print statements everywhere and work out exactly where the runtime is failing.
I am using to get the assembly for following
Assembly assembly = Application.Current.GetType().GetTypeInfo().Assembly;
and i get the ResourceNames form that assembly for using
var resources=assembly.GetManifestResourceNames()
but it gives no resource names in assembly.
Please help me how to achieve it?
In VB.NET, I do that:
Public Function LoadResourceStr(sResID As String) As String
Dim ctx As Windows.ApplicationModel.Resources.Core.ResourceContext = New Windows.ApplicationModel.Resources.Core.ResourceContext()
ctx.Languages = {Globalization.CultureInfo.CurrentUICulture.Name}
Dim rmap As Windows.ApplicationModel.Resources.Core.ResourceMap = Windows.ApplicationModel.Resources.Core.ResourceManager.Current.MainResourceMap.GetSubtree("Resources")
Return rmap.GetValue(sResID, ctx).ValueAsString
End Function
The MainResourceMap is a collection of all resources of application. Important: the files into directories of app (embedded compiled) need is configured to "Content", not "embedded resource". In this case, you can change string ID from "Resources" to "Files".
The sample above show the resource strings into xml files, to translate your app.
When you call RazorEngine.Razor.Compile(), where is the compiled template stored?
Is it available after the programs been restarted? If there is a memory shortage, will it be dumped?
I am using RazorEngine in an ASP.NET (MVC) project. Will the precompiled templates be available after the application restarts?
Would it make more sense for me to store them in the HttpContext.Cache?
If I did, then would it make more sense to use a different function (other than Compile) that bypasses the internal cache? Is there a way to execute an ITemplate and just pass it a model?
Does RazorEngine.Razor.Parse() do any caching? Or is the template recompiled each time?
Currently, after the RazorEngine compiles the templates, they are loaded into memory. These assemblies persist in memory only and do not continue beyond the lifetime of the application.
I am considering adding in support for compiling these assemblies to files, but that'll be a future version.
If you call Razor.Parse and pass in a name for the template, it will attempt to
Check the cache of in-memory assemblies for an assembly with the same name.
Invalid the cache of the content of the template has changed.
Cache the newly compiled template.
I've got this to work with RazorEngine 3.4.1.0, installed late Jan 2014.
The key is to call the expensive Razor.Compile(content, name) to put the template into cache, then call the cheap Razor.Run(name, model) to execute the template.
Remember that reading template content might be expensive -- say, involving a read from disk -- so my solution only gets template content once. This might be too much caching for you, so careful!
Here's the RenderPartial method I use inside a custom TemplateBase<T> subclass. It runs very quickly for multiple calls to the same template.
public abstract class SqlTemplate<T>: TemplateBase<T>
{
public string RenderPartial(string templateName, object model = null)
{
// loading a template might be expensive, so be careful to cache content
if (Razor.Resolve(templateName) == null)
{
// we've never seen this template before, so compile it and stick it in cache.
var templateContent = GetTemplateContent(templateName);
Razor.Compile(templateContent, templateName);
}
// by now, we know we've got a the template cached and ready to run; this is fast
var renderedContent = Razor.Run(templateName, model);
return renderedContent;
}
private string GetTemplateContent(string templateName)
{
... your implementation here
}
}
You also need to tell Razor to use this base class (SqlTempalte<T>) which you can do like this, by calling RazorEngineConfigurator.Configure();
public static class RazorEngineConfigurator
{
private static bool configured = false;
public static void Configure()
{
if (configured)
{
return;
}
var templateConfig = new TemplateServiceConfiguration
{
BaseTemplateType = typeof(SqlTemplate<>),
EncodedStringFactory = new RazorEngine.Text.RawStringFactory()
};
RazorEngine.Razor.SetTemplateService(new TemplateService(templateConfig));
configured = true;
}
}
Couldn't have done it without this SO answer -- why not give that one an up-vote, too? :)
Edit - If you need to perform caching in a more granular way, you'll need to use a different approach using RazorEngineTemplateService and ITemplateResolver.
Here's a piece of starter code;
public static RazorEngineTemplateService CreateService(ITemplateResolver resolver, ICollection<string> namespaces)
{
Check.IsNotNull(resolver, "resolver");
var config = new TemplateServiceConfiguration();
config.BaseTemplateType = typeof(PlainTextTemplate<>);
config.EncodedStringFactory = new RazorEngine.Text.RawStringFactory();
config.Resolver = resolver;
config.Namespaces = new HashSet<string>(namespaces);
var service = new RazorEngineTemplateService(config);
return service;
}
ITemplateResolver turns template names into template contents, so you can implement, eg, a CachedFileTemplateResolver which loads cached content from disk.