Skip to content

Commit

Permalink
Merge pull request #378 from evershopcommerce/dev
Browse files Browse the repository at this point in the history
Dev
  • Loading branch information
treoden authored Oct 28, 2023
2 parents 4803682 + 777ebfd commit fa5c818
Show file tree
Hide file tree
Showing 55 changed files with 1,487 additions and 499 deletions.
496 changes: 484 additions & 12 deletions package-lock.json

Large diffs are not rendered by default.

82 changes: 82 additions & 0 deletions packages/azure_file_storage/api/fileBrowser/azureFileBrowser.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
const { BlobServiceClient } = require('@azure/storage-blob');
const { getConfig } = require('@evershop/evershop/src/lib/util/getConfig');
const { getEnv } = require('@evershop/evershop/src/lib/util/getEnv');
const { debug } = require('@evershop/evershop/src/lib/log/debuger');
const {
OK,
INTERNAL_SERVER_ERROR
} = require('@evershop/evershop/src/lib/util/httpStatus');

let blobServiceClient;
let containerName;
if (getConfig('file_storage') === 'azure') {
blobServiceClient = BlobServiceClient.fromConnectionString(
getEnv('AZURE_STORAGE_CONNECTION_STRING')
);
containerName = getEnv('AZURE_STORAGE_CONTAINER_NAME', 'images');
}

module.exports = async (request, response, delegate, next) => {
// If the file storage is not Azure, call the next middleware function
if (getConfig('file_storage') !== 'azure') {
next();
} else {
try {
// Create a container if it does not exist
const containerClient =
blobServiceClient.getContainerClient(containerName);
// Create a container if it does not exist with access level set to public
await containerClient.createIfNotExists({
access: 'blob'
});

let path = request.params[0] || '';

if (path !== '') {
path = `${path}/`;
}
const blobs = containerClient.listBlobsFlat({ prefix: path });
const subfolders = new Set();
const files = [];
// eslint-disable-next-line no-restricted-syntax
for await (const blob of blobs) {
const blobName = blob.name;
const blobUrl = `${containerClient.url}/${blobName}`;

// Get the subfolder or file name within the directory
const relativePath = blobName.substring(path.length);

// Check if it's a subfolder or file
const slashIndex = relativePath.indexOf('/');
if (slashIndex === -1) {
// It's a file
files.push({
name: relativePath,
url: blobUrl
});
} else {
// It's a subfolder
const subfolder = relativePath.substring(0, slashIndex);
subfolders.add(subfolder);
}
}
// Send the response with the uploaded image details
response.status(OK).json({
data: {
folders: Array.from(subfolders),
files
}
});
} catch (error) {
debug('critical', error);
// Return an error response if there was an error uploading the images
response.status(INTERNAL_SERVER_ERROR);
response.json({
error: {
status: INTERNAL_SERVER_ERROR,
message: 'Error uploading images to Azure Blob Storage'
}
});
}
}
};
62 changes: 62 additions & 0 deletions packages/azure_file_storage/api/fileDelete/azureFileDelete.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
const { BlobServiceClient } = require('@azure/storage-blob');
const { getConfig } = require('@evershop/evershop/src/lib/util/getConfig');
const { getEnv } = require('@evershop/evershop/src/lib/util/getEnv');
const { debug } = require('@evershop/evershop/src/lib/log/debuger');
const {
OK,
INTERNAL_SERVER_ERROR,
INVALID_PAYLOAD
} = require('@evershop/evershop/src/lib/util/httpStatus');

let blobServiceClient;
let containerName;
if (getConfig('file_storage') === 'azure') {
blobServiceClient = BlobServiceClient.fromConnectionString(
getEnv('AZURE_STORAGE_CONNECTION_STRING')
);
containerName = getEnv('AZURE_STORAGE_CONTAINER_NAME', 'images');
}

module.exports = async (request, response, delegate, next) => {
if (getConfig('file_storage') !== 'azure') {
next();
} else {
try {
const containerClient =
blobServiceClient.getContainerClient(containerName);
await containerClient.createIfNotExists({
access: 'blob'
});

const path = request.params[0] || '';
const blobClient = containerClient.getBlobClient(path);
const blobProperties = await blobClient.getProperties();

if (blobProperties.contentType) {
await blobClient.delete();
response.status(OK).json({
data: {
path
}
});
} else {
response.status(INVALID_PAYLOAD).json({
error: {
status: INVALID_PAYLOAD,
message: `Path "${path}" is not a file (no content type).`
}
});
}
} catch (error) {
debug('critical', error);
// Return an error response if there was an error uploading the images
response.status(INTERNAL_SERVER_ERROR);
response.json({
error: {
status: INTERNAL_SERVER_ERROR,
message: 'Error deleting file from Azure Blob Storage'
}
});
}
}
};
57 changes: 57 additions & 0 deletions packages/azure_file_storage/api/folderCreate/azureFolderCreate.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
const { basename } = require('path');
const { BlobServiceClient } = require('@azure/storage-blob');
const { getConfig } = require('@evershop/evershop/src/lib/util/getConfig');
const { getEnv } = require('@evershop/evershop/src/lib/util/getEnv');
const { debug } = require('@evershop/evershop/src/lib/log/debuger');
const {
OK,
INTERNAL_SERVER_ERROR
} = require('@evershop/evershop/src/lib/util/httpStatus');

let blobServiceClient;
let containerName;
if (getConfig('file_storage') === 'azure') {
blobServiceClient = BlobServiceClient.fromConnectionString(
getEnv('AZURE_STORAGE_CONNECTION_STRING')
);
containerName = getEnv('AZURE_STORAGE_CONTAINER_NAME', 'images');
}

module.exports = async (request, response, delegate, next) => {
// If the file storage is not Azure, call the next middleware function
if (getConfig('file_storage') !== 'azure') {
next();
} else {
try {
// Create a container if it does not exist
const containerClient =
blobServiceClient.getContainerClient(containerName);
// Create a container if it does not exist with access level set to public
await containerClient.createIfNotExists({
access: 'blob'
});

const { path } = request.body || '';
const blobClient = containerClient.getBlockBlobClient(`${path}/`);
await blobClient.upload('', 0);

// Send the response with the uploaded image details
response.status(OK).json({
data: {
path,
name: basename(path)
}
});
} catch (error) {
debug('critical', error);
// Return an error response if there was an error uploading the images
response.status(INTERNAL_SERVER_ERROR);
response.json({
error: {
status: INTERNAL_SERVER_ERROR,
message: 'Error uploading images to Azure Blob Storage'
}
});
}
}
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
const { BlobServiceClient } = require('@azure/storage-blob');
const { getConfig } = require('@evershop/evershop/src/lib/util/getConfig');
const { getEnv } = require('@evershop/evershop/src/lib/util/getEnv');
const { debug } = require('@evershop/evershop/src/lib/log/debuger');
const {
OK,
INTERNAL_SERVER_ERROR
} = require('@evershop/evershop/src/lib/util/httpStatus');

let blobServiceClient;
let containerName;
if (getConfig('file_storage') === 'azure') {
blobServiceClient = BlobServiceClient.fromConnectionString(
getEnv('AZURE_STORAGE_CONNECTION_STRING')
);
containerName = getEnv('AZURE_STORAGE_CONTAINER_NAME', 'images');
}

module.exports = async (request, response, delegate, next) => {
// If the file storage is not Azure, call the next middleware function
if (getConfig('file_storage') !== 'azure') {
next();
} else {
try {
// Create a container if it does not exist
const containerClient =
blobServiceClient.getContainerClient(containerName);
// Create a container if it does not exist with access level set to public
await containerClient.createIfNotExists({
access: 'blob'
});

const imageFiles = request.files;
const requestedPath = request.params[0] || '';

const uploadedFiles = [];
// eslint-disable-next-line no-restricted-syntax
for (const imageFile of imageFiles) {
// Create a block blob client object that points to the blob where the image will be uploaded
const path = requestedPath
? `${requestedPath}/${imageFile.originalname}`
: `${imageFile.originalname}`;
const blobClient = containerClient.getBlockBlobClient(path);

// Upload the image file to the blob
await blobClient.upload(imageFile.buffer, imageFile.buffer.length);
// Push the uploaded image details to the uploadedFiles array
uploadedFiles.push({
name: imageFile.filename,
type: imageFile.minetype,
size: imageFile.size,
url: blobClient.url
});
}

// Send the response with the uploaded image details
response.status(OK).json({
data: {
files: uploadedFiles
}
});
} catch (error) {
debug('critical', error);
// Return an error response if there was an error uploading the images
response.status(INTERNAL_SERVER_ERROR);
response.json({
error: {
status: INTERNAL_SERVER_ERROR,
message: 'Error uploading images to Azure Blob Storage'
}
});
}
}
};
24 changes: 24 additions & 0 deletions packages/azure_file_storage/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
{
"name": "@evershop/azure_file_storage",
"version": "1.0.0",
"description": "An extension for EverShop to use Azure File Storage",
"repository": {
"type": "git",
"url": "git+https://github.com/evershopcommerce/evershop/tree/main/packages/azure_file_storage"
},
"keywords": [
"EverShop azure file storage"
],
"author": "The Nguyen (https://evershop.io/)",
"license": "GNU GENERAL PUBLIC LICENSE 3.0",
"bugs": {
"url": "https://github.com/evershopcommerce/evershop/issues"
},
"homepage": "https://github.com/evershopcommerce/evershop/tree/main/packages/azure_file_storage",
"engines": {
"node": ">= 14.0.0"
},
"dependencies": {
"@azure/storage-blob": "^12.16.0"
}
}
Loading

0 comments on commit fa5c818

Please sign in to comment.