Rewrote date time reading from db to use epoch instead of normal date to avoid string parsing of dates

This commit is contained in:
Kenneth Skovhede
2013-07-16 14:52:35 +02:00
parent 9675a4326f
commit 4809897a00
3 changed files with 25 additions and 12 deletions
@@ -139,7 +139,7 @@ namespace Duplicati.Library.Main.Database
using (var cmd = m_connection.CreateCommand())
cmd.ExecuteNonQuery(string.Format(@"CREATE TEMPORARY TABLE ""{0}"" AS SELECT ""FilesetEntry"".""FileID"" AS ""FileID"", MAX(""FilesetEntry"".""Scantime"") AS ""Scantime"", ""File"".""Path"" AS ""Path"" FROM ""FilesetEntry"" INNER JOIN ""File"" ON ""File"".""ID"" = ""FilesetEntry"".""FileID"" GROUP BY ""FilesetEntry"".""FileID"", ""File"".""Path"" ", m_scantimelookupTablename));
m_selectfileSimpleCommand.CommandText = string.Format(@"SELECT ""FileID"", ""Scantime"" FROM ""{0}"" WHERE ""Path"" = ?", m_scantimelookupTablename);
m_selectfileSimpleCommand.CommandText = string.Format(@"SELECT ""FileID"", CAST(strftime('%s', ""Scantime"") AS INTEGER) AS ""Scantime"" FROM ""{0}"" WHERE ""Path"" = ?", m_scantimelookupTablename);
m_selectfileSimpleCommand.AddParameters(1);
m_selectfileHashCommand.CommandText = @"SELECT ""Blockset"".""Fullhash"" FROM ""Blockset"", ""File"" WHERE ""Blockset"".""ID"" = ""File"".""BlocksetID"" AND ""File"".""ID"" = ? ";
@@ -203,11 +203,11 @@ namespace Duplicati.Library.Main.Database
}
if (m_fileScantimeLookup != null)
using (var rd = cmd.ExecuteReader(string.Format(@" SELECT ""FileID"", ""Scantime"", ""Path"" FROM ""{0}"" ", m_scantimelookupTablename)))
using (var rd = cmd.ExecuteReader(string.Format(@" SELECT ""FileID"", CAST(strftime('%s', ""Scantime"") AS INTEGER) AS ""Scantime"", ""Path"", ""Scantime"" FROM ""{0}"" ", m_scantimelookupTablename)))
while (rd.Read())
{
var id = Convert.ToInt64(rd.GetValue(0));
var scantime = new DateTime(Convert.ToDateTime(rd.GetValue(1)).Ticks, DateTimeKind.Utc);
var scantime = ParseFromEpochSeconds(Convert.ToInt64(rd.GetValue(1)));
var path = rd.GetValue(2).ToString();
m_fileScantimeLookup.Add((ulong)path.GetHashCode(), path, new KeyValuePair<long, DateTime>(id, scantime));
}
@@ -622,7 +622,7 @@ namespace Duplicati.Library.Main.Database
if (m_fileScantimeLookup != null)
m_fileScantimeLookup.NegativeMisses++;
oldScanned = new DateTime(Convert.ToDateTime(rd.GetValue(1)).Ticks, DateTimeKind.Utc);
oldScanned = ParseFromEpochSeconds(Convert.ToInt64(rd.GetValue(1)));
var id = Convert.ToInt64(rd.GetValue(0));
// We do not add here, because we will never query the same path twice,
@@ -844,12 +844,12 @@ namespace Duplicati.Library.Main.Database
using(var cmd = m_connection.CreateCommand())
{
cmd.Transaction = transaction;
using(var rd = cmd.ExecuteReader(@"SELECT ""ID"", ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" IN (SELECT ""FilesetID"" FROM ""FilesetEntry"") AND ""VolumeID"" NOT IN (SELECT ""ID"" FROM ""RemoteVolume"")"))
using(var rd = cmd.ExecuteReader(@"SELECT ""ID"", CAST(strftime('%s', ""Timestamp"") AS INTEGER) AS ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" IN (SELECT ""FilesetID"" FROM ""FilesetEntry"") AND ""VolumeID"" NOT IN (SELECT ""ID"" FROM ""RemoteVolume"")"))
while(rd.Read())
{
yield return new KeyValuePair<long, DateTime>(
Convert.ToInt64(rd.GetValue(0)),
Convert.ToDateTime(rd.GetValue(1)).ToLocalTime()
ParseFromEpochSeconds(Convert.ToInt64(rd.GetValue(1))).ToLocalTime()
);
}
}
@@ -136,6 +136,19 @@ namespace Duplicati.Library.Main.Database
return new DateTime(ticks, DateTimeKind.Utc);
}
/// <summary>
/// The EPOCH time (unix time)
/// </summary>
private static readonly DateTime EPOCH = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
/// <summary>
/// Creates a DateTime instance by adding the specified number of seconds to the EPOCH value
/// </summary>
public static DateTime ParseFromEpochSeconds(long seconds)
{
return Library.Utility.Utility.EPOCH.AddSeconds(seconds);
}
public void UpdateRemoteVolume(string name, RemoteVolumeState state, long size, string hash, System.Data.IDbTransaction transaction = null)
{
m_updateremotevolumeCommand.Transaction = transaction;
@@ -157,9 +170,9 @@ namespace Duplicati.Library.Main.Database
get
{
using(var cmd = m_connection.CreateCommand())
using(var rd = cmd.ExecuteReader(@"SELECT ""ID"", ""Timestamp"" FROM ""Fileset"" ORDER BY ""Timestamp"" DESC"))
using(var rd = cmd.ExecuteReader(@"SELECT ""ID"", CAST(strftime('%s', ""Timestamp"") AS INTEGER) AS ""Timestamp"" FROM ""Fileset"" ORDER BY ""Timestamp"" DESC"))
while (rd.Read())
yield return new KeyValuePair<long, DateTime>(Convert.ToInt64(rd.GetValue(0)), Convert.ToDateTime(rd.GetValue(1)).ToLocalTime());
yield return new KeyValuePair<long, DateTime>(Convert.ToInt64(rd.GetValue(0)), ParseFromEpochSeconds(Convert.ToInt64(rd.GetValue(1))).ToLocalTime());
}
}
@@ -673,7 +686,7 @@ namespace Duplicati.Library.Main.Database
filesetvolume.AddSymlink(path, metahash, metalength);
}
cmd.CommandText = @"SELECT ""F"".""Path"", ""F"".""Scantime"", ""F"".""Filelength"", ""F"".""Filehash"", ""F"".""Metahash"", ""F"".""Metalength"", ""G"".""Hash"" FROM (SELECT ""A"".""Path"" AS ""Path"", ""D"".""Scantime"" AS ""Scantime"", ""B"".""Length"" AS ""Filelength"", ""B"".""FullHash"" AS ""Filehash"", ""E"".""FullHash"" AS ""Metahash"", ""E"".""Length"" AS ""Metalength"", ""A"".""BlocksetID"" AS ""BlocksetID"" FROM ""File"" A, ""Blockset"" B, ""Metadataset"" C, ""FilesetEntry"" D, ""Blockset"" E WHERE ""A"".""ID"" = ""D"".""FileID"" AND ""D"".""FilesetID"" = ? AND ""A"".""BlocksetID"" = ""B"".""ID"" AND ""A"".""MetadataID"" = ""C"".""ID"" AND ""E"".""ID"" = ""C"".""BlocksetID"") F LEFT OUTER JOIN ""BlocklistHash"" G ON ""G"".""BlocksetID"" = ""F"".""BlocksetID"" ORDER BY ""F"".""Path"", ""G"".""Index"" ";
cmd.CommandText = @"SELECT ""F"".""Path"", CAST(strftime('%s', ""F"".""Scantime"") AS INTEGER) AS ""Scantime"", ""F"".""Filelength"", ""F"".""Filehash"", ""F"".""Metahash"", ""F"".""Metalength"", ""G"".""Hash"" FROM (SELECT ""A"".""Path"" AS ""Path"", ""D"".""Scantime"" AS ""Scantime"", ""B"".""Length"" AS ""Filelength"", ""B"".""FullHash"" AS ""Filehash"", ""E"".""FullHash"" AS ""Metahash"", ""E"".""Length"" AS ""Metalength"", ""A"".""BlocksetID"" AS ""BlocksetID"" FROM ""File"" A, ""Blockset"" B, ""Metadataset"" C, ""FilesetEntry"" D, ""Blockset"" E WHERE ""A"".""ID"" = ""D"".""FileID"" AND ""D"".""FilesetID"" = ? AND ""A"".""BlocksetID"" = ""B"".""ID"" AND ""A"".""MetadataID"" = ""C"".""ID"" AND ""E"".""ID"" = ""C"".""BlocksetID"") F LEFT OUTER JOIN ""BlocklistHash"" G ON ""G"".""BlocksetID"" = ""F"".""BlocksetID"" ORDER BY ""F"".""Path"", ""G"".""Index"" ";
cmd.Parameters.Clear();
cmd.AddParameter(filesetId);
@@ -686,7 +699,7 @@ namespace Duplicati.Library.Main.Database
var path = rd.GetValue(0).ToString();
var filehash = rd.GetValue(3).ToString();
var size = Convert.ToInt64(rd.GetValue(2));
var scantime = Convert.ToDateTime(rd.GetValue(1));
var scantime = ParseFromEpochSeconds(Convert.ToInt64(rd.GetValue(1)));
var metahash = rd.GetValue(4).ToString();
var metasize = Convert.ToInt64(rd.GetValue(5));
var blrd = new BlocklistHashEnumerable(rd);
@@ -37,7 +37,7 @@ namespace Duplicati.Library.Main.Database
using(var cmd = m_connection.CreateCommand())
{
long filesetId = GetFilesetID(NormalizeDateTime(restoretime), versions);
m_restoreTime = Convert.ToDateTime(cmd.ExecuteScalar(@"SELECT ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" = ?", filesetId));
m_restoreTime = ParseFromEpochSeconds(Convert.ToInt64(cmd.ExecuteScalar(@"SELECT CAST(strftime('%s', ""Timestamp"") AS INTEGER) AS ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" = ?", filesetId)));
cmd.Parameters.Clear();
cmd.CommandText = string.Format(@"CREATE TEMPORARY TABLE ""{0}"" (""ID"" INTEGER PRIMARY KEY, ""Path"" TEXT NOT NULL, ""BlocksetID"" INTEGER NOT NULL, ""MetadataID"" INTEGER NOT NULL, ""Targetpath"" TEXT NULL ) ", m_tempfiletable);
@@ -87,7 +87,7 @@ namespace Duplicati.Library.Main.Database
while (rd.Read())
sb.AppendLine(rd.GetValue(0).ToString());
DateTime actualrestoretime = Convert.ToDateTime(cmd.ExecuteScalar(@"SELECT ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" = ?", filesetId));
var actualrestoretime = ParseFromEpochSeconds(Convert.ToInt64(cmd.ExecuteScalar(@"SELECT CAST(strftime('%s', ""Timestamp"") AS INTEGER) AS ""Timestamp"" FROM ""Fileset"" WHERE ""ID"" = ?", filesetId)));
log.AddWarning(string.Format("{0} File(s) were not found in list of files for backup at {1}, will not be restored: {2}", p.Length - c, actualrestoretime.ToLocalTime(), sb), null);
cmd.Parameters.Clear();
}