UNPKG

@itwin/object-storage-tests-backend

Version:

Tests for generic storage packages

325 lines 19.2 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); /*--------------------------------------------------------------------------------------------- * Copyright (c) Bentley Systems, Incorporated. All rights reserved. * See LICENSE.md in the project root for license terms and full copyright notice. *--------------------------------------------------------------------------------------------*/ const crypto_1 = require("crypto"); const fs_1 = require("fs"); const path = require("path"); const chai_1 = require("chai"); const chaiAsPromised = require("chai-as-promised"); const object_storage_core_1 = require("@itwin/object-storage-core"); const Config_1 = require("./Config"); const Global_test_1 = require("./Global.test"); const utils_1 = require("./utils"); chai_1.use(chaiAsPromised); const { serverStorage } = Config_1.config; describe(`${object_storage_core_1.ServerStorage.name}: ${serverStorage.constructor.name}`, () => { describe(`${serverStorage.createBaseDirectory.name}()`, () => { it("should create directory", async () => { const testDirectory = { baseDirectory: `test-create-directory-${crypto_1.randomUUID()}`, }; Global_test_1.testDirectoryManager.addForDelete(testDirectory); await serverStorage.createBaseDirectory(testDirectory); const exists = await serverStorage.baseDirectoryExists(testDirectory); chai_1.expect(exists).to.be.equal(true); }); }); describe(`${serverStorage.upload.name}()`, () => { const contentBuffer = Buffer.from("server-upload-content"); const uploadTestCases = [ { caseName: "Buffer", objectName: "test-upload-buffer.txt", dataCallback: (_sourcePath) => contentBuffer, }, { caseName: "Stream", objectName: "test-upload-stream.txt", dataCallback: (sourcePath) => fs_1.createReadStream(sourcePath), }, { caseName: "path", objectName: "test-upload-local.txt", dataCallback: (sourcePath) => sourcePath, }, ]; for (const testCase of uploadTestCases) { const { caseName, objectName, dataCallback } = testCase; it(`should upload a file from ${caseName}`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-server-upload.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, objectName, }; await serverStorage.upload(reference, dataCallback(fileToUploadPath)); await utils_1.checkUploadedFileValidity(reference, contentBuffer); }); it(`should upload a file with relative directory from ${caseName}`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-server-upload-relative-dir.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, relativeDirectory: "relative-1/relative-2", objectName, }; const metadata = { test: "test-metadata", }; await serverStorage.upload(reference, dataCallback(fileToUploadPath), metadata); await utils_1.checkUploadedFileValidity(reference, contentBuffer); }); it(`should upload a file from ${caseName} with metadata`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-server-upload-metadata.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, objectName, }; const metadata = { test: "test-metadata", }; await serverStorage.upload(reference, dataCallback(fileToUploadPath), metadata); await utils_1.checkUploadedFileValidity(reference, contentBuffer); await utils_1.queryAndAssertMetadata(reference, metadata); }); } it("should fail to upload if specified path contains empty file", async () => { const emptyFilePath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-empty-file.txt"); const uploadPromise = serverStorage.upload({ baseDirectory: "test-directory", objectName: "test-object-name", }, emptyFilePath); await chai_1.expect(uploadPromise).to.eventually.be.rejectedWith(Error, "Provided path is an empty file."); }); }); describe(`${serverStorage.uploadInMultipleParts.name}()`, function () { const contentBuffer = Buffer.from("server-multipart-upload-content"); const uploadTestCases = [ { caseName: "Stream", objectName: "test-multipart-upload-stream.txt", dataCallback: (sourcePath) => fs_1.createReadStream(sourcePath), }, { caseName: "path", objectName: "test-multipart-upload-local.txt", dataCallback: (sourcePath) => sourcePath, }, ]; for (const testCase of uploadTestCases) { const { caseName, objectName, dataCallback } = testCase; it(`should upload a file from ${caseName}`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-multipart-server-upload.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, objectName, }; await serverStorage.uploadInMultipleParts(reference, dataCallback(fileToUploadPath)); await utils_1.checkUploadedFileValidity(reference, contentBuffer); }); it(`should upload a file with relative directory from ${caseName}`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-multipart-server-upload-relative-dir.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, relativeDirectory: "relative-1/relative-2", objectName, }; await serverStorage.uploadInMultipleParts(reference, dataCallback(fileToUploadPath)); await utils_1.checkUploadedFileValidity(reference, contentBuffer); }); it(`should upload a file from ${caseName} with metadata`, async () => { const fileToUploadPath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-multipart-server-upload-metadata.txt", contentBuffer); const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const reference = { baseDirectory: testBaseDirectory.baseDirectory, objectName, }; const metadata = { test: "test-metadata", }; await serverStorage.uploadInMultipleParts(reference, dataCallback(fileToUploadPath), { metadata }); await utils_1.checkUploadedFileValidity(reference, contentBuffer); await utils_1.queryAndAssertMetadata(reference, metadata); }); } it("should fail to upload in multiple parts if specified path contains empty file", async () => { const emptyFilePath = await Global_test_1.testLocalFileManager.createAndWriteFile("test-empty-file.txt"); const uploadPromise = serverStorage.uploadInMultipleParts({ baseDirectory: "test-directory", objectName: "test-object-name", }, emptyFilePath); await chai_1.expect(uploadPromise).to.eventually.be.rejectedWith(Error, "Provided path is an empty file."); }); }); describe(`${serverStorage.list.name}()`, () => { it("should list objects", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const reference1 = await testDirectory.uploadFile({ objectName: "reference1" }, undefined, undefined); const reference2 = await testDirectory.uploadFile({ objectName: "reference2" }, undefined, undefined); const queriedReferences = await serverStorage.list(testDirectory.baseDirectory); chai_1.expect(queriedReferences.length).to.be.equal(2); const queriedReference1 = queriedReferences.find((ref) => ref.objectName === reference1.objectName); chai_1.expect(queriedReference1).to.be.deep.equal(reference1); const queriedReference2 = queriedReferences.find((ref) => ref.objectName === reference2.objectName); chai_1.expect(queriedReference2).to.be.deep.equal(reference2); }); }); describe(`${serverStorage.deleteBaseDirectory.name}()`, () => { it("should delete directory with files", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const tempFiles = ["temp-1", "temp-2", "temp-3"]; await Promise.all(tempFiles.map(async (file) => testDirectory.uploadFile({ objectName: file }, Buffer.from(file), undefined))); await serverStorage.deleteBaseDirectory(testDirectory.baseDirectory); const doesDirectoryExist = await serverStorage.baseDirectoryExists(testDirectory.baseDirectory); chai_1.expect(doesDirectoryExist).to.be.equal(false); }); it("should not throw if base directory does not exist", async () => { const deletePromise = serverStorage.deleteBaseDirectory({ baseDirectory: crypto_1.randomUUID(), }); await chai_1.expect(deletePromise).to.eventually.be.fulfilled; }); }); describe(`${serverStorage.deleteObject.name}()`, async () => { it("should delete object", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const reference = await testDirectory.uploadFile({ objectName: "test-delete.txt" }, undefined, undefined); await serverStorage.deleteObject(reference); const objectExists = await serverStorage.objectExists(reference); chai_1.expect(objectExists).to.be.false; }); it("should not throw if file does not exist", async () => { const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const deletePromise = serverStorage.deleteObject({ baseDirectory: testBaseDirectory.baseDirectory, objectName: crypto_1.randomUUID(), }); await chai_1.expect(deletePromise).to.eventually.be.fulfilled; }); it("should not throw if the whole path does not exist", async () => { const deletePromise = serverStorage.deleteObject({ baseDirectory: crypto_1.randomUUID(), relativeDirectory: crypto_1.randomUUID(), objectName: crypto_1.randomUUID(), }); await chai_1.expect(deletePromise).to.eventually.be.fulfilled; }); it("should retain the directory after all files from it have been deleted", async () => { const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const testFileToUpload = { baseDirectory: testBaseDirectory.baseDirectory, objectName: "test-delete-object.txt", }; const contentBuffer = Buffer.from("test-delete-object"); await serverStorage.upload(testFileToUpload, contentBuffer); await serverStorage.deleteObject(testFileToUpload); const exists = await serverStorage.baseDirectoryExists(testBaseDirectory); chai_1.expect(exists).to.be.true; }); }); describe(`${serverStorage.baseDirectoryExists.name}()`, () => { it("should return true if base directory exists", async () => { const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const exists = await serverStorage.baseDirectoryExists({ baseDirectory: testBaseDirectory.baseDirectory, }); chai_1.expect(exists).to.be.true; }); it("should return false if base directory does not exist", async () => { const exists = await serverStorage.baseDirectoryExists({ baseDirectory: crypto_1.randomUUID(), }); chai_1.expect(exists).to.be.false; }); }); describe(`${serverStorage.objectExists.name}()`, () => { it("should return true if file exists", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const reference = await testDirectory.uploadFile({ objectName: "test-exists.txt" }, undefined, undefined); const exists = await serverStorage.objectExists(reference); chai_1.expect(exists).to.be.true; }); it("should return false if file does not exist", async () => { const testBaseDirectory = (await Global_test_1.testDirectoryManager.createNew()).baseDirectory; const exists = await serverStorage.objectExists({ baseDirectory: testBaseDirectory.baseDirectory, objectName: crypto_1.randomUUID(), }); chai_1.expect(exists).to.be.false; }); it("should return false if the whole path does not exist", async () => { const exists = await serverStorage.objectExists({ baseDirectory: crypto_1.randomUUID(), relativeDirectory: crypto_1.randomUUID(), objectName: crypto_1.randomUUID(), }); chai_1.expect(exists).to.be.false; }); }); describe(`${serverStorage.download.name}()`, () => { const contentBuffer = Buffer.from("test-download"); it("should download a file to buffer", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const uploadedFile = await testDirectory.uploadFile({ objectName: "file-to-download.txt" }, contentBuffer, undefined); const response = await serverStorage.download(uploadedFile, "buffer"); utils_1.assertBuffer(response, contentBuffer); }); it("should download a file to stream", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const uploadedFile = await testDirectory.uploadFile({ objectName: "file-to-download.txt" }, contentBuffer, undefined); const response = await serverStorage.download(uploadedFile, "stream"); await utils_1.assertStream(response, contentBuffer); }); it("should download a file to path", async () => { const testDownloadFolder = await Global_test_1.testLocalFileManager.getDownloadsDir(); const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const uploadedFile = await testDirectory.uploadFile({ objectName: "file-to-download.txt" }, contentBuffer, undefined); const response = await serverStorage.download(uploadedFile, "local", path.join(testDownloadFolder, "download.txt")); await utils_1.assertLocalFile(response, contentBuffer); }); }); describe(`${serverStorage.getObjectProperties.name}()`, () => { it("should get correct object properties", async () => { const data = Buffer.from("test-properties"); const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const uploadMetadata = { test: "test-metadata", }; const uploadedFile = await testDirectory.uploadFile({ objectName: "test-object-properties.txt" }, data, uploadMetadata); const { lastModified, reference: queriedReference, size, metadata, } = await serverStorage.getObjectProperties(uploadedFile); chai_1.expect(Date.now() - lastModified.getTime() < 60 * 1000).to.be.true; // not older than 1 minute chai_1.expect(queriedReference).to.equal(uploadedFile); chai_1.expect(size === data.byteLength); chai_1.expect(metadata === null || metadata === void 0 ? void 0 : metadata.test).to.be.equal("test-metadata"); }); }); describe(`${serverStorage.updateMetadata.name}()`, () => { it("should update metadata", async () => { const testDirectory = await Global_test_1.testDirectoryManager.createNew(); const initialMetadata = { test1: "test-metadata-1", test2: "test-metadata-2", }; const uploadedFile = await testDirectory.uploadFile({ objectName: "update-metadata-test.txt" }, Buffer.from("test-metadata"), initialMetadata); await utils_1.queryAndAssertMetadata(uploadedFile, initialMetadata); const updatedMetadata1 = { test1: "test-metadata-1", test2: "update-test-metadata-2", }; await serverStorage.updateMetadata(uploadedFile, updatedMetadata1); await utils_1.queryAndAssertMetadata(uploadedFile, updatedMetadata1); const updatedMetadata2 = { test3: "test-metadata-3", }; await serverStorage.updateMetadata(uploadedFile, updatedMetadata2); await utils_1.queryAndAssertMetadata(uploadedFile, updatedMetadata2); }); }); }); //# sourceMappingURL=ServerStorage.test.js.map