Existe-t-il un moyen recommandé de renvoyer une image à l'aide de l'API Web ASP.NET

86

Quelle est la meilleure façon de renvoyer une image avec 2 paramètres (x et y pour redimensionner).

Par exemple

~/api/image12345/200/200

Renvoie un 200 par 200 jpg / png / ou gif

Dois-je retourner un System.Drawing.Imageobjet ou définir manuellement le HTTPReponseMessage.Content?

Max Alexander
la source
Découvrez ma réponse ici: stackoverflow.com/a/20888749/64334
Ronnie Overby le

Réponses:

147

Vous ne devriez pas renvoyer a System.Drawing.Image, sauf si vous ajoutez également un formateur qui sait comment le convertir en octets appropriés ne se sérialise pas comme octets d'image comme vous vous en doutez.

Une solution possible consiste à renvoyer un HttpResponseMessageavec l'image stockée dans son contenu (comme illustré ci-dessous). N'oubliez pas que si vous voulez l'URL que vous avez affichée dans la question, vous aurez besoin d'un itinéraire qui mappe les paramètres {imageName}, {width} et {height}.

public HttpResponseMessage Get(string imageName, int width, int height)
{
    Image img = GetImage(imageName, width, height);
    using(MemoryStream ms = new MemoryStream())
    {
        img.Save(ms, System.Drawing.Imaging.ImageFormat.Png);

        HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
        result.Content = new ByteArrayContent(ms.ToArray());
        result.Content.Headers.ContentType = new MediaTypeHeaderValue("image/png");

        return result;
    }
}

Mais encore une fois, si vous faites cela dans de nombreux endroits, emprunter la voie du formateur peut être la voie «recommandée». Comme presque tout en programmation, la réponse dépendra de votre scénario.

carlosfigueira
la source
L'image doit-elle aussi être utilisée?
dibs487
Où est la GetImageméthode?
Yoda
1
@Yoda c'est la méthode de votre implémentation qui renverrait l'image qui doit être transférée au client.
carlosfigueira
Si vous renvoyez un fichier à partir du disque dur, je pense qu'il serait préférable d'utiliser un FileStream, comme celui-ci (voir la réponse acceptée dans cette question): stackoverflow.com/questions/11125535/…
John Gilmer
19

Les images sont lourdes. ASP.NET WebForms, HttpHandlers, MVC et Web API font tous un travail absolument terrible en servant des fichiers statiques. IIS fait un très bon travail à cet égard - souvent 20 à 100 fois plus efficacement.

Si vous souhaitez obtenir de bonnes performances, effectuez une réécriture d'URL au plus tard pendant PostAuthorizeRequest, afin qu'IIS puisse récupérer et servir le fichier. Oui, cela signifie la gestion des événements au niveau de HttpModule.

[Clause de non-responsabilité: je suis l'auteur de l'article suivant et du projet open-source]

Si vous faites quelque chose de dynamique avec des images, consultez cet article sur les pièges du traitement d'image à éviter et envisagez de jeter un coup d'œil à ImageResizer . Il dispose d'une excellente mise en cache disque (qui utilise la gestion des fichiers statiques IIS) et est facile à connecter à la génération d'images de tout type. Il a également des liaisons optionnelles pour AForge, FreeImage et WIC, si vous avez besoin de progresser.

Lilith River
la source
2
J'utilise ImageResizer dans mon projet et je suis très satisfait de son fonctionnement, en plus de moi. Seul reproche, une partie de la documentation doit être mise à jour.
Jon L