Commit 0a8ef507 authored by nanahira's avatar nanahira

add lock to image resize

parent ce97de60
Pipeline #14449 passed with stages
in 5 minutes and 7 seconds
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
"version": "0.0.1", "version": "0.0.1",
"license": "UNLICENSED", "license": "UNLICENSED",
"dependencies": { "dependencies": {
"@nestjs-modules/ioredis": "^1.0.1",
"@nestjs/axios": "^0.0.4", "@nestjs/axios": "^0.0.4",
"@nestjs/common": "^8.0.0", "@nestjs/common": "^8.0.0",
"@nestjs/config": "^1.1.6", "@nestjs/config": "^1.1.6",
...@@ -19,9 +20,11 @@ ...@@ -19,9 +20,11 @@
"@xzeldon/imagemagick-native": "^1.9.5", "@xzeldon/imagemagick-native": "^1.9.5",
"class-transformer": "^0.4.0", "class-transformer": "^0.4.0",
"class-validator": "^0.13.2", "class-validator": "^0.13.2",
"ioredis": "^4.28.5",
"lodash": "^4.17.21", "lodash": "^4.17.21",
"pg": "^8.7.1", "pg": "^8.7.1",
"pg-native": "^3.0.0", "pg-native": "^3.0.0",
"redlock": "^5.0.0-beta.2",
"reflect-metadata": "^0.1.13", "reflect-metadata": "^0.1.13",
"rimraf": "^3.0.2", "rimraf": "^3.0.2",
"rxjs": "^7.2.0", "rxjs": "^7.2.0",
...@@ -1290,6 +1293,16 @@ ...@@ -1290,6 +1293,16 @@
"url": "https://github.com/chalk/chalk?sponsor=1" "url": "https://github.com/chalk/chalk?sponsor=1"
} }
}, },
"node_modules/@nestjs-modules/ioredis": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/@nestjs-modules/ioredis/-/ioredis-1.0.1.tgz",
"integrity": "sha512-UhIOqL5pXeJlCucHMkJONwqecvLFySW/95uw34Umh0ld7v+6tvYRK3JHQYcJqzlmNiq52bfNxf7CUpuHCSdA3A==",
"peerDependencies": {
"@nestjs/common": "^6.7.0 || ^7.0.0 || ^8.0.0",
"@nestjs/core": "^6.7.0 || ^7.0.0 || ^8.0.0",
"ioredis": "^4.0.0"
}
},
"node_modules/@nestjs/axios": { "node_modules/@nestjs/axios": {
"version": "0.0.4", "version": "0.0.4",
"resolved": "https://registry.npmjs.org/@nestjs/axios/-/axios-0.0.4.tgz", "resolved": "https://registry.npmjs.org/@nestjs/axios/-/axios-0.0.4.tgz",
...@@ -3217,6 +3230,14 @@ ...@@ -3217,6 +3230,14 @@
"node": ">=0.8" "node": ">=0.8"
} }
}, },
"node_modules/cluster-key-slot": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.0.tgz",
"integrity": "sha512-2Nii8p3RwAPiFwsnZvukotvow2rIHM+yQ6ZcBXGHdniadkYGZYiGmkHJIbZPIV9nfv7m/U1IPMVVcAhoWFeklw==",
"engines": {
"node": ">=0.10.0"
}
},
"node_modules/co": { "node_modules/co": {
"version": "4.6.0", "version": "4.6.0",
"resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz",
...@@ -3536,6 +3557,14 @@ ...@@ -3536,6 +3557,14 @@
"node": ">=0.4.0" "node": ">=0.4.0"
} }
}, },
"node_modules/denque": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/denque/-/denque-1.5.1.tgz",
"integrity": "sha512-XwE+iZ4D6ZUB7mfYRMb5wByE8L74HCn30FBN7sWnXksWc1LO1bPDl67pBR9o/kC4z/xSNAwkMYcGgqDV3BE3Hw==",
"engines": {
"node": ">=0.10"
}
},
"node_modules/depd": { "node_modules/depd": {
"version": "1.1.2", "version": "1.1.2",
"resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz",
...@@ -5056,6 +5085,31 @@ ...@@ -5056,6 +5085,31 @@
"node": ">= 0.10" "node": ">= 0.10"
} }
}, },
"node_modules/ioredis": {
"version": "4.28.5",
"resolved": "https://registry.npmjs.org/ioredis/-/ioredis-4.28.5.tgz",
"integrity": "sha512-3GYo0GJtLqgNXj4YhrisLaNNvWSNwSS2wS4OELGfGxH8I69+XfNdnmV1AyN+ZqMh0i7eX+SWjrwFKDBDgfBC1A==",
"dependencies": {
"cluster-key-slot": "^1.1.0",
"debug": "^4.3.1",
"denque": "^1.1.0",
"lodash.defaults": "^4.2.0",
"lodash.flatten": "^4.4.0",
"lodash.isarguments": "^3.1.0",
"p-map": "^2.1.0",
"redis-commands": "1.7.0",
"redis-errors": "^1.2.0",
"redis-parser": "^3.0.0",
"standard-as-callback": "^2.1.0"
},
"engines": {
"node": ">=6"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/ioredis"
}
},
"node_modules/ipaddr.js": { "node_modules/ipaddr.js": {
"version": "1.9.1", "version": "1.9.1",
"resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz",
...@@ -6377,6 +6431,21 @@ ...@@ -6377,6 +6431,21 @@
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz",
"integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="
}, },
"node_modules/lodash.defaults": {
"version": "4.2.0",
"resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-4.2.0.tgz",
"integrity": "sha512-qjxPLHd3r5DnsdGacqOMU6pb/avJzdh9tFX2ymgoZE27BmjXrNy/y4LoaiTeAb+O3gL8AfpJGtqfX/ae2leYYQ=="
},
"node_modules/lodash.flatten": {
"version": "4.4.0",
"resolved": "https://registry.npmjs.org/lodash.flatten/-/lodash.flatten-4.4.0.tgz",
"integrity": "sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g=="
},
"node_modules/lodash.isarguments": {
"version": "3.1.0",
"resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz",
"integrity": "sha512-chi4NHZlZqZD18a0imDHnZPrDeBbTtVN7GXMwuGdRH9qotxAjYs3aVLKc7zNOG9eddR5Ksd8rvFEBc9SsggPpg=="
},
"node_modules/lodash.memoize": { "node_modules/lodash.memoize": {
"version": "4.1.2", "version": "4.1.2",
"resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz",
...@@ -6690,6 +6759,11 @@ ...@@ -6690,6 +6759,11 @@
"integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==",
"dev": true "dev": true
}, },
"node_modules/node-abort-controller": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/node-abort-controller/-/node-abort-controller-3.0.1.tgz",
"integrity": "sha512-/ujIVxthRs+7q6hsdjHMaj8hRG9NuWmwrz+JdRwZ14jdFoKSkm+vDsCbF9PLpnSqjaWQJuTmVtcWHNLr+vrOFw=="
},
"node_modules/node-emoji": { "node_modules/node-emoji": {
"version": "1.11.0", "version": "1.11.0",
"resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz", "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz",
...@@ -6941,6 +7015,14 @@ ...@@ -6941,6 +7015,14 @@
"node": ">=8" "node": ">=8"
} }
}, },
"node_modules/p-map": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/p-map/-/p-map-2.1.0.tgz",
"integrity": "sha512-y3b8Kpd8OAN444hxfBbFfj1FY/RjtTd8tzYwhUqNYXx0fXx2iX4maP4Qr6qhIKbQXI02wTLAda4fYUbDagTUFw==",
"engines": {
"node": ">=6"
}
},
"node_modules/p-try": { "node_modules/p-try": {
"version": "2.2.0", "version": "2.2.0",
"resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz",
...@@ -7473,6 +7555,41 @@ ...@@ -7473,6 +7555,41 @@
"node": ">= 0.10" "node": ">= 0.10"
} }
}, },
"node_modules/redis-commands": {
"version": "1.7.0",
"resolved": "https://registry.npmjs.org/redis-commands/-/redis-commands-1.7.0.tgz",
"integrity": "sha512-nJWqw3bTFy21hX/CPKHth6sfhZbdiHP6bTawSgQBlKOVRG7EZkfHbbHwQJnrE4vsQf0CMNE+3gJ4Fmm16vdVlQ=="
},
"node_modules/redis-errors": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/redis-errors/-/redis-errors-1.2.0.tgz",
"integrity": "sha512-1qny3OExCf0UvUV/5wpYKf2YwPcOqXzkwKKSmKHiE6ZMQs5heeE/c8eXK+PNllPvmjgAbfnsbpkGZWy8cBpn9w==",
"engines": {
"node": ">=4"
}
},
"node_modules/redis-parser": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/redis-parser/-/redis-parser-3.0.0.tgz",
"integrity": "sha512-DJnGAeenTdpMEH6uAJRK/uiyEIH9WVsUmoLwzudwGJUwZPp80PDBWPHXSAGNPwNvIXAbe7MSUB1zQFugFml66A==",
"dependencies": {
"redis-errors": "^1.0.0"
},
"engines": {
"node": ">=4"
}
},
"node_modules/redlock": {
"version": "5.0.0-beta.2",
"resolved": "https://registry.npmjs.org/redlock/-/redlock-5.0.0-beta.2.tgz",
"integrity": "sha512-2RDWXg5jgRptDrB1w9O/JgSZC0j7y4SlaXnor93H/UJm/QyDiFgBKNtrh0TI6oCXqYSaSoXxFh6Sd3VtYfhRXw==",
"dependencies": {
"node-abort-controller": "^3.0.1"
},
"engines": {
"node": ">=12"
}
},
"node_modules/reflect-metadata": { "node_modules/reflect-metadata": {
"version": "0.1.13", "version": "0.1.13",
"resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz", "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz",
...@@ -7971,6 +8088,11 @@ ...@@ -7971,6 +8088,11 @@
"node": ">=8" "node": ">=8"
} }
}, },
"node_modules/standard-as-callback": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/standard-as-callback/-/standard-as-callback-2.1.0.tgz",
"integrity": "sha512-qoRRSyROncaz1z0mvYqIE4lCd9p2R90i6GxW3uZv5ucSu8tU7B5HXUP1gG8pVZsYNVaXjk8ClXHPttLyxAL48A=="
},
"node_modules/statuses": { "node_modules/statuses": {
"version": "1.5.0", "version": "1.5.0",
"resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz",
...@@ -10580,6 +10702,12 @@ ...@@ -10580,6 +10702,12 @@
} }
} }
}, },
"@nestjs-modules/ioredis": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/@nestjs-modules/ioredis/-/ioredis-1.0.1.tgz",
"integrity": "sha512-UhIOqL5pXeJlCucHMkJONwqecvLFySW/95uw34Umh0ld7v+6tvYRK3JHQYcJqzlmNiq52bfNxf7CUpuHCSdA3A==",
"requires": {}
},
"@nestjs/axios": { "@nestjs/axios": {
"version": "0.0.4", "version": "0.0.4",
"resolved": "https://registry.npmjs.org/@nestjs/axios/-/axios-0.0.4.tgz", "resolved": "https://registry.npmjs.org/@nestjs/axios/-/axios-0.0.4.tgz",
...@@ -12031,6 +12159,11 @@ ...@@ -12031,6 +12159,11 @@
"integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=", "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=",
"dev": true "dev": true
}, },
"cluster-key-slot": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.0.tgz",
"integrity": "sha512-2Nii8p3RwAPiFwsnZvukotvow2rIHM+yQ6ZcBXGHdniadkYGZYiGmkHJIbZPIV9nfv7m/U1IPMVVcAhoWFeklw=="
},
"co": { "co": {
"version": "4.6.0", "version": "4.6.0",
"resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz",
...@@ -12297,6 +12430,11 @@ ...@@ -12297,6 +12430,11 @@
"integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=",
"dev": true "dev": true
}, },
"denque": {
"version": "1.5.1",
"resolved": "https://registry.npmjs.org/denque/-/denque-1.5.1.tgz",
"integrity": "sha512-XwE+iZ4D6ZUB7mfYRMb5wByE8L74HCn30FBN7sWnXksWc1LO1bPDl67pBR9o/kC4z/xSNAwkMYcGgqDV3BE3Hw=="
},
"depd": { "depd": {
"version": "1.1.2", "version": "1.1.2",
"resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz",
...@@ -13430,6 +13568,24 @@ ...@@ -13430,6 +13568,24 @@
"integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==",
"dev": true "dev": true
}, },
"ioredis": {
"version": "4.28.5",
"resolved": "https://registry.npmjs.org/ioredis/-/ioredis-4.28.5.tgz",
"integrity": "sha512-3GYo0GJtLqgNXj4YhrisLaNNvWSNwSS2wS4OELGfGxH8I69+XfNdnmV1AyN+ZqMh0i7eX+SWjrwFKDBDgfBC1A==",
"requires": {
"cluster-key-slot": "^1.1.0",
"debug": "^4.3.1",
"denque": "^1.1.0",
"lodash.defaults": "^4.2.0",
"lodash.flatten": "^4.4.0",
"lodash.isarguments": "^3.1.0",
"p-map": "^2.1.0",
"redis-commands": "1.7.0",
"redis-errors": "^1.2.0",
"redis-parser": "^3.0.0",
"standard-as-callback": "^2.1.0"
}
},
"ipaddr.js": { "ipaddr.js": {
"version": "1.9.1", "version": "1.9.1",
"resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz",
...@@ -14445,6 +14601,21 @@ ...@@ -14445,6 +14601,21 @@
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz",
"integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="
}, },
"lodash.defaults": {
"version": "4.2.0",
"resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-4.2.0.tgz",
"integrity": "sha512-qjxPLHd3r5DnsdGacqOMU6pb/avJzdh9tFX2ymgoZE27BmjXrNy/y4LoaiTeAb+O3gL8AfpJGtqfX/ae2leYYQ=="
},
"lodash.flatten": {
"version": "4.4.0",
"resolved": "https://registry.npmjs.org/lodash.flatten/-/lodash.flatten-4.4.0.tgz",
"integrity": "sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g=="
},
"lodash.isarguments": {
"version": "3.1.0",
"resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz",
"integrity": "sha512-chi4NHZlZqZD18a0imDHnZPrDeBbTtVN7GXMwuGdRH9qotxAjYs3aVLKc7zNOG9eddR5Ksd8rvFEBc9SsggPpg=="
},
"lodash.memoize": { "lodash.memoize": {
"version": "4.1.2", "version": "4.1.2",
"resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz",
...@@ -14690,6 +14861,11 @@ ...@@ -14690,6 +14861,11 @@
"integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==",
"dev": true "dev": true
}, },
"node-abort-controller": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/node-abort-controller/-/node-abort-controller-3.0.1.tgz",
"integrity": "sha512-/ujIVxthRs+7q6hsdjHMaj8hRG9NuWmwrz+JdRwZ14jdFoKSkm+vDsCbF9PLpnSqjaWQJuTmVtcWHNLr+vrOFw=="
},
"node-emoji": { "node-emoji": {
"version": "1.11.0", "version": "1.11.0",
"resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz", "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz",
...@@ -14885,6 +15061,11 @@ ...@@ -14885,6 +15061,11 @@
"p-limit": "^2.2.0" "p-limit": "^2.2.0"
} }
}, },
"p-map": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/p-map/-/p-map-2.1.0.tgz",
"integrity": "sha512-y3b8Kpd8OAN444hxfBbFfj1FY/RjtTd8tzYwhUqNYXx0fXx2iX4maP4Qr6qhIKbQXI02wTLAda4fYUbDagTUFw=="
},
"p-try": { "p-try": {
"version": "2.2.0", "version": "2.2.0",
"resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz",
...@@ -15283,6 +15464,32 @@ ...@@ -15283,6 +15464,32 @@
"resolve": "^1.1.6" "resolve": "^1.1.6"
} }
}, },
"redis-commands": {
"version": "1.7.0",
"resolved": "https://registry.npmjs.org/redis-commands/-/redis-commands-1.7.0.tgz",
"integrity": "sha512-nJWqw3bTFy21hX/CPKHth6sfhZbdiHP6bTawSgQBlKOVRG7EZkfHbbHwQJnrE4vsQf0CMNE+3gJ4Fmm16vdVlQ=="
},
"redis-errors": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/redis-errors/-/redis-errors-1.2.0.tgz",
"integrity": "sha512-1qny3OExCf0UvUV/5wpYKf2YwPcOqXzkwKKSmKHiE6ZMQs5heeE/c8eXK+PNllPvmjgAbfnsbpkGZWy8cBpn9w=="
},
"redis-parser": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/redis-parser/-/redis-parser-3.0.0.tgz",
"integrity": "sha512-DJnGAeenTdpMEH6uAJRK/uiyEIH9WVsUmoLwzudwGJUwZPp80PDBWPHXSAGNPwNvIXAbe7MSUB1zQFugFml66A==",
"requires": {
"redis-errors": "^1.0.0"
}
},
"redlock": {
"version": "5.0.0-beta.2",
"resolved": "https://registry.npmjs.org/redlock/-/redlock-5.0.0-beta.2.tgz",
"integrity": "sha512-2RDWXg5jgRptDrB1w9O/JgSZC0j7y4SlaXnor93H/UJm/QyDiFgBKNtrh0TI6oCXqYSaSoXxFh6Sd3VtYfhRXw==",
"requires": {
"node-abort-controller": "^3.0.1"
}
},
"reflect-metadata": { "reflect-metadata": {
"version": "0.1.13", "version": "0.1.13",
"resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz", "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz",
...@@ -15663,6 +15870,11 @@ ...@@ -15663,6 +15870,11 @@
} }
} }
}, },
"standard-as-callback": {
"version": "2.1.0",
"resolved": "https://registry.npmjs.org/standard-as-callback/-/standard-as-callback-2.1.0.tgz",
"integrity": "sha512-qoRRSyROncaz1z0mvYqIE4lCd9p2R90i6GxW3uZv5ucSu8tU7B5HXUP1gG8pVZsYNVaXjk8ClXHPttLyxAL48A=="
},
"statuses": { "statuses": {
"version": "1.5.0", "version": "1.5.0",
"resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz",
......
...@@ -21,6 +21,7 @@ ...@@ -21,6 +21,7 @@
"test:e2e": "jest --config ./test/jest-e2e.json" "test:e2e": "jest --config ./test/jest-e2e.json"
}, },
"dependencies": { "dependencies": {
"@nestjs-modules/ioredis": "^1.0.1",
"@nestjs/axios": "^0.0.4", "@nestjs/axios": "^0.0.4",
"@nestjs/common": "^8.0.0", "@nestjs/common": "^8.0.0",
"@nestjs/config": "^1.1.6", "@nestjs/config": "^1.1.6",
...@@ -31,9 +32,11 @@ ...@@ -31,9 +32,11 @@
"@xzeldon/imagemagick-native": "^1.9.5", "@xzeldon/imagemagick-native": "^1.9.5",
"class-transformer": "^0.4.0", "class-transformer": "^0.4.0",
"class-validator": "^0.13.2", "class-validator": "^0.13.2",
"ioredis": "^4.28.5",
"lodash": "^4.17.21", "lodash": "^4.17.21",
"pg": "^8.7.1", "pg": "^8.7.1",
"pg-native": "^3.0.0", "pg-native": "^3.0.0",
"redlock": "^5.0.0-beta.2",
"reflect-metadata": "^0.1.13", "reflect-metadata": "^0.1.13",
"rimraf": "^3.0.2", "rimraf": "^3.0.2",
"rxjs": "^7.2.0", "rxjs": "^7.2.0",
......
...@@ -7,6 +7,8 @@ import { HttpModule } from '@nestjs/axios'; ...@@ -7,6 +7,8 @@ import { HttpModule } from '@nestjs/axios';
import { AvatarApiService } from './avatar-api/avatar-api.service'; import { AvatarApiService } from './avatar-api/avatar-api.service';
import { ImageService } from './image/image.service'; import { ImageService } from './image/image.service';
import { Avatar } from './entities/Avatar.entity'; import { Avatar } from './entities/Avatar.entity';
import { LockService } from './lock/lock.service';
import { RedisModule } from '@nestjs-modules/ioredis';
@Module({ @Module({
imports: [ imports: [
...@@ -31,8 +33,16 @@ import { Avatar } from './entities/Avatar.entity'; ...@@ -31,8 +33,16 @@ import { Avatar } from './entities/Avatar.entity';
}; };
}, },
}), }),
RedisModule.forRootAsync({
inject: [ConfigService],
useFactory: async (config: ConfigService) => ({
config: {
url: config.get('REDIS_URL'),
},
}),
}),
], ],
controllers: [AppController], controllers: [AppController],
providers: [AppService, AvatarApiService, ImageService], providers: [AppService, AvatarApiService, ImageService, LockService],
}) })
export class AppModule {} export class AppModule {}
...@@ -4,6 +4,7 @@ import { Injectable, ConsoleLogger } from '@nestjs/common'; ...@@ -4,6 +4,7 @@ import { Injectable, ConsoleLogger } from '@nestjs/common';
import { ImageService } from './image/image.service'; import { ImageService } from './image/image.service';
import { AvatarApiService } from './avatar-api/avatar-api.service'; import { AvatarApiService } from './avatar-api/avatar-api.service';
import { Avatar } from './entities/Avatar.entity'; import { Avatar } from './entities/Avatar.entity';
import { LockService } from './lock/lock.service';
@Injectable() @Injectable()
export class AppService extends ConsoleLogger { export class AppService extends ConsoleLogger {
...@@ -12,6 +13,7 @@ export class AppService extends ConsoleLogger { ...@@ -12,6 +13,7 @@ export class AppService extends ConsoleLogger {
private db: Connection, private db: Connection,
private image: ImageService, private image: ImageService,
private avatarApi: AvatarApiService, private avatarApi: AvatarApiService,
private lockService: LockService,
) { ) {
super('app'); super('app');
} }
...@@ -37,30 +39,39 @@ export class AppService extends ConsoleLogger { ...@@ -37,30 +39,39 @@ export class AppService extends ConsoleLogger {
return existingAvatar.toBuffer(); return existingAvatar.toBuffer();
} }
this.log(`Resizing ${url} to ${size}`); this.log(`Resizing ${url} to ${size}`);
let originalAvatarBuffer: Buffer; return this.lockService.using(
const originalAvatar = await this.db.getRepository(Avatar).findOne({ [`avatar_${url}_${size}`],
where: { 10000,
url, async () => {
size: 0, let originalAvatarBuffer: Buffer;
const originalAvatar = await this.db.getRepository(Avatar).findOne({
where: {
url,
size: 0,
},
select: ['content'],
});
if (originalAvatar) {
originalAvatarBuffer = originalAvatar.toBuffer();
} else {
originalAvatarBuffer = await this.avatarApi.downloadAvatar(url);
try {
await this.saveAvatar(url, 0, originalAvatarBuffer);
} catch (e) {
this.error(`Fail to save original avatar: ${e.message}`);
}
}
const avatarBuffer = await this.image.resize(
originalAvatarBuffer,
size,
);
try {
await this.saveAvatar(url, size, avatarBuffer);
} catch (e) {
this.error(`Fail to save avatar: ${e.message}`);
}
return avatarBuffer;
}, },
select: ['content'], );
});
if (originalAvatar) {
originalAvatarBuffer = originalAvatar.toBuffer();
} else {
originalAvatarBuffer = await this.avatarApi.downloadAvatar(url);
try {
await this.saveAvatar(url, 0, originalAvatarBuffer);
} catch (e) {
this.error(`Fail to save original avatar: ${e.message}`);
}
}
const avatarBuffer = await this.image.resize(originalAvatarBuffer, size);
try {
await this.saveAvatar(url, size, avatarBuffer);
} catch (e) {
this.error(`Fail to save avatar: ${e.message}`);
}
return avatarBuffer;
} }
} }
import { Test, TestingModule } from '@nestjs/testing';
import { LockService } from './lock.service';
describe('LockService', () => {
let service: LockService;
beforeEach(async () => {
const module: TestingModule = await Test.createTestingModule({
providers: [LockService],
}).compile();
service = module.get<LockService>(LockService);
});
it('should be defined', () => {
expect(service).toBeDefined();
});
});
import { InjectRedis, Redis } from '@nestjs-modules/ioredis';
import { Injectable } from '@nestjs/common';
import Redlock from 'redlock';
@Injectable()
export class LockService extends Redlock {
constructor(@InjectRedis() private readonly redis: Redis) {
super([redis]);
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment