@ackplus/nest-file-storage 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +409 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +21 -0
- package/dist/index.js.map +1 -0
- package/dist/lib/constants.d.ts +2 -0
- package/dist/lib/constants.d.ts.map +1 -0
- package/dist/lib/constants.js +5 -0
- package/dist/lib/constants.js.map +1 -0
- package/dist/lib/file-storage.service.d.ts +8 -0
- package/dist/lib/file-storage.service.d.ts.map +1 -0
- package/dist/lib/file-storage.service.js +30 -0
- package/dist/lib/file-storage.service.js.map +1 -0
- package/dist/lib/index.d.ts +6 -0
- package/dist/lib/index.d.ts.map +1 -0
- package/dist/lib/index.js +22 -0
- package/dist/lib/index.js.map +1 -0
- package/dist/lib/interceptor/file-storage.interceptor.d.ts +25 -0
- package/dist/lib/interceptor/file-storage.interceptor.d.ts.map +1 -0
- package/dist/lib/interceptor/file-storage.interceptor.js +141 -0
- package/dist/lib/interceptor/file-storage.interceptor.js.map +1 -0
- package/dist/lib/nest-file-storage.module.d.ts +9 -0
- package/dist/lib/nest-file-storage.module.d.ts.map +1 -0
- package/dist/lib/nest-file-storage.module.js +80 -0
- package/dist/lib/nest-file-storage.module.js.map +1 -0
- package/dist/lib/storage/azure.storage.d.ts +19 -0
- package/dist/lib/storage/azure.storage.d.ts.map +1 -0
- package/dist/lib/storage/azure.storage.js +189 -0
- package/dist/lib/storage/azure.storage.js.map +1 -0
- package/dist/lib/storage/local.storage.d.ts +35 -0
- package/dist/lib/storage/local.storage.d.ts.map +1 -0
- package/dist/lib/storage/local.storage.js +219 -0
- package/dist/lib/storage/local.storage.js.map +1 -0
- package/dist/lib/storage/s3.storage.d.ts +20 -0
- package/dist/lib/storage/s3.storage.d.ts.map +1 -0
- package/dist/lib/storage/s3.storage.js +231 -0
- package/dist/lib/storage/s3.storage.js.map +1 -0
- package/dist/lib/storage.factory.d.ts +9 -0
- package/dist/lib/storage.factory.d.ts.map +1 -0
- package/dist/lib/storage.factory.js +82 -0
- package/dist/lib/storage.factory.js.map +1 -0
- package/dist/lib/types.d.ts +91 -0
- package/dist/lib/types.d.ts.map +1 -0
- package/dist/lib/types.js +10 -0
- package/dist/lib/types.js.map +1 -0
- package/package.json +67 -0
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.FileStorageInterceptor = FileStorageInterceptor;
|
|
7
|
+
const multer_1 = __importDefault(require("multer"));
|
|
8
|
+
const file_storage_service_1 = require("../file-storage.service");
|
|
9
|
+
const storage_factory_1 = require("../storage.factory");
|
|
10
|
+
const types_1 = require("../types");
|
|
11
|
+
// Helper function to map file object
|
|
12
|
+
function mapFileObject(file) {
|
|
13
|
+
return {
|
|
14
|
+
fieldName: file.fieldname,
|
|
15
|
+
originalName: file.originalname,
|
|
16
|
+
fileName: file.filename,
|
|
17
|
+
mimetype: file.mimetype,
|
|
18
|
+
size: file.size,
|
|
19
|
+
key: file.key,
|
|
20
|
+
path: file.path,
|
|
21
|
+
url: file.url,
|
|
22
|
+
encoding: file.encoding,
|
|
23
|
+
fullPath: file.fullPath
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
// Helper function to apply file mapping with callback
|
|
27
|
+
function applyFileKeyMapping(request, fileConfig, interceptorOptions) {
|
|
28
|
+
// Default callback returns the file key
|
|
29
|
+
const mapCallback = interceptorOptions?.mapToRequestBody || ((file) => {
|
|
30
|
+
// For arrays, return array of keys
|
|
31
|
+
if (Array.isArray(file)) {
|
|
32
|
+
return file.map(f => f.key);
|
|
33
|
+
}
|
|
34
|
+
// For single file, return the key
|
|
35
|
+
return file.key;
|
|
36
|
+
});
|
|
37
|
+
if (fileConfig.type === 'single') {
|
|
38
|
+
const file = request.file;
|
|
39
|
+
if (file) {
|
|
40
|
+
const fieldName = fileConfig.fieldName || 'file';
|
|
41
|
+
const mappedFile = mapFileObject(file);
|
|
42
|
+
request.body[fieldName] = mapCallback(mappedFile, fieldName, request);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
else if (fileConfig.type === 'array') {
|
|
46
|
+
const files = request.files;
|
|
47
|
+
if (files && files.length > 0) {
|
|
48
|
+
const fieldName = fileConfig.fieldName || 'files';
|
|
49
|
+
const mappedFiles = files.map(file => mapFileObject(file));
|
|
50
|
+
request.body[fieldName] = mapCallback(mappedFiles, fieldName, request);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
else if (fileConfig.type === 'fields') {
|
|
54
|
+
const files = request.files;
|
|
55
|
+
if (files) {
|
|
56
|
+
Object.keys(files).forEach(fieldName => {
|
|
57
|
+
const mappedFiles = files[fieldName].map(file => mapFileObject(file));
|
|
58
|
+
request.body[fieldName] = mapCallback(mappedFiles, fieldName, request);
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Function-based interceptor that accepts storage options dynamically.
|
|
65
|
+
*/
|
|
66
|
+
function FileStorageInterceptor(fileConfig, interceptorOptions) {
|
|
67
|
+
if (typeof fileConfig === 'string') {
|
|
68
|
+
fileConfig = {
|
|
69
|
+
type: 'single',
|
|
70
|
+
fieldName: fileConfig,
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
return {
|
|
74
|
+
async intercept(context, next) {
|
|
75
|
+
const options = file_storage_service_1.FileStorageService.getOptions();
|
|
76
|
+
const request = context.switchToHttp().getRequest();
|
|
77
|
+
const response = context.switchToHttp().getResponse();
|
|
78
|
+
// Determine storage type - handle both config approaches
|
|
79
|
+
let storageType;
|
|
80
|
+
let storageConfig;
|
|
81
|
+
if ('storage' in options) {
|
|
82
|
+
// Configuration-based approach
|
|
83
|
+
const configOptions = options;
|
|
84
|
+
storageType = interceptorOptions?.storageType ?? configOptions.storage;
|
|
85
|
+
storageConfig = configOptions[`${storageType}Config`];
|
|
86
|
+
}
|
|
87
|
+
else {
|
|
88
|
+
// Class factory approach - default to LOCAL
|
|
89
|
+
storageType = interceptorOptions?.storageType ?? types_1.FileStorageEnum.LOCAL;
|
|
90
|
+
storageConfig = {};
|
|
91
|
+
}
|
|
92
|
+
const storageOptions = {
|
|
93
|
+
...storageConfig,
|
|
94
|
+
...(interceptorOptions?.storageOptions || {}),
|
|
95
|
+
fileName: interceptorOptions?.fileName || storageConfig?.fileName,
|
|
96
|
+
fileDist: (file, req) => {
|
|
97
|
+
if (interceptorOptions?.fileDist) {
|
|
98
|
+
return interceptorOptions.fileDist(file, req);
|
|
99
|
+
}
|
|
100
|
+
return storageConfig?.fileDist?.(file, req);
|
|
101
|
+
},
|
|
102
|
+
prefix: interceptorOptions?.prefix || storageConfig?.prefix,
|
|
103
|
+
};
|
|
104
|
+
// Create storage instance dynamically
|
|
105
|
+
const storage = await storage_factory_1.StorageFactory.createStorage(storageType, storageOptions);
|
|
106
|
+
const multerInstance = (0, multer_1.default)({ storage });
|
|
107
|
+
// Multer setup based on fileConfig
|
|
108
|
+
let multerMiddleware;
|
|
109
|
+
switch (fileConfig.type) {
|
|
110
|
+
case 'single':
|
|
111
|
+
if (!fileConfig.fieldName) {
|
|
112
|
+
throw new Error('fieldName is required for single file upload.');
|
|
113
|
+
}
|
|
114
|
+
multerMiddleware = multerInstance.single(fileConfig.fieldName);
|
|
115
|
+
break;
|
|
116
|
+
case 'array':
|
|
117
|
+
if (!fileConfig.fieldName) {
|
|
118
|
+
throw new Error('fieldName is required for multiple file upload.');
|
|
119
|
+
}
|
|
120
|
+
multerMiddleware = multerInstance.array(fileConfig.fieldName, fileConfig.maxCount);
|
|
121
|
+
break;
|
|
122
|
+
case 'fields':
|
|
123
|
+
if (!fileConfig.fields || !Array.isArray(fileConfig.fields)) {
|
|
124
|
+
throw new Error('fields array is required for multiple fields file upload.');
|
|
125
|
+
}
|
|
126
|
+
multerMiddleware = multerInstance.fields(fileConfig.fields);
|
|
127
|
+
break;
|
|
128
|
+
default:
|
|
129
|
+
throw new Error('Invalid file upload type. Use "single", "array", or "fields".');
|
|
130
|
+
}
|
|
131
|
+
// Execute Multer middleware
|
|
132
|
+
await new Promise((resolve, reject) => {
|
|
133
|
+
multerMiddleware(request, response, (err) => (err ? reject(err) : resolve(true)));
|
|
134
|
+
});
|
|
135
|
+
// Apply file key mapping after multer processing
|
|
136
|
+
applyFileKeyMapping(request, fileConfig, interceptorOptions);
|
|
137
|
+
return next.handle();
|
|
138
|
+
}
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
//# sourceMappingURL=file-storage.interceptor.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-storage.interceptor.js","sourceRoot":"","sources":["../../../src/lib/interceptor/file-storage.interceptor.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { DynamicModule } from '@nestjs/common';
|
|
2
|
+
import { FileStorageAsyncOptions, FileStorageModuleOptions } from './types';
|
|
3
|
+
export declare class NestFileStorageModule {
|
|
4
|
+
static forRoot(options: FileStorageModuleOptions): DynamicModule;
|
|
5
|
+
static forRootAsync(options: FileStorageAsyncOptions): DynamicModule;
|
|
6
|
+
private static createAsyncProviders;
|
|
7
|
+
private static createAsyncOptionsProvider;
|
|
8
|
+
}
|
|
9
|
+
//# sourceMappingURL=nest-file-storage.module.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nest-file-storage.module.d.ts","sourceRoot":"","sources":["../../src/lib/nest-file-storage.module.ts"],"names":[],"mappings":"AAAA,OAAO,EAAU,aAAa,EAAY,MAAM,gBAAgB,CAAC;AAIjE,OAAO,EAAE,uBAAuB,EAAE,wBAAwB,EAA6B,MAAM,SAAS,CAAC;AAGvG,qBACa,qBAAqB;IAE9B,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,wBAAwB,GAAG,aAAa;IAkBhE,MAAM,CAAC,YAAY,CAAC,OAAO,EAAE,uBAAuB,GAAG,aAAa;IAWpE,OAAO,CAAC,MAAM,CAAC,oBAAoB;IAcnC,OAAO,CAAC,MAAM,CAAC,0BAA0B;CAwB5C"}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var NestFileStorageModule_1;
|
|
9
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
10
|
+
exports.NestFileStorageModule = void 0;
|
|
11
|
+
const common_1 = require("@nestjs/common");
|
|
12
|
+
const constants_1 = require("./constants");
|
|
13
|
+
const file_storage_service_1 = require("./file-storage.service");
|
|
14
|
+
let NestFileStorageModule = NestFileStorageModule_1 = class NestFileStorageModule {
|
|
15
|
+
static forRoot(options) {
|
|
16
|
+
return {
|
|
17
|
+
module: NestFileStorageModule_1,
|
|
18
|
+
providers: [
|
|
19
|
+
{
|
|
20
|
+
provide: constants_1.FILE_STORAGE_OPTIONS,
|
|
21
|
+
useFactory: async () => {
|
|
22
|
+
file_storage_service_1.FileStorageService.setOptions(options); // ✅ Store globally
|
|
23
|
+
return options;
|
|
24
|
+
},
|
|
25
|
+
inject: [],
|
|
26
|
+
},
|
|
27
|
+
file_storage_service_1.FileStorageService,
|
|
28
|
+
],
|
|
29
|
+
exports: [],
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
static forRootAsync(options) {
|
|
33
|
+
const asyncProviders = this.createAsyncProviders(options);
|
|
34
|
+
return {
|
|
35
|
+
module: NestFileStorageModule_1,
|
|
36
|
+
imports: options.imports || [],
|
|
37
|
+
providers: [...asyncProviders, file_storage_service_1.FileStorageService],
|
|
38
|
+
exports: [],
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
static createAsyncProviders(options) {
|
|
42
|
+
if (options.useExisting || options.useFactory) {
|
|
43
|
+
return [this.createAsyncOptionsProvider(options)];
|
|
44
|
+
}
|
|
45
|
+
return [
|
|
46
|
+
this.createAsyncOptionsProvider(options),
|
|
47
|
+
{
|
|
48
|
+
provide: options.useClass,
|
|
49
|
+
useClass: options.useClass,
|
|
50
|
+
},
|
|
51
|
+
];
|
|
52
|
+
}
|
|
53
|
+
static createAsyncOptionsProvider(options) {
|
|
54
|
+
if (options.useFactory) {
|
|
55
|
+
return {
|
|
56
|
+
provide: constants_1.FILE_STORAGE_OPTIONS,
|
|
57
|
+
useFactory: async (...args) => {
|
|
58
|
+
const fileStorageOptions = await options.useFactory(...args);
|
|
59
|
+
file_storage_service_1.FileStorageService.setOptions(fileStorageOptions);
|
|
60
|
+
return fileStorageOptions;
|
|
61
|
+
},
|
|
62
|
+
inject: options.inject || [],
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
return {
|
|
66
|
+
provide: constants_1.FILE_STORAGE_OPTIONS,
|
|
67
|
+
useFactory: async (optionsFactory) => {
|
|
68
|
+
const fileStorageOptions = await optionsFactory.createFileStorageOptions();
|
|
69
|
+
file_storage_service_1.FileStorageService.setOptions(fileStorageOptions);
|
|
70
|
+
return fileStorageOptions;
|
|
71
|
+
},
|
|
72
|
+
inject: [options.useExisting || options.useClass],
|
|
73
|
+
};
|
|
74
|
+
}
|
|
75
|
+
};
|
|
76
|
+
exports.NestFileStorageModule = NestFileStorageModule;
|
|
77
|
+
exports.NestFileStorageModule = NestFileStorageModule = NestFileStorageModule_1 = __decorate([
|
|
78
|
+
(0, common_1.Module)({})
|
|
79
|
+
], NestFileStorageModule);
|
|
80
|
+
//# sourceMappingURL=nest-file-storage.module.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nest-file-storage.module.js","sourceRoot":"","sources":["../../src/lib/nest-file-storage.module.ts"],"names":[],"mappings":";;;;;;;;;;AAAA,2CAAiE;AAEjE,2CAAmD;AACnD,iEAA4D;AAKrD,IAAM,qBAAqB,6BAA3B,MAAM,qBAAqB;IAE9B,MAAM,CAAC,OAAO,CAAC,OAAiC;QAC5C,OAAO;YACH,MAAM,EAAE,uBAAqB;YAC7B,SAAS,EAAE;gBACP;oBACI,OAAO,EAAE,gCAAoB;oBAC7B,UAAU,EAAE,KAAK,IAAI,EAAE;wBACnB,yCAAkB,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC,CAAC,mBAAmB;wBAC3D,OAAO,OAAO,CAAC;oBACnB,CAAC;oBACD,MAAM,EAAE,EAAE;iBACb;gBACD,yCAAkB;aACrB;YACD,OAAO,EAAE,EAAE;SACd,CAAC;IACN,CAAC;IAED,MAAM,CAAC,YAAY,CAAC,OAAgC;QAChD,MAAM,cAAc,GAAe,IAAI,CAAC,oBAAoB,CAAC,OAAO,CAAC,CAAC;QAEtE,OAAO;YACH,MAAM,EAAE,uBAAqB;YAC7B,OAAO,EAAE,OAAO,CAAC,OAAO,IAAI,EAAE;YAC9B,SAAS,EAAE,CAAC,GAAG,cAAc,EAAE,yCAAkB,CAAC;YAClD,OAAO,EAAE,EAAE;SACd,CAAC;IACN,CAAC;IAEO,MAAM,CAAC,oBAAoB,CAAC,OAAgC;QAChE,IAAI,OAAO,CAAC,WAAW,IAAI,OAAO,CAAC,UAAU,EAAE,CAAC;YAC5C,OAAO,CAAC,IAAI,CAAC,0BAA0B,CAAC,OAAO,CAAC,CAAC,CAAC;QACtD,CAAC;QAED,OAAO;YACH,IAAI,CAAC,0BAA0B,CAAC,OAAO,CAAC;YACxC;gBACI,OAAO,EAAE,OAAO,CAAC,QAAS;gBAC1B,QAAQ,EAAE,OAAO,CAAC,QAAS;aAC9B;SACJ,CAAC;IACN,CAAC;IAEO,MAAM,CAAC,0BAA0B,CAAC,OAAgC;QACtE,IAAI,OAAO,CAAC,UAAU,EAAE,CAAC;YACrB,OAAO;gBACH,OAAO,EAAE,gCAAoB;gBAC7B,UAAU,EAAE,KAAK,EAAE,GAAG,IAAW,EAAE,EAAE;oBACjC,MAAM,kBAAkB,GAAG,MAAM,OAAO,CAAC,UAAW,CAAC,GAAG,IAAI,CAAC,CAAC;oBAC9D,yCAAkB,CAAC,UAAU,CAAC,kBAAkB,CAAC,CAAC;oBAClD,OAAO,kBAAkB,CAAC;gBAC9B,CAAC;gBACD,MAAM,EAAE,OAAO,CAAC,MAAM,IAAI,EAAE;aAC/B,CAAC;QACN,CAAC;QAED,OAAO;YACH,OAAO,EAAE,gCAAoB;YAC7B,UAAU,EAAE,KAAK,EAAE,cAAyC,EAAE,EAAE;gBAC5D,MAAM,kBAAkB,GAAG,MAAM,cAAc,CAAC,wBAAwB,EAAE,CAAC;gBAC3E,yCAAkB,CAAC,UAAU,CAAC,kBAAkB,CAAC,CAAC;gBAClD,OAAO,kBAAkB,CAAC;YAC9B,CAAC;YACD,MAAM,EAAE,CAAC,OAAO,CAAC,WAAW,IAAI,OAAO,CAAC,QAAS,CAAC;SACrD,CAAC;IACN,CAAC;CAEJ,CAAA;AArEY,sDAAqB;gCAArB,qBAAqB;IADjC,IAAA,eAAM,EAAC,EAAE,CAAC;GACE,qBAAqB,CAqEjC"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { BlobSASSignatureValues } from '@azure/storage-blob';
|
|
2
|
+
import { StorageEngine } from 'multer';
|
|
3
|
+
import { AzureStorageOptions, Storage, UploadedFile } from '../types';
|
|
4
|
+
export declare class AzureStorage implements StorageEngine, Storage {
|
|
5
|
+
private options;
|
|
6
|
+
private blobServiceClient;
|
|
7
|
+
private fileNameFunction;
|
|
8
|
+
private fileDistFunction;
|
|
9
|
+
constructor(options: AzureStorageOptions);
|
|
10
|
+
_handleFile(req: any, file: any, cb: (error?: any, info?: any) => void): Promise<void>;
|
|
11
|
+
_removeFile(_req: any, file: any, cb: (error: Error | null) => void): Promise<void>;
|
|
12
|
+
getUrl(key: string): string;
|
|
13
|
+
getSignedUrl(key: string, signatureValues?: Partial<Omit<BlobSASSignatureValues, 'containerName'>>): string;
|
|
14
|
+
getFile(key: string): Promise<Buffer>;
|
|
15
|
+
putFile(buffer: Buffer, key: string): Promise<UploadedFile>;
|
|
16
|
+
deleteFile(key: string): Promise<void>;
|
|
17
|
+
copyFile(oldKey: string, newKey: string): Promise<UploadedFile>;
|
|
18
|
+
}
|
|
19
|
+
//# sourceMappingURL=azure.storage.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"azure.storage.d.ts","sourceRoot":"","sources":["../../../src/lib/storage/azure.storage.ts"],"names":[],"mappings":"AAAA,OAAO,EAEH,sBAAsB,EAKzB,MAAM,qBAAqB,CAAC;AAG7B,OAAO,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAIvC,OAAO,EAAE,mBAAmB,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAGtE,qBAAa,YAAa,YAAW,aAAa,EAAE,OAAO;IAQ3C,OAAO,CAAC,OAAO;IAN3B,OAAO,CAAC,iBAAiB,CAAoB;IAE7C,OAAO,CAAC,gBAAgB,CAAqE;IAC7F,OAAO,CAAC,gBAAgB,CAAqE;gBAGzE,OAAO,EAAE,mBAAmB;IAoB1C,WAAW,CACb,GAAG,EAAE,GAAG,EACR,IAAI,EAAE,GAAG,EACT,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,GAAG,EAAE,IAAI,CAAC,EAAE,GAAG,KAAK,IAAI,GACtC,OAAO,CAAC,IAAI,CAAC;IA6BV,WAAW,CACb,IAAI,EAAE,GAAG,EACT,IAAI,KAAA,EACJ,EAAE,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,KAAK,IAAI,GAClC,OAAO,CAAC,IAAI,CAAC;IAahB,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM;IAK3B,YAAY,CAAC,GAAG,EAAE,MAAM,EAAE,eAAe,GAAE,OAAO,CAAC,IAAI,CAAC,sBAAsB,EAAE,eAAe,CAAC,CAAM;IAqChG,OAAO,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAcrC,OAAO,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC;IAwB3D,UAAU,CAAC,GAAG,EAAE,MAAM;IAYtB,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC;CA0BxE"}
|
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
36
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
|
+
};
|
|
38
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
+
exports.AzureStorage = void 0;
|
|
40
|
+
const storage_blob_1 = require("@azure/storage-blob");
|
|
41
|
+
const concat_stream_1 = __importDefault(require("concat-stream"));
|
|
42
|
+
const moment_1 = __importDefault(require("moment"));
|
|
43
|
+
const path_1 = __importStar(require("path"));
|
|
44
|
+
const uuid_1 = require("uuid");
|
|
45
|
+
class AzureStorage {
|
|
46
|
+
constructor(options) {
|
|
47
|
+
this.options = options;
|
|
48
|
+
this.fileNameFunction = options.fileName || ((file, _req) => {
|
|
49
|
+
return `${(0, uuid_1.v4)()}-${file.originalname}`;
|
|
50
|
+
});
|
|
51
|
+
this.fileDistFunction = options.fileDist || ((_file, _req) => {
|
|
52
|
+
return path_1.default.join('uploads', (0, moment_1.default)().format('YYYY'), (0, moment_1.default)().format('MM'), (0, moment_1.default)().format('DD'));
|
|
53
|
+
});
|
|
54
|
+
const sharedKeyCredential = new storage_blob_1.StorageSharedKeyCredential(options.account, options.accountKey);
|
|
55
|
+
this.blobServiceClient = new storage_blob_1.BlobServiceClient(`https://${options.account}.blob.core.windows.net`, sharedKeyCredential);
|
|
56
|
+
}
|
|
57
|
+
async _handleFile(req, file, cb) {
|
|
58
|
+
try {
|
|
59
|
+
const dist = await this.fileDistFunction(file, req);
|
|
60
|
+
const key = await this.fileNameFunction(file, req);
|
|
61
|
+
const filePath = (0, path_1.join)(dist, key);
|
|
62
|
+
file.stream.pipe((0, concat_stream_1.default)({ encoding: 'buffer' }, async (buffer) => {
|
|
63
|
+
const uploadedFile = await this.putFile(buffer, filePath);
|
|
64
|
+
const fileInfo = {
|
|
65
|
+
...uploadedFile,
|
|
66
|
+
fieldName: file.fieldname,
|
|
67
|
+
originalName: file.originalname,
|
|
68
|
+
mimetype: file.mimetype,
|
|
69
|
+
};
|
|
70
|
+
let transformData = fileInfo;
|
|
71
|
+
if (this.options?.transformUploadedFileObject) {
|
|
72
|
+
transformData = await this.options.transformUploadedFileObject(fileInfo);
|
|
73
|
+
}
|
|
74
|
+
cb(null, transformData);
|
|
75
|
+
}));
|
|
76
|
+
}
|
|
77
|
+
catch (error) {
|
|
78
|
+
cb(error);
|
|
79
|
+
}
|
|
80
|
+
file.stream.on('error', (err) => cb(err));
|
|
81
|
+
}
|
|
82
|
+
async _removeFile(_req, file, cb) {
|
|
83
|
+
try {
|
|
84
|
+
const blobClient = this.blobServiceClient
|
|
85
|
+
.getContainerClient(this.options.container)
|
|
86
|
+
.getBlobClient(file.key);
|
|
87
|
+
await blobClient.delete();
|
|
88
|
+
cb(null);
|
|
89
|
+
}
|
|
90
|
+
catch (error) {
|
|
91
|
+
cb(error);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
getUrl(key) {
|
|
95
|
+
return `https://${this.options.account}.blob.core.windows.net/${this.options.container}/${key}`;
|
|
96
|
+
}
|
|
97
|
+
getSignedUrl(key, signatureValues = {}) {
|
|
98
|
+
if (!key)
|
|
99
|
+
return null;
|
|
100
|
+
const cloudFrontDomain = process.env.AZURE_CDN_DOMAIN_NAME;
|
|
101
|
+
if (cloudFrontDomain) {
|
|
102
|
+
return `${cloudFrontDomain}/${key}`;
|
|
103
|
+
}
|
|
104
|
+
const containerClient = this.blobServiceClient.getContainerClient(this.options.container);
|
|
105
|
+
const blobClient = containerClient.getBlobClient(key);
|
|
106
|
+
const sharedKeyCredential = new storage_blob_1.StorageSharedKeyCredential(this.options.account, this.options.accountKey);
|
|
107
|
+
// Set the SAS token options
|
|
108
|
+
const expiresOn = new Date();
|
|
109
|
+
expiresOn.setHours(expiresOn.getHours() + 1); // Set expiration time to 1 hour from now
|
|
110
|
+
const sasToken = (0, storage_blob_1.generateBlobSASQueryParameters)({
|
|
111
|
+
containerName: this.options.container,
|
|
112
|
+
blobName: key,
|
|
113
|
+
permissions: storage_blob_1.BlobSASPermissions.parse('r'), // Read permissions
|
|
114
|
+
protocol: storage_blob_1.SASProtocol.Https, // HTTPS only
|
|
115
|
+
startsOn: new Date(), // Start time (now)
|
|
116
|
+
expiresOn, // Expiration time
|
|
117
|
+
...signatureValues,
|
|
118
|
+
}, sharedKeyCredential).toString();
|
|
119
|
+
return `${blobClient.url}?${sasToken}`;
|
|
120
|
+
}
|
|
121
|
+
async getFile(key) {
|
|
122
|
+
const containerClient = this.blobServiceClient.getContainerClient(this.options.container);
|
|
123
|
+
const blobClient = containerClient.getBlobClient(key);
|
|
124
|
+
const downloadResponse = await blobClient.download();
|
|
125
|
+
const stream = downloadResponse.readableStreamBody;
|
|
126
|
+
return new Promise((resolve, reject) => {
|
|
127
|
+
const chunks = [];
|
|
128
|
+
stream?.on('data', (chunk) => chunks.push(chunk));
|
|
129
|
+
stream?.on('end', () => resolve(Buffer.concat(chunks)));
|
|
130
|
+
stream?.on('error', reject);
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
async putFile(buffer, key) {
|
|
134
|
+
try {
|
|
135
|
+
const containerClient = this.blobServiceClient.getContainerClient(this.options.container);
|
|
136
|
+
const blockBlobClient = containerClient.getBlockBlobClient(key);
|
|
137
|
+
await blockBlobClient.uploadData(buffer);
|
|
138
|
+
const fileInfo = {
|
|
139
|
+
originalName: (0, path_1.basename)(key),
|
|
140
|
+
fileName: (0, path_1.basename)(key),
|
|
141
|
+
size: buffer.length,
|
|
142
|
+
buffer,
|
|
143
|
+
key,
|
|
144
|
+
fullPath: key,
|
|
145
|
+
url: this.getUrl(key),
|
|
146
|
+
};
|
|
147
|
+
return fileInfo;
|
|
148
|
+
}
|
|
149
|
+
catch (error) {
|
|
150
|
+
console.error(`Error uploading file "${key}":`, error);
|
|
151
|
+
throw error;
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
async deleteFile(key) {
|
|
155
|
+
try {
|
|
156
|
+
const blobClient = this.blobServiceClient
|
|
157
|
+
.getContainerClient(this.options.container)
|
|
158
|
+
.getBlobClient(key);
|
|
159
|
+
await blobClient.delete();
|
|
160
|
+
}
|
|
161
|
+
catch (error) {
|
|
162
|
+
console.error(`Error deleting blob "${key}":`, error);
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
async copyFile(oldKey, newKey) {
|
|
166
|
+
try {
|
|
167
|
+
const containerClient = this.blobServiceClient.getContainerClient(this.options.container);
|
|
168
|
+
const sourceBlobClient = containerClient.getBlobClient(oldKey);
|
|
169
|
+
const destinationBlobClient = containerClient.getBlobClient(newKey);
|
|
170
|
+
const copyPoller = await destinationBlobClient.beginCopyFromURL(sourceBlobClient.url);
|
|
171
|
+
await copyPoller.pollUntilDone();
|
|
172
|
+
const properties = await destinationBlobClient.getProperties();
|
|
173
|
+
return {
|
|
174
|
+
originalName: (0, path_1.basename)(newKey),
|
|
175
|
+
size: properties.contentLength || 0,
|
|
176
|
+
fileName: (0, path_1.basename)(newKey),
|
|
177
|
+
key: newKey,
|
|
178
|
+
fullPath: newKey,
|
|
179
|
+
url: this.getUrl(newKey),
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
catch (error) {
|
|
183
|
+
console.error('Error copying file in Azure Blob Storage:', error);
|
|
184
|
+
throw error;
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
exports.AzureStorage = AzureStorage;
|
|
189
|
+
//# sourceMappingURL=azure.storage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"azure.storage.js","sourceRoot":"","sources":["../../../src/lib/storage/azure.storage.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,sDAO6B;AAC7B,kEAAmC;AACnC,oDAA4B;AAE5B,6CAA4C;AAC5C,+BAAoC;AAKpC,MAAa,YAAY;IAQrB,YAAoB,OAA4B;QAA5B,YAAO,GAAP,OAAO,CAAqB;QAC5C,IAAI,CAAC,gBAAgB,GAAG,OAAO,CAAC,QAAQ,IAAI,CAAC,CAAC,IAAI,EAAE,IAAI,EAAE,EAAE;YACxD,OAAO,GAAG,IAAA,SAAM,GAAE,IAAI,IAAI,CAAC,YAAY,EAAE,CAAC;QAC9C,CAAC,CAAC,CAAC;QAEH,IAAI,CAAC,gBAAgB,GAAG,OAAO,CAAC,QAAQ,IAAI,CAAC,CAAC,KAAK,EAAE,IAAI,EAAE,EAAE;YACzD,OAAO,cAAI,CAAC,IAAI,CAAC,SAAS,EAAE,IAAA,gBAAM,GAAE,CAAC,MAAM,CAAC,MAAM,CAAC,EAAE,IAAA,gBAAM,GAAE,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,IAAA,gBAAM,GAAE,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;QACvG,CAAC,CAAC,CAAC;QAEH,MAAM,mBAAmB,GAAG,IAAI,yCAA0B,CACtD,OAAO,CAAC,OAAO,EACf,OAAO,CAAC,UAAU,CACrB,CAAC;QAEF,IAAI,CAAC,iBAAiB,GAAG,IAAI,gCAAiB,CAC1C,WAAW,OAAO,CAAC,OAAO,wBAAwB,EAClD,mBAAmB,CACtB,CAAC;IACN,CAAC;IAED,KAAK,CAAC,WAAW,CACb,GAAQ,EACR,IAAS,EACT,EAAqC;QAErC,IAAI,CAAC;YACD,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,gBAAgB,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;YACpD,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,gBAAgB,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;YACnD,MAAM,QAAQ,GAAG,IAAA,WAAI,EAAC,IAAI,EAAE,GAAG,CAAC,CAAC;YAEjC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,IAAA,uBAAM,EAAC,EAAE,QAAQ,EAAE,QAAQ,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,EAAE;gBAC7D,MAAM,YAAY,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;gBAE1D,MAAM,QAAQ,GAAiB;oBAC3B,GAAG,YAAY;oBACf,SAAS,EAAE,IAAI,CAAC,SAAS;oBACzB,YAAY,EAAE,IAAI,CAAC,YAAY;oBAC/B,QAAQ,EAAE,IAAI,CAAC,QAAQ;iBAC1B,CAAC;gBACF,IAAI,aAAa,GAAG,QAAQ,CAAC;gBAE7B,IAAI,IAAI,CAAC,OAAO,EAAE,2BAA2B,EAAE,CAAC;oBAC5C,aAAa,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,2BAA2B,CAAC,QAAQ,CAAC,CAAC;gBAC7E,CAAC;gBACD,EAAE,CAAC,IAAI,EAAE,aAAa,CAAC,CAAC;YAC5B,CAAC,CAAC,CAAC,CAAC;QACR,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,EAAE,CAAC,KAAK,CAAC,CAAC;QACd,CAAC;QAED,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,EAAE,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC9C,CAAC;IAED,KAAK,CAAC,WAAW,CACb,IAAS,EACT,IAAI,EACJ,EAAiC;QAEjC,IAAI,CAAC;YACD,MAAM,UAAU,GAAG,IAAI,CAAC,iBAAiB;iBACpC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC;iBAC1C,aAAa,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;YAE7B,MAAM,UAAU,CAAC,MAAM,EAAE,CAAC;YAC1B,EAAE,CAAC,IAAI,CAAC,CAAC;QACb,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,EAAE,CAAC,KAAK,CAAC,CAAC;QACd,CAAC;IACL,CAAC;IAED,MAAM,CAAC,GAAW;QACd,OAAO,WAAW,IAAI,CAAC,OAAO,CAAC,OAAO,0BAA0B,IAAI,CAAC,OAAO,CAAC,SAAS,IAAI,GAAG,EAAE,CAAC;IACpG,CAAC;IAGD,YAAY,CAAC,GAAW,EAAE,kBAA0E,EAAE;QAClG,IAAI,CAAC,GAAG;YAAE,OAAO,IAAI,CAAC;QAEtB,MAAM,gBAAgB,GAAG,OAAO,CAAC,GAAG,CAAC,qBAAqB,CAAC;QAE3D,IAAI,gBAAgB,EAAE,CAAC;YACnB,OAAO,GAAG,gBAAgB,IAAI,GAAG,EAAE,CAAC;QACxC,CAAC;QAED,MAAM,eAAe,GAAG,IAAI,CAAC,iBAAiB,CAAC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;QAC1F,MAAM,UAAU,GAAG,eAAe,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;QAEtD,MAAM,mBAAmB,GAAG,IAAI,yCAA0B,CACtD,IAAI,CAAC,OAAO,CAAC,OAAO,EACpB,IAAI,CAAC,OAAO,CAAC,UAAU,CAC1B,CAAC;QAEF,4BAA4B;QAC5B,MAAM,SAAS,GAAG,IAAI,IAAI,EAAE,CAAC;QAC7B,SAAS,CAAC,QAAQ,CAAC,SAAS,CAAC,QAAQ,EAAE,GAAG,CAAC,CAAC,CAAC,CAAC,yCAAyC;QAEvF,MAAM,QAAQ,GAAG,IAAA,6CAA8B,EAC3C;YACI,aAAa,EAAE,IAAI,CAAC,OAAO,CAAC,SAAS;YACrC,QAAQ,EAAE,GAAG;YACb,WAAW,EAAE,iCAAkB,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,mBAAmB;YAC/D,QAAQ,EAAE,0BAAW,CAAC,KAAK,EAAE,aAAa;YAC1C,QAAQ,EAAE,IAAI,IAAI,EAAE,EAAE,mBAAmB;YACzC,SAAS,EAAE,kBAAkB;YAC7B,GAAG,eAAe;SACrB,EACD,mBAAmB,CACtB,CAAC,QAAQ,EAAE,CAAC;QAEb,OAAO,GAAG,UAAU,CAAC,GAAG,IAAI,QAAQ,EAAE,CAAC;IAC3C,CAAC;IAED,KAAK,CAAC,OAAO,CAAC,GAAW;QACrB,MAAM,eAAe,GAAG,IAAI,CAAC,iBAAiB,CAAC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;QAC1F,MAAM,UAAU,GAAG,eAAe,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;QACtD,MAAM,gBAAgB,GAAG,MAAM,UAAU,CAAC,QAAQ,EAAE,CAAC;QACrD,MAAM,MAAM,GAAG,gBAAgB,CAAC,kBAAkB,CAAC;QAEnD,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;YACnC,MAAM,MAAM,GAAG,EAAE,CAAC;YAClB,MAAM,EAAE,EAAE,CAAC,MAAM,EAAE,CAAC,KAAK,EAAE,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;YAClD,MAAM,EAAE,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;YACxD,MAAM,EAAE,EAAE,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;QAChC,CAAC,CAAC,CAAC;IACP,CAAC;IAED,KAAK,CAAC,OAAO,CAAC,MAAc,EAAE,GAAW;QACrC,IAAI,CAAC;YACD,MAAM,eAAe,GAAG,IAAI,CAAC,iBAAiB,CAAC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;YAC1F,MAAM,eAAe,GAAG,eAAe,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC;YAEhE,MAAM,eAAe,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC;YAEzC,MAAM,QAAQ,GAAiB;gBAC3B,YAAY,EAAE,IAAA,eAAQ,EAAC,GAAG,CAAC;gBAC3B,QAAQ,EAAE,IAAA,eAAQ,EAAC,GAAG,CAAC;gBACvB,IAAI,EAAE,MAAM,CAAC,MAAM;gBACnB,MAAM;gBACN,GAAG;gBACH,QAAQ,EAAE,GAAG;gBACb,GAAG,EAAE,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC;aACxB,CAAC;YAEF,OAAO,QAAQ,CAAC;QACpB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,CAAC,KAAK,CAAC,yBAAyB,GAAG,IAAI,EAAE,KAAK,CAAC,CAAC;YACvD,MAAM,KAAK,CAAC;QAChB,CAAC;IACL,CAAC;IAED,KAAK,CAAC,UAAU,CAAC,GAAW;QACxB,IAAI,CAAC;YACD,MAAM,UAAU,GAAG,IAAI,CAAC,iBAAiB;iBACpC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC;iBAC1C,aAAa,CAAC,GAAG,CAAC,CAAC;YAExB,MAAM,UAAU,CAAC,MAAM,EAAE,CAAC;QAC9B,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,CAAC,KAAK,CAAC,wBAAwB,GAAG,IAAI,EAAE,KAAK,CAAC,CAAC;QAC1D,CAAC;IACL,CAAC;IAED,KAAK,CAAC,QAAQ,CAAC,MAAc,EAAE,MAAc;QACzC,IAAI,CAAC;YACD,MAAM,eAAe,GAAG,IAAI,CAAC,iBAAiB,CAAC,kBAAkB,CAAC,IAAI,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;YAC1F,MAAM,gBAAgB,GAAG,eAAe,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC;YAC/D,MAAM,qBAAqB,GAAG,eAAe,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC;YAEpE,MAAM,UAAU,GAAG,MAAM,qBAAqB,CAAC,gBAAgB,CAAC,gBAAgB,CAAC,GAAG,CAAC,CAAC;YACtF,MAAM,UAAU,CAAC,aAAa,EAAE,CAAC;YAEjC,MAAM,UAAU,GAAG,MAAM,qBAAqB,CAAC,aAAa,EAAE,CAAC;YAE/D,OAAO;gBACH,YAAY,EAAE,IAAA,eAAQ,EAAC,MAAM,CAAC;gBAC9B,IAAI,EAAE,UAAU,CAAC,aAAa,IAAI,CAAC;gBACnC,QAAQ,EAAE,IAAA,eAAQ,EAAC,MAAM,CAAC;gBAC1B,GAAG,EAAE,MAAM;gBACX,QAAQ,EAAE,MAAM;gBAChB,GAAG,EAAE,IAAI,CAAC,MAAM,CAAC,MAAM,CAAC;aAC3B,CAAC;QACN,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,CAAC,KAAK,CAAC,2CAA2C,EAAE,KAAK,CAAC,CAAC;YAClE,MAAM,KAAK,CAAC;QAChB,CAAC;IACL,CAAC;CAGJ;AApMD,oCAoMC"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { StorageEngine } from 'multer';
|
|
2
|
+
import { LocalStorageOptions, Storage, UploadedFile } from '../types';
|
|
3
|
+
export declare class LocalStorage implements StorageEngine, Storage {
|
|
4
|
+
private options;
|
|
5
|
+
private rootPath;
|
|
6
|
+
private fileNameFunction;
|
|
7
|
+
private fileDistFunction;
|
|
8
|
+
/**
|
|
9
|
+
* Convert OS-specific file path to URL-friendly key
|
|
10
|
+
* This ensures keys are consistent across all platforms
|
|
11
|
+
* Windows: C:\uploads\2024\01\file.jpg -> 2024/01/file.jpg
|
|
12
|
+
* Unix: /uploads/2024/01/file.jpg -> 2024/01/file.jpg
|
|
13
|
+
*/
|
|
14
|
+
private pathToUrl;
|
|
15
|
+
/**
|
|
16
|
+
* Convert URL-friendly key to OS-specific file path
|
|
17
|
+
* This converts stored keys back to valid file system paths
|
|
18
|
+
* 2024/01/file.jpg -> Windows: 2024\01\file.jpg, Unix: 2024/01/file.jpg
|
|
19
|
+
*/
|
|
20
|
+
private urlToPath;
|
|
21
|
+
/**
|
|
22
|
+
* Get full file system path from URL-friendly key
|
|
23
|
+
*/
|
|
24
|
+
private getFullPath;
|
|
25
|
+
constructor(options: LocalStorageOptions);
|
|
26
|
+
_handleFile(req: any, file: Express.Multer.File, cb: (error?: any, info?: any) => void): Promise<void>;
|
|
27
|
+
_removeFile(_req: any, file: any, cb: (error: Error | null) => void): void;
|
|
28
|
+
getUrl(urlKey: string): string;
|
|
29
|
+
getFile(urlKey: string): Promise<Buffer>;
|
|
30
|
+
deleteFile(urlKey: string): Promise<void>;
|
|
31
|
+
putFile(fileContent: Buffer, urlKey: string): Promise<UploadedFile>;
|
|
32
|
+
path(urlKey: string): string;
|
|
33
|
+
copyFile(oldUrlKey: string, newUrlKey: string): Promise<UploadedFile>;
|
|
34
|
+
}
|
|
35
|
+
//# sourceMappingURL=local.storage.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local.storage.d.ts","sourceRoot":"","sources":["../../../src/lib/storage/local.storage.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAMvC,OAAO,EAAE,mBAAmB,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAGtE,qBAAa,YAAa,YAAW,aAAa,EAAE,OAAO;IA8C3C,OAAO,CAAC,OAAO;IA5C3B,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,gBAAgB,CAAqE;IAC7F,OAAO,CAAC,gBAAgB,CAAqE;IAE7F;;;;;OAKG;IACH,OAAO,CAAC,SAAS;IAajB;;;;OAIG;IACH,OAAO,CAAC,SAAS;IAQjB;;OAEG;IACH,OAAO,CAAC,WAAW;gBAKC,OAAO,EAAE,mBAAmB;IAmB1C,WAAW,CACb,GAAG,EAAE,GAAG,EACR,IAAI,EAAE,OAAO,CAAC,MAAM,CAAC,IAAI,EACzB,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,GAAG,EAAE,IAAI,CAAC,EAAE,GAAG,KAAK,IAAI;IAgCzC,WAAW,CACP,IAAI,EAAE,GAAG,EACT,IAAI,KAAA,EACJ,EAAE,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,KAAK,IAAI;IAarC,MAAM,CAAC,MAAM,EAAE,MAAM;IAgBf,OAAO,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAMxC,UAAU,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAMzC,OAAO,CACT,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACf,OAAO,CAAC,YAAY,CAAC;IAiCxB,IAAI,CAAC,MAAM,EAAE,MAAM;IAQb,QAAQ,CAAC,SAAS,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC;CAgC9E"}
|