小书签是浏览器的书签,它执行JavaScript而不是打开一个网页。它们也被称为书签小程序,favlets,或JavaScript书签。
书签小程序在所有主要的浏览器中都可以使用,包括Mozilla Firefox和基于Chromium的浏览器,如Chrome或Brave。
用JavaScript编写脚本
学习如何编写脚本有很多好处,即从重复性或繁琐的任务自动化中节省了大量时间。
如果你不是一个开发人员,学习编码的想法可能会让你感到害怕,然而,脚本不需要软件工程知识或设计模式。其目的不是制作可扩展的软件,而是将专门或琐碎的任务自动化。
不管是什么职业,即使你以前从未写过代码,也要考虑你在浏览器中所做的事情。如果你曾经觉得你所做的事情是重复的或机器人的,请考虑将任务委托给一个真正的机器人的可能性。
小书签的使用案例
使用小书签,你可以操作当前页面,因为该功能将拥有当前标签的上下文。这意味着你可以:
- 点击按钮实际上是
- 修改内容
- 使用页面的内容来打开一个新的页面
- 移除页面中的元素
你也可以制作完全不利用上下文的书签,如有条件地打开一个URL,或为一个新标签生成HTML。
你会在实例书签中看到我为这篇文章制作的一些书签。它们只是用来演示的,但应该能使能力和实现变得明显。
如何创建小书签
创建一个小书签与创建一个普通的书签几乎是一样的。唯一的区别是,你将在URL字段中写入JavaScript,而不是HTTP/HTTPS URL。
导航到书签菜单
火狐浏览器
无论是在你的书签栏,还是在书签侧边栏(CTRL
+B
),你都可以右键单击,然后点击 “添加书签…”:
Chromium
你可以右键点击你的书签栏,然后点击 “添加页面…”。或者,你可以进入你的书签管理器,然后右击并点击 “添加新书签”:
如何编写小书签
在书签模版的URL字段中,以下列格式编写一个JavaScript函数。
javascript: (() => { // Your code here!})();
javascript:
是URL的协议。这表明浏览器应将书签作为JavaScript执行。
(() => { })
定义了一个匿名函数(lambda)。你应该把你想执行的代码写在大括号之间。
();
将执行你刚刚创建的匿名函数。
javascript: (() => { alert('Hello, World!');})();
“Hello, World!”作为一个浏览器书签。
你也可以让它生成HTML并作为HTML文档打开:
javascript: (() => { return '<h1 style="color: white; background-color: black;">Hello, World! </h1>';})();
小书签的换行
大多数浏览器不允许在书签URL中设置多行输入字段,因此在编写书签时,你通常必须严格使用大括号({
和}
)和分号(;
)。这在限定条件结构(if/
for
/while
)的范围时尤其重要。
除此以外,换行并不重要。不要害怕在一行中出现大量的代码,因为那是你的全部:
javascript: (() => { constdocumentHTML=document.documentElement.outerHTML; constmatches=documentHTML.matchAll(/[\w.+=~-]+@[a-zA-Z0-9-]+(?:\. [a-zA-Z0-]+)*/g); constflatMatches=Array.from(matches).map((item) =>item[0]); constuniqueMatches=Array.from(new Set(flatMatches)); if (uniqueMatches.length> 0) { constresult=uniqueMatches.join('\n'); alert(result); else { alert('No emails found!'); } }();
用一行写一个JavaScript函数的例子。
如果你的脚本很复杂,在Visual Studio Code这样的代码编辑器中维护你的书签会更容易。你可以在准备好后把它复制并粘贴到你的浏览器上。
如何与网站互动
你用书签做的最常见的事情是操纵或与你打开的网站进行互动。
全局文件对象
由于小书签拥有你所在页面的上下文,你可以访问文档
对象。
为我们的用例选择元素的理想功能是:
querySelector
通过CSS选择器来选择一个单一的元素。querySelectorAll
,通过CSS选择器选择所有匹配的元素。评估
,通过XPath选择所有匹配的元素。
还有其他一些函数,如getElementById
和getElementsByClassName
,但我们想避免误报,所以我们总是使用多个元素属性进行严格的选择。
CSS选择器和XPath
如果你只是根据元素名称、ID、类和其他属性来选择元素,使用CSS选择器将是简单而有效的。
CSS选择器是用来选择HTML文档中的元素以应用样式。如果你熟悉网页开发或一般的CSS,那么你已经知道如何使用CSS选择器。(更多信息:MDN,freeCodeCamp)
如果你需要同时匹配一个元素的文本内容,那么你就必须使用XPath来代替。
XPath用于遍历XML文档,它提供了CSS选择器的所有功能以及更多,包括比较元素的内容或使用正则表达式进行匹配。(更多信息:MDN,维基百科)
如何从网页上选择元素
小书签最常见的用途之一是操纵网页。要与网页上的元素进行互动、操作或删除,你总是要先选择这些元素。
- 首先按
F12
,或CTRL
+SHIFT
+I
,打开浏览器的开发工具。 - 点击检查器/ 元素选项卡,显示你所打开的页面的完整HTML文档。
- 使用元素选择工具
(CTRL
+SHIFT
+C
),点击你想互动的元素。文档查看器将滚动到你在HTML文档中点击的元素。你会看到元素的ID、类别和属性。 - 检查你是否在正确的元素上。元素可以嵌套在HTML中,这样更容易手动导航到它。例如,你可能点击了一个
svg
元素,但实际上需要它所在的按钮
或div
。 - 定义一个与你想要的一切相匹配的CSS选择器或XPath,你可能想让它比必要的更严格,以避免潜在的假阳性反应。
例如,假设我想拒绝Twitter上的所有话题建议,因为它们很烦人。下面是一个可点击的元素,用来驳回一个话题,看起来是这样的。
推特话题建议,有一个X按钮可以标记为 “不感兴趣”。
<div aria-label="Dismiss" role="button" tabindex="0" class="..."> <!-- 父级div元素有点击监听器。--><div class="... "> <svg viewBox= "0 0 24 24" aria-hidden= "true" class="... "> <!-- 实际的X图标。--></svg></div></div >
一个合适的选择器是div[aria-label=Dismiss][role=button]
。
我们需要使用The Global Document Object的querySelectorAll
函数,然后调用click
方法来模拟点击。
可以实现一个书签来选择每一个解雇按钮,并以250ms的间隔对所有按钮触发一个点击事件。
javascript: (() => { constselector= 'div[aria-label=Dismiss][role=button]'; consttopics=document.querySelectorAll(selector); for (leti= 0;i<topics.length; i++) { lettopic=topics[i]; setTimeout()=>topic.click(),i* 250); })() ;)
在Twitter上把所有建议的话题标记为 “不感兴趣”。
如何重新分配小书签
要 “安装 “一个小书签,用户在他们的浏览器上创建一个书签,并复制和粘贴代码到它。
这可能是不方便的,所以在分享时通常会链接小书签。这就像把它放在你的链接锚的href
属性中一样简单。
<a href="javascript: (() => { alert('Hello, World!'); }) ();">Hello, World!</a>
现在,用户可以右键单击并 “收藏链接”,或将其拖到书签栏,以方便访问。
点击网页上的链接将立即执行该脚本。确保如果用户不小心点击了它,它不会妨碍用户在你的网站上想要实现的目标。
例如,下面的链接将显示一个用户内容和内容安全政策的绕过
如果你经营的服务允许用户生成的内容包含自定义HTML,那么对链接锚进行消毒是很重要的 该书签在开发者工具控制台中像代码一样执行,并绕过了配置的内容安全策略(CSP)。 “Hello, World!”链接可以很容易地将数据发送到另一个服务器,包括表单字段的输入,或cookies。 作为一个服务提供商,必须警惕用户可以利用这一点在你的平台上分享恶意代码。如果他们的链接锚在你的域名下的一个页面上运行,它可以访问页面上的敏感信息和 你可以在沙盒环境中自己尝试: 作为用户,需要注意的是,任何代码都可能是恶意的,只有点击或添加书签时,至少有以下一项为真: 小书签可以很方便,但我们也有网络扩展和用户脚本。是什么让它们与众不同? 网络扩展是令人难以置信的用户友好和灵活。小书签不能阻止网络请求,不能随着页面变化而更新内容,也不能管理标签。 然而,使用小书签比其他任何东西都有一些好处,即隐私和安全。 修改所有网页上的字体的扩展必须获得访问所有网页上的所有数据的权限。在Firefox和Chrome上,这包括所有的输入和密码字段。(更多信息:Mozilla,Google) 相比之下,书签程序只有在它执行的那一刻才能访问页面,而且只有在用户手动触发的时候才能访问。 这导致了更少的恶意软件风险,一个流氓员工无法推送恶意更新,数据也不会悄悄地被发送到其他服务器。 此前,Chrome网络商店有几个恶意的扩展程序,不得不被删除。其中一些在被删除之前有数百万的安装量。(更多信息) 这里有一个书签想法的列表,以及实现它们的代码。你可以将它们复制并粘贴到新的书签中,以尝试它们。 收集当前页面的所有电子邮件地址,并在警报中显示。 找到页面中的 “工作”、”职业 “或 “招聘 “链接,并点击它。 将当前页面上所有文字的字体设置为 “Comic Sans MS”。 谢谢你的阅读!现在去创造你自己的小书签吧。(a
)。document.cookies
。<a href="javascript:(() => { alert(document.cookie); })();"> EvilScript</a>
只运行你信任的代码
隐私和安全
小书签实例
javascript: (() => { constdocumentHTML=document.documentElement.outerHTML; constmatches=documentHTML.matchAll(/[\w.+=~-]+@[a-zA-Z0-9-]+(?:\.[a-zA-Z0-]+)*/g); constflatMatches=Array.from(matches).map((item) =>item[0]); constuniqueMatches=Array.from(new Set(flatMatches)); if (uniqueMatches.length> 0) { constresult=uniqueMatches.join('\n'); alert(result); else { alert('No emails found!'); } }();
javascript: (() => { constxpath= "/a [contains(., 'Jobs') or contains(., 'Careers') or contains(., 'Hiring')]"; constelements=document.evaluation(xpath,document); constelement=elements.iterateNext();if (element) {element.click(); } else { alert('No links for jobs found! '); })();
javascript: (() => { constallElements=document.querySelectorAll('*'); for (letelementofallElements) {element.style.fontFamily= 'Comic Sans MS'; })();