feat(medusa-file-s3,medusa-file-minio): Upgrade to TypeScript (#3740)

This commit is contained in:
Derek Wene authored and GitHub committed 2023-04-23 12:31:16 +02:00
1 parent ba45a316a7
commit 8b6464180a
11 files changed
+661 -420

No files matched your search

-139
View File
@@ -1,139 +0,0 @@
import fs from "fs"
import aws from "aws-sdk"
import { parse } from "path"
import { AbstractFileService } from "@medusajs/medusa"
import stream from "stream"
class S3Service extends AbstractFileService {
// eslint-disable-next-line no-empty-pattern
constructor({}, options) {
super({}, options)
this.bucket_ = options.bucket
this.s3Url_ = options.s3_url
this.accessKeyId_ = options.access_key_id
this.secretAccessKey_ = options.secret_access_key
this.region_ = options.region
this.endpoint_ = options.endpoint
this.awsConfigObject_ = options.aws_config_object
this.client_ = new aws.S3()
}
upload(file) {
this.updateAwsConfig()
return this.uploadFile(file)
}
uploadProtected(file) {
this.updateAwsConfig()
return this.uploadFile(file, { acl: "private" })
}
uploadFile(file, options = { isProtected: false, acl: undefined }) {
const parsedFilename = parse(file.originalname)
const fileKey = `${parsedFilename.name}-${Date.now()}${parsedFilename.ext}`
const params = {
ACL: options.acl ?? (options.isProtected ? "private" : "public-read"),
Bucket: this.bucket_,
Body: fs.createReadStream(file.path),
Key: fileKey,
}
return new Promise((resolve, reject) => {
this.client_.upload(params, (err, data) => {
if (err) {
reject(err)
return
}
resolve({ url: data.Location, key: data.Key })
})
})
}
async delete(file) {
this.updateAwsConfig()
const params = {
Bucket: this.bucket_,
Key: `${file}`,
}
return new Promise((resolve, reject) => {
this.client_.deleteObject(params, (err, data) => {
if (err) {
reject(err)
return
}
resolve(data)
})
})
}
async getUploadStreamDescriptor(fileData) {
this.updateAwsConfig()
const pass = new stream.PassThrough()
const fileKey = `${fileData.name}.${fileData.ext}`
const params = {
ACL: fileData.acl ?? "private",
Bucket: this.bucket_,
Body: pass,
Key: fileKey,
}
return {
writeStream: pass,
promise: this.client_.upload(params).promise(),
url: `${this.s3Url_}/${fileKey}`,
fileKey,
}
}
async getDownloadStream(fileData) {
this.updateAwsConfig()
const params = {
Bucket: this.bucket_,
Key: `${fileData.fileKey}`,
}
return this.client_.getObject(params).createReadStream()
}
async getPresignedDownloadUrl(fileData) {
this.updateAwsConfig({
signatureVersion: "v4",
})
const params = {
Bucket: this.bucket_,
Key: `${fileData.fileKey}`,
Expires: this.downloadUrlDuration,
}
return await this.client_.getSignedUrlPromise("getObject", params)
}
updateAwsConfig(additionalConfiguration = {}) {
aws.config.setPromisesDependency(null)
const config = {
...additionalConfiguration,
accessKeyId: this.accessKeyId_,
secretAccessKey: this.secretAccessKey_,
region: this.region_,
endpoint: this.endpoint_,
...this.awsConfigObject_,
}
aws.config.update(config, true)
}
}
export default S3Service
+157
View File
@@ -0,0 +1,157 @@
import fs from "fs"
import aws from "aws-sdk"
import { parse } from "path"
import {
AbstractFileService,
DeleteFileType,
FileServiceUploadResult,
GetUploadedFileType,
IFileService,
UploadStreamDescriptorType,
} from "@medusajs/medusa"
import stream from "stream"
import { PutObjectRequest } from "aws-sdk/clients/s3"
import { ClientConfiguration } from "aws-sdk/clients/s3"
class S3Service extends AbstractFileService implements IFileService {
protected bucket_: string
protected s3Url_: string
protected accessKeyId_: string
protected secretAccessKey_: string
protected region_: string
protected endpoint_: string
protected awsConfigObject_: any
protected downloadFileDuration_: string
constructor({}, options) {
super({}, options)
this.bucket_ = options.bucket
this.s3Url_ = options.s3_url
this.accessKeyId_ = options.access_key_id
this.secretAccessKey_ = options.secret_access_key
this.region_ = options.region
this.endpoint_ = options.endpoint
this.downloadFileDuration_ = options.download_file_duration
this.awsConfigObject_ = options.aws_config_object ?? {}
}
protected getClient(overwriteConfig: Partial<ClientConfiguration> = {}) {
const config: ClientConfiguration = {
accessKeyId: this.accessKeyId_,
secretAccessKey: this.secretAccessKey_,
region: this.region_,
endpoint: this.endpoint_,
...this.awsConfigObject_,
...overwriteConfig,
}
return new aws.S3(config)
}
async upload(file: Express.Multer.File): Promise<FileServiceUploadResult> {
return await this.uploadFile(file)
}
async uploadProtected(file: Express.Multer.File) {
return await this.uploadFile(file, { acl: "private" })
}
async uploadFile(
file: Express.Multer.File,
options: { isProtected?: boolean; acl?: string } = {
isProtected: false,
acl: undefined,
}
) {
const client = this.getClient()
const parsedFilename = parse(file.originalname)
const fileKey = `${parsedFilename.name}-${Date.now()}${parsedFilename.ext}`
const params = {
ACL: options.acl ?? (options.isProtected ? "private" : "public-read"),
Bucket: this.bucket_,
Body: fs.createReadStream(file.path),
Key: fileKey,
ContentType: file.mimetype,
}
const result = await client.upload(params).promise()
return {
url: result.Location,
key: result.Key,
}
}
async delete(file: DeleteFileType): Promise<void> {
const client = this.getClient()
const params = {
Bucket: this.bucket_,
Key: `${file}`,
}
return new Promise((resolve, reject) => {
client.deleteObject(params, (err, data) => {
if (err) {
reject(err)
return
}
resolve()
})
})
}
async getUploadStreamDescriptor(fileData: UploadStreamDescriptorType) {
const client = this.getClient()
const pass = new stream.PassThrough()
const fileKey = `${fileData.name}.${fileData.ext}`
const params: PutObjectRequest = {
ACL: fileData.acl ?? "private",
Bucket: this.bucket_,
Body: pass,
Key: fileKey,
ContentType: fileData.contentType as string,
}
return {
writeStream: pass,
promise: client.upload(params).promise(),
url: `${this.s3Url_}/${fileKey}`,
fileKey,
}
}
async getDownloadStream(
fileData: GetUploadedFileType
): Promise<NodeJS.ReadableStream> {
const client = this.getClient()
const params = {
Bucket: this.bucket_,
Key: `${fileData.fileKey}`,
}
return await client.getObject(params).createReadStream()
}
async getPresignedDownloadUrl(
fileData: GetUploadedFileType
): Promise<string> {
const client = this.getClient({ signatureVersion: "v4" })
const params = {
Bucket: this.bucket_,
Key: `${fileData.fileKey}`,
Expires: this.downloadFileDuration_,
}
return await client.getSignedUrlPromise("getObject", params)
}
}
export default S3Service