如何知道它是否真的是 404 页面?
How to know if it's actually a 404 page?
我从Foregenix中学到了什么:
The HTTP 404 Not Found Error means that the webpage you were trying to reach could not be found on the server. It is a Client-side Error which means that either the page has been removed or moved and the URL was not changed accordingly, or that you typed in the URL incorrectly
但后来我也用 Python 进行网络应用程序渗透测试,我想知道如果我只检查页面上的字符串 404
,它可能不是真正的 404
错误。
有可能页面存在但标题是 404
只是为了愚弄我们。
那我到底是怎么知道的呢?
您可以查看HTTP状态码,看看是不是404。状态码在响应的第一行:
HTTP/1.1 404 Not Found
如果您正在使用 HTTPlib,您可以只读取 HTTPResponse
对象的 status
属性。
但是,决定发送什么 HTTP 状态代码的是服务器。仅仅因为 404 被定义为 "page not found" 并不意味着服务器不能骗你。做这样的事情很常见:
- 发送 404 而不是 403,以隐藏需要身份验证的资源。
- 发送 404 而不是 500,以掩盖某些东西不工作的事实。
- 当您的 IP 由于某种原因被阻止时发送 404。
如果不能访问服务器,就不可能知道幕后到底发生了什么。
你是对的:有人可以在 HTML 页面中写下“404 页面未找到”,让你认为该页面不存在。
为了正确识别 404 等 HTTP 状态代码,您应该使用 Python 捕获 HTTP 响应并解析它。 HTTP 1 和 HTTP 2 标准规定,以 HTTP 通用消息格式编写的 HTTP 响应必须包含状态代码。
HTTP 响应示例(来自 Tutorials Point):
HTTP/1.1 404 Not Found
Date: Sun, 18 Oct 2012 10:36:20 GMT
Server: Apache/2.2.14 (Win32)
Content-Length: 230
Connection: Closed
Content-Type: text/html; charset=iso-8859-1
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html>
<head>
<title>404 Not Found</title>
</head>
<body>
<h1>Not Found</h1>
<p>The requested URL /t.html was not found on this server.</p>
</body>
</html>
您绝对不要相信 HTML 部分,它会显示 404 错误(甚至 418 I'm a teapot),但实际上可以找到该页面。
除了 Anders 的回答之外,我还找到了一种方法来检测 404 被滥用于定时攻击的某些情况。但是,它几乎不可靠。
- 发送 404 而不是 403,以隐藏需要身份验证的资源。
通常服务器需要更多时间来确定 "you dont have authorization to get this resource",因为它们需要更多往返于外部资源(如数据库),然后它们需要确定 "this is not there",通常甚至可以缓存并快速确定。
以 RDBS 作为后端的 MVC 应用程序中的一个典型示例是简单 SELECT COUNT(id) FROM articles WHERE id=123 LIMIT 1
和更复杂的 SELECT access FROM accesses JOIN articles ON articles.id = accesses.foreign_id WHERE articles.id = 123 AND accesses.type='articles' AND accesses.user_id = (SELECT id FROM users WHERE token='t0k3n' LIMIT 1)
。这意味着应用程序可以首先进行此类单行查询:更多时候是很多 "fetch a user, extract some data, now fetch a Thing, now ask Thing if user may access it through an authorization-api".
除非开发人员或网站的框架注意涵盖这种情况,否则您经常会发现服务这两种 404 情况的时间存在显着差异。
- 发送 404 而不是 500,以隐藏某些东西不工作的事实。
通常,只有在某些代码 运行 之后才会发生崩溃或意外错误。 404 检测通常来得很早:毕竟,确定某物不存在的成本很低(见上文)。而错误会在以后发生。这意味着这样一个 500-hidden-as-404-error 与正常的 404 相比,通常需要更长的时间才能到达您身边。
- 当您的 IP 由于某种原因被阻止时发送 404。
在这里,时间安排通常是相反的,具体取决于实施方式。这种 IP 阻止通常会保留在网络应用程序(CMS 等)之外,因为它在堆栈中处理更高层更简单且性能更高:网络服务器、代理等。
然而,当应用程序自己处理这个问题时,生成实际的 404 通常相当便宜,而在数据库中查找 IP、应用掩码等需要一些时间。类似于将 403 隐藏为 404。
我从Foregenix中学到了什么:
The HTTP 404 Not Found Error means that the webpage you were trying to reach could not be found on the server. It is a Client-side Error which means that either the page has been removed or moved and the URL was not changed accordingly, or that you typed in the URL incorrectly
但后来我也用 Python 进行网络应用程序渗透测试,我想知道如果我只检查页面上的字符串 404
,它可能不是真正的 404
错误。
有可能页面存在但标题是 404
只是为了愚弄我们。
那我到底是怎么知道的呢?
您可以查看HTTP状态码,看看是不是404。状态码在响应的第一行:
HTTP/1.1 404 Not Found
如果您正在使用 HTTPlib,您可以只读取 HTTPResponse
对象的 status
属性。
但是,决定发送什么 HTTP 状态代码的是服务器。仅仅因为 404 被定义为 "page not found" 并不意味着服务器不能骗你。做这样的事情很常见:
- 发送 404 而不是 403,以隐藏需要身份验证的资源。
- 发送 404 而不是 500,以掩盖某些东西不工作的事实。
- 当您的 IP 由于某种原因被阻止时发送 404。
如果不能访问服务器,就不可能知道幕后到底发生了什么。
你是对的:有人可以在 HTML 页面中写下“404 页面未找到”,让你认为该页面不存在。
为了正确识别 404 等 HTTP 状态代码,您应该使用 Python 捕获 HTTP 响应并解析它。 HTTP 1 和 HTTP 2 标准规定,以 HTTP 通用消息格式编写的 HTTP 响应必须包含状态代码。
HTTP 响应示例(来自 Tutorials Point):
HTTP/1.1 404 Not Found
Date: Sun, 18 Oct 2012 10:36:20 GMT
Server: Apache/2.2.14 (Win32)
Content-Length: 230
Connection: Closed
Content-Type: text/html; charset=iso-8859-1
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html>
<head>
<title>404 Not Found</title>
</head>
<body>
<h1>Not Found</h1>
<p>The requested URL /t.html was not found on this server.</p>
</body>
</html>
您绝对不要相信 HTML 部分,它会显示 404 错误(甚至 418 I'm a teapot),但实际上可以找到该页面。
除了 Anders 的回答之外,我还找到了一种方法来检测 404 被滥用于定时攻击的某些情况。但是,它几乎不可靠。
- 发送 404 而不是 403,以隐藏需要身份验证的资源。
通常服务器需要更多时间来确定 "you dont have authorization to get this resource",因为它们需要更多往返于外部资源(如数据库),然后它们需要确定 "this is not there",通常甚至可以缓存并快速确定。
以 RDBS 作为后端的 MVC 应用程序中的一个典型示例是简单 SELECT COUNT(id) FROM articles WHERE id=123 LIMIT 1
和更复杂的 SELECT access FROM accesses JOIN articles ON articles.id = accesses.foreign_id WHERE articles.id = 123 AND accesses.type='articles' AND accesses.user_id = (SELECT id FROM users WHERE token='t0k3n' LIMIT 1)
。这意味着应用程序可以首先进行此类单行查询:更多时候是很多 "fetch a user, extract some data, now fetch a Thing, now ask Thing if user may access it through an authorization-api".
除非开发人员或网站的框架注意涵盖这种情况,否则您经常会发现服务这两种 404 情况的时间存在显着差异。
- 发送 404 而不是 500,以隐藏某些东西不工作的事实。
通常,只有在某些代码 运行 之后才会发生崩溃或意外错误。 404 检测通常来得很早:毕竟,确定某物不存在的成本很低(见上文)。而错误会在以后发生。这意味着这样一个 500-hidden-as-404-error 与正常的 404 相比,通常需要更长的时间才能到达您身边。
- 当您的 IP 由于某种原因被阻止时发送 404。
在这里,时间安排通常是相反的,具体取决于实施方式。这种 IP 阻止通常会保留在网络应用程序(CMS 等)之外,因为它在堆栈中处理更高层更简单且性能更高:网络服务器、代理等。 然而,当应用程序自己处理这个问题时,生成实际的 404 通常相当便宜,而在数据库中查找 IP、应用掩码等需要一些时间。类似于将 403 隐藏为 404。