39948-vm/backend/tests/upload-session-manager.test.ts
2026-07-02 13:13:36 +02:00

103 lines
3.3 KiB
TypeScript

import assert from 'node:assert/strict';
import fs from 'node:fs';
import os from 'node:os';
import path from 'node:path';
import test from 'node:test';
import UploadSessionManager from '../src/services/file/UploadSessionManager.ts';
function makeSessionManager(ttlMs = 60_000): {
manager: UploadSessionManager;
rootDir: string;
} {
const rootDir = fs.mkdtempSync(path.join(os.tmpdir(), 'upload-sessions-'));
return {
manager: new UploadSessionManager({ sessionDir: rootDir, ttlMs }),
rootDir,
};
}
void test('UploadSessionManager creates metadata and tracks uploaded chunks', async () => {
const { manager, rootDir } = makeSessionManager();
try {
const sessionId = manager.createSession({
filename: 'tour.mp4',
folder: 'assets',
totalChunks: 2,
totalSize: 11,
userId: 'user-1',
contentType: 'video/mp4',
});
let meta = manager.readMeta(sessionId);
assert.equal(meta?.filename, 'tour.mp4');
assert.equal(meta?.uploadedChunks !== undefined, true);
assert.equal(manager.isComplete(sessionId), false);
await manager.saveChunk(sessionId, 0, Buffer.from('hello '));
await manager.saveChunk(sessionId, 1, Buffer.from('world'));
meta = manager.readMeta(sessionId);
assert.equal(meta?.uploadedChunks[0]?.size, 6);
assert.equal(meta?.uploadedChunks[1]?.size, 5);
assert.equal(manager.chunkExists(sessionId, 0), true);
assert.equal(manager.isComplete(sessionId), true);
} finally {
fs.rmSync(rootDir, { recursive: true, force: true });
}
});
void test('UploadSessionManager assembles chunks in index order', async () => {
const { manager, rootDir } = makeSessionManager();
try {
const sessionId = manager.createSession({
filename: 'image.bin',
folder: 'assets',
totalChunks: 3,
totalSize: 9,
});
await manager.saveChunk(sessionId, 2, Buffer.from('ghi'));
await manager.saveChunk(sessionId, 0, Buffer.from('abc'));
await manager.saveChunk(sessionId, 1, Buffer.from('def'));
const targetPath = path.join(rootDir, 'assembled', 'image.bin');
await manager.assembleChunks(sessionId, targetPath);
assert.equal(fs.readFileSync(targetPath, 'utf8'), 'abcdefghi');
} finally {
fs.rmSync(rootDir, { recursive: true, force: true });
}
});
void test('UploadSessionManager removes expired and invalid sessions during cleanup', () => {
const { manager, rootDir } = makeSessionManager(1);
try {
const expiredSessionId = manager.createSession({
filename: 'expired.txt',
folder: 'assets',
totalChunks: 1,
totalSize: 1,
});
const meta = manager.readMeta(expiredSessionId);
assert.ok(meta);
meta.updatedAt = new Date(Date.now() - 10_000).toISOString();
manager.writeMeta(expiredSessionId, meta);
const invalidSessionId = 'invalid-session';
const invalidSessionDir = manager.getSessionDir(invalidSessionId);
fs.mkdirSync(invalidSessionDir, { recursive: true });
fs.writeFileSync(
manager.getMetaPath(invalidSessionId),
JSON.stringify({ sessionId: invalidSessionId }),
'utf8',
);
manager.cleanupExpiredSessions();
assert.equal(fs.existsSync(manager.getSessionDir(expiredSessionId)), false);
assert.equal(fs.existsSync(invalidSessionDir), false);
} finally {
fs.rmSync(rootDir, { recursive: true, force: true });
}
});