1
0
Fork 0
forked from dlang/cdcdb

Оптимизация

This commit is contained in:
Alexander Zhirov 2025-09-13 00:48:36 +03:00
parent d93dc4d81b
commit 8716a90463
Signed by: alexander
GPG key ID: C8D8BE544A27C511

View file

@ -4,7 +4,7 @@ import cdcdb.dblite;
import zstd : uncompress; import zstd : uncompress;
import std.digest.sha : SHA256, digest, SHA256Digest; import std.digest.sha : SHA256, digest;
import std.datetime : DateTime; import std.datetime : DateTime;
import std.exception : enforce; import std.exception : enforce;
@ -13,6 +13,25 @@ final class Snapshot
private: private:
DBLite _db; DBLite _db;
DBSnapshot _snapshot; DBSnapshot _snapshot;
const(ubyte)[] getBytes(const ref DBSnapshotChunkData chunk)
{
ubyte[] bytes;
if (chunk.zstd)
{
enforce(chunk.zSize == chunk.content.length, "Размер сжатого фрагмента не соответствует ожидаемому");
bytes = cast(ubyte[]) uncompress(chunk.content);
}
else
{
bytes = chunk.content.dup;
}
enforce(chunk.size == bytes.length, "Оригинальный размер не соответствует ожидаемому");
enforce(chunk.sha256 == digest!SHA256(bytes), "Хеш-сумма фрагмента не совпадает");
return bytes;
}
public: public:
this(DBLite dblite, DBSnapshot dbSnapshot) this(DBLite dblite, DBSnapshot dbSnapshot)
{ {
@ -30,25 +49,18 @@ public:
{ {
auto chunks = _db.getChunks(_snapshot.id); auto chunks = _db.getChunks(_snapshot.id);
ubyte[] content; ubyte[] content;
content.reserve(_snapshot.sourceLength);
auto fctx = SHA256();
foreach (chunk; chunks) foreach (chunk; chunks)
{ {
ubyte[] bytes; const(ubyte)[] bytes = getBytes(chunk);
if (chunk.zstd)
{
enforce(chunk.zSize == chunk.content.length, "Размер сжатого фрагмента не соответствует ожидаемому");
bytes = cast(ubyte[]) uncompress(chunk.content);
}
else
{
bytes = chunk.content;
}
enforce(chunk.size == bytes.length, "Оригинальный размер не соответствует ожидаемому");
enforce(chunk.sha256 == digest!SHA256(bytes), "Хеш-сумма фрагмента не совпадает");
content ~= bytes; content ~= bytes;
fctx.put(bytes);
} }
enforce(_snapshot.sha256 == digest!SHA256(content), "Хеш-сумма файла не совпадает"); enforce(_snapshot.sha256 == fctx.finish(), "Хеш-сумма файла не совпадает");
return content; return content;
} }
@ -56,29 +68,16 @@ public:
void data(void delegate(const(ubyte)[]) sink) void data(void delegate(const(ubyte)[]) sink)
{ {
auto chunks = _db.getChunks(_snapshot.id); auto chunks = _db.getChunks(_snapshot.id);
auto fctx = new SHA256Digest(); auto fctx = SHA256();
foreach (chunk; chunks) foreach (chunk; chunks)
{ {
ubyte[] bytes; const(ubyte)[] bytes = getBytes(chunk);
if (chunk.zstd)
{
enforce(chunk.zSize == chunk.content.length, "Размер сжатого фрагмента не соответствует ожидаемому");
bytes = cast(ubyte[]) uncompress(chunk.content);
}
else
{
bytes = chunk.content;
}
enforce(chunk.size == bytes.length, "Оригинальный размер не соответствует ожидаемому");
enforce(chunk.sha256 == digest!SHA256(bytes), "Хеш-сумма фрагмента не совпадает");
sink(bytes); sink(bytes);
fctx.put(bytes); fctx.put(bytes);
} }
enforce(_snapshot.sha256 = fctx.finish(), "Хеш-сумма файла не совпадает"); enforce(_snapshot.sha256 == fctx.finish(), "Хеш-сумма файла не совпадает");
} }
bool remove() bool remove()
@ -132,6 +131,7 @@ public:
@property string status() const @property string status() const
{ {
import std.conv : to; import std.conv : to;
return _snapshot.status.to!string; return _snapshot.status.to!string;
} }