jQuery 入门与遗留项目维护:选择器、事件和安全更新
本文目录
jQuery 仍会出现在长期维护的站点、CMS 和插件中。维护时先确认项目锁定的 jQuery 版本和插件依赖,再小步修复;不必为了现代化一次性重写所有页面。新项目通常可以先评估原生 DOM、事件和 Fetch 是否已足够。
jQuery 集合和原生 DOM 节点不是同一对象
const $button = $('#save');
const button = $button[0];
if (button) {
button.disabled = true;
$(button).text('保存中');
}
选择器返回 jQuery 集合,集合可包装零个或多个 DOM 节点;数组索引或 get(0) 取得原生节点,$(node) 再包装为 jQuery 对象。原生节点的 addEventListener 与 jQuery 的 on 属于不同 API,读旧代码时先确认当前变量类型。链式调用方便,但不要把链式返回值误认为某个元素或业务数据。
DOM ready 与 window load
$(function () {
const $root = $('#orders');
if ($root.length === 0) return;
$root.on('click.orders', '.js-remove', handleRemove);
});
$(handler) 在 DOM 可操作时运行,即便脚本在 DOM ready 之后才加载也会执行。window load 则等待页面依赖资源加载完成,只有需要图片自然尺寸等信息时才考虑。它们都不是所有业务请求完成的信号。经典脚本可用 defer 把 DOM 时机放到解析之后;模块脚本默认延后执行。
事件委托、命名空间和清理
动态列表中的按钮会被重新创建,直接绑定到旧节点的事件会随节点替换而丢失。把事件委托到稳定容器,并在功能销毁时按命名空间解绑。委托选择器应足够具体,避免一个点击触发多个业务分支。
function handleRemove(event) {
const id = event.currentTarget.dataset.id;
if (!id) return;
removeOrder(id);
}
function mountOrderList($root) {
$root.on('click.orders', '[data-action="remove"]', handleRemove);
return () => $root.off('.orders');
}
事件 currentTarget 是匹配选择器并处理回调的元素;target 可能是它内部被点击的图标。命名空间便于精确清理,不要在组件卸载时无条件调用 off() 删除别的模块注册的监听。新代码可以用 addEventListener 的事件委托、AbortSignal 管理生命周期。
文本、HTML 与属性
用 .text(untrustedValue) 更新普通文本;.html(value) 会解析标记并可能形成 XSS 注入点。只有经过明确的 sanitizer、策略校验并被认定可信的富文本才可进入 HTML sink。不要把用户输入、URL 参数或接口消息拼成 HTML 字符串。写属性时区分 .attr() 与 .prop():静态 HTML 属性和值、DOM 当前属性状态并不总是同一件事,例如 checkbox 的 checked 状态。
隐式迭代意味着对多个匹配节点调用 .text() 会逐个更新;但读取 .text() 会聚合集合文本。选择器没有命中时,很多 jQuery 写操作会静默无效,因此关键操作应检查 length,并结合测试避免选择器拼写错误被掩盖。
渐进迁移路线
- 先记录 jQuery、插件和浏览器支持范围,锁定版本并检查能否升级到受支持版本。
- 修复 XSS、事件泄漏、重复初始化和未处理的异步错误等行为问题。
- 新功能可用原生 DOM 或框架实现;旧页面通过明确的边界与之互操作。
- 逐页替换插件和全局依赖,确认样式、表单、键盘和浏览器要求后再删除依赖。
jQuery 不会替应用解决权限、CORS、表单校验或可信来源问题。浏览器端隐藏按钮不是授权;数据接口仍需服务端验证身份、资源归属与输入。不要仅因使用 jQuery 就把所有代码描述成不兼容现代浏览器,应以目标浏览器和实际依赖测试为准。
参考:jQuery ready、jQuery on、jQuery off、jQuery text、jQuery html、OWASP DOM XSS Prevention、MDN addEventListener。
Live Notes
留言提交后会先进入审核,审核通过后对其他读者公开。