C# 如何使用 ASP.Net MVC 路由来路由图像?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1146652/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 09:20:48  来源:igfitidea点击:

How do I route images using ASP.Net MVC routing?

c#asp.netasp.net-mvcroutingurl-rewriting

提问by The Matt

I upgraded my site to use ASP.Net MVC from traditional ASP.Net webforms. I'm using the MVC routing to redirect requests for old .aspx pages to their new Controller/Action equivalent:

我将我的网站升级为使用来自传统 ASP.Net 网络表单的 ASP.Net MVC。我正在使用 MVC 路由将旧 .aspx 页面的请求重定向到它们的新控制器/操作等效项:

        routes.MapRoute(
            "OldPage",
            "oldpage.aspx",
            new { controller = "NewController", action = "NewAction", id = "" }
        );

This is working great for pages because they map directly to a controller and action. However, my problem is requests for images - I'm not sure how to redirect those incoming requests.

这对页面非常有用,因为它们直接映射到控制器和操作。但是,我的问题是对图像的请求 - 我不确定如何重定向这些传入请求。

I need to redirect incoming requests for http://www.domain.com/graphics/image.pngto http://www.domain.com/content/images/image.png.

我需要将http://www.domain.com/graphics/image.png 的传入请求重定向到http://www.domain.com/content/images/image.png

What is the correct syntax when using the .MapRoute()method?

使用该.MapRoute()方法时的正确语法是什么?

采纳答案by womp

You can't do this "out of the box" with the MVC framework. Remember that there is a difference between Routing and URL-rewriting. Routing is mapping every request to a resource, and the expected resource is a piece of code.

你不能用 MVC 框架“开箱即用”地做到这一点。请记住,路由和 URL 重写之间存在差异。路由就是把每一个请求映射到一个资源上,期望的资源就是一段代码。

However - the flexibility of the MVC framework allows you to do this with no real problem. By default, when you call routes.MapRoute(), it's handling the request with an instance of MvcRouteHandler(). You can build a customhandler to handle your image urls.

但是 - MVC 框架的灵活性使您可以毫无问题地做到这一点。默认情况下,当您调用 时routes.MapRoute(),它会使用 的实例处理请求MvcRouteHandler()。您可以构建一个自定义处理程序来处理您的图像 url。

  1. Create a class, maybe called ImageRouteHandler, that implements IRouteHandler.

  2. Add the mapping to your app like this:

    routes.Add("ImagesRoute", new Route("graphics/{filename}",
    new ImageRouteHandler()));

  3. That's it.

  1. 创建一个类,可能称为 ImageRouteHandler,它实现IRouteHandler.

  2. 像这样将映射添加到您的应用程序:

    routes.Add("ImagesRoute", new Route("graphics/{filename}",
    new ImageRouteHandler()));

  3. 就是这样。

Here's what your IRouteHandlerclass looks like:

这是您的IRouteHandler课程的样子:

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Web;
using System.Web.Compilation;
using System.Web.Routing;
using System.Web.UI;

namespace MvcApplication1
{
    public class ImageRouteHandler : IRouteHandler
    {
        public IHttpHandler GetHttpHandler(RequestContext requestContext)
        {
            string filename = requestContext.RouteData.Values["filename"] as string;

            if (string.IsNullOrEmpty(filename))
            {
                // return a 404 HttpHandler here
            }
            else
            {
                requestContext.HttpContext.Response.Clear();
                requestContext.HttpContext.Response.ContentType = GetContentType(requestContext.HttpContext.Request.Url.ToString());

                // find physical path to image here.  
                string filepath = requestContext.HttpContext.Server.MapPath("~/test.jpg");

                requestContext.HttpContext.Response.WriteFile(filepath);
                requestContext.HttpContext.Response.End();

            }
            return null;
        }

        private static string GetContentType(String path)
        {
            switch (Path.GetExtension(path))
            {
                case ".bmp": return "Image/bmp";
                case ".gif": return "Image/gif";
                case ".jpg": return "Image/jpeg";
                case ".png": return "Image/png";
                default: break;
            }
            return "";
        }
    }
}

回答by awright18

If you were to do this using ASP.NET 3.5 Sp1 WebForms you would have to create a seperate ImageHTTPHandler that implements IHttpHandler to handle the response. Essentially all you would have to do is put the code that is currently in the GetHttpHandler method into your ImageHttpHandler's ProcessRequest method. I also would move the GetContentType method into the ImageHTTPHandler class. Also add a variable to hold the name of the file.

如果要使用 ASP.NET 3.5 Sp1 WebForms 执行此操作,则必须创建一个单独的 ImageHTTPHandler 来实现 IHttpHandler 来处理响应。基本上,您需要做的就是将当前在 GetHttpHandler 方法中的代码放入 ImageHttpHandler 的 ProcessRequest 方法中。我还会将 GetContentType 方法移动到 ImageHTTPHandler 类中。还要添加一个变量来保存文件的名称。

Then your ImageRouteHanlder class looks like:

然后你的 ImageRouteHanlder 类看起来像:

public class ImageRouteHandler:IRouteHandler
    {
        public IHttpHandler GetHttpHandler(RequestContext requestContext)
        {
            string filename = requestContext.RouteData.Values["filename"] as string;

            return new ImageHttpHandler(filename);

        }
    } 

and you ImageHttpHandler class would look like:

你的 ImageHttpHandler 类看起来像:

 public class ImageHttpHandler:IHttpHandler
    {
        private string _fileName;

        public ImageHttpHandler(string filename)
        {
            _fileName = filename;
        }

        #region IHttpHandler Members

        public bool IsReusable
        {
            get { throw new NotImplementedException(); }
        }

        public void ProcessRequest(HttpContext context)
        {
            if (string.IsNullOrEmpty(_fileName))
            {
                context.Response.Clear();
                context.Response.StatusCode = 404;
                context.Response.End();
            }
            else
            {
                context.Response.Clear();
                context.Response.ContentType = GetContentType(context.Request.Url.ToString());

                // find physical path to image here.  
                string filepath = context.Server.MapPath("~/images/" + _fileName);

                context.Response.WriteFile(filepath);
                context.Response.End();
            }

        }

        private static string GetContentType(String path)
        {
            switch (Path.GetExtension(path))
            {
                case ".bmp": return "Image/bmp";
                case ".gif": return "Image/gif";
                case ".jpg": return "Image/jpeg";
                case ".png": return "Image/png";
                default: break;
            }
            return "";
        }

        #endregion
    }