Razor Pages, MVC and minimal APIs
The viewer is not tied to a hosting style. Render the mount div from a Razor view or a static page and open the document from a controller action, a page handler or a mapped endpoint.
Doconut is registered the way everything else in ASP.NET Core is registered: a service in the container and middleware in the pipeline. It inherits your authentication, your logging, your DI graph and your deployment story, because it is running inside them rather than beside them.
The problem
Most document viewers arrive as a separate service. That means a second deployment unit, a second set of credentials, a network hop your documents now travel across, and a second thing to page someone about at 2am.
Doconut is a library. AddDoconut() puts it in your service collection; UseDoconut() puts it in your pipeline. It runs under your process identity, sees your configuration, writes to your logger, and is deployed by whatever already deploys your application.
The practical consequence is that authorization stays where it belongs. You call OpenDocumentAsync() after your own permission check, and the viewer can only ever render what you decided to hand it.
Capabilities
The viewer is not tied to a hosting style. Render the mount div from a Razor view or a static page and open the document from a controller action, a page handler or a mapped endpoint.
Because the endpoints live in your pipeline, [Authorize] works the way it always did. There is no second identity system to federate with.
Document security rides on ASP.NET session state, which is why UseSession() has to be registered before UseDoconut(). It means the viewer's notion of who you are is the same as the application's.
Multiple nodes behind a load balancer share the render cache, so a session opened on one node keeps working when the next request lands elsewhere.
IIS, Kestrel, or a container image you build yourself. Nothing about the integration changes between them except where the licence file is mounted.
With the Converter plugin, DocumentConverter.ConvertAsync() runs in the same process — no second service, no temporary upload, no round trip.
Integration
UserMayRead and ResolvePath are your own code. That is the point: Doconut never learns which documents exist or who is allowed to see them.
Supported platforms
// Program.cs
builder.Services.AddDoconut(options =>
{
options.LicensePath = "Doconut.Viewer.lic";
});
builder.Services.AddSession(); // document security rides on session state
var app = builder.Build();
app.UseSession(); // call UseSession() before UseDoconut()
app.UseDoconutResources(); // must be registered before UseDoconut()
app.UseDoconut();
// Open the document server-side, behind your own authorization
app.MapPost("/api/open", async (Viewer viewer, HttpContext ctx, string documentId) =>
{
if (!await ctx.UserMayRead(documentId))
return Results.Forbid();
// The token is opaque — hand it to the widget, never log or persist it.
string token = await viewer.OpenDocumentAsync(ResolvePath(documentId));
return Results.Ok(new { token });
}).RequireAuthorization();Details
Yes. Both are supported and use the same DI-plus-middleware architecture. There are dedicated pages for each if you need version-specific detail.
No, and that is deliberate. Integration is always middleware plus the JavaScript widget, which keeps the same integration valid across Razor Pages, MVC, Web Forms and Blazor instead of fragmenting into four.
Web farm and distributed deployment are supported through a shared render cache. A document opened on one node stays readable when subsequent requests hit another.
No. Rendering is native — there is no Office interop, no headless Word, and no COM automation to babysit.
Blazor
Server-side rendering with a widget that mounts cleanly into the Blazor interop lifecycle — Server and WebAssembly both supported.
BlazorWord
Native DOC/DOCX/RTF/ODT rendering with no Office install, no COM interop and no server-side automation.
WordA temporary licence takes a few minutes to request and runs entirely on your own machine. The files that matter are the ones already breaking your current viewer.