Saltar al contenido

Devolver PDF al navegador usando ASP.NET Core

Te damos la bienvenida a nuestra página web, aquí encontrarás la solucíon de lo que andabas buscando.

Solución:

Como se explica en ASP.NET Core HTTPRequestMessage devuelve un mensaje JSON extraño, ASP.NET Core no admite la devolución de un HttpResponseMessage (¿Qué paquete instaló para obtener acceso a ese tipo?).

Debido a esto, el serializador simplemente escribe todas las propiedades públicas del HttpResponseMessage a la salida, como lo haría con cualquier otro tipo de respuesta no compatible.

Para admitir respuestas personalizadas, debe devolver un IActionResult-tipo de ejecución. Hay un montón de esos. En tu caso, investigaría el FileStreamResult:

public IActionResult Get(int id)

    var stream = new FileStream(@"pathtofile", FileMode.Open);
    return new FileStreamResult(stream, "application/pdf");     

O simplemente use un PhysicalFileResultdonde la transmisión se maneja por usted:

public IActionResult Get(int id)

    return new PhysicalFileResult(@"pathtofile", "application/pdf");

Por supuesto, todo esto se puede simplificar utilizando métodos auxiliares, como Controller.File():

public IActionResult Get(int id)

    var stream = new FileStream(@"pathtofile", FileMode.Open);
    return File(stream, "application/pdf", "FileDownloadName.ext");

Esto simplemente abstrae la creación de un FileContentResult o FileStreamResult (para esta sobrecarga, lo último).

O si está convirtiendo una aplicación MVC o Web API más antigua y no quiere convertir todo su código a la vez, agregue una referencia a WebApiCompatShim (NuGet) y envuelva su código actual en un ResponseMessageResult:

public IActionResult Get(int id)

    var response = new HttpResponseMessage(HttpStatusCode.OK);           
    var stream = ...
    response.Content...

    return new ResponseMessageResult(response);

Si no quieres usar return File(fileName, contentType, fileDownloadName)entonces el FileStreamResult no admite la configuración del encabezado de disposición de contenido desde el constructor o mediante propiedades.

En ese caso, deberá agregar ese encabezado de respuesta a la respuesta usted mismo antes de devolver el resultado del archivo:

var contentDisposition = new ContentDispositionHeaderValue("attachment");
contentDisposition.SetHttpFileName("foo.txt");
Response.Headers[HeaderNames.ContentDisposition] = contentDisposition.ToString();

No pude comentar la respuesta de CodeCaster ya que mi reputación no es lo suficientemente alta. al intentar

public IActionResult Get(int id)

    using (var stream = new FileStream(@"pathtofile", FileMode.Open))
    
        return File(stream, "application/pdf", "FileDownloadName.ext");
           
 

tenemos un

ObjectDisposedException: no se puede acceder a un objeto desechado. Nombre del objeto: ‘No se puede acceder a un archivo cerrado.’. System.IO.FileStream.BeginRead(byte[]
arrayint offset, int numBytes, devolución de llamada AsyncCallback, estado del objeto)

Eliminamos el uso

   [HttpGet]
   [Route("getImageFile")]
   public IActionResult GetWorkbook()
   
        var stream = new FileStream(@"pathToFile", FileMode.Open);
        return File(stream, "image/png", "image.png");
   

Y eso funcionó. Este es ASP.NET Core 2.1 ejecutándose en IIS Express.

No tengo suficiente reputación para publicar esto como un comentario, así que lo publico como respuesta. Las primeras 3 soluciones de @CodeCaster y la solución de @BernhardMaertl son correctas.

Sin embargo, para alguien que no trabaje con archivos a menudo (como yo), tenga en cuenta que si el proceso que ejecuta este código (por ejemplo, la API) solo tiene permisos de lectura para el archivo, deberá especificarlo como el tercer parámetro al crear tu FileStreamde lo contrario, el comportamiento predeterminado es abrir el archivo para lectura/escritura y obtendrá una excepción ya que no tiene permisos de escritura.

La tercera solución de @CodeCaster se vería así:

public IActionResult Get(int id)

    var stream = new FileStream(@"pathtofile", FileMode.Open, FileAccess.Read);
    return File(stream, "application/pdf", "FileDownloadName.ext");

Puedes añadir valor a nuestra información añadiendo tu experiencia en las interpretaciones.

¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)



Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *