网页中经常需要显示图片给用户看,对网站本身来说有的图片是从本地图片服务器来的,但是一旦数量多了以后,磁盘空间又是一个问题。

所以有时就希望显示其他网站的Image,直接把其他网站的图片显示在我的网站上。但并不是所有的外网Image 都能直接连接过来显示。

很多情况下网站开发人员就会遇到 403 forbidden的问题。比如想显示来自IMDB的一张图片

<img src="http://ia.media-imdb.com/images/M/MV5BMjIwMjYyNjk4Nl5BMl5BanBnXkFtZTcwNzA4NDYwMw@@._V1_UY317_CR12,0,214,317_AL_.jpg" height="350" width="200">

本地localhost Debug的时候完全可以显示,但是将网站部署到服务器后就会遇到这样的错误

奇怪的是通过浏览器访问图片的连接,图片就正常的显示了出来。

这又是为什么?其实Referer是由浏览器自动加上的,但是也有例外比如

1. 直接通过浏览器访问

2. 在web前段使用location.href 或者location.replace

3. 利用HTTPS等加密协议

这就是HotLinking 盗链问题, 可以通过配置网站Server 端来实现这种反盗链的行为。

为什么像IMDB这样的网站要做 Anti HotLinking反盗链的事情呢?

版权的问题是一方面。

另一方面可以称作Bandwidth Theft, 当用户访问IMDB页面的时候,IMDB需要Bandwidth传输数据,而Bandwidth 是网站的成本之一。

好比谁也不愿意陌生人偷偷的把电器插到你的插座,偷偷的用你的电,而你去负担所有的费用。

如何配置Server实现Anti HotLinking 呢?

以Asp.net MVC 为例

可以给Controller 添加ActionFilter 或者添加处理AntiHotLinking 的 IHttpHandler

核心都是UrlReferrer

HttpRequest 有个字段 UrlReferrer:

该字段表示哪个Url  通过像上面Img Src的方式访问了Server.

//访问者的域
var refDomain = Request.UrlReferrer.Host;//当前WebSite的域
var serverDomain = Request.Url.Host;

最后可以通过判断 是否来自同一个域 来决定Anti HotLinking的策略

或者可以通过在web.config 中配置URLRewrite来实现

<rewrite>
<rules><rule name="Anti HotLinking Rule for Image" enabled="true" stopProcessing="true"><match url=".*\.(gif|jpg|png)$" /><conditions><add input="{HTTP_REFERER}" negate="true" pattern="^$" /><add input="{HTTP_REFERER}" negate="true" pattern="http://www.yourwebsite.com/.*" /><add input="{HTTP_REFERER}" negate="true" pattern="http://yourwebsite.com/.*" /></conditions><action type="Rewrite" url="/images/anti-hotlinking.png" />
</rule>
</rules>
</rewrite>

如果网站用户就是希望看到不能显示的图片或者视频呢?

这里给大家推荐一个Chrome 插件 Anti-Anti-HotLinking

安装后就能看到未能显示的图片。

对该插件我没有仔细研究,有可能是通过Download来解决Hotlinking 问题的,也有可能是通过Chrome劫持Request 修改UrlReferer实现的。

对网站开发人员有什么解决办法吗?

1. 将外网的Image在Server端下载 再转换成 base64 最后传输给img 标签。

        public static string ImageToBase64(Stream imageStream, ImageFormat format){using (System.Drawing.Image image = System.Drawing.Image.FromStream(imageStream)){using (MemoryStream stream = new MemoryStream()){image.Save(stream, format);var result = System.Convert.ToBase64String(stream.ToArray());return result;}}}

<img src="data:image/png;base64,这里存放转换成base64的字符串 />

2. 利用RefererKiller这个JavaScript插件 绕过UrlReferer

  ReferrerKiller.imageHtml("fakeweb/fakeimage.png"); 返回能够显示的img的Html字符串

  ReferrerKiller.imageHtml("fakeweb/fakeimage.png"); 返回能够显示的img的DOM节点

  其实这两个函数是同一个东西,可以捡方便的用。

  这种方式解决HotLinking问题其实原理很简单,在web中 比如<script src="differentDomain/fake.js"> </script>

  加载js 是没有跨域访问的问题。

  ReferrerKiller 就动态生成一个iframe,并在iframe内加入img标签。利用src加载的特性把代码放到src中,就可以去掉Referer。

  所以ReferrerKiller.imageHtml返回的是一个能显示图片的iframe。

关于img 403 forbidden的一些思考相关推荐

  1. 解决github push错误403 Forbidden while accessing

    业务场景 我原来在github上创建了一个repository,名称为github_test,我上传了一些文件.但是几年后,我想再次利用该repository,更新并上传文件. 我在一台虚拟机上面gi ...

  2. nginx 403 forbidden 二种原因

    1,缺少index.html或者index.php文件 server { listen       80; server_name  localhost; index  index.php index ...

  3. [Hihocoder 1289] 403 Forbidden (微软2016校园招聘4月在线笔试)

    传送门 #1289 : 403 Forbidden 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 Little Hi runs a web server. Someti ...

  4. img 标签 访问图片 返回403 forbidden问题

    之前在项目里,本地调试的时候,图片src引用了第三方网站的图片资源,导致控制台出现了如下的报错: 403 forbidden,说明了这个网络资源这样获取是被拒绝的,那么通过简单的百度,找到了相关的解决 ...

  5. 解决github push错误The requested URL returned error: 403 Forbidden while accessing(转)

    github push错误: git push error: The requested URL returned error: 403 Forbidden while accessing https ...

  6. 配置https后访问返回403 forbidden

    今天在配置https的时候配置好,http能访问,https访问返回403 forbidden: 网上找了很多,改nginx.conf的user的 修改配置文件的 其实就是权限问题,是网站根目录的权限 ...

  7. 关于Linux访问web遇到403 Forbidden的问题

    问题: 大数据平台的集群监控地址是通过一个代理(ip:port)访问,在windows环境下设置代理是可以正常访问: 但在linux环境下设置了代理却不能访问:telnet和ping代理是可以,但cu ...

  8. urllib2.HTTPError: HTTP Error 403: Forbidden的解决方案

    在使用python爬取网络爬虫时,经常会以为目标网站因为禁止爬取网络爬虫而出现403 Forbidden的错误 问:为什么会出现403 Forbidden的错误 答:出现urllib2.HTTPErr ...

  9. (转)wamp2.5虚拟主机VirtualHost出现403 Forbidden问题解决

    (转)wamp2.5虚拟主机VirtualHost出现403 Forbidden问题解决 笔者刚刚重装完系统,win8.1退回win7,感觉win8还是给触摸屏的PC设计的吧,没win7用的顺手啊.作 ...

最新文章

  1. 解决Parameter ‘__frch_item_0‘ not found. Available parameters 问题
  2. JavaScript常用API总结
  3. 【数据分析学习】数据预处理
  4. 设计师应该尊重技术的限制
  5. CV之Harris特征点检测器-兴趣点检测(详解)
  6. c++11 string转ing_pdfkit | 利用python实现html文件转pdf
  7. 【iOS】Unlock iPhone to Continue Xcode cannot launch demo1_greating on iPhone because the device is lo
  8. linux 汇编语言ldreq,请教一个中断句柄的问题 - ARM技术论坛-ARM嵌入式论坛-人气最火爆ARM学习论坛 - 21ic电子技术开发论坛...
  9. OSGI嵌入tomcat应用服务器(gem-web)——资源下载
  10. 【C语言】简单小游戏项目:《别踩白块儿》
  11. 制造业生产规划与排程的福音—APS系统
  12. 把汇总报表页面生成 pdf文件方案!
  13. java加载so包,undefined symbol处理方法
  14. 前端项目的总结——为什么要组件化?
  15. 29. 人类将如何变革--走出金字塔模型(上)
  16. Revit中添加了标高看不见原来轴网解决方法及轴网转化
  17. DNSPod十问花生壳陈宇晔:远程办公领域的下一个“独角兽”?
  18. Android 创建 文件 和 文件夹
  19. 登录EMC VNX5100存储管理界面报Java版本问题处理
  20. 在Simscape中创建虚拟机器人环境(一):组装机器人并从CAD中导入

热门文章

  1. php 虚拟空间,什么是php虚拟主机?
  2. 汇编语言-004(LABEL 、间接寻址、变址操作数、指针使用、TypeDef、LOOP、DWORD变量交换高位低位字)
  3. [Golang]Go语言学习资源集合
  4. ZOj 2104——Let the Balloon Rise
  5. 237. 删除链表中的节点 golang
  6. arm嵌入式linux应用实例开发pdf,零点起步——ARM嵌入式Linux应用开发入门一书的源代码...
  7. 软件工程---07.设计与实现
  8. 设计模式---4(抽象工厂模式的概念,产品组和产品等级的概念,抽象工厂模式的实现)
  9. 【报错解决】linux网络编程报错storage size of ‘serv_addr’ isn’t known解决办法
  10. 计算机网络【4】传输层