如何在 Tampermonkey 中捕获状态 503

Posted

技术标签:

【中文标题】如何在 Tampermonkey 中捕获状态 503【英文标题】:How to catch status 503 in tampermonkey 【发布时间】:2019-03-07 21:06:18 【问题描述】:

我有一个每秒刷新一次页面的用户脚本,但有时它尝试刷新的网站会遇到状态 503 错误,这会阻止脚本继续运行。这意味着脚本将不再尝试每秒刷新页面。页面遇到状态 503 错误后,如何保持脚本运行?控制台中的错误如下所示:

加载资源失败:服务器响应状态为 503(服务不可用)

// ==UserScript==
// @name        script
// @namespace   name
// @description example
// @match       *^https://example.com/$*
// @version     1
// @require     https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js
// @grant       GM_xmlhttpRequest
// @run-at document-end
// ==/UserScript==

//*****************************************START OF SET_TIMEOUT
var timeOne = 1000;
var theTime = timeOne;

var timeout = setTimeout("location.reload(true);", theTime);
function resetTimeout() 
clearTimeout(timeout);
timeout = setTimeout("location.reload(true);", theTime);
 //end of function resetTimeout()
//*****************************************END OF SET_TIMEOUT

【问题讨论】:

【参考方案1】:

我能想到的简单解决方案是将每秒需要刷新的实际网页移动到另一个框架或某个 html 容器,并使用您的用户脚本,您可以使用您想要刷新的 HTML 页面刷新或重新加载该容器。

除非您发出 http 请求以从脚本加载网页,否则可能无法处理 http 错误(我可能错了!)。您的用户脚本应该处于超集级别,即使在出现任何 503 或任何类似的 HTTP 错误之后,它也将具有控制或范围。

您可以使用页面状态更改事件来确保或检查刷新框架/容器中的页面是否已加载,以避免在加载之前重新加载网页。除非您想重新加载而不管网页是否成功加载。

希望这会有所帮助..

【讨论】:

如何将实际网页移动到另一个框架或 HTML 容器?你能写一个示例代码吗?【参考方案2】:

用户脚本在页面加载时运行,如果页面根本没有加载除 200 之外的任何状态代码,它们将不会运行。您可以按照@Hemanth 的建议使用<iframe>,但您必须打破无限循环因为<iframe> 也会加载用户脚本等等。要打破它,只需检查用户脚本是否加载到顶部窗口中。

if (window == window.top) 
    // Remove everything from the page
    // Add an iframe with current page URL as it's source
    // Add an event to reload the iframe few seconds after it is loaded

完整代码:

(function ($) 
  'use strict';
  var interval = 5000;
  if (window == window.top) 
    var body = $('body').empty();
    var myframe = $('<iframe>')
      .attr( src: location.href )
      .css( height: '95vh', width: '100%' )
      .appendTo(body)
      .on('load', function () 
        setTimeout(function () 
          myframe.attr( src: location.href );
        , interval);
      );
  
)(jQuery);

【讨论】:

如果需要更多帮助,请告诉我。 嘿。我还有一个与此问题相关的问题:***.com/questions/52960065/…【参考方案3】:

问题是location.reload试图用重新加载的版本完全替换页面,但是如果浏览器无法连接到服务器,页面将不会被加载,并且该页面的任何用户脚本都将无法运行,因为没有可供它们运行的​​页面。

一种解决方法是使用 javascript 网络请求来获取新页面的文本,然后使用 Javascript 将现有内容替换为新内容 - 如果响应是 503 错误(或其他错误),您可以简单地忽略它并重试。这可确保您始终停留在同一个(已加载)页面上,因此用户脚本将无限期地继续运行,即使响应有时会失败。

这是一个用户脚本示例,它每 10 秒用新的 HTML 更新 *** 的主页。您可以使用DOMParser 将响应文本转换为可以使用querySelector 导航的文档,除此之外:

// ==UserScript==
// @name         Update SO
// @namespace    CertainPerformance
// @version      1
// @match        https://***.com/
// @grant        none
// ==/UserScript==

const container = document.querySelector('.container');
function getNewData() 
  console.log('getting new data');
  fetch('https://***.com',
    
      // The following is needed to include your existing cookies with the request, which may be needed:
      credentials: "same-origin"
    )
    .then((resp) => 
      // If there are errors, such as a 503 error, proceed directly to the `finally` to try again:
      if (!resp.ok) return;
      return resp.text();
    )
    .then((text) => 
      const doc = new DOMParser().parseFromString(text, 'text/html');
      container.innerHTML = doc.querySelector('.container').innerHTML;
    )
    .finally(() => 
      // Whether there was an error or not, try to refresh again in a few seconds:
      setTimeout(getNewData, 10000);
    );


setTimeout(getNewData, 10000);

【讨论】:

以上是关于如何在 Tampermonkey 中捕获状态 503的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Tampermonkey 中获取 cookie? [复制]

如何安装tampermonkey

如何/在哪里将数据存储在除 localStorage 之外的 Chrome Tampermonkey 脚本中?

调试 Tampermonkey 脚本

如何在axios中捕获状态=取消?

使用 Tampermonkey/javascript 控制 Netflix (HTML5) 播放