【问题标题】:Navigate to a URL Only if it Exists with JavaScript仅当它与 JavaScript 一起存在时才导航到 URL
【发布时间】:2013-12-21 10:11:09
【问题描述】:

我正在尝试让我的网页导航到提供的 URL。如果提供的 URL 不存在,我希望我的页面重定向到备用 URL。我需要在 JavaScript 中执行此操作。

这是我迄今为止尝试过的:

var customUrl    = 'http://www.StackOverflow.com/ThisPageWillResultIn404';
var alternateUrl = 'AlternateUrl.html?e=PageIs404'

setTimeout(function() { window.location=alternateUrl; }, 25);
window.location = customUrl;

这似乎在 IOS 中可以正常工作,但在 Android 中却不行。

【问题讨论】:

  • 链接中提供的所有解决方案,使 ajax 请求/xmlhttp 请求的 ue 仅在同一域中正常工作。跨域将无法使用它。请帮我解决跨域问题。
  • 我已经发布了一个我认为可以正确回答您的问题并提供简单解决方案的答案。

标签: javascript


【解决方案1】:

为什么 Javascript 不能做到这一点 -

如果您跨域(而不是从您的站点域)发出请求,则请求将失败。这是由于一个名为“Same-Origin Policy”的安全策略在主流浏览器中强制执行以防止XSS (cross site scripting)。 Same-Origin Policy Wikipedia 页面中列出的表格很好地描述了什么是跨域的,什么不是。

总而言之,客户端脚本不能也不应该能够访问被同源策略视为跨域的站点。

这意味着 Javascript 将无法执行您的要求,因为它无法确定您的用户提供的链接的任何内容,除非这些链接指向您自己的网站。

这似乎在 IOS 中可以正常工作,但在 Android 中却不行。

虽然这在任何设备上都不可能实现,但您当前的方法很可能有效,因为不存在的页面可能会导致设备的浏览器在尝试加载不存在的页面时停留。虽然它仍然挥之不去,但您在超时中的代码会运行并重定向。虽然这很聪明,但它依赖于几个假设:

  1. 浏览器在遇到不存在的页面时会停留。
  2. 浏览器将停留超过 25 毫秒。

那么这些假设有什么问题?

  1. 您不能假设所有浏览器都会逗留。这可以解释为什么 Android 设备似乎不适合您。如果负责调用链接的服务器配置为返回 404 页面,则页面将正常加载,而您的脚本不会意识到该链接实际上并不存在。例如,this page 不存在,但仍返回 404 页面。

  2. 页面加载所需的时间还取决于几个因素,例如连接速度、浏览器、页面对不回复请求的超时/容忍度等。很可能以慢速连接使用您网站的客户端将无法访问任何网站,因为加载它们的时间超过 25 毫秒,而使用快速连接和特定浏览器的用户可能会遇到所有页面加载速度超过 25 毫秒的情况,从而阻碍您的系统意图。

这能做什么?

此问题的正确解决方案需要在服务器端执行某些操作。服务器端语言可以访问跨域链接并确定页面是否存在。 Stackoverflow 用户 karim79 展示了如何使用以下 PHP sn-p (How can I check if a URL exists via PHP?) 完成此操作:

$file = 'http://www.domain.com/somefile.jpg';
$file_headers = @get_headers($file);
if($file_headers[0] == 'HTTP/1.1 404 Not Found') {
    $exists = false;
}
else {
    $exists = true;
}

您的 Javascript 使用 ajax 调用然后可用于向脚本发送参数,然后得到响应。显然,必须对上面的 PHP 脚本进行细微的调整以包含参数和返回值。

幸运的是,Yahoo 提供了一个由 YQL 驱动的 API,他们将这项服务描述为:

通过一种简单的方式跨 Web 服务查询、过滤和连接数据 语。无需学习如何调用不同的 API。

另一位寻找类似解决方案的用户 (Can jQuery/js help me determine if an URL exists) 得到了 Stackoverflow 用户 Sheikh Heera 的回答,该用户使用 Yahoo API 提供了以下解决方案:

function isUrlExists(url)
{
    $.getJSON("http://query.yahooapis.com/v1/public/yql?"+
      "q=select%20*%20from%20html%20where%20url%3D%22"+
      encodeURIComponent(url)+"%22&format=json'&callback=?", function(data){
          if(data.results[0]){
              alert('Exists');
          }
          else{
              alert('Doesn\'t exist');  
          }        
      }
    );
}
isUrlExists('http://google.com');

基本上,Yahoo 会在服务器端发出请求,让您无需自己在服务器端编写任何内容即可获得结果。 这太棒了!这个特殊的例子使用了jQuery,然而,它可以用简单的Javascript来完成。

我已经用这种似乎有效的特殊方法编写了一个 JS-Fiddle。看看吧:

http://jsfiddle.net/L84RV/embedded/result/

【讨论】:

  • 嗨,Xander。我尝试使用雅虎 API。访问时出现以下错误。
  • " query.yahooapis.com/v1/public/yql?q=select%20*%20from%20html%20where%20url%3D%22money2%3A%2F%2FdomainName%2FUSMHC%2FHCP%2Fsignon%2Fsignon.action%22&format=json'&callback=jQuery180011892682965844487_1384=7782 1387782433722"
  • jquery 阻止了我的网页,说它运行了不安全的内容。请帮忙
  • 您的网站是否通过 SSL 运行(您网站的 URL 是否以 https:// 开头)?
  • 尝试将请求的 URL 更改为 Yahoo API 以使用 https(将其从 http://query.yahooapis.com/v1/publ... 更改为 https://query.yahooapis.com/v1/publ...)。
猜你喜欢
  • 1970-01-01
  • 2013-12-27
  • 2013-06-14
  • 2011-04-12
  • 1970-01-01
  • 2021-01-21
  • 1970-01-01
  • 2011-05-05
  • 2010-10-06
相关资源
最近更新 更多