@ts-common/azure-js-dev-tools
Version:
Developer dependencies for TypeScript related projects
1,120 lines (1,119 loc) • 64.9 kB
JavaScript
"use strict";
/**
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for
* license information.
*/
Object.defineProperty(exports, "__esModule", { value: true });
exports.AzureBlobStorage = exports.getAzureContainerAccessPermissions = exports.validateBlobName = exports.InMemoryBlobStorage = exports.constructBlobStorageCredentials = exports.getStorageAccountName = exports.constructBlobStorageURL = exports.BlobStorage = exports.BlobStorageAppendBlob = exports.BlobStorageBlockBlob = exports.BlobStorageBlob = exports.BlobStorageContainer = exports.BlobStoragePrefix = exports.BlobPath = exports.getFileLengthInBytes = void 0;
var tslib_1 = require("tslib");
var storage_blob_1 = require("@azure/storage-blob");
var fs = tslib_1.__importStar(require("fs"));
var arrays_1 = require("./arrays");
var common_1 = require("./common");
var url_1 = require("./url");
var defaultEncoding = "utf8";
/**
* Get the number of bytes in the provided file.
* @param filePath The path to the file.
*/
function getFileLengthInBytes(filePath) {
return new Promise(function (resolve, reject) {
fs.lstat(filePath, function (error, stats) {
if (error) {
reject(error);
}
else {
resolve(stats.size);
}
});
});
}
exports.getFileLengthInBytes = getFileLengthInBytes;
/**
* A path to a blob.
*/
var BlobPath = /** @class */ (function () {
function BlobPath(containerName, blobName) {
this.containerName = containerName;
this.blobName = blobName;
}
/**
* Concatenate the provided blobName onto this BlobPath.
* @param blobName The blobName to concatenate to this BlobPath.
*/
BlobPath.prototype.concatenate = function (blobName) {
return !blobName ? this : new BlobPath(this.containerName, this.blobName + blobName);
};
/**
* Get the string representation of this BlobPath object.
*/
BlobPath.prototype.toString = function () {
return this.containerName + "/" + this.blobName;
};
/**
* Parse a BlobPath object from the provided blobPath. The blobPath string must contain a forward
* slash.
* @param blobPath The blob path to parse.
*/
BlobPath.parse = function (blobPath) {
var result;
if (blobPath instanceof BlobPath) {
result = blobPath;
}
else if (!blobPath) {
result = new BlobPath("", "");
}
else {
if (blobPath.startsWith("/")) {
blobPath = blobPath.substring(1);
}
var firstSlashIndex = blobPath.indexOf("/");
if (firstSlashIndex === -1) {
result = new BlobPath(blobPath, "");
}
else {
result = new BlobPath(blobPath.substring(0, firstSlashIndex), blobPath.substring(firstSlashIndex + 1));
}
}
return result;
};
return BlobPath;
}());
exports.BlobPath = BlobPath;
/**
* A prefix to other BlobStorageBlobs.
*/
var BlobStoragePrefix = /** @class */ (function () {
/**
* Create a new prefix within the provided BlobStorage system.
* @param storage The BlobStorage system that this prefix targets.
* @param path The path of this prefix.
*/
function BlobStoragePrefix(storage, path) {
this.storage = storage;
this.path = typeof path === "string" ? BlobPath.parse(path) : path;
}
/**
* Get the URL for this prefix.
*/
BlobStoragePrefix.prototype.getURL = function (options) {
if (options === void 0) { options = {}; }
return this.storage.getBlobURL(this.path, options);
};
/**
* Get the container that this prefix belongs to.
*/
BlobStoragePrefix.prototype.getContainer = function () {
return this.storage.getContainer(this.path.containerName);
};
/**
* Get a blob with the provided name relative to this prefix.
* @param blobName The name to append to this prefix.
*/
BlobStoragePrefix.prototype.getBlob = function (blobName) {
return this.storage.getBlob(this.path.concatenate(blobName));
};
/**
* Get a block blob with the provided name relative to this prefix.
* @param blockBlobName The name to append to this prefix.
*/
BlobStoragePrefix.prototype.getBlockBlob = function (blockBlobName) {
return this.storage.getBlockBlob(this.path.concatenate(blockBlobName));
};
/**
* Get an append blob with the provided name relative to this prefix.
* @param appendBlobName The name to append to this prefix.
*/
BlobStoragePrefix.prototype.getAppendBlob = function (appendBlobName) {
return this.storage.getAppendBlob(this.path.concatenate(appendBlobName));
};
/**
* Get a prefix that can be used to perform blob operations relative to the provided path.
* @param blobName The path to the prefix.
*/
BlobStoragePrefix.prototype.getPrefix = function (blobName) {
return !blobName ? this : this.storage.getPrefix(this.path.concatenate(blobName));
};
/**
* Create a block blob relative to this container with the provided name.
* @param blockBlobName The name of the blob relative to this container.
*/
BlobStoragePrefix.prototype.createBlockBlob = function (blockBlobName, options) {
if (options === void 0) { options = {}; }
return this.storage.createBlockBlob(this.path.concatenate(blockBlobName), options);
};
/**
* Create an append blob relative to this container with the provided name.
* @param appendBlobName The name of the append blob relative to this container.
*/
BlobStoragePrefix.prototype.createAppendBlob = function (appendBlobName, options) {
if (options === void 0) { options = {}; }
return this.storage.createAppendBlob(this.path.concatenate(appendBlobName), options);
};
/**
* Get whether or not a blob exists with the provided name relative to this prefix.
* @param blobName The name of the blob relative to this prefix.
*/
BlobStoragePrefix.prototype.blobExists = function (blobName) {
return this.storage.blobExists(this.path.concatenate(blobName));
};
/**
* Get the properties for the blob at the provided path.
* @param blobPath The path to the blob.
*/
BlobStoragePrefix.prototype.getBlobProperties = function (blobName) {
return this.storage.getBlobProperties(this.path.concatenate(blobName));
};
/**
* Get the content type that has been assigned to the provided blob.
* @param blobName The name of to the blob.
*/
BlobStoragePrefix.prototype.getBlobContentType = function (blobName) {
return this.storage.getBlobContentType(this.path.concatenate(blobName));
};
/**
* Assign the provided content type to the provided blob.
* @param blobName The name of the blob.
* @param contentType The content type to assign to the provided blob.
*/
BlobStoragePrefix.prototype.setBlobContentType = function (blobName, contentType) {
return this.storage.setBlobContentType(this.path.concatenate(blobName), contentType);
};
/**
* Get the contents of the blob with the provided name relative to this prefix.
* @param blobName The name of the blob relative to this prefix.
*/
BlobStoragePrefix.prototype.getBlobContentsAsString = function (blobName) {
return this.storage.getBlobContentsAsString(this.path.concatenate(blobName));
};
/**
* Set the contents of the blob with the provided name relative to this prefix.
* @param blockBlobName The name of the blob relative to this prefix.
* @param blobContents The contents to set.
*/
BlobStoragePrefix.prototype.setBlockBlobContentsFromString = function (blockBlobName, blobContents, options) {
return this.storage.setBlockBlobContentsFromString(this.path.concatenate(blockBlobName), blobContents, options);
};
/**
* Add the provided blob contents to append to the append blob with the provided name relative to
* this container.
* @param appendBlobName The name of the append blob relative to this container.
* @param blobContentsToAppend The contents to add the append blob.
*/
BlobStoragePrefix.prototype.addToAppendBlobContentsFromString = function (appendBlobName, blobContentsToAppend, options) {
return this.storage.addToAppendBlobContentsFromString(this.path.concatenate(appendBlobName), blobContentsToAppend, options);
};
/**
* Delete the blob with the provided name relative to this prefix. This method returns whether or
* not the blob was deleted. Returning false means that the blob didn't exist before this method
* was called.
* @param blobPath The path to the blob to delete relative to this prefix.
*/
BlobStoragePrefix.prototype.deleteBlob = function (blobName) {
return this.storage.deleteBlob(this.path.concatenate(blobName));
};
return BlobStoragePrefix;
}());
exports.BlobStoragePrefix = BlobStoragePrefix;
var BlobStorageContainer = /** @class */ (function (_super) {
tslib_1.__extends(BlobStorageContainer, _super);
/**
* Create a new reference to a container within the provided BlobStorage system.
* @param storage The BlobStorage system that this container belongs to.
* @param name The name of the container.
*/
function BlobStorageContainer(storage, name) {
var _this = _super.call(this, storage, new BlobPath(name, "")) || this;
_this.name = name;
return _this;
}
/**
* Get the URL for this prefix.
*/
BlobStorageContainer.prototype.getURL = function (options) {
if (options === void 0) { options = {}; }
return this.storage.getContainerURL(this.name, options);
};
/**
* Get the container that this prefix belongs to.
*/
BlobStorageContainer.prototype.getContainer = function () {
return this;
};
/**
* Create this container. This method will return false when the container already exists.
*/
BlobStorageContainer.prototype.create = function (options) {
if (options === void 0) { options = {}; }
return this.storage.createContainer(this.name, options);
};
/**
* Get whether or not this container exists.
*/
BlobStorageContainer.prototype.exists = function () {
return this.storage.containerExists(this.name);
};
/**
* Get the access policy for this container.
*/
BlobStorageContainer.prototype.getAccessPolicy = function () {
return this.storage.getContainerAccessPolicy(this.name);
};
/**
* Set the access policy for this container.
* @param policy The new access policy for this container.
*/
BlobStorageContainer.prototype.setAccessPolicy = function (policy) {
return this.storage.setContainerAccessPolicy(this.name, policy);
};
/**
* Delete this container. This method returns whether or not the container was deleted. Returning
* false means that the container didn't exist before this method was called.
*/
BlobStorageContainer.prototype.delete = function () {
return this.storage.deleteContainer(this.name);
};
return BlobStorageContainer;
}(BlobStoragePrefix));
exports.BlobStorageContainer = BlobStorageContainer;
/**
* An class that describes the common functions between the different types of blobs in a
* BlobStorage system.
*/
var BlobStorageBlob = /** @class */ (function () {
/**
* Create a new reference to a block blob within the provided BlobStorage system.
* @param storage The BlobStorage system that this blob belongs to.
* @param path The path to this block blob.
*/
function BlobStorageBlob(storage, path) {
this.storage = storage;
this.path = typeof path === "string" ? BlobPath.parse(path) : path;
}
/**
* Get the URL for this blob.
*/
BlobStorageBlob.prototype.getURL = function (options) {
if (options === void 0) { options = {}; }
return this.storage.getBlobURL(this.path, options);
};
/**
* Get the container that contains this blob.
*/
BlobStorageBlob.prototype.getContainer = function () {
return this.storage.getContainer(this.path.containerName);
};
/**
* Get whether or not this blob exists.
*/
BlobStorageBlob.prototype.exists = function () {
return this.storage.blobExists(this.path);
};
/**
* Get the properties for this blob.
*/
BlobStorageBlob.prototype.getProperties = function () {
return this.storage.getBlobProperties(this.path);
};
/**
* Delete this blob. This method returns whether or not the blob was deleted. Returning false
* means that the blob didn't exist before this method was called.
*/
BlobStorageBlob.prototype.delete = function () {
return this.storage.deleteBlob(this.path);
};
/**
* Get the contents of this blob as a UTF-8 decoded string.
*/
BlobStorageBlob.prototype.getContentsAsString = function () {
return this.storage.getBlobContentsAsString(this.path);
};
/**
* Get the content type that has been assigned to this blob.
*/
BlobStorageBlob.prototype.getContentType = function () {
return this.storage.getBlobContentType(this.path);
};
/**
* Assign the provided content type to this blob.
* @param contentType The content type to assign to this blob.
*/
BlobStorageBlob.prototype.setContentType = function (contentType) {
return this.storage.setBlobContentType(this.path, contentType);
};
return BlobStorageBlob;
}());
exports.BlobStorageBlob = BlobStorageBlob;
/**
* A class that can be used to interact with a block blob in a BlobStorage system.
*/
var BlobStorageBlockBlob = /** @class */ (function (_super) {
tslib_1.__extends(BlobStorageBlockBlob, _super);
function BlobStorageBlockBlob() {
return _super !== null && _super.apply(this, arguments) || this;
}
/**
* Create this block blob. This method will return false when the block blob already exists.
*/
BlobStorageBlockBlob.prototype.create = function (options) {
if (options === void 0) { options = {}; }
return this.storage.createBlockBlob(this.path, options);
};
/**
* Set the contents of this block blob to be the provided UTF-8 encoded string.
* @param blockBlobContents The contents to set. This will be UTF-8 encoded.
*/
BlobStorageBlockBlob.prototype.setContentsFromString = function (blockBlobContents, options) {
if (options === void 0) { options = {}; }
return this.storage.setBlockBlobContentsFromString(this.path, blockBlobContents, options);
};
/**
* Upload the file at the provided path to this block blob.
* @param filePath The path to the file that contains the block blob's contents.
* @param options Options that will be applied to the block blob.
*/
BlobStorageBlockBlob.prototype.setContentsFromFile = function (filePath, options) {
if (options === void 0) { options = {}; }
return this.storage.setBlockBlobContentsFromFile(this.path, filePath, options);
};
return BlobStorageBlockBlob;
}(BlobStorageBlob));
exports.BlobStorageBlockBlob = BlobStorageBlockBlob;
/**
* A class that can be used to interact with an append blob in a BlobStorage system.
*/
var BlobStorageAppendBlob = /** @class */ (function (_super) {
tslib_1.__extends(BlobStorageAppendBlob, _super);
function BlobStorageAppendBlob() {
return _super !== null && _super.apply(this, arguments) || this;
}
/**
* Create this append blob. This method will return false when the append blob already exists.
*/
BlobStorageAppendBlob.prototype.create = function (options) {
if (options === void 0) { options = {}; }
return this.storage.createAppendBlob(this.path, options);
};
/**
* Append the provided UTF-8 encoded contents to this append blob.
* @param contentsToAppend The contents to append to this append blob. This will be UTF-8 encoded.
*/
BlobStorageAppendBlob.prototype.addToContents = function (contentsToAppend) {
return this.storage.addToAppendBlobContentsFromString(this.path, contentsToAppend);
};
return BlobStorageAppendBlob;
}(BlobStorageBlob));
exports.BlobStorageAppendBlob = BlobStorageAppendBlob;
/**
* A class for interacting with a blob storage system.
*/
var BlobStorage = /** @class */ (function () {
function BlobStorage() {
}
/**
* Get a reference to a blob at the provided path. This will not modify the BlobStorage system at
* all. This simply gets a reference to the blob.
* @param blobPath The path to the blob.
*/
BlobStorage.prototype.getBlob = function (blobPath) {
return new BlobStorageBlob(this, blobPath);
};
/**
* Get a reference to a block blob at the provided path. This will not modify the BlobStorage
* system at all. This simply gets a reference to the block blob.
* @param blockBlobPath The path to the block blob.
*/
BlobStorage.prototype.getBlockBlob = function (blockBlobPath) {
return new BlobStorageBlockBlob(this, blockBlobPath);
};
/**
* Get a reference to an append blob at the provided path. This will not modify the BlobStorage
* system at all. This simply gets a reference to the append blob.
* @param appendBlobPath The path to the blob.
*/
BlobStorage.prototype.getAppendBlob = function (appendBlobPath) {
return new BlobStorageAppendBlob(this, appendBlobPath);
};
/**
* Get a prefix that can be used to perform blob operations relative to the provided prefix.
* @param prefix The path to the prefix.
*/
BlobStorage.prototype.getPrefix = function (prefix) {
return new BlobStoragePrefix(this, prefix);
};
/**
* Get a reference to a container with the provided name. This will not modify the BlobStorage
* system at all. This simply gets a reference to the container.
* @param containerName The name of the container.
*/
BlobStorage.prototype.getContainer = function (containerName) {
return new BlobStorageContainer(this, containerName);
};
return BlobStorage;
}());
exports.BlobStorage = BlobStorage;
function encodeBlobName(blobName) {
return !blobName ? blobName : encodeURIComponent(blobName);
}
function decodeBlobName(blobName) {
return !blobName ? blobName : decodeURIComponent(blobName);
}
function processBlobUrl(url, options, credentials) {
if (options.sasToken !== true || options.encodeBlobName) {
url = processBlobUrlBuilder(url_1.URLBuilder.parse(url), options, credentials);
}
return url;
}
function processBlobUrlBuilder(urlBuilder, options, credentials) {
if (options.sasToken !== true) {
urlBuilder.removeQuery();
if (options.sasToken && typeof options.sasToken !== "boolean") {
if (!(credentials instanceof storage_blob_1.SharedKeyCredential)) {
throw new Error("Cannot create a new SAS token if the BlobStorage credentials are not a SharedKeyCredential.");
}
else {
var urlPath = urlBuilder.getPath();
if (!urlPath) {
throw new Error("Cannot create a new SAS token when the provided URL does not contain a path.");
}
else {
var blobPath = BlobPath.parse(urlPath);
var sasSignatureValues = {
blobName: blobPath.blobName,
containerName: blobPath.containerName,
expiryTime: options.sasToken.endTime,
startTime: options.sasToken.startTime,
permissions: "r",
};
var sasQueryParameters = storage_blob_1.generateBlobSASQueryParameters(sasSignatureValues, credentials);
if (sasQueryParameters.cacheControl) {
urlBuilder.setQueryParameter("rscc", sasQueryParameters.cacheControl);
}
if (sasQueryParameters.contentDisposition) {
urlBuilder.setQueryParameter("rscd", sasQueryParameters.contentDisposition);
}
if (sasQueryParameters.contentEncoding) {
urlBuilder.setQueryParameter("rsce", sasQueryParameters.contentEncoding);
}
if (sasQueryParameters.contentLanguage) {
urlBuilder.setQueryParameter("rscl", sasQueryParameters.contentLanguage);
}
if (sasQueryParameters.contentType) {
urlBuilder.setQueryParameter("rsct", sasQueryParameters.contentType);
}
if (sasQueryParameters.expiryTime) {
urlBuilder.setQueryParameter("se", sasQueryParameters.expiryTime.toISOString());
}
if (sasQueryParameters.identifier) {
urlBuilder.setQueryParameter("si", sasQueryParameters.identifier);
}
if (sasQueryParameters.permissions) {
urlBuilder.setQueryParameter("sp", sasQueryParameters.permissions);
}
if (sasQueryParameters.protocol) {
urlBuilder.setQueryParameter("spr", sasQueryParameters.protocol);
}
if (sasQueryParameters.resource) {
urlBuilder.setQueryParameter("sr", sasQueryParameters.resource);
}
if (sasQueryParameters.services) {
urlBuilder.setQueryParameter("ss", sasQueryParameters.services);
}
if (sasQueryParameters.signature) {
urlBuilder.setQueryParameter("sig", sasQueryParameters.signature);
}
if (sasQueryParameters.startTime) {
urlBuilder.setQueryParameter("st", sasQueryParameters.startTime.toISOString());
}
if (sasQueryParameters.version) {
urlBuilder.setQueryParameter("sv", sasQueryParameters.version);
}
}
}
}
}
if (options.encodeBlobName) {
var path = urlBuilder.getPath();
if (path) {
var blobPath = BlobPath.parse(path);
urlBuilder.setPath(blobPath.containerName + "/" + encodeBlobName(blobPath.blobName));
}
}
return urlBuilder.toString();
}
function constructBlobStorageURL(storageAccountNameOrUrl) {
var urlBuilder = typeof storageAccountNameOrUrl === "string" ? url_1.URLBuilder.parse(storageAccountNameOrUrl) : storageAccountNameOrUrl;
if (!urlBuilder.getScheme()) {
urlBuilder.setScheme("https");
}
var host = urlBuilder.getHost();
if (!host) {
throw new Error("Cannot construct a storage account URL with an empty or undefined storage account name or URL argument.");
}
var hostDotIndex = host.indexOf(".");
if (hostDotIndex === -1) {
urlBuilder.setHost(host + ".blob.core.windows.net");
}
return urlBuilder.toString();
}
exports.constructBlobStorageURL = constructBlobStorageURL;
function getStorageAccountName(storageAccountNameOrUrl) {
var urlBuilder = url_1.URLBuilder.parse(storageAccountNameOrUrl);
var host = urlBuilder.getHost();
if (!host) {
throw new Error("Cannot get a storage account's name with an storage account URL argument with an empty or undefined host.");
}
var hostDotIndex = host.indexOf(".");
return host.substring(0, hostDotIndex);
}
exports.getStorageAccountName = getStorageAccountName;
function constructBlobStorageCredentials(storageAccountUrl, credentials) {
if (!credentials) {
credentials = new storage_blob_1.AnonymousCredential();
}
else if (typeof credentials === "string") {
var storageAccountName = getStorageAccountName(storageAccountUrl);
credentials = new storage_blob_1.SharedKeyCredential(storageAccountName, credentials);
}
return credentials;
}
exports.constructBlobStorageCredentials = constructBlobStorageCredentials;
function bumpETag(etag) {
return (Number.parseInt(etag) + 1).toString();
}
/**
* A BlobStorage system that is stored in memory.
*/
var InMemoryBlobStorage = /** @class */ (function (_super) {
tslib_1.__extends(InMemoryBlobStorage, _super);
function InMemoryBlobStorage(storageAccountNameOrUrl, credentials) {
if (storageAccountNameOrUrl === void 0) { storageAccountNameOrUrl = "https://fake.storage.com/"; }
var _this = _super.call(this) || this;
_this.containers = {};
_this.url = constructBlobStorageURL(storageAccountNameOrUrl);
_this.credentials = constructBlobStorageCredentials(_this.url, credentials);
return _this;
}
InMemoryBlobStorage.prototype.getInMemoryContainer = function (containerName) {
containerName = typeof containerName === "string" ? containerName : containerName.containerName;
var result;
if (!containerName || containerName !== containerName.toLowerCase()) {
result = Promise.reject(new Error("InvalidResourceName: The specifed resource name contains invalid characters."));
}
else {
var container = this.containers[containerName];
if (!container) {
result = Promise.reject(new Error("ContainerNotFound: The specified container does not exist."));
}
else {
result = Promise.resolve(container);
}
}
return result;
};
InMemoryBlobStorage.prototype.getInMemoryBlob = function (blobPath) {
blobPath = BlobPath.parse(blobPath);
var blobName = blobPath.blobName;
return this.getInMemoryContainer(blobPath.containerName)
.then(function (container) {
return validateBlobName(blobPath)
.then(function () {
return blobName in container.blobs
? Promise.resolve(container.blobs[blobName])
: Promise.reject(new Error("BlobNotFound: The specified blob does not exist."));
});
});
};
InMemoryBlobStorage.prototype.getURL = function (options) {
if (options === void 0) { options = {}; }
return processBlobUrl(this.url, options, this.credentials);
};
InMemoryBlobStorage.prototype.getContainerURL = function (containerName, options) {
if (options === void 0) { options = {}; }
var urlBuilder = url_1.URLBuilder.parse(this.url);
urlBuilder.setPath(containerName);
return processBlobUrlBuilder(urlBuilder, options, this.credentials);
};
InMemoryBlobStorage.prototype.getBlobURL = function (blobPath, options) {
if (options === void 0) { options = {}; }
blobPath = BlobPath.parse(blobPath);
var urlBuilder = url_1.URLBuilder.parse(this.url);
urlBuilder.setPath(blobPath.toString());
return processBlobUrlBuilder(urlBuilder, options, this.credentials);
};
InMemoryBlobStorage.prototype.createInMemoryBlob = function (blobPath, blobType, options) {
if (options === void 0) { options = {}; }
return tslib_1.__awaiter(this, void 0, void 0, function () {
var blobName, container, blob, created, etag, result;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blobPath = BlobPath.parse(blobPath);
blobName = blobPath.blobName;
return [4 /*yield*/, this.getInMemoryContainer(blobPath)];
case 1:
container = _a.sent();
if (!blobName) {
throw new Error("InvalidUri: The requested URI does not represent any resource on the server.");
}
blob = container.blobs[blobName];
created = !blob;
if (created) {
etag = "1";
container.blobs[blobName] = {
blobType: blobType,
contents: "",
contentType: options.contentType || "application/octet-stream",
etag: etag,
};
}
result = { created: created };
if (etag) {
result.etag = etag;
}
return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.createBlockBlob = function (blobPath, options) {
if (options === void 0) { options = {}; }
return this.createInMemoryBlob(blobPath, "block", options);
};
InMemoryBlobStorage.prototype.createAppendBlob = function (appendBlobPath, options) {
if (options === void 0) { options = {}; }
return this.createInMemoryBlob(appendBlobPath, "append", options);
};
InMemoryBlobStorage.prototype.blobExists = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var result, error_1;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blobPath = BlobPath.parse(blobPath);
_a.label = 1;
case 1:
_a.trys.push([1, 3, , 4]);
return [4 /*yield*/, this.getBlobProperties(blobPath)];
case 2:
_a.sent();
result = true;
return [3 /*break*/, 4];
case 3:
error_1 = _a.sent();
if (error_1.message.includes("BlobNotFound")) {
result = false;
}
else {
throw error_1;
}
return [3 /*break*/, 4];
case 4: return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.getBlobProperties = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var result, blob, error_2;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blobPath = BlobPath.parse(blobPath);
_a.label = 1;
case 1:
_a.trys.push([1, 3, , 4]);
return [4 /*yield*/, this.getInMemoryBlob(blobPath)];
case 2:
blob = _a.sent();
result = {
etag: blob.etag,
};
return [3 /*break*/, 4];
case 3:
error_2 = _a.sent();
if (error_2.message.includes("ContainerNotFound")) {
throw new Error("BlobNotFound: The specified blob does not exist.");
}
else {
throw error_2;
}
return [3 /*break*/, 4];
case 4: return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.getBlobContentsAsString = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var result, blob, error_3;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
_a.trys.push([0, 2, , 3]);
return [4 /*yield*/, this.getInMemoryBlob(blobPath)];
case 1:
blob = _a.sent();
result = {
contents: blob.contents.toString(),
etag: blob.etag,
};
return [3 /*break*/, 3];
case 2:
error_3 = _a.sent();
if (error_3.message.includes("ContainerNotFound")) {
throw new Error("BlobNotFound: The specified blob does not exist.");
}
else {
throw error_3;
}
return [3 /*break*/, 3];
case 3: return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.setBlockBlobContentsFromString = function (blobPath, blobContents, options) {
if (options === void 0) { options = {}; }
return tslib_1.__awaiter(this, void 0, void 0, function () {
var blobName, container, blob, etag, result;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blobPath = BlobPath.parse(blobPath);
blobName = blobPath.blobName;
return [4 /*yield*/, this.getInMemoryContainer(blobPath)];
case 1:
container = _a.sent();
blob = container.blobs[blobName];
if (options.etag && (!blob || blob.etag !== options.etag)) {
throw new Error("ConditionNotMet: The condition specified using HTTP conditional header(s) is not met.");
}
if (!blob) {
etag = "1";
container.blobs[blobName] = {
contents: blobContents,
contentType: options.contentType || "application/octet-stream",
blobType: "block",
etag: etag,
};
}
else {
etag = bumpETag(blob.etag);
blob.contents = blobContents;
blob.contentType = options.contentType || "application/octet-stream";
blob.etag = etag;
}
result = {
created: !blob,
etag: etag,
};
return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.setBlockBlobContentsFromFile = function (blockBlobPath, filePath, options) {
if (options === void 0) { options = {}; }
return tslib_1.__awaiter(this, void 0, void 0, function () {
var blockBlobName, container, blockBlob, etag, result;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blockBlobPath = BlobPath.parse(blockBlobPath);
blockBlobName = blockBlobPath.blobName;
return [4 /*yield*/, this.getInMemoryContainer(blockBlobPath)];
case 1:
container = _a.sent();
blockBlob = container.blobs[blockBlobName];
if (options.etag && (!blockBlob || blockBlob.etag !== options.etag)) {
throw new Error("ConditionNotMet: The condition specified using HTTP conditional header(s) is not met.");
}
if (!blockBlob) {
etag = "1";
container.blobs[blockBlobName] = {
contents: fs.readFileSync(filePath, defaultEncoding),
contentType: options.contentType || "application/octet-stream",
blobType: "block",
etag: etag,
};
}
else {
etag = bumpETag(blockBlob.etag);
blockBlob.contents = fs.readFileSync(filePath, defaultEncoding);
blockBlob.contentType = options.contentType || "application/octet-stream";
blockBlob.etag = etag;
}
result = {
created: !blockBlob,
etag: etag,
};
return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.addToAppendBlobContentsFromString = function (appendBlobPath, blobContentsToAppend, options) {
if (options === void 0) { options = {}; }
return tslib_1.__awaiter(this, void 0, void 0, function () {
var appendBlob, result;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0: return [4 /*yield*/, this.getInMemoryBlob(appendBlobPath)];
case 1:
appendBlob = _a.sent();
if (options.etag && appendBlob.etag !== options.etag) {
throw new Error("ConditionNotMet: The condition specified using HTTP conditional header(s) is not met.");
}
appendBlob.contents += blobContentsToAppend;
appendBlob.etag = bumpETag(appendBlob.etag);
result = { etag: appendBlob.etag };
return [2 /*return*/, result];
}
});
});
};
InMemoryBlobStorage.prototype.getBlobContentType = function (blobPath) {
return this.getInMemoryBlob(blobPath)
.then(function (blob) { return blob.contentType; });
};
InMemoryBlobStorage.prototype.setBlobContentType = function (blobPath, contentType) {
return this.getInMemoryBlob(blobPath)
.then(function (blob) {
blob.contentType = contentType;
});
};
InMemoryBlobStorage.prototype.deleteBlob = function (blobPath) {
var _this = this;
blobPath = BlobPath.parse(blobPath);
var blobName = blobPath.blobName;
return validateBlobName(blobPath)
.then(function () {
return _this.getInMemoryContainer(blobPath)
.then(function (container) {
var result = false;
if (blobName in container.blobs) {
result = true;
delete container.blobs[blobName];
}
return result;
});
});
};
InMemoryBlobStorage.prototype.createContainer = function (containerName, options) {
var _this = this;
if (options === void 0) { options = {}; }
return this.getInMemoryContainer(containerName)
.catch(function (error) { return resolveIfErrorMessageContains(error, "ContainerNotFound", undefined); })
.then(function () {
var result = !(containerName in _this.containers);
if (result) {
_this.containers[containerName] = {
name: containerName,
blobs: {},
accessPolicy: options.accessPolicy || "private"
};
}
return result;
});
};
InMemoryBlobStorage.prototype.containerExists = function (containerName) {
return this.getInMemoryContainer(containerName)
.then(function () { return true; })
.catch(function (error) { return resolveIfErrorMessageContains(error, "ContainerNotFound", false); });
};
InMemoryBlobStorage.prototype.getContainerAccessPolicy = function (containerName) {
return this.getInMemoryContainer(containerName)
.then(function (container) { return container.accessPolicy; });
};
InMemoryBlobStorage.prototype.setContainerAccessPolicy = function (containerName, permissions) {
return this.getInMemoryContainer(containerName)
.then(function (container) {
container.accessPolicy = permissions;
});
};
InMemoryBlobStorage.prototype.deleteContainer = function (containerName) {
var _this = this;
return this.getInMemoryContainer(containerName)
.then(function () {
delete _this.containers[containerName];
return true;
})
.catch(function (error) { return resolveIfErrorMessageContains(error, "ContainerNotFound", false); });
};
InMemoryBlobStorage.prototype.listContainers = function () {
var e_1, _a;
var result = [];
try {
for (var _b = tslib_1.__values(Object.keys(this.containers)), _c = _b.next(); !_c.done; _c = _b.next()) {
var containerName = _c.value;
result.push(this.getContainer(containerName));
}
}
catch (e_1_1) { e_1 = { error: e_1_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_1) throw e_1.error; }
}
return Promise.resolve(result);
};
return InMemoryBlobStorage;
}(BlobStorage));
exports.InMemoryBlobStorage = InMemoryBlobStorage;
/**
* Validate that the provided BlobPath's blobName is defined and not-empty.
* @param blobPath The blob path to validate.
*/
function validateBlobName(blobPath) {
blobPath = BlobPath.parse(blobPath);
return !blobPath.blobName
? Promise.reject(new Error("InvalidUri: The requested URI does not represent any resource on the server."))
: Promise.resolve();
}
exports.validateBlobName = validateBlobName;
function getAzureContainerAccessPermissions(permissions) {
return permissions && permissions !== "private" ? permissions : undefined;
}
exports.getAzureContainerAccessPermissions = getAzureContainerAccessPermissions;
/**
* The maximum number of bytes that can be uploaded in a single AppendBlob block.
*/
var maximumAppendBlobUploadSize = 4 * 1024 * 1024;
/**
* A BlobStorage system that uses Azure Blob Storage to store data.
*/
var AzureBlobStorage = /** @class */ (function (_super) {
tslib_1.__extends(AzureBlobStorage, _super);
function AzureBlobStorage(storageAccountNameOrUrl, credentials) {
var _this = _super.call(this) || this;
_this.url = constructBlobStorageURL(storageAccountNameOrUrl);
_this.credentials = constructBlobStorageCredentials(_this.url, credentials);
var pipeline = storage_blob_1.StorageURL.newPipeline(_this.credentials);
_this.serviceUrl = new storage_blob_1.ServiceURL(_this.url, pipeline);
return _this;
}
AzureBlobStorage.prototype.getAzureContainerURL = function (containerName) {
return storage_blob_1.ContainerURL.fromServiceURL(this.serviceUrl, containerName);
};
AzureBlobStorage.prototype.getBlockBlobURL = function (blockBlobPath) {
blockBlobPath = BlobPath.parse(blockBlobPath);
var containerUrl = this.getAzureContainerURL(blockBlobPath.containerName);
return storage_blob_1.BlockBlobURL.fromContainerURL(containerUrl, blockBlobPath.blobName);
};
AzureBlobStorage.prototype.getAppendBlobURL = function (appendBlobPath) {
appendBlobPath = BlobPath.parse(appendBlobPath);
var containerUrl = this.getAzureContainerURL(appendBlobPath.containerName);
return storage_blob_1.AppendBlobURL.fromContainerURL(containerUrl, appendBlobPath.blobName);
};
AzureBlobStorage.prototype.getURL = function (options) {
if (options === void 0) { options = {}; }
return processBlobUrl(this.url, options, this.credentials);
};
AzureBlobStorage.prototype.getContainerURL = function (containerName, options) {
if (options === void 0) { options = {}; }
var containerUrl = this.getAzureContainerURL(containerName);
return processBlobUrl(containerUrl.url, options, this.credentials);
};
AzureBlobStorage.prototype.getBlobURL = function (blobPath, options) {
if (options === void 0) { options = {}; }
var blobUrl = this.getBlockBlobURL(blobPath);
var urlBuilder = url_1.URLBuilder.parse(blobUrl.url);
var path = urlBuilder.getPath();
if (path) {
var blobPath_1 = BlobPath.parse(path);
if (blobPath_1.blobName) {
urlBuilder.setPath(blobPath_1.containerName + "/" + decodeBlobName(blobPath_1.blobName));
}
}
return processBlobUrlBuilder(urlBuilder, options, this.credentials);
};
AzureBlobStorage.prototype.blobExists = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var result, error_4;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
_a.trys.push([0, 2, , 3]);
return [4 /*yield*/, this.getBlobProperties(blobPath)];
case 1:
_a.sent();
result = true;
return [3 /*break*/, 3];
case 2:
error_4 = _a.sent();
if (error_4.message.includes("BlobNotFound")) {
result = false;
}
else {
throw error_4;
}
return [3 /*break*/, 3];
case 3: return [2 /*return*/, result];
}
});
});
};
AzureBlobStorage.prototype.getBlobProperties = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var blockBlobUrl, result, getPropertiesResult, error_5;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0:
blockBlobUrl = this.getBlockBlobURL(blobPath);
_a.label = 1;
case 1:
_a.trys.push([1, 3, , 4]);
return [4 /*yield*/, blockBlobUrl.getProperties(storage_blob_1.Aborter.none)];
case 2:
getPropertiesResult = _a.sent();
result = {
etag: getPropertiesResult.eTag,
};
return [3 /*break*/, 4];
case 3:
error_5 = _a.sent();
if (error_5.statusCode === 404) {
throw new Error("BlobNotFound: The specified blob does not exist.");
}
else {
throw error_5;
}
return [3 /*break*/, 4];
case 4: return [2 /*return*/, result];
}
});
});
};
AzureBlobStorage.prototype.getBlobContentsAsString = function (blobPath) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var blockBlobUrl, result, blobDownloadResponse, _a, error_6;
return tslib_1.__generator(this, function (_b) {
switch (_b.label) {
case 0: return [4 /*yield*/, validateBlobName(blobPath)];
case 1:
_b.sent();
blockBlobUrl = this.getBlockBlobURL(blobPath);
_b.label = 2;
case 2:
_b.trys.push([2, 5, , 6]);
return [4 /*yield*/, blockBlobUrl.download(storage_blob_1.Aborter.none, 0, undefined)];
case 3:
blobDownloadResponse = _b.sent();
_a = {};
return [4 /*yield*/, common_1.readEntireString(blobDownloadResponse.readableStreamBody)];
case 4:
result = (_a.contents = (_b.sent()),
_a.etag = blobDownloadResponse.eTag,
_a);
return [3 /*break*/, 6];
case 5:
error_6 = _b.sent();
if (error_6.statusCode === 404) {
throw new Error("BlobNotFound: The specified blob does not exist.");
}
else {
throw error_6;
}