原来有个脚本,作用是打开新标签时保留来源标签的历史(源码见文末)
例如标签A为本论坛,历史是{第2页,第3页,第4页},长按“返回”按钮会显示三行记录,分别是2、3、4页
中键在新标签B打开“第5页”链接后,新标签B并不会继承来源标签A的历史记录,在标签B长按返回按钮不会有效果,利用fire gesture等方法强行显示的话,能看见历史只有{第5页}一项
脚本的作用就是使得标签B继承标签A的历史,新标签打开后显示历史为{第2页,第3页,第4页,第5页}
升级到
55b1开发者版后,脚本失效,任何新打开的标签均抛出异常,例如拖拽打开新标签时的异常为:
Exception {
message: "Component returned failure code: 0x80004005 (NS_ERROR_FAILURE) [nsISHistoryInternal.addEntry]",
result: 2147500037,
name: "NS_ERROR_FAILURE",
filename: "chrome://userchromejs/content/userChromeJS.js -> file:///K:/App/Pool/Fx/chrome/Main/RetainSessionHistoryInNewTab.js",
lineNumber: 18,
columnNumber: 0,
data: null,
stack: "copyHistory@chrome://userchromejs/content/userChromeJS.js -> file:///K:/App/Pool/Fx/chrome/Main/RetainSessionHistoryInNewTab.js:18:4loadOneTab@chrome://userchromejs/content/userChromeJS.js -> file:///K:/App/Pool/Fx/chrome/Main/RetainSessionHistoryInNewTab.js line 28 > eval:83:32DragToGo/this.DragDropHandler@chrome://userchromejs/content/userChromeJS.js -> file:///K:/App/Pool/Fx/chrome/Main/DragToGo.uc.js:221:10",
location: XPCWrappedNative_NoHelper
}
一个在本机上可复现的测试脚本
var tabB = gBrowser.mCurrentTab;
var tabA = tabA.previousSibling;
var shB = tabB.linkedBrowser.sessionHistory.QueryInterface(Ci.nsISHistoryInternal);
var shA = tabA.linkedBrowser.sessionHistory;
shB.addEntry(shA.getEntryAtIndex(shA.index - 1, false), true);
1. 复制脚本到代码草稿纸内,切换为chrome运行环境
2. 新建标签A打开任意论坛(例如
本论坛),点击右上角的翻页数字,依次点击2、3、4页。此时长按地址栏旁边“返回”按钮(←)应该能看见数行历史记录(sessionHistory)
3. 中键点击第5页数字链接,在新标签B打开第5页,并切换到新标签B。保证标签A、B相邻且A在B的左边。
4. 回到代码草稿纸,以“显示”模式(Ctrl+L)运行脚本
期望结果
无特殊显示,无异常。在标签B长按“返回”按钮出现新的历史记录。
实际结果
Exception: [Exception... "Component returned failure code: 0x80004005 (NS_ERROR_FAILURE) [nsISHistoryInternal.addEntry]" nsresult: "0x80004005 (NS_ERROR_FAILURE)" location: "JS frame :: Scratchpad/2 :: <TOP_LEVEL> :: line 7" data: no]
原脚本全文
// ==UserScript==
// @id RetainSessionHistoryInNewTab #BAD
// @version 0.1.0.20130612
// @namespace RetainSessionHistoryInNewTab@Byzod.UC.js
// @author Byzod
// @modifiedfrom ithinc
// @description Retain Session History In New Tab
// ==/UserScript==
var SessionHistoryRetainer = {
copyHistory : function(fromTab, newTab){
try{
let currentHistory = fromTab.linkedBrowser.sessionHistory;
let newHistory = newTab.linkedBrowser.sessionHistory.QueryInterface(Ci.nsISHistoryInternal);
/*TODO: linkedBrowser.sessionHistory is null*/
for (let i = 0; i <= currentHistory.index; i++) {
newHistory.addEntry(currentHistory.getEntryAtIndex(i, false), true);
}
} catch(ex){
console.error(ex);
}
},
initialize : function (e) {
// Hack
eval(
"gBrowser.loadOneTab="
+ gBrowser.loadOneTab.toString()
.replace("{", "{\nvar currentTab = this.mCurrentTab;")
.replace("return tab;",
"if (aReferrerURI) {SessionHistoryRetainer.copyHistory(currentTab, tab);}"
+ "\nreturn tab;")
)
},
};
if (window.location == "chrome://browser/content/browser.xul") {
SessionHistoryRetainer.initialize();
}