如何恢复损坏的SQLite3数据库?

lin*_*sek 57 database sqlite recovery corruption

这是以前回答的帖子的后续问题:是否有用于在Linux中验证SQLite数据库的命令行实用程序?

如果数据库产生以下错误:

$ sqlite3 mydata.db "PRAGMA integrity_check"
Error: database disk image is malformed
Run Code Online (Sandbox Code Playgroud)

是否有任何清理处理可以将数据库恢复到可用状态?即使有可能丢失一些腐败记录?

谢谢

CL.*_*CL. 104

如果有任何自动方法,SQLite已经能够做到.

有时,损坏只是或主要在索引中,在这种情况下,可以通过尝试转储整个数据库来获取一些或大多数记录.dump,并使用这些命令来创建新数据库:

$ sqlite3 mydata.db ".dump" | sqlite3 new.db
Run Code Online (Sandbox Code Playgroud)

但是,这并不总是可行的.

最简单,最可靠的方法是从备份中恢复数据库文件.

  • 这实际上对我有用.".dump"从我的损坏文件中生成了可接受的SQL,即integrity_check失败. (3认同)
  • 非常感谢您的回复!几分钟内修复了我的数据库;)但是,重要的是要注意,所有包含格式错误的数据的条目都不会被复制,新数据库将包含可以从旧数据库中恢复的所有条目.只需看看.dump的输出,你就会看到你的数据库如何工作以及哪些条目产生错误;) (3认同)
  • 这使我免于头疼,谢谢! (2认同)
  • @NeMo CL 编写的命令分为两部分。第一部分创建整个数据库的 SQL 脚本 (.dump)。后半部分将其写入新的数据库。但由于它将一个命令的输出通过管道传输到另一个命令,因此您永远不会获得实际的文件。如果将第一个命令的输出通过管道传输到文件,您将能够编辑它。因此,如果您改为运行 sqlite3 mydata.db ".dump" > db_script.sql`,您将获得一个可以编辑的 SQL 脚本,并确保最后没有像 ROLLBACK 这样的奇怪内容;然后,您可以使用“sqlite3 returned.db < db_script.sql”从该脚本创建数据库 (2认同)

aru*_*run 35

Sqlite 3.29.0.recover中,CLI 引入了一个新命令:

添加“.recover”命令,该命令尝试从损坏的数据库文件中恢复尽可能多的内容。

sqlite3 broken.db ".recover" | sqlite3 new.db
Run Code Online (Sandbox Code Playgroud)

  • 这对我有用(尽管我的内存不足)。我使用了`sqlite3broken.db“.recover”| sqlite3 new.db` (3认同)
  • “.recover”为我工作了>1Gb 的数据库。只需 1 分钟即可恢复数据库,因此它比我之前尝试过的任何商业 SQLite 恢复工具都要高效(其中一些甚至无法恢复数据库,而另一些则需要近一个小时才能恢复)。非常感谢 SQLite 开发团队提供了这个非常有用的功能 (2认同)

joh*_*chd 18

我有一个腐败的sqlite文件,会显示这样的症状.

select count(*) from corruptTable;
return:38000;
Run Code Online (Sandbox Code Playgroud)

但是当我尝试加载记录时

select * from corruptTable;
Run Code Online (Sandbox Code Playgroud)

它只会返回7条记录.

我尝试了几件事,但这些步骤最成功.

在Mac上,打开终端并在损坏的数据库上运行这些命令.(这些是sqlite3命令,因此您应该能够在其他系统中使用其他sqlite3编辑器或类似命令).

1 sqlite3 dbWithCorruptTable.sqlite (Obviously replace "dbWithCorruptTable" to your sqlite3 file that has the corrupt table)
2 .mode insert
3 .output dump_all.sql
4 .dump
5 .exit
6 Manually edit the dump_all.sql file in a text editor and remove the transaction statements. Usually there is a "BEGIN TRANSACTION" statement on the 2nd line of the file and a "ROLLBACK" statement on the last line. Remove these and save the file
Run Code Online (Sandbox Code Playgroud)

这些步骤来自本网站:http://www.dosomethinghere.com/2013/02/20/fixing-the-sqlite-error-the-database-disk-image-is-malformed/

  • 注意:如果文件非常大(例如500Mb),则无法轻松编辑SQL文件。然后,您应该使用以下命令行:-> cat dump_all_last.sql | grep -v TRANSACTION | grep -v ROLLBACK> dump_all_last_notrans.sql (2认同)

Sta*_*r00 10

如果数据库严重损坏,.dump则会包含错误,并且某些数据可能会丢失.

对于更复杂的数据模式,这将意味着可能使应用程序混淆的孤立和/或部分记录.

可能最好.dump是文件,然后使用文本编辑器删除有问题的行.ERROR在转储文件中搜索.


Oli*_*ter 8

我能够通过这种方式修复我的Chrome历史文件(这是一个sqlite3数据库文件):

sqlite3.exe History ".backup History-new"
Run Code Online (Sandbox Code Playgroud)

  • 太好了!我一直使用.dump,然后将其加载到新数据库中。您的方法有一个好处,那就是它可以用于使用自定义归类等不使用.dump的数据库。 (2认同)

Thi*_*eye 6

pragmawritable_schema禁用了一些完整性检查,因此这两个命令也可以达到目的,保持数据库自定义:

PRAGMA writable_schema=ON;
VACUUM;
Run Code Online (Sandbox Code Playgroud)


小智 6

我的方法很相似,可以防止错误回滚脚本:

sqlite3 database.db ".dump" | sed -e 's|^ROLLBACK;\( -- due to errors\)*$|COMMIT;|g' | sqlite3 database.new
Run Code Online (Sandbox Code Playgroud)

  • 这是允许我修复 nextcloud sqlite 数据库方案的唯一方法,因此我可以恢复备份(这需要运行主脚本,这将防止早期架构错误)。 (2认同)

小智 5

我知道这是一个老问题,但是我仍然想分享我的解决方案。我的问题是kodi(xbmc)的sqlite3数据库已损坏。

.dump在我的情况下不起作用

file is encrypted or is not a database

起作用的是以下内容:

  1. 备份了旧的db文件
  2. 让kodi创建一个新的数据库文件
  3. 站点上检查了sqlite文件的头格式
  4. 使用十六进制编辑器(bless)打开两个文件,并检查前96个字节
  5. 前40个字节不同,因此我将前40个字节从新的db文件复制到了旧的db文件
  6. 完成此操作后,我的数据库文件再次工作!

  • 好一个。完成此操作后,您可能应该立即重建数据库,例如使用“.dump”/“.repair”,如其他答案中所示,以确保文件具有完整的完整性。 (2认同)