目录:
有时候,我们需要将数据存储在浏览器端。对于数据量较小的场景,可以存入 localStorage。但它有容量限制,通常上限为 5MB。当数据量较大时,建议使用 IndexedDB,这是浏览器内置的一种 NoSQL 数据库。相比于 localStorage,IndexedDB 具备以下核心优势:
onupgradeneeded 是 IndexedDB 中唯一允许创建对象仓库(表)和索引的事件监听器,所有数据库结构的初始化与修改都必须在此事件中完成。
// 第一个参数是数据库名称,第二个参数是版本号
const request = indexedDB.open('MyDB', 1);
// 数据库首次创建或版本升级时触发
request.onupgradeneeded = (event) => {
const db = event.target.result;
// 创建对象存储(类似表),主键为 id
db.createObjectStore('users', { keyPath: 'id' });
};
// 数据库创建成功会进入该方法
request.onsuccess = (event) => {
const db = event.target.result;
console.log('数据库打开成功');
// 后续操作...
};
function addUser(db) {
const tx = db.transaction('users', 'readwrite');
const store = tx.objectStore('users');
store.add({ id: 1, name: '张三', age: 25 });
}
根据过滤条件读取数据。
function getUser(db, id) {
const tx = db.transaction('users', 'readonly');
const store = tx.objectStore('users');
const request = store.get(id);
request.onsuccess = () => {
console.log(request.result) // 是个对象字面量
};
}
读取全部数据。
function getUser(db, id) {
const tx = db.transaction('users', 'readonly');
const store = tx.objectStore('users');
const request = store.getAll();
request.onsuccess = () => {
console.log(request.result) // 是个数组
};
}
function updateUser(db) {
const tx = db.transaction('users', 'readwrite');
const store = tx.objectStore('users');
store.put({ id: 1, name: '李四', age: 30 }); // put 会覆盖已有数据
}
function deleteUser(db, id) {
const tx = db.transaction('users', 'readwrite');
const store = tx.objectStore('users');
store.delete(id);
}
以下代码可直接复制到 HTML 文件中,在浏览器中打开即可测试运行。
打开控制台,依次展开 Application → IndexedDB,即可看到 UserDatabase,再点开就能看到其中的 users 表。
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<title>IndexedDB 增删改查演示</title>
<style>
body { font-family: Arial, sans-serif; margin: 20px; line-height: 1.6; }
.container { max-width: 800px; margin: 0 auto; }
button { margin: 5px; padding: 8px 16px; cursor: pointer; }
input { margin: 5px; padding: 6px; }
table { width: 100%; border-collapse: collapse; margin-top: 20px; }
th, td { border: 1px solid #ddd; padding: 8px; text-align: left; }
th { background-color: #f4f4f4; }
.section { margin: 20px 0; padding: 15px; border: 1px solid #ddd; border-radius: 4px; }
.result { margin-top: 10px; padding: 10px; background: #f9f9f9; border-left: 3px solid #4CAF50; }
</style>
</head>
<body>
<div class="container">
<h1>IndexedDB 增删改查演示</h1>
<!-- 添加数据区域 -->
<div class="section">
<h3>添加用户</h3>
<input type="text" id="addName" placeholder="姓名">
<input type="number" id="addAge" placeholder="年龄">
<input type="email" id="addEmail" placeholder="邮箱">
<button onclick="addUser()">添加</button>
</div>
<!-- 查找数据区域 -->
<div class="section">
<h3>查询用户</h3>
<input type="number" id="queryId" placeholder="输入 ID">
<button onclick="getUserById()">按ID查询</button>
<button onclick="getAllUsers()">查询全部</button>
</div>
<!-- 更新数据区域 -->
<div class="section">
<h3>更新用户</h3>
<input type="number" id="updateId" placeholder="用户ID">
<input type="text" id="updateName" placeholder="新姓名">
<input type="number" id="updateAge" placeholder="新年龄">
<button onclick="updateUser()">更新</button>
</div>
<!-- 删除数据区域 -->
<div class="section">
<h3>删除用户</h3>
<input type="number" id="deleteId" placeholder="输入 ID">
<button onclick="deleteUser()">删除</button>
<button onclick="clearAll()">清空全部</button>
</div>
<!-- 结果显示区域 -->
<div class="section">
<h3>数据展示</h3>
<table id="userTable">
<thead>
<tr>
<th>ID</th>
<th>姓名</th>
<th>年龄</th>
<th>邮箱</th>
</tr>
</thead>
<tbody id="userList"></tbody>
</table>
<div id="result" class="result">操作结果将显示在这里</div>
</div>
</div>
<script>
// ==================== 数据库配置 ====================
const DB_NAME = 'UserDatabase';
const DB_VERSION = 1;
const STORE_NAME = 'users';
let db = null;
// ==================== 打开/创建数据库 ====================
function openDatabase() {
return new Promise((resolve, reject) => {
const request = indexedDB.open(DB_NAME, DB_VERSION);
// 数据库创建或版本升级时触发
request.onupgradeneeded = (event) => {
const database = event.target.result;
// 创建对象仓库(类似表),主键为 id,自增
if (!database.objectStoreNames.contains(STORE_NAME)) {
const store = database.createObjectStore(STORE_NAME, {
keyPath: 'id',
autoIncrement: true
});
// 创建索引,方便按邮箱等字段查询
store.createIndex('email', 'email', { unique: true });
store.createIndex('name', 'name', { unique: false });
store.createIndex('age', 'age', { unique: false });
}
};
request.onsuccess = (event) => {
db = event.target.result;
console.log('数据库打开成功');
resolve(db);
};
request.onerror = (event) => {
console.error('数据库打开失败:', event.target.error);
reject(event.target.error);
};
});
}
// ==================== 添加数据 ====================
function addUser() {
const name = document.getElementById('addName').value.trim();
const age = parseInt(document.getElementById('addAge').value);
const email = document.getElementById('addEmail').value.trim();
if (!name || !age || !email) {
showResult('请填写完整的用户信息');
return;
}
const userData = { name, age, email };
// 使用事务进行写操作
const transaction = db.transaction([STORE_NAME], 'readwrite');
const store = transaction.objectStore(STORE_NAME);
const request = store.add(userData);
request.onsuccess = () => {
showResult(`用户添加成功,ID: ${request.result}`);
clearInputs();
getAllUsers(); // 刷新展示
};
request.onerror = (event) => {
if (event.target.error.name === 'ConstraintError') {
showResult('邮箱已存在,请使用其他邮箱');
} else {
showResult('添加失败: ' + event.target.error);
}
};
}
// ==================== 查询数据 ====================
// 按ID查询
function getUserById() {
const id = parseInt(document.getElementById('queryId').value);
if (!id) {
showResult('请输入要查询的 ID');
return;
}
const transaction = db.transaction([STORE_NAME], 'readonly');
const store = transaction.objectStore(STORE_NAME);
const request = store.get(id);
request.onsuccess = () => {
if (request.result) {
showResult(`查询结果: ${JSON.stringify(request.result, null, 2)}`);
renderUsers([request.result]);
} else {
showResult('未找到该用户');
}
};
}
// 查询全部用户
function getAllUsers() {
const transaction = db.transaction([STORE_NAME], 'readonly');
const store = transaction.objectStore(STORE_NAME);
const request = store.getAll();
request.onsuccess = () => {
const users = request.result || [];
renderUsers(users);
showResult(`共查询到 ${users.length} 条记录`);
};
}
// ==================== 更新数据 ====================
function updateUser() {
const id = parseInt(document.getElementById('updateId').value);
const name = document.getElementById('updateName').value.trim();
const age = parseInt(document.getElementById('updateAge').value);
if (!id) {
showResult('请输入要更新的用户 ID');
return;
}
// 先查询是否存在
const transaction = db.transaction([STORE_NAME], 'readwrite');
const store = transaction.objectStore(STORE_NAME);
const getRequest = store.get(id);
getRequest.onsuccess = () => {
const existingUser = getRequest.result;
if (!existingUser) {
showResult('未找到要更新的用户');
return;
}
// 修改数据,使用 put 方法更新
if (name) existingUser.name = name;
if (age) existingUser.age = age;
const updateRequest = store.put(existingUser);
updateRequest.onsuccess = () => {
showResult(`用户 ID:${id} 更新成功`);
getAllUsers(); // 刷新展示
};
};
}
// ==================== 删除数据 ====================
function deleteUser() {
const id = parseInt(document.getElementById('deleteId').value);
if (!id) {
showResult('请输入要删除的 ID');
return;
}
const transaction = db.transaction([STORE_NAME], 'readwrite');
const store = transaction.objectStore(STORE_NAME);
const request = store.delete(id);
request.onsuccess = () => {
showResult(`用户 ID:${id} 删除成功`);
getAllUsers(); // 刷新展示
};
}
// 清空全部数据
function clearAll() {
if (!confirm('确定要清空所有用户数据吗?')) return;
const transaction = db.transaction([STORE_NAME], 'readwrite');
const store = transaction.objectStore(STORE_NAME);
const request = store.clear();
request.onsuccess = () => {
showResult('所有用户数据已清空');
renderUsers([]);
};
}
// ==================== 界面辅助函数 ====================
// 渲染用户表格
function renderUsers(users) {
const tbody = document.getElementById('userList');
tbody.innerHTML = '';
users.forEach(user => {
const tr = document.createElement('tr');
tr.innerHTML = `
<td>${user.id}</td>
<td>${user.name}</td>
<td>${user.age}</td>
<td>${user.email}</td>
`;
tbody.appendChild(tr);
});
}
// 显示操作结果
function showResult(message) {
document.getElementById('result').textContent = message;
}
// 清空输入框
function clearInputs() {
document.getElementById('addName').value = '';
document.getElementById('addAge').value = '';
document.getElementById('addEmail').value = '';
}
// ==================== 初始化 ====================
// 页面加载完成后打开数据库并加载数据
window.onload = async () => {
try {
await openDatabase();
getAllUsers(); // 加载已有数据
showResult('数据库初始化成功,可以开始操作');
} catch (error) {
showResult('数据库初始化失败: ' + error.message);
}
};
</script>
</body>
</html>
↶ 返回首页 ↶