{"id":31322790,"url":"https://github.com/lfsc09/kdongs-mono","last_synced_at":"2026-04-06T09:33:42.653Z","repository":{"id":312972227,"uuid":"1049531172","full_name":"lfsc09/kdongs-mono","owner":"lfsc09","description":"Kdongs project","archived":false,"fork":false,"pushed_at":"2026-03-28T14:08:24.000Z","size":2417,"stargazers_count":0,"open_issues_count":16,"forks_count":1,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-03-28T16:53:07.113Z","etag":null,"topics":["adonis","angular","biomejs","docker","husky","postgres","prettier"],"latest_commit_sha":null,"homepage":"https:/kdongs.com","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"agpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/lfsc09.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-09-03T05:50:51.000Z","updated_at":"2026-02-02T22:07:08.000Z","dependencies_parsed_at":null,"dependency_job_id":"d0d98b55-6fbe-49cf-a9ad-89a6f467fb52","html_url":"https://github.com/lfsc09/kdongs-mono","commit_stats":null,"previous_names":["lfsc09/kdongs-mono"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/lfsc09/kdongs-mono","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lfsc09%2Fkdongs-mono","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lfsc09%2Fkdongs-mono/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lfsc09%2Fkdongs-mono/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lfsc09%2Fkdongs-mono/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/lfsc09","download_url":"https://codeload.github.com/lfsc09/kdongs-mono/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/lfsc09%2Fkdongs-mono/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31466629,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-06T08:36:52.050Z","status":"ssl_error","status_checked_at":"2026-04-06T08:36:51.267Z","response_time":112,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["adonis","angular","biomejs","docker","husky","postgres","prettier"],"created_at":"2025-09-25T19:14:38.268Z","updated_at":"2026-04-06T09:33:42.644Z","avatar_url":"https://github.com/lfsc09.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Kdongs\n\nA set of web tools, that over the years I could not find software (paid) that would cover all my needs.\n\n### Roadmap\n\n#### Finished\n\n- [x] Wallet management (create, delete);\n\n#### In Progress\n\n- [x] Make wallet movements (deposit, withdraw);\n- [ ] Manage asset inclusion in wallets;\n- [ ] Wallet profit calculation;\n- [x] Deployment scripts\n\n#### Backlog\n\n- [ ] Allow change wallet currency (simulation only);\n- [ ] Market data;\n  - [ ] Stocks;\n  - [ ] Currency rates;\n  - [ ] Private and public bonds info (cdi, selic, etc);\n- [ ] Investments alerts;\n- [ ] Investment calculators;\n\n### Additional READMEs\n\n1. [Backend Adonisjs Api](packages/backend/README.md)\n2. [Frontend Angular](packages/frontend/README.md)\n\n\u003c/br\u003e\n\u003c/br\u003e\n\n# Ecosystem (Deployment)\n\n## Services\n\n| Service | Description |\n| -- | -- |\n| nginx | Web server and reverse proxy (serves static Angular frontend files, proxies `/api/*` to backend, etc) |\n| certbot | SSL certificate management with ACME challenge via webroot |\n| api-backend | Adonisjs RESTful API endpoints |\n| api-postgres | PostgreSQL 16 Alpine database (with pg_stat_statements extension) |\n| frontend-builder | Builds Angular application |\n\n\u003c/br\u003e\n\n## First Time Installation\n\n#### 1. Run the bootstrap script `production.bootstrap.sh`\n\n\u003e **What it does**:\n\u003e\n\u003e At **root** phase:\n\u003e   1. Create deploy user `\u003cvps-user\u003e` with sudo access\n\u003e   2. Generate SSH key for GitHub Actions deployment\n\u003e   3. Update and install necessary packages (Docker, Docker Compose, Git, UFW, Fail2Ban, etc.)\n\u003e   4. Configure firewall (UFW) and Fail2Ban\n\u003e   5. Enable automatic security updates\n\u003e   6. Setup log rotation for backup logs\n\u003e   7. Switch to deploy user for application setup\n\u003e\n\u003e At **user** phase:\n\u003e   1. Clone or update the application repository\n\u003e   2. Configure git for read-only access\n\u003e   3. Generate Docker secrets (DB password, APP_KEY)\n\u003e   4. Update `\u003cdomain\u003e` in nginx configuration\n\u003e   5. Set proper permissions for secrets\n\u003e   6. Create backup directory\n\u003e   7. Setup automated database backups via crontab\n\n**Usage**: `sudo ./production.bootstrap.sh \u003cvps-user\u003e \u003cdomain\u003e \u003cemail\u003e`\n\n\u003e More info in [`production.bootstrap.sh`](./scripts/production.bootstrap.sh)\n\n```bash\n# Example\n# bash \u003c(curl -fsSL https://raw.githubusercontent.com/lfsc09/kdongs-mono/main/scripts/production.bootstrap.sh) \\\n#   \u003cvps-user\u003e \\\n#   your-domain.com \\\n#   your-email@example.com\n```\n\n```bash\nbash \u003c(curl -fsSL https://raw.githubusercontent.com/lfsc09/kdongs-mono/main/scripts/production.bootstrap.sh)\n```\n\n**Notes**:\n\n\u003e Must be run as root initially (will switch to created user automatically)\n\n\u003e The script is idempotent - safe to run multiple times\n\n\u003e Configure containers env variables in `docker/compose.production.yaml`.\n\n\u003e There are resource limitations for containers configured in `docker/compose.production.yaml`.\n\n#### 2. Start all services:\n\n```bash\nsu \u003cvps-user\u003e \u0026\u0026 cd ~/kdongs-mono/docker\n```\n\n```bash\ndocker compose -f compose.production.yaml up -d\n```\n\n#### 2. Obtain SSL certificate:\n\n```bash\ndocker compose run --rm certbot certonly \\\n  --webroot -w /var/www/certbot \\\n  -d \u003cyour-domain.com\u003e -d \u003cwww.your-domain.com\u003e \\\n  --email \u003cyour-email@example.com\u003e \\\n  --agree-tos\n```\n\n\u003c/br\u003e\n\n## Certificates\n\nThe certbot container runs a renewal loop every 12 hours.\n\n\u003c/br\u003e\n\n## Backups\n\n### Manual generation with `export-database.sh`\n\n\u003e **What it does**:\n\u003e 1. Exports the specified PostgreSQL database from the Docker container.\n\u003e 2. Compresses the output using gzip.\n\n**Usage**: `[CONTAINER_NAME=\u003ccontainer-name\u003e] [DB_NAME=\u003cdb-name\u003e] [DB_USER=\u003cdb-user\u003e] ./export-database.sh [backup-name-prefix] [backup-dir]`\n\n\u003e More info in [`export-database.sh`](./docker/postgres/scripts/export-database.sh)\n\n```bash\n# Export to default backup name prefix and backup dir\n~/kdongs-mono/docker/postgres/scripts/export-database.sh\n\n# Export to custom backup name prefix and backup dir\n~/kdongs-mono/docker/postgres/scripts/export-database.sh backup /custom/path\n\n# Custom container, DB, user, backup name prefix, and backup dir\nCONTAINER_NAME=my-postgres-container DB_NAME=mydb DB_USER=dbuser ~/kdongs-mono/docker/postgres/scripts/export-database.sh backup /custom/path\n```\n\n### Automatic generation with `auto-backup.sh` and `cron`\n\n\u003e **What it does**:\n\u003e 1. Creates a database backup using export-database.sh.\n\u003e 2. Cleans up backups older than the specified retention period.\n\n**Usage**: `[BACKUP_DIR=\u003cbackup-dir\u003e] [DB_NAME=\u003cdb-name\u003e] [DB_USER=\u003cdb-user\u003e] ./auto-backup.sh [retention-days]`\n\n\u003e More info in [`auto-backup.sh`](./docker/postgres/scripts/auto-backup.sh)\n\n```bash\n# Backup with 7 days retention\n~/kdongs-mono/docker/postgres/scripts/auto-backup.sh\n\n# Backup with 14 days retention\n~/kdongs-mono/docker/postgres/scripts/auto-backup.sh 14\n\n# Custom backup directory with 7 days retention\nBACKUP_DIR=/custom/path ~/kdongs-mono/docker/postgres/scripts/auto-backup.sh\n\n# Custom DB and user with 7 days retention\nDB_NAME=mydb DB_USER=dbuser ~/kdongs-mono/docker/postgres/scripts/auto-backup.sh\n```\n\n**Cron Config**: `0 2 * * * [DB_NAME=\u003cdb-name\u003e] [DB_USER=\u003cdb-user\u003e] /home/\u003cvps-user\u003e/kdongs-mono/docker/postgres/scripts/auto-backup.sh \u003cretention-days\u003e \u003e\u003e /var/log/kdongs-backup.log 2\u003e\u00261`\n\n```bash\n# Default values\n0 2 * * * /home/\u003cvps-user\u003e/kdongs-mono/docker/postgres/scripts/auto-backup.sh \u003e\u003e /var/log/kdongs-backup.log 2\u003e\u00261\n\n# 14 days retention\n0 2 * * * /home/\u003cvps-user\u003e/kdongs-mono/docker/postgres/scripts/auto-backup.sh 14 \u003e\u003e /var/log/kdongs-backup.log 2\u003e\u00261\n\n# Custom backup directory\n0 2 * * * BACKUP_DIR=/custom/path /home/\u003cvps-user\u003e/kdongs-mono/docker/postgres/scripts/auto-backup.sh \u003e\u003e /var/log/kdongs-backup.log 2\u003e\u00261\n\n# Custom DB and user\n0 2 * * * DB_NAME=mydb DB_USER=dbuser /home/\u003cvps-user\u003e/kdongs-mono/docker/postgres/scripts/auto-backup.sh \u003e\u003e /var/log/kdongs-backup.log 2\u003e\u00261\n```\n\n\u003e Automated backups are configured via cron. (setup in `production.bootstrap.sh`)\n\n\u003e Logs created will be rotated as configured by `production.bootstrap.sh`.\n\n### Sync to remote storage\n\nSync backups to remote storage.\n\n```bash\n# Configure remote (S3, Google Drive, etc.)\nrclone config\n\n# Add to cron after auto-backup (runs at 3 AM daily)\n0 3 * * * rclone sync /home/\u003cvps-user\u003e/backups/ remote:kdongs-backups/\n```\n\n### Restore backup with `import-database.sh`\n\n\u003e **What it does**:\n\u003e 1. Imports the specified PostgreSQL database into the Docker container. (`.sql.gz` or `.sql`)\n\n**Usage**: `[DB_NAME=\u003cdb-name\u003e] [DB_USER=\u003cdb-user\u003e] ./import-database.sh \u003cbackup-file\u003e`\n\n\u003e More info in [`import-database.sh`](./docker/postgres/scripts/import-database.sh)\n\n```bash\n# Import from compressed backup file\n~/kdongs-mono/docker/postgres/scripts/import-database.sh ./backups/backup-20241209-120000.sql.gz\n\n# Import from uncompressed backup file\n~/kdongs-mono/docker/postgres/scripts/import-database.sh ./backups/backup-20241209-120000.sql\n\n# Custom DB and user\nDB_NAME=mydb DB_USER=dbuser ~/kdongs-mono/docker/postgres/scripts/import-database.sh ./backups/backup-20241209-120000.sql.gz\n```\n\n\u003c/br\u003e\n\n## Deployment\n\n### Manual deployment with `production.deploy.sh`\n\n\u003e **What it does**:\n\u003e 1. Prompts for confirmation before proceeding.\n\u003e 2. Checks out the specified tag or latest from main branch.\n\u003e 3. Creates a database backup. *(with \"pre-deploy\" prefix)*\n\u003e 4. Builds and deploys the Docker containers.\n\n**Usage**: `[BACKUP_DIR=\u003cbackup-dir\u003e] [DB_NAME=\u003cdb-name\u003e] [DB_USER=\u003cdb-user\u003e] ./production.deploy.sh [\u003ctag\u003e|latest]`\n\n\u003e More info in [`production.deploy.sh`](./scripts/production.deploy.sh)\n\n```bash\n# Deploy latest from main branch (default)\n~/kdongs-mono/scripts/production.deploy.sh\n\n# Deploy latest from main branch (explicit)\n~/kdongs-mono/scripts/production.deploy.sh latest\n\n# Deploy specific tag\n~/kdongs-mono/scripts/production.deploy.sh v1.2.3\n\n# Custom backup directory\nBACKUP_DIR=/custom/path ~/kdongs-mono/scripts/production.deploy.sh\n\n# Custom DB and backup dir\nBACKUP_DIR=/custom/path DB_NAME=mydb DB_USER=dbuser ~/kdongs-mono/scripts/production.deploy.sh\n```\n\n### Automated deployment\n\nDeployments are triggered automatically on GitHub releases via workflows [`deploy.yaml`](./.github/workflows/deploy.yml).\n\nAdd the required Github secrets.\n\n| **Secret Name** | **Description** |\n|-----------------|-----------------|\n| `VPS_SSH_KEY` | Private SSH key for authentication to VPS (e.g. `~/.ssh/id_ed25519`) |\n| `VPS_HOST` | VPS server hostname or IP address |\n| `VPS_USER` | SSH username for VPS login |\n| `VPS_REPO_PATH` | Full path to repository inside VPS |\n| `VPS_BACKUP_DB_NAME` | PostgreSQL database name for backups |\n| `VPS_BACKUP_DB_USER` | PostgreSQL database user for backups |\n| `VPS_BACKUP_PATH` | Directory path for storing backups (defaults to `/home/\u003cVPS_USER\u003e/backups`)|\n| `VPS_HEALTHCHECK_ENDPOINT` | URL endpoint for health check after deployment |\n\n\u003c/br\u003e\n\n## Troubleshooting\n\n| **Commands** | **Description** |\n| -- | -- |\n| **Container Commands** | |\n| `docker compose restart \u003ccontainer-name\u003e` | Restart a container |\n| `docker exec kdongs-api-postgres pg_isready -U adonisjs` | Check DB is healthy |\n| `docker exec -it kdongs-api-postgres psql -U adonisjs -d app` | Access DB container |\n| `docker compose up -d --build frontend-builder` | Rebuild frontend |\n| **Certificate Commands** | |\n| `docker compose exec nginx openssl x509 -in /etc/letsencrypt/live/\u003cyour-domain\u003e/cert.pem -noout -dates` | Check certificate |\n| `docker compose exec certbot certbot renew --dry-run` | Manual test certificate generation |\n| `docker compose run --rm certbot certonly --webroot -w /var/www/certbot -d \u003cyour-domain\u003e --force-renewal` | Certificate manual renewal |\n| **Backup Commands** | |\n| `docker run --rm -v kdongs_api-postgres-data:/data -v $(pwd):/backup alpine tar czf /backup/postgres-data-backup.tar.gz /data` | Backup database volume |\n| `docker run --rm -v kdongs_api-postgres-data:/data -v $(pwd):/backup alpine sh -c \"cd /data \u0026\u0026 tar xzf /backup/postgres-data-backup.tar.gz --strip 1\"` | Restore database volume |\n| `find ~/backups -name \"*.sql.gz\" -mtime +30 -delete` | Manually remove old backups |\n\n\u003c/br\u003e\n\n## Monitoring\n\n### Database\n\n```bash\n# Connect to database\ndocker exec -it kdongs-api-postgres psql -U adonisjs -d app\n\n# Check database size\nSELECT pg_size_pretty(pg_database_size('app'));\n\n# Check active connections\nSELECT count(*) FROM pg_stat_activity;\n\n# Check slow queries\nSELECT query, calls, total_time, mean_time\nFROM pg_stat_statements\nORDER BY total_time DESC\nLIMIT 10;\n\n# Exit psql\n\\q\n```\n\n\u003c/br\u003e\n\u003c/br\u003e\n\n# Ecosystem (Development)\n\n## Installation\n\n#### 1. Clone the repository.\n\n```bash\ngit clone https://github.com/lfsc09/kdongs-mono.git\ncd kdongs-mono\n```\n\n#### 2. Install dependencies.\n\n```bash\nnpm install\n```\n\n#### 3. Setup project.\n\n```bash\nnpm run dev:setup\n```\n\n\u003e **This will**:\n\u003e \n\u003e 1. Create the project `.env` and `.env.test` file if they don't exist.\n\u003e 2. Generate an `APP_KEY` in both files.\n\u003e 3. Create a random `root` DB user password, for the Docker Postgres container to use and fill it in `.env` and `.env.test`.\n\u003e 4. Fill the created password in `.env` and `.env.test` at `DB_PASSWORD`.\n\n#### 4. Bring up the backend ecosystem.\n\n##### only db\n\n```bash\nnpm run dev:docker-db-up\n```\n\n##### node + db\n\n```bash\nnpm run dev:docker-full-up\n```\n\n\u003e Configure containers env variables in `docker/compose.local.yaml`.\n\n\u003e *Will automatically run migrations with adonisjs Entrypoint.\n\n#### 5. Run **backend** migrations \u0026 seeds. (**dev:docker-db-up only**)\n\n\u003e The ecosystem will have two isolated databases, one for the `.env` and another for the `.env.test`. So the tests will have a dedicated database, because each test completely erases all the data, before it runs.\n\n##### regular migrations\n\n```bash\n# migrate with .env\nnpm run dev:backend:migrate\n```\n\n##### migrations for testing purposes\n\n\u003e Test migrations don't need seeding.\n\n```bash\n# migrate with .env.test\nnpm run test:backend:migrate\n```\n\n\u003c/br\u003e\n\n## Run\n\n##### backend\n\n```bash\nnpm run dev:backend\n```\n\n##### frontend\n\n```bash\nnpm run dev:frontend\n```\n\n##### both\n\n```bash\nnpm run dev:mono\n```\n\n\u003c/br\u003e\n\n## Run tests\n\n##### backend tests\n\n\u003e Migrate the test-db first\n\n```bash\nnpm run test:backend:migrate\n```\n\n```bash\nnpm run test:backend\n```\n\n##### frontend tests\n\n```bash\nnpm run test:frontend\n```\n\n\u003c/br\u003e\n\n## Uninstall\n\n\u003e *Will delete all the data.*\n\n##### db-only profile\n\n```bash\nnpm run dev:backend:docker-db-down\n```\n\n##### full profile\n\n```bash\nnpm run dev:backend:docker-full-down\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flfsc09%2Fkdongs-mono","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flfsc09%2Fkdongs-mono","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flfsc09%2Fkdongs-mono/lists"}