在MVC中,如何确定调用操作?

时间:2021-05-25 05:03:59

I have the following controller that, along with returning images, prevents direct linking:

我有以下控制器,连同返回的图像,防止直接链接:

public class ImageController : Controller
{
    [HttpGet]
    public ActionResult Details(string id, string file)
    {
        if (null == Request.UrlReferrer ||
            Request.UrlReferrer.Authority != Request.Url.Authority ||
            Request.UrlReferrer.AbsolutePath.ToLower() != Url.Action("Photos", "Home", new { id = id }).ToLower())
        {
            return base.File(Server.MapPath("/Content/images/notfound.jpg"));
        }

        // else process and return image
    }
}

This works, but it has a slight smell. Is there something MVC-ier that will tell me this? I was initially hopeful about ControllerContext, but that wasn't it.

这行得通,但它有一种轻微的气味。有什么可以告诉我的吗?我最初对ControllerContext很有信心,但事实并非如此。

Here is how I am calling this action from my view:

在我看来,我是这样称呼这一行动的:

@foreach (var item in Model.Items)
{
    <li>
        <img src='@Url.Action("Details", "Image", new { id = Model.Project, file = item.ThumbnailPath })' />
    </li>
}

1 个解决方案

#1


1  

In your view generate an encrypted string containing id+file+datetime. In your img src @Url.Action pass this encrypted string.

在视图中生成包含id+file+datetime的加密字符串。在img src @Url中。操作传递这个加密字符串。

In your Controller, decrypt this string to obtain the id & file & datetime. If the datetime is greater than 15 seconds, dont serve the image. If the key is not decrypted successfully dont serve the image.

在您的控制器中,解密该字符串以获得id & file & datetime。如果日期时间大于15秒,不要发送图像。如果密钥未被成功解密,则不提供图像。

Since the encryption logic is private, others can not forge a request and since you have datetime in the encrypted key, you can expire the links in 10-15 seconds, so others can not hotlink to your images.

由于加密逻辑是私有的,其他人不能伪造请求,而且由于加密密钥中有datetime,所以可以在10-15秒内使链接过期,因此其他人不能对您的图像进行hotlink。

Hope this makes sense.

希望这是有意义的。

@foreach (var item in Model.Items) {    

<li>
        <img src='@Url.Action("Details", "Image", new { encryptedString= item.encryptedString})' />    

</li> }

public class ImageController : Controller
{    

   [HttpGet]    
   public ActionResult Details(string encryptedString)   
   {        
           try
           {

            string[] values = DescryptString(encryptedString);
            // values[0] = id
            // values[1] = file
            // values[2] = datetime

             if(dateTime difference < 10 seconds )
                 return process and return image    ;
             else // link expired
                return base.File(Server.MapPath("/Content/images/notfound.jpg"));                  
            }
            catch(DecodingException e)
            {
                // forged request
                return base.File(Server.MapPath("/Content/images/notfound.jpg"));              
             }                       

    }
}

#1


1  

In your view generate an encrypted string containing id+file+datetime. In your img src @Url.Action pass this encrypted string.

在视图中生成包含id+file+datetime的加密字符串。在img src @Url中。操作传递这个加密字符串。

In your Controller, decrypt this string to obtain the id & file & datetime. If the datetime is greater than 15 seconds, dont serve the image. If the key is not decrypted successfully dont serve the image.

在您的控制器中,解密该字符串以获得id & file & datetime。如果日期时间大于15秒,不要发送图像。如果密钥未被成功解密,则不提供图像。

Since the encryption logic is private, others can not forge a request and since you have datetime in the encrypted key, you can expire the links in 10-15 seconds, so others can not hotlink to your images.

由于加密逻辑是私有的,其他人不能伪造请求,而且由于加密密钥中有datetime,所以可以在10-15秒内使链接过期,因此其他人不能对您的图像进行hotlink。

Hope this makes sense.

希望这是有意义的。

@foreach (var item in Model.Items) {    

<li>
        <img src='@Url.Action("Details", "Image", new { encryptedString= item.encryptedString})' />    

</li> }

public class ImageController : Controller
{    

   [HttpGet]    
   public ActionResult Details(string encryptedString)   
   {        
           try
           {

            string[] values = DescryptString(encryptedString);
            // values[0] = id
            // values[1] = file
            // values[2] = datetime

             if(dateTime difference < 10 seconds )
                 return process and return image    ;
             else // link expired
                return base.File(Server.MapPath("/Content/images/notfound.jpg"));                  
            }
            catch(DecodingException e)
            {
                // forged request
                return base.File(Server.MapPath("/Content/images/notfound.jpg"));              
             }                       

    }
}