浏览器已经是超级计算机。只要你问一下。
Source: Dev.to
开发者花费数小时配置构建工具、审计依赖并争论 bundle 大小——结果却是把已经内置在浏览器中、完整构建、完全免费且随时可用的功能直接交付。无需 npm install。无需从 CDN 导入。无需第三方信任。
下面列出其中的十项功能。每一项都已准备好用于生产,得到广泛支持,且足够强大,能够取代你今天可能会去寻找的库。
1. Fetch + Streams API
fetch 是 HTTP 请求的标准。结合 Streams API,你可以在数据到达时进行处理——这正是 AI token 流式传输的工作方式。
2. Web Workers
JavaScript 在单线程上运行。Web Workers 为你提供第二条线程,让繁重的任务(解析、加密、数据处理)在后台运行,而不会冻结 UI。
// Worker code must live in its own scope — use a Blob URL to inline it
const code = `
self.onmessage = ({ data }) => {
const result = data.map(n => n * 2);
self.postMessage(result);
};
`;
const blob = new Blob([code], { type: 'application/javascript' });
const worker = new Worker(URL.createObjectURL(blob));
worker.postMessage([1, 2, 3, 4, 5]);
worker.onmessage = e => console.log('Done:', e.data); // [2, 4, 6, 8, 10]
3. IntersectionObserver
当元素进入或离开视口时触发回调。处理懒加载和滚动动画的正确方式——无需滚动事件监听器。
const observer = new IntersectionObserver((entries, observer) => {
entries.forEach(entry => {
if (entry.isIntersecting) {
entry.target.classList.add('visible');
observer.unobserve(entry.target);
}
});
}, { threshold: 0.2 });
document.querySelectorAll('.card').forEach(el => observer.observe(el));
4. IndexedDB
浏览器中的完整异步数据库。可存储结构化数据、二进制大对象(blob)和文件——远超 localStorage 的能力。
const request = indexedDB.open('AppDB', 1);
request.onupgradeneeded = e => {
e.target.result.createObjectStore('notes', { autoIncrement: true });
};
request.onsuccess = e => {
const db = e.target.result;
const tx = db.transaction('notes', 'readwrite');
tx.objectStore('notes').add({ text: 'Hello', date: Date.now() });
};
5. WebSocket
一种在浏览器和服务器之间持久的双向连接。任一方都可以随时发送消息——非常适用于聊天、实时仪表盘和多人游戏。
const ws = new WebSocket('wss://your-server.com/socket');
ws.onopen = () => ws.send(JSON.stringify({ type: 'hello' }));
ws.onmessage = e => console.log(JSON.parse(e.data));
ws.onclose = () => console.log('Disconnected');
6. 文件系统访问 API
读取和写入用户磁盘上的真实文件(需获得权限)。使能够在浏览器中完整运行的桌面级编辑器和工具成为可能。
async function openAndSave() {
const [handle] = await window.showOpenFilePicker();
const file = await handle.getFile();
const text = await file.text();
const edited = text + '\n// edited';
const writable = await handle.createWritable();
await writable.write(edited);
await writable.close();
}
// Call the function, e.g. on a button click
// openAndSave();
7. Canvas 与 OffscreenCanvas
Canvas 为你提供像素级别的绘图。OffscreenCanvas 将渲染移到 Worker 中进行,从而使图形渲染永不与主线程竞争。
const ctx = document.getElementById('c').getContext('2d');
function draw(t) {
ctx.clearRect(0, 0, 400, 200);
ctx.fillStyle = '#c8f542';
ctx.beginPath();
ctx.arc(200 + Math.sin(t / 500) * 150, 100, 20, 0, Math.PI * 2);
ctx.fill();
requestAnimationFrame(draw);
}
requestAnimationFrame(draw);
8. MediaDevices & MediaRecorder
访问摄像头、麦克风或屏幕,并记录所有传入的内容——无需第三方 SDK。
const audio = document.getElementById('playback');
const stream = await navigator.mediaDevices.getUserMedia({ audio: true });
const recorder = new MediaRecorder(stream);
const chunks = [];
recorder.ondataavailable = e => chunks.push(e.data);
recorder.onstop = () => {
const blob = new Blob(chunks, { type: 'audio/webm' });
audio.src = URL.createObjectURL(blob);
};
recorder.start();
setTimeout(() => recorder.stop(), 5000); // record for 5 seconds
9. requestAnimationFrame + Performance API
requestAnimationFrame 将你的代码与屏幕刷新率同步。Performance API 以亚毫秒精度测量经过的时间。两者结合可实现平滑、精准的动画。
const canvas = document.getElementById('c');
const ctx = canvas.getContext('2d');
let x = 0;
let last = 0;
function loop(timestamp) {
const delta = timestamp - last;
last = timestamp;
ctx.clearRect(0, 0, canvas.width, canvas.height);
x = (x + 200 * (delta / 1000)) % canvas.width;
ctx.beginPath();
ctx.arc(x, canvas.height / 2, 16, 0, Math.PI * 2);
ctx.fillStyle = '#c8f542';
ctx.fill();
requestAnimationFrame(loop);
}
requestAnimationFrame(loop);
10. BroadcastChannel
让同源的标签页、窗口和 worker 能够即时通信。同步认证状态、共享缓存更新,或在多个打开的标签页之间协调 UI——无需服务器。
const channel = new BroadcastChannel('app');
// Send from any tab
channel.postMessage({ type: 'logout' });
// Receive in every other tab
channel.onmessage = ({ data }) => {
if (data.type === 'logout') redirectToLogin();
};
要点
这些 API 都不需要 npm、添加到你的 bundle 中,也不依赖第三方代码。它们已经内置在所有现代浏览器中多年——因此你可以更快发布,保持 bundle 体积小,并且完全掌控你的应用。
在寻找库之前,值得先问问平台是否已经提供了你需要的功能。通常情况下,它们已经有了。
今天你学到了有价值的东西吗?
— Muhammad Usman
Developer’s Journey – 展示你的支持。