SQLite 自带的 sqlite3 命令行工具很适合临时查数据、排查问题、导入导出小文件。下面整理一份常用命令,日常够用了。

启动和打开数据库

# 打开已有数据库;文件不存在时会自动创建
sqlite3 app.db

# 只读方式打开,适合线上排查
sqlite3 -readonly app.db

# 直接执行一条 SQL 后退出
sqlite3 app.db "select count(*) from users;"

# 打开内存数据库
sqlite3 :memory:

进入交互终端后,提示符一般是:

sqlite>

SQLite 终端里有两类命令:

  • SQL 语句:例如 select * from users;,末尾需要分号。
  • 点命令:例如 .tables.schema,以 . 开头,不需要分号。

查看帮助和退出

.help       -- 查看所有点命令
.quit       -- 退出
.exit       -- 退出

如果 SQL 写了一半进入了多行模式,可以用 Ctrl+C 取消当前输入。

查看数据库结构

.databases              -- 查看当前连接的数据库文件
.tables                 -- 查看所有表
.tables user%           -- 按模式过滤表名
.schema                 -- 查看完整建表语句
.schema users           -- 查看某张表的建表语句
.indexes                -- 查看所有索引
.indexes users          -- 查看某张表的索引

也可以直接查系统表:

select name, type
from sqlite_master
where type in ('table', 'index', 'view')
order by type, name;

查看表字段:

pragma table_info(users);

查看外键:

pragma foreign_key_list(users);

输出格式设置

默认输出不太适合阅读,建议先打开表头和列模式:

.headers on
.mode column
select id, name, created_at from users limit 10;

常用输出模式:

.mode column       -- 表格列对齐,适合人看
.mode box          -- 边框表格,新版本 sqlite3 更好看
.mode list         -- 默认模式
.mode csv          -- CSV
.mode json         -- JSON
.mode line         -- 每列一行,适合字段很多的记录

设置空值显示:

.nullvalue NULL

打开 SQL 执行时间:

.timer on

常用查询

查看前几行:

select * from users limit 10;

按时间倒序:

select *
from users
order by created_at desc
limit 20;

统计行数:

select count(*) from users;

模糊搜索:

select *
from users
where name like '%tom%';

查看重复数据:

select email, count(*) as n
from users
group by email
having n > 1;

删除数据

删除前先查一遍,确认条件命中了正确的数据:

select *
from users
where id = 10;

删除一条记录:

delete from users
where id = 10;

按条件删除多条记录:

delete from users
where status = 'disabled';

删除前统计影响行数:

select count(*)
from users
where status = 'disabled';

更稳妥的做法是放进事务里:

begin;

delete from users
where status = 'disabled';

-- 确认删除后的结果
select count(*) from users;

commit;

如果发现删错了,在 commit; 之前可以回滚:

rollback;

清空整张表:

delete from users;

如果表有自增主键,并且想同时重置自增序列:

delete from users;
delete from sqlite_sequence where name = 'users';

SQLite 没有 MySQL 那种 truncate table users;,清空表一般就是用 delete from users;

删除表结构和数据:

drop table users;

drop table 会把整张表删掉,表结构也没了,执行前最好先 .schema users.dump users 留一份。

导入和导出

导出查询结果到 CSV

.headers on
.mode csv
.once users.csv
select id, name, email from users;

.once 只影响下一条 SQL。也可以用 .output 持续输出到文件:

.output users.csv
select * from users;
.output stdout

导入 CSV 到表

先确认表已经存在:

create table users_import (
    id integer,
    name text,
    email text
);

再导入:

.mode csv
.import users.csv users_import

如果 CSV 第一行是表头,新版 sqlite3 可以这样跳过:

.import --skip 1 users.csv users_import

导出整个数据库

sqlite3 app.db ".dump" > app.sql

只导出某张表:

sqlite3 app.db ".dump users" > users.sql

从 SQL 文件恢复:

sqlite3 new.db < app.sql

备份和复制数据库

在 sqlite3 交互终端中备份:

.backup backup.db

把当前数据库保存为新文件:

.save copy.db

如果数据库正在被应用使用,优先用 .backup,不要直接复制 app.db 文件。

执行 SQL 文件

sqlite3 app.db < migration.sql

或在交互终端里执行:

.read migration.sql

事务操作

手动开启事务:

begin;

update users
set status = 'disabled'
where last_login_at < '2025-01-01';

commit;

发现不对就回滚:

rollback;

线上手动改数据时,建议先 begin;,查清影响范围后再 commit;

查看执行计划

explain query plan
select *
from users
where email = 'a@example.com';

如果结果里看到全表扫描,并且这条查询很频繁,可以考虑加索引:

create index idx_users_email on users(email);

常用 PRAGMA

查看 SQLite 版本:

select sqlite_version();

查看数据库页大小和大小信息:

pragma page_size;
pragma page_count;
pragma freelist_count;

开启外键约束:

pragma foreign_keys = on;

查看外键是否开启:

pragma foreign_keys;

检查数据库完整性:

pragma integrity_check;

清理空间:

vacuum;

更新统计信息,帮助查询优化器:

analyze;

Attach 多个数据库

有时需要在两个 SQLite 数据库之间复制数据:

attach database 'old.db' as old;

insert into users (id, name, email)
select id, name, email
from old.users;

detach database old;

查看当前连接:

.databases

排查锁问题

如果遇到:

database is locked

可以先设置等待时间:

.timeout 5000

表示最多等待 5000 毫秒。

也可以检查当前 journal 模式:

pragma journal_mode;

开发环境可以考虑启用 WAL:

pragma journal_mode = wal;

WAL 通常能改善读写并发,但是否适合线上环境要结合部署方式判断,尤其是网络文件系统上要谨慎。

一个常用启动模板

平时查库可以这样开:

sqlite3 -readonly app.db

进入后先执行:

.headers on
.mode box
.timer on
.nullvalue NULL
.tables

如果 sqlite3 版本不支持 .mode box,就换成:

.mode column

小结

最常用的一组命令:

.help
.databases
.tables
.schema users
.headers on
.mode box
.timer on
.once result.csv
.import data.csv table_name
.backup backup.db
.read file.sql
.quit

记住点命令不加分号、SQL 语句要加分号,基本就能顺畅使用 sqlite3 终端了。