From a1c54ad26fdea070fb784603a0946920a7b04dd2 Mon Sep 17 00:00:00 2001 From: zkldi Date: Mon, 31 May 2021 12:10:53 +0100 Subject: [PATCH] Fixes #147 --- server/.github/workflows/tests.yml | 4 +- server/.taprc | 2 +- server/.vscode/tasks.json | 4 +- server/package.json | 4 +- server/pnpm-lock.yaml | 205 ++++++++++++++++-- server/scripts/set-indexes.ts | 16 +- server/src/external/mongo/db.ts | 16 +- server/src/external/redis/redis-IPC.test.ts | 4 +- .../redis/{redis-store.ts => redis.ts} | 3 - .../eamusement-iidx-csv/converter.test.ts | 29 ++- .../router/api/v1/import/router.test.ts | 9 + server/src/server/server.ts | 20 +- server/src/test-utils/close-connections.ts | 2 +- server/src/test-utils/mock-api.ts | 2 +- server/src/utils/session.test.ts | 2 + server/src/utils/user.test.ts | 5 + 16 files changed, 280 insertions(+), 47 deletions(-) rename server/src/external/redis/{redis-store.ts => redis.ts} (82%) diff --git a/server/.github/workflows/tests.yml b/server/.github/workflows/tests.yml index 2affe4b14..9a5baa635 100644 --- a/server/.github/workflows/tests.yml +++ b/server/.github/workflows/tests.yml @@ -50,8 +50,8 @@ jobs: - name: Set Mongo Indexes run: pnpx ts-node scripts/set-indexes.ts - - name: Run Tests - run: pnpm test + - name: Run Tests In Parallel + run: pnpm paralleltest - name: Upload Coverage if: always() diff --git a/server/.taprc b/server/.taprc index e366b0744..25e67ebdb 100644 --- a/server/.taprc +++ b/server/.taprc @@ -1,7 +1,7 @@ files: "src/**/*.test.ts" test-env: NODE_ENV=test jobs: 1 # disable parallel to avoid db clashes -timeout: 60 # might need to be increased +timeout: 120 # might need to be increased ts: true before: "./src/test-utils/setup.ts" check-coverage: true diff --git a/server/.vscode/tasks.json b/server/.vscode/tasks.json index 025136223..6776c6d07 100644 --- a/server/.vscode/tasks.json +++ b/server/.vscode/tasks.json @@ -3,9 +3,9 @@ "tasks": [ { "type": "npm", - "script": "devrun", + "script": "buildrun", "problemMatcher": [], - "label": "npm: devrun", + "label": "npm: buildrun", "detail": "tsc && export NODE_ENV=\"dev\" && node js/main.js", "group": { "kind": "build", diff --git a/server/package.json b/server/package.json index e24fc4ccb..5faaa147d 100644 --- a/server/package.json +++ b/server/package.json @@ -5,11 +5,11 @@ "main": "js/index.js", "scripts": { "fulltest": "tap", - "test": "tap", + "paralleltest": "export KTBSV_PARALLEL_TESTS=true && tap -J", "watchtest": "tap --watch", "build": "tsc --project tsconfig.build.json", "lint": "eslint ./src --ext .ts --fix", - "devrun": "tsc --project tsconfig.build.json && node -r dotenv/config js/main.js" + "buildrun": "tsc --project tsconfig.build.json && node js/main.js" }, "author": "zkldi", "license": "ISC", diff --git a/server/pnpm-lock.yaml b/server/pnpm-lock.yaml index aa68ace92..097908860 100644 --- a/server/pnpm-lock.yaml +++ b/server/pnpm-lock.yaml @@ -33,6 +33,7 @@ specifiers: fast-xml-parser: ^3.19.0 kamaitachi-common: github:zkldi/Kamaitachi-common mongodb: ^3.6.6 + mongodb-memory-server: ^6.9.6 monk: ^7.3.4 multer: ^1.4.2 node-fetch: ^2.6.1 @@ -40,6 +41,7 @@ specifiers: prettier: ^2.2.1 prudence: ^0.9.6 redis: ^3.1.2 + redis-mock: ^0.56.3 supertest: ^6.1.3 tap: ^15.0.5 ts-node: ^9.1.1 @@ -91,8 +93,10 @@ devDependencies: eslint-plugin-import: 2.22.1_eslint@7.25.0 eslint-plugin-prettier: 3.4.0_ed07edc0d33fb90bb2bebf56b9b5e0f9 express-request-mock: 3.1.0 + mongodb-memory-server: 6.9.6 node-mocks-http: 1.10.1 prettier: 2.2.1 + redis-mock: 0.56.3 supertest: 6.1.3 tap: 15.0.5_ts-node@9.1.1+typescript@4.2.4 ts-node: 9.1.1_typescript@4.2.4 @@ -588,6 +592,10 @@ packages: '@types/node': 15.0.1 dev: true + /@types/tmp/0.2.0: + resolution: {integrity: sha512-flgpHJjntpBAdJD43ShRosQvNC0ME97DCfGvZEDlAThQmnerRXrLbX6YgzRBQCZTthET9eAWFAMaYP0m0Y4HzQ==} + dev: true + /@types/uuid/8.3.0: resolution: {integrity: sha512-eQ9qFW/fhfGJF8WKHGEHZEyVWfZxrT+6CLIJGBcZPfxUh/+BnEj+UCGYMlr9qZuX/2AltsvwrGqp0LhEW8D0zQ==} dev: true @@ -730,7 +738,6 @@ packages: debug: 4.3.1 transitivePeerDependencies: - supports-color - dev: false /aggregate-error/3.1.0: resolution: {integrity: sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==} @@ -904,6 +911,10 @@ packages: /balanced-match/1.0.2: resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} + /base64-js/1.5.1: + resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} + dev: true + /bcrypt-pbkdf/1.0.2: resolution: {integrity: sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=} dependencies: @@ -945,7 +956,14 @@ packages: dependencies: readable-stream: 2.3.7 safe-buffer: 5.2.1 - dev: false + + /bl/4.1.0: + resolution: {integrity: sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==} + dependencies: + buffer: 5.7.1 + inherits: 2.0.4 + readable-stream: 3.6.0 + dev: true /body-parser/1.19.0: resolution: {integrity: sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw==} @@ -991,11 +1009,21 @@ packages: /bson/1.1.6: resolution: {integrity: sha512-EvVNVeGo4tHxwi8L6bPj3y3itEvStdwvvlojVxxbyYfoaxJ6keLgrTuKdyfEAszFK+H3olzBuafE0yoh0D1gdg==} engines: {node: '>=0.6.19'} - dev: false + + /buffer-crc32/0.2.13: + resolution: {integrity: sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=} + dev: true /buffer-from/1.1.1: resolution: {integrity: sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==} + /buffer/5.7.1: + resolution: {integrity: sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==} + dependencies: + base64-js: 1.5.1 + ieee754: 1.2.1 + dev: true + /busboy/0.2.14: resolution: {integrity: sha1-bCpiLvz0fFe7vh4qnDetNseSVFM=} engines: {node: '>=0.8.0'} @@ -1054,6 +1082,11 @@ packages: engines: {node: '>=6'} dev: true + /camelcase/6.2.0: + resolution: {integrity: sha512-c7wVvbw3f37nuobQNtgsgG9POC9qMbNuMQmTCqZv23b6MIz0fcYpBiOlv9gEN/hdLdnZTDQhg6e9Dq5M1vKvfg==} + engines: {node: '>=10'} + dev: true + /caniuse-lite/1.0.30001218: resolution: {integrity: sha512-0ASydOWSy3bB88FbDpJSTt+PfDwnMqrym3yRZfqG8EXSQ06OZhF+q5wgYP/EN+jJMERItNcDQUqMyNjzZ+r5+Q==} dev: true @@ -1349,7 +1382,6 @@ packages: /denque/1.5.0: resolution: {integrity: sha512-CYiCSgIF1p6EUByQPlGkKnP1M9g0ZV3qMIrqMqZqdwazygIA/YP2vrbcyl1h/WppKJTdl1F85cXIle+394iDAQ==} engines: {node: '>=0.10'} - dev: false /depd/1.1.2: resolution: {integrity: sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=} @@ -1442,6 +1474,12 @@ packages: engines: {node: '>= 0.8'} dev: false + /end-of-stream/1.4.4: + resolution: {integrity: sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==} + dependencies: + once: 1.4.0 + dev: true + /enquirer/2.3.6: resolution: {integrity: sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==} engines: {node: '>=8.6'} @@ -1814,6 +1852,12 @@ packages: reusify: 1.0.4 dev: true + /fd-slicer/1.1.0: + resolution: {integrity: sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=} + dependencies: + pend: 1.2.0 + dev: true + /fecha/4.2.1: resolution: {integrity: sha512-MMMQ0ludy/nBs1/o0zVOiKTpG7qMbonKUzjJgQFEuvq6INZ1OraKPRAWkBq5vlKLOUMpmNYG1JoN3oDPUQ9m3Q==} dev: false @@ -1854,6 +1898,10 @@ packages: pkg-dir: 4.2.0 dev: true + /find-package-json/1.2.0: + resolution: {integrity: sha512-+SOGcLGYDJHtyqHd87ysBhmaeQ95oWspDKnMXBrnQ9Eq4OkLNqejgoaD8xVWu6GPa0B6roa6KinCMEMcVeqONw==} + dev: true + /find-up/2.1.0: resolution: {integrity: sha1-RdG35QbHF93UgndaK3eSCjwMV6c=} engines: {node: '>=4'} @@ -1936,6 +1984,10 @@ packages: resolution: {integrity: sha512-cHEpEQHUg0f8XdtZCc2ZAhrHzKzT0MrFUTcvx+hfxYu7rGMDc5SKoXFh+n4YigxsHXRzc6OrCshdR1bWH6HHyg==} dev: true + /fs-constants/1.0.0: + resolution: {integrity: sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==} + dev: true + /fs-exists-cached/1.0.0: resolution: {integrity: sha1-zyVVTKBQ3EmuZla0HeQiWJidy84=} dev: true @@ -2003,6 +2055,11 @@ packages: engines: {node: '>=8.0.0'} dev: true + /get-port/5.1.1: + resolution: {integrity: sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==} + engines: {node: '>=8'} + dev: true + /getpass/0.1.7: resolution: {integrity: sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=} dependencies: @@ -2157,7 +2214,6 @@ packages: debug: 4.3.1 transitivePeerDependencies: - supports-color - dev: false /iconv-lite/0.4.24: resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} @@ -2166,6 +2222,10 @@ packages: safer-buffer: 2.1.2 dev: false + /ieee754/1.2.1: + resolution: {integrity: sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==} + dev: true + /ignore/4.0.6: resolution: {integrity: sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==} engines: {node: '>= 4'} @@ -2554,6 +2614,12 @@ packages: p-locate: 4.1.0 dev: true + /lockfile/1.0.4: + resolution: {integrity: sha512-cvbTwETRfsFh4nHsL1eGWapU1XFi5Ot9E85sWAwia7Y7EgB7vfqcZhTKZ+l7hCGxSPoushMv5GKhT5PdLv03WA==} + dependencies: + signal-exit: 3.0.3 + dev: true + /lodash.clonedeep/4.5.0: resolution: {integrity: sha1-4j8/nE+Pvd6HJSnBBxhXoIblzO8=} dev: true @@ -2612,13 +2678,18 @@ packages: resolution: {integrity: sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==} dev: true + /md5-file/5.0.0: + resolution: {integrity: sha512-xbEFXCYVWrSx/gEKS1VPlg84h/4L20znVIulKw6kMfmBUAZNAnF00eczz9ICMl+/hjQGo5KSXRxbL/47X3rmMw==} + engines: {node: '>=10.13.0'} + hasBin: true + dev: true + /media-typer/0.3.0: resolution: {integrity: sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=} engines: {node: '>= 0.6'} /memory-pager/1.5.0: resolution: {integrity: sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg==} - dev: false optional: true /merge-descriptors/1.0.1: @@ -2696,6 +2767,53 @@ packages: engines: {node: '>=10'} hasBin: true + /mongodb-memory-server-core/6.9.6: + resolution: {integrity: sha512-ZcXHTI2TccH3L5N9JyAMGm8bbAsfLn8SUWOeYGHx/vDx7vu4qshyaNXTIxeHjpUQA29N+Z1LtTXA6vXjl1eg6w==} + engines: {node: '>=10.15.0'} + dependencies: + '@types/tmp': 0.2.0 + camelcase: 6.2.0 + cross-spawn: 7.0.3 + debug: 4.3.1 + find-cache-dir: 3.3.1 + find-package-json: 1.2.0 + get-port: 5.1.1 + https-proxy-agent: 5.0.0 + lockfile: 1.0.4 + md5-file: 5.0.0 + mkdirp: 1.0.4 + semver: 7.3.5 + tar-stream: 2.2.0 + tmp: 0.2.1 + uuid: 8.3.2 + yauzl: 2.10.0 + optionalDependencies: + mongodb: 3.6.9 + transitivePeerDependencies: + - aws4 + - bson-ext + - kerberos + - mongodb-client-encryption + - mongodb-extjson + - snappy + - supports-color + dev: true + + /mongodb-memory-server/6.9.6: + resolution: {integrity: sha512-BjGPPh5f61lMueG7px9DneBIrRR/GoWUHDvLWVAXhQhKVcwMMXxgeEba6zdDolZHfYAu6aYGPzhOuYKIKPgpBQ==} + requiresBuild: true + dependencies: + mongodb-memory-server-core: 6.9.6 + transitivePeerDependencies: + - aws4 + - bson-ext + - kerberos + - mongodb-client-encryption + - mongodb-extjson + - snappy + - supports-color + dev: true + /mongodb/3.6.3: resolution: {integrity: sha512-rOZuR0QkodZiM+UbQE5kDsJykBqWi0CL4Ec2i1nrGrUI3KO11r6Fbxskqmq3JK2NH7aW4dcccBuUujAP0ERl5w==} engines: {node: '>=4'} @@ -2762,6 +2880,40 @@ packages: saslprep: 1.0.3 dev: false + /mongodb/3.6.9: + resolution: {integrity: sha512-1nSCKgSunzn/CXwgOWgbPHUWOO5OfERcuOWISmqd610jn0s8BU9K4879iJVabqgpPPbA6hO7rG48eq+fGED3Mg==} + engines: {node: '>=4'} + peerDependencies: + aws4: '*' + bson-ext: '*' + kerberos: '*' + mongodb-client-encryption: '*' + mongodb-extjson: '*' + snappy: '*' + peerDependenciesMeta: + aws4: + optional: true + bson-ext: + optional: true + kerberos: + optional: true + mongodb-client-encryption: + optional: true + mongodb-extjson: + optional: true + snappy: + optional: true + dependencies: + bl: 2.2.1 + bson: 1.1.6 + denque: 1.5.0 + optional-require: 1.0.3 + safe-buffer: 5.2.1 + optionalDependencies: + saslprep: 1.0.3 + dev: true + optional: true + /monk-middleware-cast-ids/0.2.1: resolution: {integrity: sha1-QMQOWmyzPM7cKJIglDJ17ohhxSk=} dev: false @@ -3024,7 +3176,6 @@ packages: /optional-require/1.0.3: resolution: {integrity: sha512-RV2Zp2MY2aeYK5G+B/Sps8lW5NHAzE5QClbFP15j+PWmP+T9PxlJXBOOLoSAdgwFvS4t0aMR4vpedMkbHfh0nA==} engines: {node: '>=4'} - dev: false /optionator/0.9.1: resolution: {integrity: sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==} @@ -3165,6 +3316,10 @@ packages: engines: {node: '>=8'} dev: true + /pend/1.2.0: + resolution: {integrity: sha1-elfrVQpng/kRUzH89GY9XI4AelA=} + dev: true + /performance-now/2.1.0: resolution: {integrity: sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=} dev: true @@ -3213,7 +3368,6 @@ packages: /process-nextick-args/2.0.1: resolution: {integrity: sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==} - dev: false /process-on-spawn/1.0.0: resolution: {integrity: sha512-1WsPDsUSMmZH5LeMLegqkPDrsGgsWwk1Exipy2hvB0o/F0ASzbpIctSCcZIK1ykJvtTJULEH+20WOFjMvGnCTg==} @@ -3353,7 +3507,6 @@ packages: safe-buffer: 5.1.2 string_decoder: 1.1.1 util-deprecate: 1.0.2 - dev: false /readable-stream/3.6.0: resolution: {integrity: sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==} @@ -3379,6 +3532,11 @@ packages: engines: {node: '>=4'} dev: false + /redis-mock/0.56.3: + resolution: {integrity: sha512-ynaJhqk0Qf3Qajnwvy4aOjS4Mdf9IBkELWtjd+NYhpiqu4QCNq6Vf3Q7c++XRPGiKiwRj9HWr0crcwy7EiPjYQ==} + engines: {node: '>=6'} + dev: true + /redis-parser/2.6.0: resolution: {integrity: sha1-Uu0J2srBCPGmMcB+m2mUHnoZUEs=} engines: {node: '>=0.10.0'} @@ -3536,7 +3694,6 @@ packages: engines: {node: '>=6'} dependencies: sparse-bitfield: 3.0.3 - dev: false optional: true /semver/5.7.1: @@ -3658,7 +3815,6 @@ packages: resolution: {integrity: sha1-/0rm5oZWBWuks+eSqzM004JzyhE=} dependencies: memory-pager: 1.5.0 - dev: false optional: true /spawn-wrap/2.0.0: @@ -3785,7 +3941,6 @@ packages: resolution: {integrity: sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==} dependencies: safe-buffer: 5.1.2 - dev: false /string_decoder/1.3.0: resolution: {integrity: sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==} @@ -3966,6 +4121,17 @@ packages: - treport - '@types/react' + /tar-stream/2.2.0: + resolution: {integrity: sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==} + engines: {node: '>=6'} + dependencies: + bl: 4.1.0 + end-of-stream: 1.4.4 + fs-constants: 1.0.0 + inherits: 2.0.4 + readable-stream: 3.6.0 + dev: true + /tar/6.1.0: resolution: {integrity: sha512-DUCttfhsnLCjwoDoFcI+B2iJgYa93vBnDUATYEeRx6sntCTdN01VnqsIuTlALXla/LWooNg0yEGeB+Y8WdFxGA==} engines: {node: '>= 10'} @@ -4002,6 +4168,13 @@ packages: resolution: {integrity: sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=} dev: true + /tmp/0.2.1: + resolution: {integrity: sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==} + engines: {node: '>=8.17.0'} + dependencies: + rimraf: 3.0.2 + dev: true + /to-fast-properties/2.0.0: resolution: {integrity: sha1-3F5pjL0HkmW8c+A3doGk5Og/YW4=} engines: {node: '>=4'} @@ -4173,7 +4346,6 @@ packages: /uuid/8.3.2: resolution: {integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==} hasBin: true - dev: false /v8-compile-cache/2.3.0: resolution: {integrity: sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==} @@ -4339,6 +4511,13 @@ packages: yargs-parser: 18.1.3 dev: true + /yauzl/2.10.0: + resolution: {integrity: sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=} + dependencies: + buffer-crc32: 0.2.13 + fd-slicer: 1.1.0 + dev: true + /yn/3.1.1: resolution: {integrity: sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==} engines: {node: '>=6'} diff --git a/server/scripts/set-indexes.ts b/server/scripts/set-indexes.ts index 9f72fbfe8..2ce40d389 100644 --- a/server/scripts/set-indexes.ts +++ b/server/scripts/set-indexes.ts @@ -18,8 +18,6 @@ program.option( program.parse(process.argv); const options = program.opts(); -const db = monk(`${process.env.MONGO_BASE_URL ?? "127.0.0.1"}/${options.db ?? "ktblackdb"}`); - interface Index { fields: Record; options?: IndexOptions; @@ -115,7 +113,9 @@ for (const game of supportedGames) { } } -(async () => { +export async function SetIndexes(dbst: string) { + const db = monk(`${process.env.MONGO_BASE_URL ?? "127.0.0.1"}/${dbst}`); + logger.info(`Starting indexing for ${options.db ?? "ktblackdb"}...`); for (const collection in indexes) { @@ -133,6 +133,12 @@ for (const game of supportedGames) { } } + db.close(); + logger.info("Done."); - process.exit(0); -})(); +} + +// if calling this as a script +if (require.main === module) { + SetIndexes(options.db ?? "ktblackdb").then(process.exit(0)); +} diff --git a/server/src/external/mongo/db.ts b/server/src/external/mongo/db.ts index 48aec9261..b234491e1 100644 --- a/server/src/external/mongo/db.ts +++ b/server/src/external/mongo/db.ts @@ -14,7 +14,6 @@ import { FolderChartLookup, ImportTimingsDocument, PrivateUserDocument, - PublicAPIKeyDocument, ScoreDocument, KaiAuthDocument, SessionDocument, @@ -26,7 +25,7 @@ import { UserMilestoneDocument, BMSCourseDocument, } from "kamaitachi-common"; -import monk from "monk"; +import monk, { IMonkManager } from "monk"; import { MONGO_BASE_URL } from "../../lib/env/env"; import CreateLogCtx from "../../lib/logger/logger"; @@ -36,7 +35,17 @@ const logger = CreateLogCtx(__filename); const base = MONGO_BASE_URL ?? "127.0.0.1"; /* istanbul ignore next */ -const url = process.env.NODE_ENV === "test" ? `${base}:27017/testingdb` : `${base}:27017/ktblackdb`; +let url = `${base}:27017/ktblackdb`; + +if (process.env.NODE_ENV === "test") { + if (process.env.KTBSV_PARALLEL_TESTS) { + url = `${base}:27017/test-ephemeral-${process.pid}`; + } else { + url = `${base}:27017/testingdb`; + } +} + +logger.info(`Connecting to ${url}`); let dbtime: [number, number] = [0, 0]; /* istanbul ignore next */ @@ -46,7 +55,6 @@ if (process.env.NODE_ENV !== "test") { } export const monkDB = monk(url); - monkDB .then(() => { /* istanbul ignore next */ diff --git a/server/src/external/redis/redis-IPC.test.ts b/server/src/external/redis/redis-IPC.test.ts index 678d32a34..868135a88 100644 --- a/server/src/external/redis/redis-IPC.test.ts +++ b/server/src/external/redis/redis-IPC.test.ts @@ -3,13 +3,13 @@ import { CloseRedisPubSub, RedisPub, RedisSub } from "./redis-IPC"; t.test("Basic PUB/SUB testing", (t) => { t.setTimeout(2000); - RedisSub("class-update", (d) => { + RedisSub("test" as any, (d) => { t.equal(d.userID, 1); t.pass(); t.end(); }); - RedisPub("class-update", { userID: 1 } as any); + RedisPub("test" as any, { userID: 1 } as any); }); t.teardown(CloseRedisPubSub); diff --git a/server/src/external/redis/redis-store.ts b/server/src/external/redis/redis.ts similarity index 82% rename from server/src/external/redis/redis-store.ts rename to server/src/external/redis/redis.ts index 564d11407..4898933d2 100644 --- a/server/src/external/redis/redis-store.ts +++ b/server/src/external/redis/redis.ts @@ -1,11 +1,8 @@ -import connectRedis from "connect-redis"; -import expressSession from "express-session"; import CreateLogCtx from "../../lib/logger/logger"; import redis from "redis"; const logger = CreateLogCtx(__filename); -export const RedisStore = connectRedis(expressSession); logger.verbose("Instantiated Redis Store"); export const RedisClient = redis.createClient(); diff --git a/server/src/lib/score-import/import-types/common/eamusement-iidx-csv/converter.test.ts b/server/src/lib/score-import/import-types/common/eamusement-iidx-csv/converter.test.ts index 4e76996d8..9817b0e0f 100644 --- a/server/src/lib/score-import/import-types/common/eamusement-iidx-csv/converter.test.ts +++ b/server/src/lib/score-import/import-types/common/eamusement-iidx-csv/converter.test.ts @@ -71,13 +71,22 @@ const data = { t.test("#EamScoreConverter", async (t) => { t.beforeEach(ResetDBState); - // this returns 511 - const song = await db.songs.iidx.findOne(); + const song = { + title: "5.1.1.", + artist: "dj nagureo", + id: 1, + firstVersion: "0", + "alt-titles": [], + "search-titles": [], + data: { + genre: "PIANO AMBIENT", + }, + }; function EamScoreConverterAuto(score: Partial = {}) { return EamScoreConverter( deepmerge(valid511Score, score) as EamusementScoreData, - song!, + song, converterContext, data, false, @@ -323,13 +332,23 @@ t.test("#EamScoreConverter", async (t) => { t.test("#EamScoreConverterWrapper", async (t) => { t.beforeEach(ResetDBState); - const song = await db.songs.iidx.findOne(); + const song = { + title: "5.1.1.", + artist: "dj nagureo", + id: 1, + firstVersion: "0", + "alt-titles": [], + "search-titles": [], + data: { + genre: "PIANO AMBIENT", + }, + }; // wrapper wrapper, lol function EamScoreConverterWrapperAuto(score: Partial = {}) { return EamScoreConverterWrapper( deepmerge(valid511Score, score) as EamusementScoreData, - song!, + song, converterContext, data, false, diff --git a/server/src/server/router/api/v1/import/router.test.ts b/server/src/server/router/api/v1/import/router.test.ts index 17d5e27cb..e018e47be 100644 --- a/server/src/server/router/api/v1/import/router.test.ts +++ b/server/src/server/router/api/v1/import/router.test.ts @@ -11,12 +11,15 @@ import { RequireNeutralAuthentication } from "../../../../../test-utils/api-comm import { CreateFakeAuthCookie } from "../../../../../test-utils/fake-session"; import ResetDBState from "../../../../../test-utils/reset-db-state"; import db from "../../../../../external/mongo/db"; +import { SetIndexes } from "../../../../../../scripts/set-indexes"; // reset DB handles the post-stuff t.test("POST /api/v1/import/file", async (t) => { const cookie = await CreateFakeAuthCookie(mockApi); + await SetIndexes(`test-ephemeral-${process.pid.toString()}`); + t.beforeEach(ResetDBState); RequireNeutralAuthentication("/api/v1/import/file", "POST"); @@ -321,3 +324,9 @@ t.test("POST /api/v1/import/file", async (t) => { }); t.teardown(CloseAllConnections); + +import winr from "why-is-node-running"; + +setTimeout(() => { + winr(); +}, 80_000); diff --git a/server/src/server/server.ts b/server/src/server/server.ts index 3e9b13525..94d16f162 100644 --- a/server/src/server/server.ts +++ b/server/src/server/server.ts @@ -3,22 +3,30 @@ import "express-async-errors"; import CreateLogCtx from "../lib/logger/logger"; import expressSession from "express-session"; import { integer } from "kamaitachi-common"; -import { RedisClient, RedisStore } from "../external/redis/redis-store"; +import { RedisClient } from "../external/redis/redis"; import { SESSION_SECRET } from "../lib/env/env"; +import connectRedis from "connect-redis"; const logger = CreateLogCtx(__filename); +let store; + +if (process.env.NODE_ENV !== "test") { + const RedisStore = connectRedis(expressSession); + store = new RedisStore({ + host: "localhost", + port: 6379, + client: RedisClient, + }); +} + const userSessionMiddleware = expressSession({ // append node_env onto the end of the session name // so we can separate tokens under the same URL. // say for staging.kamaitachi.xyz name: `ktblack_session_${process.env.NODE_ENV}`, secret: SESSION_SECRET, - store: new RedisStore({ - host: "localhost", - port: 6379, - client: RedisClient, - }), + store, resave: true, saveUninitialized: false, cookie: { diff --git a/server/src/test-utils/close-connections.ts b/server/src/test-utils/close-connections.ts index 7c70f6cb5..7b582007f 100644 --- a/server/src/test-utils/close-connections.ts +++ b/server/src/test-utils/close-connections.ts @@ -1,6 +1,6 @@ import { CloseMongoConnection } from "../external/mongo/db"; import { CloseRedisPubSub } from "../external/redis/redis-IPC"; -import { CloseRedisConnection } from "../external/redis/redis-store"; +import { CloseRedisConnection } from "../external/redis/redis"; import { CloseServerConnection } from "./mock-api"; export async function CloseAllConnections() { diff --git a/server/src/test-utils/mock-api.ts b/server/src/test-utils/mock-api.ts index ba2dea59c..dab17c609 100644 --- a/server/src/test-utils/mock-api.ts +++ b/server/src/test-utils/mock-api.ts @@ -6,7 +6,7 @@ const logger = CreateLogCtx(__filename); import server from "../server/server"; logger.verbose("Creating Mock Server Connection..."); -const connection = server.listen(8079); +const connection = server.listen(); logger.verbose("Connecting to Supertest..."); const mockApi = supertest(connection); diff --git a/server/src/utils/session.test.ts b/server/src/utils/session.test.ts index 4c11aec2c..32403d2fd 100644 --- a/server/src/utils/session.test.ts +++ b/server/src/utils/session.test.ts @@ -7,6 +7,8 @@ import { GetScoresFromSession } from "./session"; t.test("#GetScoresFromSession", async (t) => { t.beforeEach(ResetDBState); + await ResetDBState(); + const exampleSession = await db.sessions.findOne(); const scores = await GetScoresFromSession(exampleSession!); diff --git a/server/src/utils/user.test.ts b/server/src/utils/user.test.ts index 502368eb7..5170a8a1d 100644 --- a/server/src/utils/user.test.ts +++ b/server/src/utils/user.test.ts @@ -4,8 +4,11 @@ import { prAssert } from "../test-utils/asserts"; import { GetUserCaseInsensitive, PRIVATEINFO_GetUserCaseInsensitive, FormatUserDoc } from "./user"; import { PublicUserDocument } from "kamaitachi-common"; import { CloseAllConnections } from "../test-utils/close-connections"; +import ResetDBState from "../test-utils/reset-db-state"; t.test("#GetUserCaseInsensitive", (t) => { + t.beforeEach(ResetDBState); + t.test("Should return the user for an exact username", async (t) => { const result = await GetUserCaseInsensitive("test_zkldi"); @@ -46,6 +49,8 @@ t.test("#GetUserCaseInsensitive", (t) => { }); t.test("#PRIVATEINFO_GetUserCaseInsensitive", (t) => { + t.beforeEach(ResetDBState); + t.test("Should return the user for an exact username", async (t) => { const result = await PRIVATEINFO_GetUserCaseInsensitive("test_zkldi");