From 4e896108defa9bfa77f2de4a4c714ac691eb4886 Mon Sep 17 00:00:00 2001 From: Anmol Sharma Date: Sun, 14 Apr 2024 13:08:47 +0530 Subject: [PATCH] fix: use config to load credentials for db Signed-off-by: Anmol Sharma --- config/config.yaml | 7 +++ config/dev.config.yaml | 7 +++ nest-cli.json | 8 ++- package-lock.json | 113 ++++++++++++++++++++++------------------- package.json | 7 ++- src/app.module.ts | 29 +++++++---- src/common/common.ts | 9 ++++ src/configuration.ts | 44 ++++++++++++++++ 8 files changed, 161 insertions(+), 63 deletions(-) create mode 100644 config/config.yaml create mode 100644 config/dev.config.yaml create mode 100644 src/common/common.ts create mode 100644 src/configuration.ts diff --git a/config/config.yaml b/config/config.yaml new file mode 100644 index 0000000..56d0046 --- /dev/null +++ b/config/config.yaml @@ -0,0 +1,7 @@ +db: + host: + port: + username: + password: + databaseName: silent-pay-indexer + synchronize: false diff --git a/config/dev.config.yaml b/config/dev.config.yaml new file mode 100644 index 0000000..f0b4b7d --- /dev/null +++ b/config/dev.config.yaml @@ -0,0 +1,7 @@ +db: + host: localhost + port: 5432 + username: root + password: password + databaseName: silent-pay-indexer + synchronize: false diff --git a/nest-cli.json b/nest-cli.json index c85031e..cef8b1f 100644 --- a/nest-cli.json +++ b/nest-cli.json @@ -6,6 +6,12 @@ "webpack": true, "webpackConfigPath": "webpack.config.js", "builder": "webpack", - "deleteOutDir": true + "deleteOutDir": true, + "assets": [ + { + "include": "../config/*", + "outDir": "./dist/config" + } + ] } } diff --git a/package-lock.json b/package-lock.json index 88b50d1..a3d28a1 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,6 +10,7 @@ "license": "UNLICENSED", "dependencies": { "@nestjs/common": "^9.0.0", + "@nestjs/config": "^3.2.2", "@nestjs/core": "^10.3.7", "@nestjs/microservices": "^10.3.7", "@nestjs/passport": "^9.0.3", @@ -19,6 +20,7 @@ "@nestjs/swagger": "^7.3.1", "@nestjs/typeorm": "^10.0.2", "@nestjs/websockets": "^10.3.7", + "js-yaml": "^4.1.0", "pg": "^8.11.5", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", @@ -30,6 +32,7 @@ "@nestjs/testing": "^10.3.7", "@types/express": "^4.17.13", "@types/jest": "29.5.0", + "@types/js-yaml": "^4.0.9", "@types/node": "18.15.11", "@types/supertest": "^2.0.11", "@typescript-eslint/eslint-plugin": "^5.0.0", @@ -761,7 +764,7 @@ "version": "0.8.1", "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz", "integrity": "sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==", - "devOptional": true, + "dev": true, "dependencies": { "@jridgewell/trace-mapping": "0.3.9" }, @@ -773,7 +776,7 @@ "version": "0.3.9", "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz", "integrity": "sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==", - "devOptional": true, + "dev": true, "dependencies": { "@jridgewell/resolve-uri": "^3.0.3", "@jridgewell/sourcemap-codec": "^1.4.10" @@ -1383,7 +1386,7 @@ "version": "3.1.2", "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", - "devOptional": true, + "dev": true, "engines": { "node": ">=6.0.0" } @@ -1411,7 +1414,7 @@ "version": "1.4.15", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz", "integrity": "sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==", - "devOptional": true + "dev": true }, "node_modules/@jridgewell/trace-mapping": { "version": "0.3.25", @@ -1551,6 +1554,33 @@ } } }, + "node_modules/@nestjs/config": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/@nestjs/config/-/config-3.2.2.tgz", + "integrity": "sha512-vGICPOui5vE6kPz1iwQ7oCnp3qWgqxldPmBQ9onkVoKlBtyc83KJCr7CjuVtf4OdovMAVcux1d8Q6jglU2ZphA==", + "dependencies": { + "dotenv": "16.4.5", + "dotenv-expand": "10.0.0", + "lodash": "4.17.21", + "uuid": "9.0.1" + }, + "peerDependencies": { + "@nestjs/common": "^8.0.0 || ^9.0.0 || ^10.0.0", + "rxjs": "^7.1.0" + } + }, + "node_modules/@nestjs/config/node_modules/uuid": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", + "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", + "funding": [ + "https://github.com/sponsors/broofa", + "https://github.com/sponsors/ctavan" + ], + "bin": { + "uuid": "dist/bin/uuid" + } + }, "node_modules/@nestjs/core": { "version": "10.3.7", "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-10.3.7.tgz", @@ -1978,25 +2008,25 @@ "version": "1.0.11", "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.11.tgz", "integrity": "sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==", - "devOptional": true + "dev": true }, "node_modules/@tsconfig/node12": { "version": "1.0.11", "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.11.tgz", "integrity": "sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==", - "devOptional": true + "dev": true }, "node_modules/@tsconfig/node14": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.3.tgz", "integrity": "sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==", - "devOptional": true + "dev": true }, "node_modules/@tsconfig/node16": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.4.tgz", "integrity": "sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==", - "devOptional": true + "dev": true }, "node_modules/@types/babel__core": { "version": "7.20.5", @@ -2176,6 +2206,12 @@ "pretty-format": "^29.0.0" } }, + "node_modules/@types/js-yaml": { + "version": "4.0.9", + "resolved": "https://registry.npmjs.org/@types/js-yaml/-/js-yaml-4.0.9.tgz", + "integrity": "sha512-k4MGaQl5TGo/iipqb2UDG2UwjXziSWkh0uysQelTlJpX1qGlpUZYm8PnO4DxG1qBomtJUdYJ6qR6xdIah10JLg==", + "dev": true + }, "node_modules/@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", @@ -2659,7 +2695,7 @@ "version": "8.11.3", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz", "integrity": "sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==", - "devOptional": true, + "dev": true, "bin": { "acorn": "bin/acorn" }, @@ -2689,7 +2725,7 @@ "version": "8.3.2", "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.2.tgz", "integrity": "sha512-cjkyv4OtNCIeqhHrfS81QWXoCBPExR/J62oyEqepVw8WaQeSqpW2uhuLPh1m9eWhDuOo/jUXVTlifvesOWp/4A==", - "devOptional": true, + "dev": true, "engines": { "node": ">=0.4.0" } @@ -2820,7 +2856,7 @@ "version": "4.1.3", "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", - "devOptional": true + "dev": true }, "node_modules/argparse": { "version": "2.0.1", @@ -3855,7 +3891,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", "integrity": "sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==", - "devOptional": true + "dev": true }, "node_modules/cron": { "version": "2.3.1", @@ -4073,7 +4109,7 @@ "version": "4.0.2", "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", - "devOptional": true, + "dev": true, "engines": { "node": ">=0.3.1" } @@ -4122,6 +4158,14 @@ "url": "https://dotenvx.com" } }, + "node_modules/dotenv-expand": { + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/dotenv-expand/-/dotenv-expand-10.0.0.tgz", + "integrity": "sha512-GopVGCpVS1UKH75VKHGuQFqS1Gusej0z4FyQkPdwjil2gNIv+LNsqBlboOzpJFZKVT95GkCyWJbBSdFEFUWI2A==", + "engines": { + "node": ">=12" + } + }, "node_modules/eastasianwidth": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", @@ -7520,7 +7564,7 @@ "version": "1.3.6", "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", - "devOptional": true + "dev": true }, "node_modules/makeerror": { "version": "1.0.12", @@ -8097,33 +8141,6 @@ "node": ">= 0.8" } }, - "node_modules/passport": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/passport/-/passport-0.6.0.tgz", - "integrity": "sha512-0fe+p3ZnrWRW74fe8+SvCyf4a3Pb2/h7gFkQ8yTJpAO50gDzlfjZUZTO1k5Eg9kUct22OxHLqDZoKUWRHOh9ug==", - "peer": true, - "dependencies": { - "passport-strategy": "1.x.x", - "pause": "0.0.1", - "utils-merge": "^1.0.1" - }, - "engines": { - "node": ">= 0.4.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/jaredhanson" - } - }, - "node_modules/passport-strategy": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/passport-strategy/-/passport-strategy-1.0.0.tgz", - "integrity": "sha512-CB97UUvDKJde2V0KDWWB3lyf6PC3FaZP7YxZ2G8OAtn9p4HI9j9JLP9qjOGZFvyl8uwNT8qM+hGnz/n16NI7oA==", - "peer": true, - "engines": { - "node": ">= 0.4.0" - } - }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -8201,12 +8218,6 @@ "node": ">=8" } }, - "node_modules/pause": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/pause/-/pause-0.0.1.tgz", - "integrity": "sha512-KG8UEiEVkR3wGEb4m5yZkVCzigAD+cVEJck2CzYZO37ZGJfctvVptVO192MwrtPhzONn6go8ylnOdMhKqi4nfg==", - "peer": true - }, "node_modules/pg": { "version": "8.11.5", "resolved": "https://registry.npmjs.org/pg/-/pg-8.11.5.tgz", @@ -9925,7 +9936,7 @@ "version": "10.9.2", "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz", "integrity": "sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==", - "devOptional": true, + "dev": true, "dependencies": { "@cspotcode/source-map-support": "^0.8.0", "@tsconfig/node10": "^1.0.7", @@ -10352,7 +10363,7 @@ "version": "4.9.5", "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", - "devOptional": true, + "dev": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" @@ -10468,7 +10479,7 @@ "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==", - "devOptional": true + "dev": true }, "node_modules/v8-to-istanbul": { "version": "9.2.0", @@ -10845,7 +10856,7 @@ "version": "3.1.1", "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz", "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==", - "devOptional": true, + "dev": true, "engines": { "node": ">=6" } diff --git a/package.json b/package.json index ed91397..637e5d8 100644 --- a/package.json +++ b/package.json @@ -9,8 +9,8 @@ "build": "nest build", "format": "prettier --write \"src/**/*.ts\" \"test/**/*.ts\"", "start": "nest start", - "start:dev": "nest build --webpack --webpackPath webpack-hmr.config.js --watch", - "start:debug": "nest build --webpack --webpackPath webpack-hmr.config.js --debug --watch", + "start:dev": "NODE_ENV=dev nest build --webpack --webpackPath webpack-hmr.config.js --watch", + "start:debug": "NODE_ENV=dev nest build --webpack --webpackPath webpack-hmr.config.js --debug --watch", "start:prod": "node dist/main", "format:check": "prettier --check \"src/**/*.ts\"", "format:fix": "prettier --write --loglevel=silent \"src/**/*.ts\"", @@ -24,6 +24,7 @@ }, "dependencies": { "@nestjs/common": "^9.0.0", + "@nestjs/config": "^3.2.2", "@nestjs/core": "^10.3.7", "@nestjs/microservices": "^10.3.7", "@nestjs/passport": "^9.0.3", @@ -33,6 +34,7 @@ "@nestjs/swagger": "^7.3.1", "@nestjs/typeorm": "^10.0.2", "@nestjs/websockets": "^10.3.7", + "js-yaml": "^4.1.0", "pg": "^8.11.5", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", @@ -44,6 +46,7 @@ "@nestjs/testing": "^10.3.7", "@types/express": "^4.17.13", "@types/jest": "29.5.0", + "@types/js-yaml": "^4.0.9", "@types/node": "18.15.11", "@types/supertest": "^2.0.11", "@typescript-eslint/eslint-plugin": "^5.0.0", diff --git a/src/app.module.ts b/src/app.module.ts index 2cb5273..243b27e 100644 --- a/src/app.module.ts +++ b/src/app.module.ts @@ -2,18 +2,29 @@ import { Module } from '@nestjs/common'; import { AppController } from '@/app.controller'; import { AppService } from '@/app.service'; import { TypeOrmModule } from '@nestjs/typeorm'; +import { ConfigModule, ConfigService } from '@nestjs/config'; +import configuration from '@/configuration'; @Module({ imports: [ - TypeOrmModule.forRoot({ - type: 'postgres', - host: 'localhost', - port: 5432, - username: 'root', - password: 'password', - database: 'silent-pay-indexer', - synchronize: true, - autoLoadEntities: true, + ConfigModule.forRoot({ + ignoreEnvFile: true, + load: [configuration], + isGlobal: true, + }), + TypeOrmModule.forRootAsync({ + imports: [ConfigModule], + inject: [ConfigService], + useFactory: (configService: ConfigService) => ({ + type: 'postgres', + host: configService.get('db.host'), + port: configService.get('db.port'), + username: configService.get('db.username'), + password: configService.get('db.password'), + database: configService.get('db.databaseName'), + synchronize: configService.get('db.synchronize'), + autoLoadEntities: true, + }), }), ], controllers: [AppController], diff --git a/src/common/common.ts b/src/common/common.ts new file mode 100644 index 0000000..586270d --- /dev/null +++ b/src/common/common.ts @@ -0,0 +1,9 @@ +export const camelToSnakeCase = (inputString: string) => { + return inputString + .split('.') + .map((string) => { + return string.replace(/[A-Z]/g, (letter) => `_${letter}`); + }) + .join('_') + .toUpperCase(); +}; diff --git a/src/configuration.ts b/src/configuration.ts new file mode 100644 index 0000000..837bbc6 --- /dev/null +++ b/src/configuration.ts @@ -0,0 +1,44 @@ +import { join } from 'path'; +import { readFileSync } from 'fs'; +import { load } from 'js-yaml'; +import { camelToSnakeCase } from '@/common/common'; + +const getConfigFilePath = () => { + switch (process.env.NODE_ENV) { + case 'dev': + case 'test': + return join(__dirname, 'config', 'dev.config.yaml'); + default: + return join(__dirname, 'config', 'config.yaml'); + } +}; + +export function mergeEnvVariablesRecursive( + config: Record, + envVarName = '', +) { + for (const key of Object.keys(config)) { + const currentEnvVarName = envVarName + ? `${envVarName}_${camelToSnakeCase(key)}` + : key.toUpperCase(); + const currentEnvVarValue = process.env[currentEnvVarName]; + if (config[key] && typeof config[key] === 'object') { + mergeEnvVariablesRecursive(config[key], currentEnvVarName); + } else if (typeof currentEnvVarValue !== 'undefined') { + try { + config[key] = JSON.parse(currentEnvVarValue); + } catch (error) { + config[key] = currentEnvVarValue; + } + } + } +} + +export default () => { + const config = load(readFileSync(getConfigFilePath(), 'utf8')) as Record< + string, + any + >; + mergeEnvVariablesRecursive(config); + return config; +};