【问题标题】:What is the "-journal" SQLite database in Android?什么是 Android 中的“-journal”SQLite 数据库?
【发布时间】:2014-11-30 06:59:32
【问题描述】:

在我的 Android 应用程序的数据库目录 (/data/data/com.me.myApp/databases) 中,对于我创建的每个 sqlite 数据库,都有一个相应的同名数据库,并在其名称后附加“-journal”。

例如:myDatabase、myDatabase-journal、myOtherDatabase.db、myOtherDatabase.db-journal

这是什么?

和,

如果我为我的应用程序提供预填充的数据库(根据:http://www.reigndesign.com/blog/using-your-own-sqlite-database-in-android-applications/),我是否也需要包含这些数据库?'

【问题讨论】:

    标签: android sqlite journal


    【解决方案1】:

    此类-journal 文件不需要(并且应该)分发。

    这是因为各种日志文件代表 SQLite 使用的临时数据(参考SQLite's Use Of Temporary Disk Files)。特别是-journal 文件是一个回滚日志

    回滚日志是用于在 SQLite 中实现原子提交和回滚功能的临时文件。 (有关其工作原理的详细讨论,请参阅名为 Atomic Commit In SQLite 的单独文档。)回滚日志始终与数据库文件位于同一目录中,并且与数据库文件具有相同的名称,除了 8 个字符“ -journal”附加。

    回滚日志通常在事务首次启动时创建,通常在事务提交或回滚时删除。回滚日志文件对于实现 SQLite 的原子提交和回滚功能至关重要。如果没有回滚日志,SQLite 将无法回滚不完整的事务,并且如果在事务中间发生崩溃或断电,则整个数据库可能会在没有回滚日志的情况下损坏。

    一般来说,这些-journal 文件应该只存在于有一个打开的 SQLite 数据库 - 或者更确切地说,一个正在运行的事务 - 但可以通过 PRAGMA journal_mode 控制。使用默认编译指示设置,-journal 文件将被删除。

    DELETE 日志模式是正常行为。在 DELETE 模式下,回滚日志在每个事务结束时被删除。实际上,删除操作是导致事务提交的操作。

    确保在数据库打开且所有日志已被 SQLite 自身删除(或清除)时复制实际的数据库文件;这意味着所有事务都已完成,并且数据库处于一致状态。

    【讨论】:

    • 如果 -journal 文件始终存在且大小不小(例如 30kB),但您的应用程序没有对数据库执行任何活动,并且不会让数据库保持打开状态,该怎么办?
    • @Michael 这是一个很好的问题 - 但我担心它会被埋没在评论中,因为我没有直接的专业知识答案。考虑创建另一个 SO 问题,链接到这个(和其他)问题/答案以提供良好的基础。
    • @Michael 对不起,我可能来得太晚了,但我有一些有趣的信息here。它表示当提交事务时,标头通常为零。在每次提交时,都会写入标头,然后写入页面,覆盖原始内容,然后在成功时仅将标头归零。如果另一个提交没有这样做,“清理”(例如删除)文件的一般解决方案可能是在数据库中执行 VACUUM。
    【解决方案2】:

    DB-JOURNAL 文件是 SQLite 数据库管理系统在应用程序和数据库之间的事务期间创建的临时数据库文件。它包含一个回滚日志,它是一个临时数据库,用于存储数据库的最新状态。

    【讨论】:

      【解决方案3】:

      这个问题解决了吗?我有一种情况,我无法从 android 设备复制我想在本地机器上复制的 .db。我必须手动删除设备上的 -journal 才能成功复制 .db。这是我用 C# 编写的代码

      var devices = MediaDevice.GetDevices();
      using (var device = devices.First(d => d.Description == "PM67"))
      {
          device.Connect();
          var photoDir = device.GetDirectoryInfo(@"\Internal Shared Storage\Databases");
      
          var files = photoDir.EnumerateFiles("database.db", SearchOption.AllDirectories);
      
          foreach (var file in files)
          {
              MemoryStream memoryStream = new System.IO.MemoryStream();
              device.DownloadFile(file.FullName, memoryStream);
              memoryStream.Position = 0;
      
              try
              {
                  device.DeleteFile(@"\Internal Storage\Databases\database.db-journal");//this is the part where I'd like to delete the -journal but it's not working
              }
              catch
              {
              }
      
              try
              {
                  if (File.Exists(result) == true)
                  {
                      File.Delete(result);
                  }
              }
              catch
              {
              }
              WriteSreamToDisk(result, memoryStream);
          }
          device.Disconnect();
      }
      

      【讨论】:

      • 这不清楚,这是提供解决方案的答案,还是您要求给定代码不起作用的解决方案?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-04-02
      • 2011-04-19
      • 2011-09-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多