feat: add docker pipeline and preview fixes
This commit is contained in:
@@ -0,0 +1,137 @@
|
||||
import test from 'node:test';
|
||||
import assert from 'node:assert/strict';
|
||||
import fs from 'node:fs';
|
||||
import os from 'node:os';
|
||||
import path from 'node:path';
|
||||
|
||||
import { DuplicatiRepository } from '../src/db/duplicatiRepository.js';
|
||||
import { openWritableSqlite } from '../src/db/sqlite.js';
|
||||
import { createDuplicatiFixture } from './support/duplicatiFixture.js';
|
||||
|
||||
function createAppDatabasePath() {
|
||||
const tempDirectory = fs.mkdtempSync(path.join(os.tmpdir(), 'duplicati-app-'));
|
||||
return {
|
||||
appDbPath: path.join(tempDirectory, 'app.sqlite'),
|
||||
cleanup() {
|
||||
fs.rmSync(tempDirectory, { recursive: true, force: true });
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
async function openAttachedRepository(sourceOverrides = {}) {
|
||||
const fixture = createDuplicatiFixture(sourceOverrides);
|
||||
const appDb = createAppDatabasePath();
|
||||
const database = await openWritableSqlite(appDb.appDbPath);
|
||||
await database.attachDatabase('source', fixture.databasePath, { readOnly: true });
|
||||
const sourceLayout = sourceOverrides.layout ?? 'file';
|
||||
|
||||
const repository = new DuplicatiRepository({
|
||||
database,
|
||||
previewMaxBytes: 1024,
|
||||
source: {
|
||||
id: 'source-1',
|
||||
storagePath: fixture.databasePath,
|
||||
sha256: 'sha-demo',
|
||||
capabilities: {
|
||||
archiveEntryIndex: true,
|
||||
volumeCryptoCache: true
|
||||
}
|
||||
},
|
||||
sourceLayout
|
||||
});
|
||||
|
||||
return {
|
||||
fixture,
|
||||
appDb,
|
||||
repository,
|
||||
database
|
||||
};
|
||||
}
|
||||
|
||||
test('listDirectory returns immediate directory and file children', async () => {
|
||||
const session = await openAttachedRepository();
|
||||
|
||||
try {
|
||||
const result = await session.repository.listDirectory({
|
||||
apiPath: '/C:/media',
|
||||
snapshotId: 'latest'
|
||||
});
|
||||
|
||||
assert.equal(result.path, '/C:/media');
|
||||
assert.equal(result.entries.length, 2);
|
||||
assert.deepEqual(
|
||||
result.entries.map((entry) => ({
|
||||
type: entry.type,
|
||||
path: entry.path
|
||||
})),
|
||||
[
|
||||
{ type: 'dir', path: '/C:/media/movies' },
|
||||
{ type: 'file', path: '/C:/media/readme.txt' }
|
||||
]
|
||||
);
|
||||
} finally {
|
||||
await session.database.detachDatabase('source');
|
||||
await session.database.close();
|
||||
session.fixture.cleanup();
|
||||
session.appDb.cleanup();
|
||||
}
|
||||
});
|
||||
|
||||
test('getFileInfo expands ordered segments and required dblocks', async () => {
|
||||
const session = await openAttachedRepository();
|
||||
|
||||
try {
|
||||
const listing = await session.repository.listDirectory({
|
||||
apiPath: '/C:/media/movies',
|
||||
snapshotId: 'latest'
|
||||
});
|
||||
const fileId = listing.entries.find((entry) => entry.type === 'file')?.id;
|
||||
|
||||
assert.ok(fileId);
|
||||
|
||||
const result = await session.repository.getFileInfo(fileId);
|
||||
assert.equal(result.file.path, '/C:/media/movies/demo.mp4');
|
||||
assert.equal(result.restorePlan.segmentCount, 3);
|
||||
assert.equal(result.restorePlan.blockSize, 102400);
|
||||
assert.equal(result.requiredDblocks.length, 1);
|
||||
assert.equal(result.requiredDblocks[0], 'duplicati-demo.dblock.zip.aes');
|
||||
assert.equal(result.volumes[0].encryption.streamFormat, 'v2');
|
||||
assert.equal(result.segments[0].logicalOffset, 0);
|
||||
assert.equal(result.segments[1].logicalOffset, 102400);
|
||||
assert.equal(result.segments[2].zip.compressionMethod, 'deflate');
|
||||
} finally {
|
||||
await session.database.detachDatabase('source');
|
||||
await session.database.close();
|
||||
session.fixture.cleanup();
|
||||
session.appDb.cleanup();
|
||||
}
|
||||
});
|
||||
|
||||
test('listDirectory supports FileLookup plus PathPrefix based databases', async () => {
|
||||
const session = await openAttachedRepository({ layout: 'file_lookup' });
|
||||
|
||||
try {
|
||||
const result = await session.repository.listDirectory({
|
||||
apiPath: '/source/media',
|
||||
snapshotId: 'latest'
|
||||
});
|
||||
|
||||
assert.equal(result.path, '/source/media');
|
||||
assert.equal(result.entries.length, 2);
|
||||
assert.deepEqual(
|
||||
result.entries.map((entry) => ({
|
||||
type: entry.type,
|
||||
path: entry.path
|
||||
})),
|
||||
[
|
||||
{ type: 'dir', path: '/source/media/movies' },
|
||||
{ type: 'file', path: '/source/media/readme.txt' }
|
||||
]
|
||||
);
|
||||
} finally {
|
||||
await session.database.detachDatabase('source');
|
||||
await session.database.close();
|
||||
session.fixture.cleanup();
|
||||
session.appDb.cleanup();
|
||||
}
|
||||
});
|
||||
Reference in New Issue
Block a user