diff --git a/config/config.js b/config/config.js index 07c2deec..f92b0ee7 100644 --- a/config/config.js +++ b/config/config.js @@ -20,6 +20,14 @@ config.development = { bucketName: "", downloadUrl: "" // Binary files download host address. }, + // Config for upyun (https://www.upyun.com/) storage when storageType value is "upyun" + upyun: { + storageDir: process.evv.UPYUN_STORAGE_DIR, + serviceName: process.env.UPYUN_SERVICE_NAME, + operatorName: process.env.UPYUN_OPERATOR_NAME, + operatorPass: process.env.UPYUN_OPERATOR_PASS, + downloadUrl: process.env.DOWNLOAD_URL, + }, // Config for Amazon s3 (https://aws.amazon.com/cn/s3/) storage when storageType value is "s3". s3: { accessKeyId: process.env.AWS_ACCESS_KEY_ID, diff --git a/core/utils/common.js b/core/utils/common.js index e7f7db08..6d221535 100644 --- a/core/utils/common.js +++ b/core/utils/common.js @@ -7,6 +7,7 @@ var config = require('../config'); var _ = require('lodash'); var validator = require('validator'); var qiniu = require("qiniu"); +var upyun = require('upyun'); var common = {}; var AppError = require('../app-error'); var jschardet = require("jschardet"); @@ -225,6 +226,8 @@ common.uploadFileToStorage = function (key, filePath) { return common.uploadFileToOSS(key, filePath); } else if (storageType === 'qiniu') { return common.uploadFileToQiniu(key, filePath); + } else if (storageType === 'upyun') { + return common.uploadFileToUpyun(key, filePath); } else if (storageType === 'tencentcloud') { return common.uploadFileToTencentCloud(key, filePath); } @@ -350,6 +353,43 @@ common.uploadFileToQiniu = function (key, filePath) { }); }; +common.uploadFileToUpyun = function (key, filePath) { + var serviceName = _.get(config, "upyun.serviceName"); + var operatorName = _.get(config, "upyun.operatorName"); + var operatorPass = _.get(config, "upyun.operatorPass", ""); + var storageDir = _.get(config, "upyun.storageDir", ""); + var service = new upyun.Service(serviceName, operatorName, operatorPass); + var client = new upyun.Client(service); + return ( + new Promise((resolve, reject) => { + client.makeDir(storageDir).then(result => { + if(!storageDir) { + reject(new AppError.AppError('Please config the upyun remoteDir!')); + return; + } + let remotePath = storageDir + '/' + key; + log.debug('uploadFileToUpyun remotePath:', remotePath); + log.debug('uploadFileToUpyun mkDir result:', result); + client.putFile(remotePath, fs.createReadStream(filePath)).then(data => { + log.debug('uploadFileToUpyun putFile response:', data); + if(data) { + resolve(key) + } else { + log.debug('uploadFileToUpyun putFile failed!', data); + reject(new AppError.AppError('Upload file to upyun failed!')); + } + }).catch(e1 => { + log.debug('uploadFileToUpyun putFile exception e1:', e1); + reject(new AppError.AppError(JSON.stringify(e1))); + }) + }).catch(e => { + log.debug('uploadFileToUpyun putFile exception e:', e); + reject(new AppError.AppError(JSON.stringify(e))); + }); + }) + ); +}; + common.uploadFileToS3 = function (key, filePath) { var AWS = require('aws-sdk'); return ( diff --git a/docs/process.json b/docs/process.json index de88022b..8ef0e3e1 100644 --- a/docs/process.json +++ b/docs/process.json @@ -10,6 +10,14 @@ "NODE_ENV" : "production", "PORT" : 3000, "CONFIG_FILE" : "/path/to/production/config.js" + + // Must set add config when STORAGE_TYPE is upyun + // "STORAGE_TYPE" : "upyun", + // "DOWNLOAD_URL" : "", + // "UPYUN_STORAGE_DIR" : "", + // "UPYUN_SERVICE_NAME" : "", + // "UPYUN_OPERATOR_NAME" : "", + // "UPYUN_OPERATOR_PASS" : "" } } ] diff --git a/package-lock.json b/package-lock.json index ef06fecf..79668d14 100644 --- a/package-lock.json +++ b/package-lock.json @@ -255,6 +255,22 @@ "resolved": "http://registry.npm.taobao.org/aws4/download/aws4-1.6.0.tgz", "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=" }, + "axios": { + "version": "0.18.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.18.1.tgz", + "integrity": "sha512-0BfJq4NSfQXd+SkFdrvFbG7addhYSBA2mQwISr46pD6E5iqkWg02RAs8vyTT/j0RTnoYmeXauBuSv1qKwR179g==", + "requires": { + "follow-redirects": "1.5.10", + "is-buffer": "^2.0.2" + }, + "dependencies": { + "is-buffer": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.3.tgz", + "integrity": "sha512-U15Q7MXTuZlrbymiz95PJpZxu8IlipAp4dtS3wOdgPXx3mqBnslrWU14kxfHB+Py/+2PVKSr37dMAgM2A4uArw==" + } + } + }, "babel-runtime": { "version": "6.26.0", "resolved": "http://registry.npm.taobao.org/babel-runtime/download/babel-runtime-6.26.0.tgz", @@ -285,6 +301,11 @@ "resolved": "http://registry.npm.taobao.org/balanced-match/download/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, + "base-64": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/base-64/-/base-64-0.1.0.tgz", + "integrity": "sha1-eAqZyE59YAJgNhURxId2E78k9rs=" + }, "base64-js": { "version": "1.2.3", "resolved": "http://registry.npm.taobao.org/base64-js/download/base64-js-1.2.3.tgz", @@ -452,6 +473,11 @@ "is-regex": "^1.0.3" } }, + "charenc": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", + "integrity": "sha1-wKHS86cJLgN3S/qD8UwPxXkKhmc=" + }, "circular-json": { "version": "0.5.5", "resolved": "http://registry.npm.taobao.org/circular-json/download/circular-json-0.5.5.tgz", @@ -668,6 +694,11 @@ "which": "^1.2.9" } }, + "crypt": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", + "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=" + }, "cryptiles": { "version": "3.1.2", "resolved": "http://registry.npm.taobao.org/cryptiles/download/cryptiles-3.1.2.tgz", @@ -1081,6 +1112,14 @@ "locate-path": "^3.0.0" } }, + "follow-redirects": { + "version": "1.5.10", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.5.10.tgz", + "integrity": "sha512-0V5l4Cizzvqt5D44aTXbFZz+FtyXV1vrDN6qrelxtfYQKW0KO0W2T/hkE8xvGa/540LkZlkaUjO4ailYTFtHVQ==", + "requires": { + "debug": "=3.1.0" + } + }, "forever-agent": { "version": "0.6.1", "resolved": "http://registry.npm.taobao.org/forever-agent/download/forever-agent-0.6.1.tgz", @@ -1314,6 +1353,11 @@ "resolved": "http://registry.npm.taobao.org/hide-powered-by/download/hide-powered-by-1.0.0.tgz", "integrity": "sha1-SoWtZYgfYoV/xwr3F0oRhNzM4ys=" }, + "hmacsha1": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/hmacsha1/-/hmacsha1-1.0.0.tgz", + "integrity": "sha1-wbeuA6TqEWNICQrxT4FIwSk4qRc=" + }, "hoek": { "version": "4.2.1", "resolved": "http://registry.npm.taobao.org/hoek/download/hoek-4.2.1.tgz", @@ -1962,6 +2006,16 @@ "xregexp": "^2.0.0" } }, + "md5": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/md5/-/md5-2.2.1.tgz", + "integrity": "sha1-U6s41f48iJG6RlMp6iP6wFQBJvk=", + "requires": { + "charenc": "~0.0.1", + "crypt": "~0.0.1", + "is-buffer": "~1.1.1" + } + }, "mdurl": { "version": "1.0.1", "resolved": "http://registry.npm.taobao.org/mdurl/download/mdurl-1.0.1.tgz", @@ -3450,6 +3504,20 @@ "resolved": "http://registry.npm.taobao.org/unpipe/download/unpipe-1.0.0.tgz", "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" }, + "upyun": { + "version": "3.3.9", + "resolved": "https://registry.npmjs.org/upyun/-/upyun-3.3.9.tgz", + "integrity": "sha512-UqvSKvvFgbQwLI+yjTO0WUnmS2i2KIvX4N2Je6ZTRN4cja17DHX7ARd13DO6h65/JOQJPs/Nua2zlnixNFIdWA==", + "requires": { + "axios": "^0.18.0", + "base-64": "^0.1.0", + "form-data": "^2.1.4", + "hmacsha1": "^1.0.0", + "is-promise": "^2.1.0", + "md5": "^2.2.1", + "mime-types": "^2.1.15" + } + }, "url": { "version": "0.10.3", "resolved": "http://registry.npm.taobao.org/url/download/url-0.10.3.tgz", diff --git a/package.json b/package.json index 6e60a383..1e3fc19a 100644 --- a/package.json +++ b/package.json @@ -65,6 +65,7 @@ "nodemailer": "^4.0.1", "pug": "^2.0.1", "qiniu": "^7.1.3", + "upyun": "^3.3.9", "rand-token": "^0.4.0", "recursive-readdir": "^2.1.1", "redis": "^2.6.2",