2015-06-11 11 views
11

voglio visualizzare diversi messaggi di errore per ogni esempio codice di stato:ASP.NET MVC errori 6 di movimentazione basati su codice di stato HTTP

  • 400 Bad Request
  • 403 Forbidden
  • 500 Internal Server Error
  • 404 Not Found
  • 401 non autorizzato

Come può Lo raggiungo nelle nuove applicazioni ASP.NET MVC 6? Posso farlo usando il metodo builtErrorHandler?

application.UseErrorHandler("/error"); 

Inoltre, ho notato che anche con il conduttore sopra, inserendo un URL inesistente esempio/this-page-does-not-exist, causa una brutta pagina di errore 404 non trovata da IIS. Come può essere gestito anche questo?

In MVC 5 abbiamo dovuto utilizzare la sezione customErrors System.web per ASP.NET e la sezione system.webServer httpErrors nel file web.config, ma era difficile lavorare con un ingombrante, con un sacco di comportamento molto strano. MVC 6 lo rende molto più semplice?

risposta

11

Per questo è possibile utilizzare lo StatusCodePagesMiddleware. Di seguito è riportato un esempio:

public void Configure(IApplicationBuilder app, ILoggerFactory loggerFactory) 
{ 
    app.UseStatusCodePagesWithReExecute("/StatusCodes/StatusCode{0}"); 

    app.UseMvcWithDefaultRoute(); 

controller che gestisce le richieste di codice di stato:

public class StatusCodesController : Controller 
{ 
    public IActionResult StatusCode404() 
    { 
     return View(viewName: "NotFound"); // you have a view called NotFound.cshtml 
    } 

    ... more actions here to handle other status codes 
} 

Alcune note:

  • Controllare le altre metodi di estensione come UseStatusCodePagesWithRedirects e UseStatusCodePages per altre funzionalità.
  • Ho provato ad avere StatusCode come stringa di query nel mio esempio, ma sembra che questo middleware non gestisca le stringhe di query, ma puoi dare un'occhiata al codice this e risolvere questo problema.
+1

Nota: questa è una soluzione migliore di quella fornita di seguito. –

+0

Questo codice viene eseguito per tutte le richieste. Ho ragione nel dire che questo sarebbe stato aggiunto al delegato di Action che può essere passato a UseErrorHandler? –

+1

@RehanSaeed: sì, questo potrebbe essere eseguito per tutte le richieste in quanto è necessario intercettare le risposte per verificare il codice di stato. Non sono chiaro riguardo alla tua seconda domanda. Questo è un middleware diverso da "UserErrorHandler". puoi elaborare di più? –

3

Come posso ottenere questo risultato nelle nuove applicazioni ASP.NET MVC 6? Posso farlo usando il metodo builtErrorHandler?

Risposta rapida: Non in modo elegante.

Spiegazione/alternativa: Per iniziare permette primo sguardo a ciò che il metodo UseErrorHandler è in realtà facendo: https://github.com/aspnet/Diagnostics/blob/6dbbe831c493e6e7259de81f83a04d1654170137/src/Microsoft.AspNet.Diagnostics/ErrorHandlerExtensions.cs#L25 che aggiunge il seguente middleware: https://github.com/aspnet/Diagnostics/blob/6dbbe831c493e6e7259de81f83a04d1654170137/src/Microsoft.AspNet.Diagnostics/ErrorHandlerMiddleware.csNota linee 29-78 (il metodo invoke)

L'invoke il metodo viene eseguito ogni volta che una richiesta arriva (controllata dalla posizione del tuo application.UseErrorHandler("...") nel tuo Startup.cs). Quindi lo UseErrorHandler è un modo glorioso di aggiungere un middleware personalizzato: middleware = componente che può agire su una richiesta http.

Ora con quello sfondo, se volevamo aggiungere il nostro stesso middleware di errore che richieste differenziate. Potremmo fare questo aggiungendo un middleware simile che è come il default ErrorHandlerMiddleware modificando queste linee: https://github.com/aspnet/Diagnostics/blob/6dbbe831c493e6e7259de81f83a04d1654170137/src/Microsoft.AspNet.Diagnostics/ErrorHandlerMiddleware.cs#L48-L51 Con tale approccio potremmo controllare il percorso di reindirizzamento basato sul codice di stato.

In MVC 5 abbiamo dovuto utilizzare la sezione customErrors System.Web per ASP.NET e la sezione system.webServer httpErrors nel file web.config, ma era difficile lavorare con un ingombrante, con un sacco di comportamento molto strano. MVC 6 lo rende molto più semplice?

Risposta: Di sicuro fa :). Proprio come la risposta di cui sopra la soluzione sta nell'aggiungere il middleware.C'è una scorciatoia per aggiungere middleware semplice tramite IApplicationBuilder nel tuo Startup.cs; alla fine del metodo Configure è possibile aggiungere il seguente:

app.Run(async (context) => 
{ 
    await context.Response.WriteAsync("Could not handle the request."); 

    // Nothing else will run after this middleware. 
}); 

Ciò funzionerà perché significa che hai raggiunto la fine della pipeline http senza la richiesta di essere manipolati (dato che è alla fine del tuo metodo Configure in Startup.cs). Se volete aggiungere questo middleware (nel campo della moda veloce) con la possibilità di eseguire middleware dopo di voi, ecco come fare:

app.Use(async (context, next) => 
{ 
    await context.Response.WriteAsync("Could not handle the request."); 

    // This ensures that any other middelware added after you runs. 
    await next(); 
}); 

Spero che questo aiuti!

+0

Presumibilmente questo è un sostituto per la sezione customErrors del web.config solo e non avrebbe funzionato per 404 errori non trovati. Per questo avremmo ancora bisogno di usare httpErrors? –

+1

Funzionerebbe anche per 404 errori non trovati. Un 404 si verifica quando nulla può gestire la richiesta. –

0

Funziona con vari codici di stato senza specificarli singolarmente nel controller.

Startup.cs:

public void Configure(IApplicationBuilder app, ILoggerFactory loggerFactory) 
{ 
    app.UseStatusCodePagesWithRedirects("/StatusCodes?statusCode={0}"); 
    app.UseMvcWithDefaultRoute(); 

Controller:

public class StatusCodesController : Controller 
    { 
    public IActionResult Index(string statusCode) 
    { 
     if(statusCode == null) statusCode = ""; 
     if(statusCode == "404") return View("Error404"); 
     return View("Index",statusCode); 
    } 

    public IActionResult Test404() { return StatusCode(404); } 
    public IActionResult Test500() { return StatusCode(500); } 

Vista:

@model string 
@{ ViewData["Title"] = Model + " Oops!"; } 

<style> 
    .error-template { 
    padding: 40px 15px; 
    text-align: center; 
    } 

    .error-actions { 
    margin-bottom: 15px; 
    margin-top: 15px; 
    } 

    .error-actions .btn { 
     margin-right: 10px; 
    } 
</style> 

<div class="container"> 
    <div class="row"> 
    <div class="col-md-12"> 
     <div class="error-template"> 
     <h2>Oops!</h2> 
     <h2>@Model Error</h2> 
     <div class="error-details">Sorry, an error has occurred!</div> 
     <div class="error-actions"> 
      <a class="btn btn-primary btn-lg" href="/"><span class="glyphicon glyphicon-home"></span> Take Me Home </a> 
      <a class="btn btn-default btn-lg" href="/Home/ContactUs"><span class="glyphicon glyphicon-envelope"></span> Contact Support </a> 
     </div> 
     </div> 
    </div> 
    </div> 
</div>