@things-factory/attachment-base 8.0.38 → 9.0.0-9.0.0-beta.59.0
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/dist-server/index.js +7 -0
- package/dist-server/index.js.map +1 -1
- package/dist-server/nfc-normalize.d.ts +1 -0
- package/dist-server/nfc-normalize.js +24 -0
- package/dist-server/nfc-normalize.js.map +1 -0
- package/dist-server/service/attachment/attachment-mutation.js +9 -0
- package/dist-server/service/attachment/attachment-mutation.js.map +1 -1
- package/dist-server/storage-database.js +3 -1
- package/dist-server/storage-database.js.map +1 -1
- package/dist-server/storage-file.js +3 -1
- package/dist-server/storage-file.js.map +1 -1
- package/dist-server/storage-s3.js +3 -1
- package/dist-server/storage-s3.js.map +1 -1
- package/dist-server/tsconfig.tsbuildinfo +1 -1
- package/package.json +5 -5
- package/server/attachment-const.ts +0 -5
- package/server/awb-storage-s3.ts +0 -44
- package/server/index.ts +0 -15
- package/server/routes.ts +0 -35
- package/server/service/attachment/attachment-mutation.ts +0 -343
- package/server/service/attachment/attachment-query.ts +0 -78
- package/server/service/attachment/attachment-types.ts +0 -76
- package/server/service/attachment/attachment.ts +0 -129
- package/server/service/attachment/index.ts +0 -6
- package/server/service/index.ts +0 -19
- package/server/storage-azure-blob.ts +0 -111
- package/server/storage-database.ts +0 -78
- package/server/storage-file.ts +0 -78
- package/server/storage-s3.ts +0 -139
- package/server/util/index.ts +0 -1
- package/server/util/upload-awb.ts +0 -11
package/dist-server/index.js
CHANGED
@@ -14,4 +14,11 @@ Object.defineProperty(exports, "singleUpload", { enumerable: true, get: function
|
|
14
14
|
require("./routes");
|
15
15
|
tslib_1.__exportStar(require("./attachment-const"), exports);
|
16
16
|
tslib_1.__exportStar(require("./util"), exports);
|
17
|
+
const nfc_normalize_1 = require("./nfc-normalize");
|
18
|
+
process.on('bootstrap-module-start', async ({ app, config, client }) => {
|
19
|
+
/* 이 코드는 기존 첨부파일의 NFC 정규화를 강제로 실행하기 위해서 임시로 작성되었다. */
|
20
|
+
(0, nfc_normalize_1.normalizeNamesToNFC)()
|
21
|
+
.then(() => console.log('Normalization completed.'))
|
22
|
+
.catch(err => console.error('Error during normalization:', err));
|
23
|
+
});
|
17
24
|
//# sourceMappingURL=index.js.map
|
package/dist-server/index.js.map
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../server/index.ts"],"names":[],"mappings":";;;;AAAA,6DAAkC;AAClC,oDAAyB;AACzB,gFAOiD;AAN/C,uHAAA,gBAAgB,OAAA;AAChB,wHAAA,iBAAiB,OAAA;AACjB,uHAAA,gBAAgB,OAAA;AAChB,6HAAA,sBAAsB,OAAA;AACtB,qHAAA,cAAc,OAAA;AACd,mHAAA,YAAY,OAAA;AAGd,oBAAiB;AAEjB,6DAAkC;AAClC,iDAAsB","sourcesContent":["export * from './attachment-const'\nexport * from './service'\nexport {\n createAttachment,\n createAttachments,\n deleteAttachment,\n deleteAttachmentsByRef,\n multipleUpload,\n singleUpload\n} from './service/attachment/attachment-mutation'\n\nimport './routes'\n\nexport * from './attachment-const'\nexport * from './util'\n"]}
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../server/index.ts"],"names":[],"mappings":";;;;AAAA,6DAAkC;AAClC,oDAAyB;AACzB,gFAOiD;AAN/C,uHAAA,gBAAgB,OAAA;AAChB,wHAAA,iBAAiB,OAAA;AACjB,uHAAA,gBAAgB,OAAA;AAChB,6HAAA,sBAAsB,OAAA;AACtB,qHAAA,cAAc,OAAA;AACd,mHAAA,YAAY,OAAA;AAGd,oBAAiB;AAEjB,6DAAkC;AAClC,iDAAsB;AAEtB,mDAAqD;AAErD,OAAO,CAAC,EAAE,CAAC,wBAA+B,EAAE,KAAK,EAAE,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,EAAO,EAAE,EAAE;IACjF,qDAAqD;IACrD,IAAA,mCAAmB,GAAE;SAClB,IAAI,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,GAAG,CAAC,0BAA0B,CAAC,CAAC;SACnD,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,6BAA6B,EAAE,GAAG,CAAC,CAAC,CAAA;AACpE,CAAC,CAAC,CAAA","sourcesContent":["export * from './attachment-const'\nexport * from './service'\nexport {\n createAttachment,\n createAttachments,\n deleteAttachment,\n deleteAttachmentsByRef,\n multipleUpload,\n singleUpload\n} from './service/attachment/attachment-mutation'\n\nimport './routes'\n\nexport * from './attachment-const'\nexport * from './util'\n\nimport { normalizeNamesToNFC } from './nfc-normalize'\n\nprocess.on('bootstrap-module-start' as any, async ({ app, config, client }: any) => {\n /* 이 코드는 기존 첨부파일의 NFC 정규화를 강제로 실행하기 위해서 임시로 작성되었다. */\n normalizeNamesToNFC()\n .then(() => console.log('Normalization completed.'))\n .catch(err => console.error('Error during normalization:', err))\n})\n"]}
|
@@ -0,0 +1 @@
|
|
1
|
+
export declare function normalizeNamesToNFC(): Promise<void>;
|
@@ -0,0 +1,24 @@
|
|
1
|
+
"use strict";
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
3
|
+
exports.normalizeNamesToNFC = normalizeNamesToNFC;
|
4
|
+
const shell_1 = require("@things-factory/shell");
|
5
|
+
const attachment_1 = require("./service/attachment/attachment");
|
6
|
+
async function normalizeNamesToNFC() {
|
7
|
+
const attachmentRepository = (0, shell_1.getRepository)(attachment_1.Attachment);
|
8
|
+
// 모든 Attachment 항목을 조회
|
9
|
+
const attachments = await attachmentRepository.find();
|
10
|
+
// NFD로 저장된 name을 NFC로 변환하여 업데이트
|
11
|
+
for (const attachment of attachments) {
|
12
|
+
if (attachment.name) {
|
13
|
+
const normalizedName = attachment.name.normalize('NFC');
|
14
|
+
// name이 NFD로 저장된 경우만 업데이트
|
15
|
+
if (attachment.name !== normalizedName) {
|
16
|
+
attachment.name = normalizedName;
|
17
|
+
await attachmentRepository.save(attachment);
|
18
|
+
console.log(`Updated name for attachment ID ${attachment.id}: ${normalizedName}`);
|
19
|
+
}
|
20
|
+
}
|
21
|
+
}
|
22
|
+
console.log('All names have been normalized to NFC.');
|
23
|
+
}
|
24
|
+
//# sourceMappingURL=nfc-normalize.js.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"nfc-normalize.js","sourceRoot":"","sources":["../server/nfc-normalize.ts"],"names":[],"mappings":";;AAGA,kDAqBC;AAxBD,iDAAqD;AACrD,gEAA4D;AAErD,KAAK,UAAU,mBAAmB;IACvC,MAAM,oBAAoB,GAAG,IAAA,qBAAa,EAAC,uBAAU,CAAC,CAAA;IAEtD,uBAAuB;IACvB,MAAM,WAAW,GAAG,MAAM,oBAAoB,CAAC,IAAI,EAAE,CAAA;IAErD,gCAAgC;IAChC,KAAK,MAAM,UAAU,IAAI,WAAW,EAAE,CAAC;QACrC,IAAI,UAAU,CAAC,IAAI,EAAE,CAAC;YACpB,MAAM,cAAc,GAAG,UAAU,CAAC,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,CAAA;YAEvD,0BAA0B;YAC1B,IAAI,UAAU,CAAC,IAAI,KAAK,cAAc,EAAE,CAAC;gBACvC,UAAU,CAAC,IAAI,GAAG,cAAc,CAAA;gBAChC,MAAM,oBAAoB,CAAC,IAAI,CAAC,UAAU,CAAC,CAAA;gBAC3C,OAAO,CAAC,GAAG,CAAC,kCAAkC,UAAU,CAAC,EAAE,KAAK,cAAc,EAAE,CAAC,CAAA;YACnF,CAAC;QACH,CAAC;IACH,CAAC;IAED,OAAO,CAAC,GAAG,CAAC,wCAAwC,CAAC,CAAA;AACvD,CAAC","sourcesContent":["import { getRepository } from '@things-factory/shell'\nimport { Attachment } from './service/attachment/attachment'\n\nexport async function normalizeNamesToNFC() {\n const attachmentRepository = getRepository(Attachment)\n\n // 모든 Attachment 항목을 조회\n const attachments = await attachmentRepository.find()\n\n // NFD로 저장된 name을 NFC로 변환하여 업데이트\n for (const attachment of attachments) {\n if (attachment.name) {\n const normalizedName = attachment.name.normalize('NFC')\n\n // name이 NFD로 저장된 경우만 업데이트\n if (attachment.name !== normalizedName) {\n attachment.name = normalizedName\n await attachmentRepository.save(attachment)\n console.log(`Updated name for attachment ID ${attachment.id}: ${normalizedName}`)\n }\n }\n }\n\n console.log('All names have been normalized to NFC.')\n}\n"]}
|
@@ -60,6 +60,7 @@ let AttachmentMutation = class AttachmentMutation {
|
|
60
60
|
exports.AttachmentMutation = AttachmentMutation;
|
61
61
|
tslib_1.__decorate([
|
62
62
|
(0, type_graphql_1.Directive)('@transaction'),
|
63
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
63
64
|
(0, type_graphql_1.Mutation)(returns => attachment_1.Attachment),
|
64
65
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('attachment', type => attachment_types_1.NewAttachment)),
|
65
66
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -69,6 +70,7 @@ tslib_1.__decorate([
|
|
69
70
|
], AttachmentMutation.prototype, "createAttachment", null);
|
70
71
|
tslib_1.__decorate([
|
71
72
|
(0, type_graphql_1.Directive)('@transaction'),
|
73
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
72
74
|
(0, type_graphql_1.Mutation)(returns => [attachment_1.Attachment]),
|
73
75
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('attachments', type => [attachment_types_1.NewAttachment])),
|
74
76
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -78,6 +80,7 @@ tslib_1.__decorate([
|
|
78
80
|
], AttachmentMutation.prototype, "createAttachments", null);
|
79
81
|
tslib_1.__decorate([
|
80
82
|
(0, type_graphql_1.Directive)('@transaction'),
|
83
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
81
84
|
(0, type_graphql_1.Mutation)(returns => attachment_1.Attachment),
|
82
85
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('id')),
|
83
86
|
tslib_1.__param(1, (0, type_graphql_1.Arg)('patch', type => attachment_types_1.AttachmentPatch)),
|
@@ -88,6 +91,7 @@ tslib_1.__decorate([
|
|
88
91
|
], AttachmentMutation.prototype, "updateAttachment", null);
|
89
92
|
tslib_1.__decorate([
|
90
93
|
(0, type_graphql_1.Directive)('@transaction'),
|
94
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
91
95
|
(0, type_graphql_1.Mutation)(returns => Boolean),
|
92
96
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('id')),
|
93
97
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -97,6 +101,7 @@ tslib_1.__decorate([
|
|
97
101
|
], AttachmentMutation.prototype, "deleteAttachment", null);
|
98
102
|
tslib_1.__decorate([
|
99
103
|
(0, type_graphql_1.Directive)('@transaction'),
|
104
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
100
105
|
(0, type_graphql_1.Mutation)(returns => Boolean),
|
101
106
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('refBys', type => [String])),
|
102
107
|
tslib_1.__param(1, (0, type_graphql_1.Arg)('refType', type => String, { nullable: true })),
|
@@ -107,6 +112,7 @@ tslib_1.__decorate([
|
|
107
112
|
], AttachmentMutation.prototype, "deleteAttachmentsByRef", null);
|
108
113
|
tslib_1.__decorate([
|
109
114
|
(0, type_graphql_1.Directive)('@transaction'),
|
115
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
110
116
|
(0, type_graphql_1.Mutation)(returns => attachment_1.Attachment),
|
111
117
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('file', type => GraphQLUpload_js_2.default)),
|
112
118
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -116,6 +122,7 @@ tslib_1.__decorate([
|
|
116
122
|
], AttachmentMutation.prototype, "singleUpload", null);
|
117
123
|
tslib_1.__decorate([
|
118
124
|
(0, type_graphql_1.Directive)('@transaction'),
|
125
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
119
126
|
(0, type_graphql_1.Mutation)(returns => [attachment_1.Attachment]),
|
120
127
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('files', type => [GraphQLUpload_js_2.default])),
|
121
128
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -125,6 +132,7 @@ tslib_1.__decorate([
|
|
125
132
|
], AttachmentMutation.prototype, "multipleUpload", null);
|
126
133
|
tslib_1.__decorate([
|
127
134
|
(0, type_graphql_1.Mutation)(returns => attachment_types_1.UploadURL),
|
135
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
128
136
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('type', type => String)),
|
129
137
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
130
138
|
tslib_1.__metadata("design:type", Function),
|
@@ -133,6 +141,7 @@ tslib_1.__decorate([
|
|
133
141
|
], AttachmentMutation.prototype, "generateUploadURL", null);
|
134
142
|
tslib_1.__decorate([
|
135
143
|
(0, type_graphql_1.Directive)('@transaction'),
|
144
|
+
(0, type_graphql_1.Directive)('@privilege(category: "attachment", privilege: "mutation", domainOwnerGranted: true)'),
|
136
145
|
(0, type_graphql_1.Mutation)(returns => [attachment_1.Attachment], { description: 'To import some Attachments' }),
|
137
146
|
tslib_1.__param(0, (0, type_graphql_1.Arg)('file', () => GraphQLUpload_js_2.default)),
|
138
147
|
tslib_1.__param(1, (0, type_graphql_1.Ctx)()),
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"attachment-mutation.js","sourceRoot":"","sources":["../../../server/service/attachment/attachment-mutation.ts"],"names":[],"mappings":"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","sourcesContent":["import { FileUpload } from 'graphql-upload/GraphQLUpload.js'\nimport GraphQLUpload from 'graphql-upload/GraphQLUpload.js'\nimport promisesAll from 'promises-all'\n\nimport { Arg, Ctx, Directive, Mutation, Resolver } from 'type-graphql'\nimport { In } from 'typeorm'\n\nimport { config, logger } from '@things-factory/env'\nimport { getRepository } from '@things-factory/shell'\n\nimport { STORAGE } from '../../attachment-const'\nimport { Attachment } from './attachment'\nimport { AttachmentPatch, NewAttachment, UploadURL } from './attachment-types'\n\nconst allowedMimeTypes = config.get('fileUpload/mimeTypes', [])\n\n@Resolver(Attachment)\nexport class AttachmentMutation {\n @Directive('@transaction')\n @Mutation(returns => Attachment)\n async createAttachment(\n @Arg('attachment', type => NewAttachment) attachment: NewAttachment,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n return await createAttachment(null, { attachment }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => [Attachment])\n async createAttachments(\n @Arg('attachments', type => [NewAttachment]) attachments: NewAttachment[],\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await createAttachments(null, { attachments }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => Attachment)\n async updateAttachment(\n @Arg('id') id: string,\n @Arg('patch', type => AttachmentPatch) patch: AttachmentPatch,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n const attachment = await getRepository(Attachment).findOne({\n where: {\n domain: { id: context.state.domain.id },\n id\n }\n })\n\n return await getRepository(Attachment).save({\n ...attachment,\n ...patch,\n updater: context.state.user\n })\n }\n\n @Directive('@transaction')\n @Mutation(returns => Boolean)\n async deleteAttachment(@Arg('id') id: string, @Ctx() context: ResolverContext): Promise<boolean> {\n return await deleteAttachment(null, { id }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => Boolean)\n async deleteAttachmentsByRef(\n @Arg('refBys', type => [String]) refBys: string[],\n @Arg('refType', type => String, { nullable: true }) refType: string,\n @Ctx() context: ResolverContext\n ): Promise<boolean> {\n return await deleteAttachmentsByRef(null, { refBys, refType }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => Attachment)\n async singleUpload(\n @Arg('file', type => GraphQLUpload) file: FileUpload,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n return await singleUpload(null, { file }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => [Attachment])\n async multipleUpload(\n @Arg('files', type => [GraphQLUpload]) files: FileUpload[],\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await multipleUpload(null, { files }, context)\n }\n\n @Mutation(returns => UploadURL)\n async generateUploadURL(\n @Arg('type', type => String) type: string,\n @Ctx() context: ResolverContext\n ): Promise<{ url: string; fields: { [key: string]: string } }> {\n return await generateUploadURL(null, { type }, context)\n }\n\n @Directive('@transaction')\n @Mutation(returns => [Attachment], { description: 'To import some Attachments' })\n async importAttachments(\n @Arg('file', () => GraphQLUpload) file: FileUpload,\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await importAttachments(file, context)\n }\n}\n\nexport async function createAttachment(_: any, { attachment }, context: ResolverContext): Promise<Attachment> {\n const { file, category, refType = '', refBy, description } = attachment\n const { mimetype } = (await file) as FileUpload\n\n if (allowedMimeTypes instanceof Array && allowedMimeTypes.length > 0 && !allowedMimeTypes.includes('*/*')) {\n const isAllowed = allowedMimeTypes.some(type => {\n const [typeMain, typeSub] = type.split('/')\n const [mimeMain, mimeSub] = mimetype.split('/')\n return (\n (typeMain === mimeMain && (typeSub === '*' || typeSub === mimeSub)) || (typeMain === '*' && typeSub === '*')\n )\n })\n\n if (!isAllowed) {\n throw Error(context.t(`error.not allowed file type for upload`, { mimetype }))\n }\n }\n\n const { id, path, size, filename, encoding, contents } = await STORAGE.uploadFile({ file, context })\n const { domain, user, tx } = context.state\n\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n\n return await repository.save({\n domain,\n creator: user,\n updater: user,\n id,\n description,\n name: filename,\n mimetype,\n encoding,\n refType,\n refBy,\n category: category || mimetype.split('/').shift(),\n size: size as any,\n path,\n contents\n })\n}\n\nexport async function createAttachments(_: any, { attachments }, context: ResolverContext): Promise<Attachment[]> {\n const { resolve, reject } = await promisesAll.all(\n attachments.map(attachment => createAttachment(_, { attachment }, context))\n )\n\n if (reject.length) {\n reject.forEach(({ name, message }) => logger.error(`${name}: ${message}`))\n\n return reject\n }\n\n return resolve\n}\n\nexport async function deleteAttachment(_: any, { id }, context: ResolverContext): Promise<boolean> {\n const { domain, tx } = context.state\n\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n const attachment = await repository.findOne({\n where: { domain: { id: domain.id }, id }\n })\n\n if (attachment) {\n await repository.delete({ id: attachment.id })\n await STORAGE.deleteFile(attachment.path)\n return true\n } else {\n return false\n }\n}\n\ninterface DeleteAttachmentsObject {\n refBys: Array<string>\n refType?: string\n}\nexport async function deleteAttachmentsByRef(\n _: any,\n { refBys, refType = null }: DeleteAttachmentsObject,\n context: ResolverContext\n): Promise<boolean> {\n const { domain, tx } = context.state\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n const inquryWhereClause: any = { domain: { id: domain.id }, refBy: In(refBys) }\n const deleteWhereClause: any = { refBy: In(refBys) }\n \n // refType이 존재하면 where 절에 추가\n if (refType) {\n inquryWhereClause.refType = refType;\n deleteWhereClause.refType = refType;\n }\n \n const attachments = await repository.find({\n where: inquryWhereClause\n })\n\n //remove attachment from repo\n await repository.delete(deleteWhereClause)\n\n //remove files from attachments folder\n if (attachments.length) {\n await Promise.all(\n attachments.map(async attachment => {\n await STORAGE.deleteFile(attachment.path)\n })\n )\n\n return true\n } else {\n return false\n }\n}\n\nexport async function generateUploadURL(\n _: any,\n { type },\n context: ResolverContext\n): Promise<{ url: string; fields: { [key: string]: string } }> {\n return await STORAGE.generateUploadURL(type)\n}\n\nexport async function singleUpload(_: any, { file }, context: ResolverContext): Promise<Attachment> {\n return await createAttachment(null, { attachment: { file } }, context)\n}\n\nexport async function multipleUpload(_: any, { files }, context: ResolverContext): Promise<Attachment[]> {\n return await createAttachments(null, { attachments: { files } }, context)\n}\n\nasync function parseJSONFile(uploadedFile: FileUpload): Promise<any> {\n var { createReadStream } = await uploadedFile\n\n return new Promise((resolve, reject) => {\n const chunks: Uint8Array[] = []\n\n createReadStream()\n .on('data', (chunk: Uint8Array) => {\n chunks.push(chunk)\n })\n .on('end', () => {\n try {\n const fileContents = Buffer.concat(chunks).toString('utf-8')\n const jsonData = JSON.parse(fileContents)\n resolve(jsonData)\n } catch (error) {\n reject(error)\n }\n })\n .on('error', (error: Error) => {\n reject(error)\n })\n })\n}\n\nfunction dataURLToFileUpload(dataURL: string, filename: string, mimeType: string): FileUpload {\n const indexOfComma = dataURL.indexOf(',')\n if (indexOfComma === -1) {\n throw new Error('Invalid Data URL')\n }\n\n const base64Data = dataURL.slice(indexOfComma + 1)\n const buffer = Buffer.from(base64Data, 'base64')\n\n return {\n filename,\n mimetype: mimeType,\n encoding: 'base64',\n createReadStream: () => {\n const stream = require('stream')\n const readable = new stream.Readable()\n readable.push(buffer)\n readable.push(null)\n return readable\n }\n }\n}\n\nexport async function importAttachments(upload: FileUpload, context: ResolverContext): Promise<Attachment[]> {\n const { domain, user, notify, tx } = context.state\n\n const repository = tx.getRepository(Attachment)\n\n const attachments = []\n\n const parsed = await parseJSONFile(upload)\n\n for (const id in parsed) {\n var { name, description, category, mimetype, encoding, contents } = parsed[id]\n if (!name || !contents || !mimetype) {\n throw 'Malformed attachments import file'\n }\n\n var sameIdAttachment = await repository.findOneBy({ id })\n\n if (sameIdAttachment) {\n if (sameIdAttachment.domainId != domain.id) {\n throw `Attachment with id/name(${id}/${name}) is already taken in another domain`\n }\n\n // 동일 아이디 첨부파일이 있다면, 스킵한다.\n continue\n }\n\n const file = dataURLToFileUpload(contents, name, mimetype)\n\n var { path, size, contents } = await STORAGE.uploadFile({ id, file, context })\n\n attachments.push(\n await repository.save({\n domain,\n creator: user,\n updater: user,\n id,\n description,\n name,\n mimetype,\n encoding,\n category: category || mimetype.split('/').shift(),\n size: size as any,\n path,\n contents\n })\n )\n }\n\n notify &&\n notify({\n mode: 'in-app',\n title: `${attachments.length} Attachment(s) are imported`,\n body: `${attachments.length} Attachment(s) are imported by ${user.name}`\n })\n\n return attachments\n}\n"]}
|
1
|
+
{"version":3,"file":"attachment-mutation.js","sourceRoot":"","sources":["../../../server/service/attachment/attachment-mutation.ts"],"names":[],"mappings":"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","sourcesContent":["import { FileUpload } from 'graphql-upload/GraphQLUpload.js'\nimport GraphQLUpload from 'graphql-upload/GraphQLUpload.js'\nimport promisesAll from 'promises-all'\n\nimport { Arg, Ctx, Directive, Mutation, Resolver } from 'type-graphql'\nimport { In } from 'typeorm'\n\nimport { config, logger } from '@things-factory/env'\nimport { getRepository } from '@things-factory/shell'\n\nimport { STORAGE } from '../../attachment-const'\nimport { Attachment } from './attachment'\nimport { AttachmentPatch, NewAttachment, UploadURL } from './attachment-types'\n\nconst allowedMimeTypes = config.get('fileUpload/mimeTypes', [])\n\n@Resolver(Attachment)\nexport class AttachmentMutation {\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => Attachment)\n async createAttachment(\n @Arg('attachment', type => NewAttachment) attachment: NewAttachment,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n return await createAttachment(null, { attachment }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => [Attachment])\n async createAttachments(\n @Arg('attachments', type => [NewAttachment]) attachments: NewAttachment[],\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await createAttachments(null, { attachments }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => Attachment)\n async updateAttachment(\n @Arg('id') id: string,\n @Arg('patch', type => AttachmentPatch) patch: AttachmentPatch,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n const attachment = await getRepository(Attachment).findOne({\n where: {\n domain: { id: context.state.domain.id },\n id\n }\n })\n\n return await getRepository(Attachment).save({\n ...attachment,\n ...patch,\n updater: context.state.user\n })\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => Boolean)\n async deleteAttachment(@Arg('id') id: string, @Ctx() context: ResolverContext): Promise<boolean> {\n return await deleteAttachment(null, { id }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => Boolean)\n async deleteAttachmentsByRef(\n @Arg('refBys', type => [String]) refBys: string[],\n @Arg('refType', type => String, { nullable: true }) refType: string,\n @Ctx() context: ResolverContext\n ): Promise<boolean> {\n return await deleteAttachmentsByRef(null, { refBys, refType }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => Attachment)\n async singleUpload(\n @Arg('file', type => GraphQLUpload) file: FileUpload,\n @Ctx() context: ResolverContext\n ): Promise<Attachment> {\n return await singleUpload(null, { file }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => [Attachment])\n async multipleUpload(\n @Arg('files', type => [GraphQLUpload]) files: FileUpload[],\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await multipleUpload(null, { files }, context)\n }\n\n @Mutation(returns => UploadURL)\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n async generateUploadURL(\n @Arg('type', type => String) type: string,\n @Ctx() context: ResolverContext\n ): Promise<{ url: string; fields: { [key: string]: string } }> {\n return await generateUploadURL(null, { type }, context)\n }\n\n @Directive('@transaction')\n @Directive('@privilege(category: \"attachment\", privilege: \"mutation\", domainOwnerGranted: true)')\n @Mutation(returns => [Attachment], { description: 'To import some Attachments' })\n async importAttachments(\n @Arg('file', () => GraphQLUpload) file: FileUpload,\n @Ctx() context: ResolverContext\n ): Promise<Attachment[]> {\n return await importAttachments(file, context)\n }\n}\n\nexport async function createAttachment(_: any, { attachment }, context: ResolverContext): Promise<Attachment> {\n const { file, category, refType = '', refBy, description } = attachment\n const { mimetype } = (await file) as FileUpload\n\n if (allowedMimeTypes instanceof Array && allowedMimeTypes.length > 0 && !allowedMimeTypes.includes('*/*')) {\n const isAllowed = allowedMimeTypes.some(type => {\n const [typeMain, typeSub] = type.split('/')\n const [mimeMain, mimeSub] = mimetype.split('/')\n return (\n (typeMain === mimeMain && (typeSub === '*' || typeSub === mimeSub)) || (typeMain === '*' && typeSub === '*')\n )\n })\n\n if (!isAllowed) {\n throw Error(context.t(`error.not allowed file type for upload`, { mimetype }))\n }\n }\n\n const { id, path, size, filename, encoding, contents } = await STORAGE.uploadFile({ file, context })\n const { domain, user, tx } = context.state\n\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n\n return await repository.save({\n domain,\n creator: user,\n updater: user,\n id,\n description,\n name: filename,\n mimetype,\n encoding,\n refType,\n refBy,\n category: category || mimetype.split('/').shift(),\n size: size as any,\n path,\n contents\n })\n}\n\nexport async function createAttachments(_: any, { attachments }, context: ResolverContext): Promise<Attachment[]> {\n const { resolve, reject } = await promisesAll.all(\n attachments.map(attachment => createAttachment(_, { attachment }, context))\n )\n\n if (reject.length) {\n reject.forEach(({ name, message }) => logger.error(`${name}: ${message}`))\n\n return reject\n }\n\n return resolve\n}\n\nexport async function deleteAttachment(_: any, { id }, context: ResolverContext): Promise<boolean> {\n const { domain, tx } = context.state\n\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n const attachment = await repository.findOne({\n where: { domain: { id: domain.id }, id }\n })\n\n if (attachment) {\n await repository.delete({ id: attachment.id })\n await STORAGE.deleteFile(attachment.path)\n return true\n } else {\n return false\n }\n}\n\ninterface DeleteAttachmentsObject {\n refBys: Array<string>\n refType?: string\n}\nexport async function deleteAttachmentsByRef(\n _: any,\n { refBys, refType = null }: DeleteAttachmentsObject,\n context: ResolverContext\n): Promise<boolean> {\n const { domain, tx } = context.state\n const repository = tx ? tx.getRepository(Attachment) : getRepository(Attachment)\n const inquryWhereClause: any = { domain: { id: domain.id }, refBy: In(refBys) }\n const deleteWhereClause: any = { refBy: In(refBys) }\n\n // refType이 존재하면 where 절에 추가\n if (refType) {\n inquryWhereClause.refType = refType\n deleteWhereClause.refType = refType\n }\n\n const attachments = await repository.find({\n where: inquryWhereClause\n })\n\n //remove attachment from repo\n await repository.delete(deleteWhereClause)\n\n //remove files from attachments folder\n if (attachments.length) {\n await Promise.all(\n attachments.map(async attachment => {\n await STORAGE.deleteFile(attachment.path)\n })\n )\n\n return true\n } else {\n return false\n }\n}\n\nexport async function generateUploadURL(\n _: any,\n { type },\n context: ResolverContext\n): Promise<{ url: string; fields: { [key: string]: string } }> {\n return await STORAGE.generateUploadURL(type)\n}\n\nexport async function singleUpload(_: any, { file }, context: ResolverContext): Promise<Attachment> {\n return await createAttachment(null, { attachment: { file } }, context)\n}\n\nexport async function multipleUpload(_: any, { files }, context: ResolverContext): Promise<Attachment[]> {\n return await createAttachments(null, { attachments: { files } }, context)\n}\n\nasync function parseJSONFile(uploadedFile: FileUpload): Promise<any> {\n var { createReadStream } = await uploadedFile\n\n return new Promise((resolve, reject) => {\n const chunks: Uint8Array[] = []\n\n createReadStream()\n .on('data', (chunk: Uint8Array) => {\n chunks.push(chunk)\n })\n .on('end', () => {\n try {\n const fileContents = Buffer.concat(chunks).toString('utf-8')\n const jsonData = JSON.parse(fileContents)\n resolve(jsonData)\n } catch (error) {\n reject(error)\n }\n })\n .on('error', (error: Error) => {\n reject(error)\n })\n })\n}\n\nfunction dataURLToFileUpload(dataURL: string, filename: string, mimeType: string): FileUpload {\n const indexOfComma = dataURL.indexOf(',')\n if (indexOfComma === -1) {\n throw new Error('Invalid Data URL')\n }\n\n const base64Data = dataURL.slice(indexOfComma + 1)\n const buffer = Buffer.from(base64Data, 'base64')\n\n return {\n filename,\n mimetype: mimeType,\n encoding: 'base64',\n createReadStream: () => {\n const stream = require('stream')\n const readable = new stream.Readable()\n readable.push(buffer)\n readable.push(null)\n return readable\n }\n }\n}\n\nexport async function importAttachments(upload: FileUpload, context: ResolverContext): Promise<Attachment[]> {\n const { domain, user, notify, tx } = context.state\n\n const repository = tx.getRepository(Attachment)\n\n const attachments = []\n\n const parsed = await parseJSONFile(upload)\n\n for (const id in parsed) {\n var { name, description, category, mimetype, encoding, contents } = parsed[id]\n if (!name || !contents || !mimetype) {\n throw 'Malformed attachments import file'\n }\n\n var sameIdAttachment = await repository.findOneBy({ id })\n\n if (sameIdAttachment) {\n if (sameIdAttachment.domainId != domain.id) {\n throw `Attachment with id/name(${id}/${name}) is already taken in another domain`\n }\n\n // 동일 아이디 첨부파일이 있다면, 스킵한다.\n continue\n }\n\n const file = dataURLToFileUpload(contents, name, mimetype)\n\n var { path, size, contents } = await STORAGE.uploadFile({ id, file, context })\n\n attachments.push(\n await repository.save({\n domain,\n creator: user,\n updater: user,\n id,\n description,\n name,\n mimetype,\n encoding,\n category: category || mimetype.split('/').shift(),\n size: size as any,\n path,\n contents\n })\n )\n }\n\n notify &&\n notify({\n mode: 'in-app',\n title: `${attachments.length} Attachment(s) are imported`,\n body: `${attachments.length} Attachment(s) are imported by ${user.name}`\n })\n\n return attachments\n}\n"]}
|
@@ -11,7 +11,9 @@ if (attachment_const_1.STORAGE && attachment_const_1.STORAGE.type == 'database')
|
|
11
11
|
attachment_const_1.STORAGE.uploadFile = async ({ id, file, context }) => {
|
12
12
|
var _a, e_1, _b, _c;
|
13
13
|
var { createReadStream, filename, mimetype, encoding } = await file;
|
14
|
-
filename = Buffer.from(filename, 'latin1')
|
14
|
+
filename = Buffer.from(filename, 'latin1')
|
15
|
+
.toString('utf-8')
|
16
|
+
.normalize('NFC'); /* Because busboy uses latin1 encoding */
|
15
17
|
const stream = createReadStream();
|
16
18
|
const chunks = [];
|
17
19
|
try {
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"storage-database.js","sourceRoot":"","sources":["../server/storage-database.ts"],"names":[],"mappings":";;;AAAA,sFAAoD;AAEpD,6CAA4C;AAC5C,iDAAqD;AAErD,gEAA4D;AAC5D,yDAA6D;AAE7D,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAA;AAEhC,IAAI,0BAAO,IAAI,0BAAO,CAAC,IAAI,IAAI,UAAU,EAAE,CAAC;IAC1C,0BAAO,CAAC,UAAU,GAAG,KAAK,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE,EAAE,EAAE;;QACnD,IAAI,EAAE,gBAAgB,EAAE,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,MAAM,IAAI,CAAA;QACnE,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,QAAQ,CAAC,
|
1
|
+
{"version":3,"file":"storage-database.js","sourceRoot":"","sources":["../server/storage-database.ts"],"names":[],"mappings":"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","sourcesContent":["import contentDisposition from 'content-disposition'\n\nimport { logger } from '@things-factory/env'\nimport { getRepository } from '@things-factory/shell'\n\nimport { Attachment } from './service/attachment/attachment'\nimport { ATTACHMENT_PATH, STORAGE } from './attachment-const'\n\nconst crypto = require('crypto')\n\nif (STORAGE && STORAGE.type == 'database') {\n STORAGE.uploadFile = async ({ id, file, context }) => {\n var { createReadStream, filename, mimetype, encoding } = await file\n filename = Buffer.from(filename, 'latin1')\n .toString('utf-8')\n .normalize('NFC') /* Because busboy uses latin1 encoding */\n\n const stream = createReadStream()\n\n const chunks: Buffer[] = []\n for await (const chunk of stream) {\n if (chunk instanceof Buffer) {\n chunks.push(chunk)\n }\n }\n\n id = id || crypto.randomUUID()\n const ext = filename.split('.').pop()\n const path = ext ? `${id}.${ext}` : id\n\n const contents = Buffer.concat(chunks)\n\n return {\n id,\n filename,\n mimetype,\n encoding,\n contents,\n path,\n size: contents.length\n }\n }\n\n STORAGE.deleteFile = async path => {}\n\n STORAGE.sendFile = async (context, attachment, next) => {\n const id = attachment.split('.')[0]\n\n const entity = await getRepository(Attachment).findOne({\n select: ['name', 'contents'],\n where: { id }\n })\n\n context.set('Content-Disposition', contentDisposition(entity.name))\n context.body = entity.contents\n context.type = entity.mimetype\n }\n\n STORAGE.readFile = async (attachment, encoding) => {\n const id = attachment.split('.')[0]\n\n const entity = await getRepository(Attachment).findOne({\n select: ['name', 'contents'],\n where: { id }\n })\n\n return await entity.contents\n }\n\n STORAGE.generateUploadURL = async (type: string): Promise<{ url: string; fields: { [key: string]: string } }> => {\n const id = crypto.randomUUID()\n\n return await {\n url: `/${ATTACHMENT_PATH}`,\n fields: {}\n }\n }\n\n logger.info('File Storage is Ready.')\n}\n"]}
|
@@ -12,7 +12,9 @@ if (attachment_const_1.STORAGE && attachment_const_1.STORAGE.type == 'file') {
|
|
12
12
|
const uploadDir = env_1.config.getPath(null, attachment_const_1.STORAGE.base || 'attachments');
|
13
13
|
attachment_const_1.STORAGE.uploadFile = async ({ id, file }) => {
|
14
14
|
var { createReadStream, filename, mimetype, encoding } = await file;
|
15
|
-
filename = Buffer.from(filename, 'latin1')
|
15
|
+
filename = Buffer.from(filename, 'latin1')
|
16
|
+
.toString('utf-8')
|
17
|
+
.normalize('NFC'); /* Because busboy uses latin1 encoding */
|
16
18
|
const stream = createReadStream();
|
17
19
|
mkdirp.sync(uploadDir);
|
18
20
|
id = id || crypto.randomUUID();
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"storage-file.js","sourceRoot":"","sources":["../server/storage-file.ts"],"names":[],"mappings":";;;AAAA,+CAAwB;AACxB,uDAAgC;AAChC,+BAA8B;AAE9B,6CAAoD;AAEpD,yDAA6D;AAE7D,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAA;AAChC,MAAM,IAAI,GAAG,OAAO,CAAC,UAAU,CAAC,CAAA;AAEhC,IAAI,0BAAO,IAAI,0BAAO,CAAC,IAAI,IAAI,MAAM,EAAE,CAAC;IACtC,MAAM,SAAS,GAAG,YAAM,CAAC,OAAO,CAAC,IAAI,EAAE,0BAAO,CAAC,IAAI,IAAI,aAAa,CAAC,CAAA;IAErE,0BAAO,CAAC,UAAU,GAAG,KAAK,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE,EAAE,EAAE;QAC1C,IAAI,EAAE,gBAAgB,EAAE,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,MAAM,IAAI,CAAA;QACnE,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,QAAQ,CAAC,
|
1
|
+
{"version":3,"file":"storage-file.js","sourceRoot":"","sources":["../server/storage-file.ts"],"names":[],"mappings":"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","sourcesContent":["import * as fs from 'fs'\nimport * as mkdirp from 'mkdirp'\nimport { resolve } from 'path'\n\nimport { config, logger } from '@things-factory/env'\n\nimport { ATTACHMENT_PATH, STORAGE } from './attachment-const'\n\nconst crypto = require('crypto')\nconst send = require('koa-send')\n\nif (STORAGE && STORAGE.type == 'file') {\n const uploadDir = config.getPath(null, STORAGE.base || 'attachments')\n\n STORAGE.uploadFile = async ({ id, file }) => {\n var { createReadStream, filename, mimetype, encoding } = await file\n filename = Buffer.from(filename, 'latin1')\n .toString('utf-8')\n .normalize('NFC') /* Because busboy uses latin1 encoding */\n\n const stream = createReadStream()\n\n mkdirp.sync(uploadDir)\n\n id = id || crypto.randomUUID()\n const ext = filename.split('.').pop()\n const path = ext ? resolve(uploadDir, `${id}.${ext}`) : resolve(uploadDir, id)\n const relativePath = path.split('\\\\').pop().split('/').pop()\n var size: number = 0\n\n return new Promise<{\n id: string\n filename: string\n path: string\n size: number\n mimetype: string\n encoding: string\n }>((resolve, reject) =>\n stream\n .on('error', error => {\n if (stream.truncated)\n // Delete the truncated file\n fs.unlinkSync(path)\n reject(error)\n })\n .on('data', chunk => {\n size += chunk.length\n })\n .pipe(fs.createWriteStream(path))\n .on('finish', () => resolve({ id, filename, path: relativePath, size, mimetype, encoding }))\n )\n }\n\n STORAGE.deleteFile = async path => {\n const fullpath = resolve(uploadDir, path)\n\n await fs.unlink(fullpath, logger.error)\n }\n\n STORAGE.sendFile = async (context, attachment, next) => {\n await send(context, attachment, { root: uploadDir })\n }\n\n STORAGE.readFile = (attachment, encoding) => {\n const fullpath = resolve(uploadDir, attachment)\n\n return fs.readFileSync(fullpath, encoding)\n }\n\n STORAGE.generateUploadURL = async (type: string): Promise<{ url: string; fields: { [key: string]: string } }> => {\n const id = crypto.randomUUID()\n\n return await {\n url: `/${ATTACHMENT_PATH}`,\n fields: {}\n }\n }\n\n logger.info('File Storage is Ready.')\n}\n"]}
|
@@ -24,7 +24,9 @@ if (attachment_const_1.STORAGE && attachment_const_1.STORAGE.type == 's3') {
|
|
24
24
|
/* upload file */
|
25
25
|
attachment_const_1.STORAGE.uploadFile = async ({ id, file }) => {
|
26
26
|
var { createReadStream, filename, mimetype, encoding } = await file;
|
27
|
-
filename = Buffer.from(filename, 'latin1')
|
27
|
+
filename = Buffer.from(filename, 'latin1')
|
28
|
+
.toString('utf-8')
|
29
|
+
.normalize('NFC'); /* Because busboy uses latin1 encoding */
|
28
30
|
const stream = createReadStream();
|
29
31
|
id = id || crypto.randomUUID();
|
30
32
|
const ext = filename.split('.').pop();
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"storage-s3.js","sourceRoot":"","sources":["../server/storage-s3.ts"],"names":[],"mappings":";;AAEA,kDAM2B;AAC3B,sDAA6C;AAC7C,kEAAgE;AAChE,6CAA4C;AAE5C,yDAA4C;AAE5C,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAA;AAChC,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,CAAA;AAE5B,IAAI,0BAAO,IAAI,0BAAO,CAAC,IAAI,IAAI,IAAI,EAAE,CAAC;IACpC,MAAM,MAAM,GAAG,IAAI,oBAAQ,CAAC;QAC1B,WAAW,EAAE;YACX,WAAW,EAAE,0BAAO,CAAC,WAAW;YAChC,eAAe,EAAE,0BAAO,CAAC,eAAe;SACzC;QACD,MAAM,EAAE,0BAAO,CAAC,MAAM;KACvB,CAAC,CAAA;IAEF,MAAM,cAAc,GAAG,CAAC,MAAgB,EAAE,EAAE,CAC1C,IAAI,OAAO,CAAS,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;QACtC,MAAM,MAAM,GAAa,EAAE,CAAA;QAC3B,MAAM,CAAC,EAAE,CAAC,MAAM,EAAE,KAAK,CAAC,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAA;QAC9C,MAAM,CAAC,IAAI,CAAC,KAAK,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,CAAA;QACxD,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,MAAM,CAAC,CAAA;IAC9B,CAAC,CAAC,CAAA;IAEJ,iBAAiB;IACjB,0BAAO,CAAC,UAAU,GAAG,KAAK,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE,EAAE,EAAE;QAC1C,IAAI,EAAE,gBAAgB,EAAE,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,MAAM,IAAI,CAAA;QACnE,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,QAAQ,CAAC,
|
1
|
+
{"version":3,"file":"storage-s3.js","sourceRoot":"","sources":["../server/storage-s3.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Readable } from 'stream'\n\nimport {\n DeleteObjectCommand,\n GetObjectCommand,\n GetObjectCommandInput,\n HeadObjectCommand,\n S3Client\n} from '@aws-sdk/client-s3'\nimport { Upload } from '@aws-sdk/lib-storage'\nimport { createPresignedPost } from '@aws-sdk/s3-presigned-post'\nimport { logger } from '@things-factory/env'\n\nimport { STORAGE } from './attachment-const'\n\nconst crypto = require('crypto')\nconst mime = require('mime')\n\nif (STORAGE && STORAGE.type == 's3') {\n const client = new S3Client({\n credentials: {\n accessKeyId: STORAGE.accessKeyId,\n secretAccessKey: STORAGE.secretAccessKey\n },\n region: STORAGE.region\n })\n\n const streamToBuffer = (stream: Readable) =>\n new Promise<Buffer>((resolve, reject) => {\n const chunks: Buffer[] = []\n stream.on('data', chunk => chunks.push(chunk))\n stream.once('end', () => resolve(Buffer.concat(chunks)))\n stream.once('error', reject)\n })\n\n /* upload file */\n STORAGE.uploadFile = async ({ id, file }) => {\n var { createReadStream, filename, mimetype, encoding } = await file\n filename = Buffer.from(filename, 'latin1')\n .toString('utf-8')\n .normalize('NFC') /* Because busboy uses latin1 encoding */\n\n const stream = createReadStream()\n id = id || crypto.randomUUID()\n const ext = filename.split('.').pop()\n const key = ext ? `${id}.${ext}` : id\n\n const upload = new Upload({\n client,\n params: {\n Bucket: STORAGE.bucketName,\n Key: key,\n Body: stream\n }\n })\n\n await upload.done()\n\n const headObjectCommand = new HeadObjectCommand({\n Bucket: STORAGE.bucketName,\n Key: key\n })\n\n const { ContentLength } = await client.send(headObjectCommand)\n\n return {\n id,\n path: key,\n filename,\n size: ContentLength,\n mimetype,\n encoding\n }\n }\n\n STORAGE.deleteFile = async (path: string) => {\n const command = new DeleteObjectCommand({\n Bucket: STORAGE.bucketName,\n Key: path\n })\n\n return await client.send(command)\n }\n\n /* TODO Streaming to Streaming 으로 구현하라. */\n STORAGE.sendFile = async (context, attachment, next) => {\n const result = await client.send(\n new GetObjectCommand({\n Bucket: STORAGE.bucketName,\n Key: attachment\n } as GetObjectCommandInput)\n )\n\n context.set({\n 'Content-Length': result.ContentLength,\n 'Content-Type': mime.getType(attachment),\n 'Last-Modified': result.LastModified.toUTCString(),\n ETag: result.ETag,\n 'Cache-Control': 'public, max-age=31556926'\n })\n\n context.body = result.Body\n }\n\n STORAGE.readFile = async (attachment: string, encoding: string) => {\n /*\n * refered to\n * https://transang.me/modern-fetch-and-how-to-get-buffer-output-from-aws-sdk-v3-getobjectcommand/#the-body-type\n */\n const result = await client.send(\n new GetObjectCommand({\n Bucket: STORAGE.bucketName,\n Key: attachment\n } as GetObjectCommandInput)\n )\n\n var body = result.Body as Readable\n var buffer = await streamToBuffer(body)\n\n switch (encoding) {\n case 'base64':\n return buffer.toString('base64')\n default:\n return await buffer\n }\n }\n\n STORAGE.generateUploadURL = async (type: string): Promise<{ url: string; fields: { [key: string]: string } }> => {\n const expiresInMinutes = 1\n const id = crypto.randomUUID()\n\n return await createPresignedPost(client, {\n Bucket: STORAGE.bucketName,\n Key: id,\n Expires: expiresInMinutes * 60,\n Conditions: [['eq', '$Content-Type', type]]\n })\n }\n\n logger.info('S3 Bucket Storage is Ready.')\n}\n"]}
|