Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
1db550a
fix(aws-migration): trustProxy 1-hop + Node 22 in CI (A6, A11)
ericmt-98 Jul 24, 2026
02232b4
fix(aws-migration): embed RDS CA bundle, verify-full DB TLS (A5)
ericmt-98 Jul 24, 2026
03d44a0
Merge origin/main: compliance reporting engine + Didit KYC integration
ericmt-98 Jul 24, 2026
a763cf1
fix(map): remove hardcoded online:true fake signal from offer UI
ericmt-98 Jul 25, 2026
db7455b
fix(privacy): rate-limit and coarsen /merchants/available discovery (G1)
ericmt-98 Jul 25, 2026
f706c7f
feat(map): real MapLibre GL map component (WP1)
ericmt-98 Jul 26, 2026
1cf99eb
feat(map): merchant location capture flow (WP2)
ericmt-98 Jul 26, 2026
1e7faf9
chore(map): remove deprecated MapSim, dead seed.ts, close out audit (…
ericmt-98 Jul 26, 2026
0769565
fix(map): street-level fallback style (OpenFreeMap) instead of demotiles
ericmt-98 Jul 26, 2026
3f2090d
fix(map): pin maplibre-gl to v5, switch fallback style to OpenFreeMap
ericmt-98 Jul 26, 2026
4824bf8
fix(cetes): route "¿Sin cripto?" CTA to the Etherfuse SPEI ramp, not …
ericmt-98 Jul 26, 2026
6be7b30
fix(kyc): send required Etherfuse email, surface onboarding errors
ericmt-98 Jul 26, 2026
37e5bc9
docs: plan del split del repo de agentes y del puente XRPL
ericmt-98 Aug 7, 2026
72b4497
fix(auth): exigir prueba de posesion de llave al registrar
ericmt-98 Aug 10, 2026
34a4b23
fix(ramp): validar pertenencia de la orden antes de exponerla (IDOR)
ericmt-98 Aug 10, 2026
4a087d3
perf(trades): paginar getTradeHistory en SQL y borrar codigo muerto
ericmt-98 Aug 10, 2026
7667a67
fix(api): registrar la ruta client-errors
ericmt-98 Aug 10, 2026
d30afc1
feat(rate): endpoint /rate/usdc-mxn con fuentes multiples
ericmt-98 Aug 10, 2026
8c41083
fix(ui): quitar el mensaje de chat falso y fijar links de explorer
ericmt-98 Aug 10, 2026
8108aeb
chore(apk): apuntar los builds a api.micopay.app (AWS)
ericmt-98 Aug 10, 2026
c3cf3ea
ci: construir y arrancar la imagen Docker de produccion en cada PR
ericmt-98 Aug 10, 2026
64f0c1f
docs: marcar findings resueltos y sumar planes pendientes
ericmt-98 Aug 10, 2026
c77ad31
docs: que la app de MicoPay encabece el README, ZK al final
ericmt-98 Aug 14, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 56 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ jobs:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
node-version: 22
cache: npm
cache-dependency-path: micopay/backend/package-lock.json
- run: npm ci
Expand All @@ -43,7 +43,7 @@ jobs:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
node-version: 22
cache: npm
cache-dependency-path: micopay/frontend/package-lock.json
# El lock se genera en Windows y omite los binarios opcionales de Linux
Expand All @@ -61,3 +61,57 @@ jobs:
- name: Tests (vitest) — informativo, NO bloqueante todavía
run: npm run test
continue-on-error: true

image:
name: Imagen Docker de producción (micopay/backend)
runs-on: ubuntu-latest
# El contenedor es el artefacto que se despliega en AWS (ver
# docs/AWS_MIGRATION_PLAN_2026-07.md). Este job lo construye y lo arranca
# en cada PR para que no pueda romperse sin que nadie se entere.
steps:
- uses: actions/checkout@v4

- uses: docker/setup-buildx-action@v3

- name: Build — BLOQUEANTE
uses: docker/build-push-action@v6
with:
# Contexto `micopay/` (no `micopay/backend/`): la imagen necesita
# copiar sql/, que vive fuera de backend/. Ver el Dockerfile.
context: micopay
file: micopay/backend/Dockerfile
platforms: linux/amd64
push: false
load: true
tags: micopay-backend:ci
cache-from: type=gha
cache-to: type=gha,mode=max

- name: Las migraciones SQL tienen que viajar en la imagen
# Sin esto, runMigrations() falla en boot, el error solo se loguea y el
# servicio arranca contra una BD sin esquema.
run: |
docker run --rm --entrypoint sh micopay-backend:ci -c \
'ls -1 /app/sql/init.sql && ls -1 /app/sql/migrations | head -3'

- name: Smoke test — el contenedor arranca y responde /health
run: |
docker run -d --name micopay-smoke -p 3000:3000 \
-e NODE_ENV=test \
-e MOCK_STELLAR=true \
-e ALLOW_IN_MEMORY_DB=true \
-e PORT=3000 \
-e SECRET_ENCRYPTION_KEY=0000000000000000000000000000000000000000000000000000000000000000 \
micopay-backend:ci
for i in $(seq 1 30); do
curl -fsS http://localhost:3000/health -o health.json && break
sleep 2
done
docker logs micopay-smoke
cat health.json
grep -q '"status":"ok"' health.json
curl -fsS http://localhost:3000/.well-known/assetlinks.json > /dev/null

- name: Limpieza
if: always()
run: docker rm -f micopay-smoke || true
56 changes: 56 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
# Changelog

All notable changes to MicoPay are documented here going forward, per
[Keep a Changelog](https://keepachangelog.com/en/1.1.0/). This file starts
from the pre-mainnet audit (2026-07-01) — see `git log` for the full history
before that point.

## [Unreleased]

### Security
- `POST /users/register` now requires a signed challenge (same SEP-10-style
flow already used by login), closing an address-squatting gap where anyone
could register another user's public Stellar address before they did.
- `PATCH /users/me/availability`, and auth applied to all fund-moving
`/defi/*` routes (`cetes/buy`, `cetes/sell`, `blend/supply`,
`blend/borrow`), which were previously callable without a token.
- `/defi/ramp/order/:orderId` and its `regenerate_tx` sibling now verify the
caller created the order (new `ramp_orders` ownership table) instead of
allowing any authenticated user to poll any order.
- Production boot now refuses to start with a weak/default `JWT_SECRET`,
`MOCK_STELLAR=true`, or a malformed `SECRET_ENCRYPTION_KEY`.

### Fixed
- Cancelling a `locked`/`revealing` trade now has a real path to recover the
on-chain funds: either participant can trigger a refund once the
contract's timeout passes, and a background sweep does it automatically
every 5 minutes without requiring any user action.
- SPEI (CETES onramp/offramp) quote/order flow, broken by a frontend/backend
payload mismatch, now works end-to-end.
- KYC start/status calls, previously sent without an auth token and always
rejected, now authenticate correctly.
- The deposit flow's QR code was a hardcoded stock image — it now encodes
the real trade for the agent to scan.
- The 401 session-expiry handler was clearing the wrong local storage key,
leaving orphaned sessions behind.
- `GET /trades/history` no longer loads every user in the database to
resolve counterparty usernames — replaced with a SQL join and
server-side pagination.

### Added
- `GET /rate/usdc-mxn`, mirroring the existing `/rate/xlm-mxn` multi-source
live rate endpoint, so screens showing USDC-MXN conversions stop using a
hardcoded `17.5`.
- `POST /client-errors` is now actually registered (the route existed but
was never wired up, so client crash reports were silently dropped).

### Removed
- CETES buy/sell and Blend supply/borrow are hidden behind
`VITE_ENABLE_DEFI_TRADING` until they're implemented against the user's
own wallet instead of the platform account.
- Dead code: an `updateMerchantReputation` function that wrote to a
`merchants` table that doesn't exist in this schema (silently caught and
logged on every completed trade).

See `docs/AUDIT_MOBILE_MAINNET.md` for the full pre-mainnet audit, findings,
and remaining open items.
26 changes: 26 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# AWS Guidance

- Prefer the AWS MCP Server for AWS interactions — it provides sandboxed
execution, observability, and audit logging. If unavailable, use the
AWS CLI directly.
- Before starting a task, check whether a relevant AWS skill is available.
Load the skill with `retrieve_skill` and prefer its guidance over
general knowledge.
- When uncertain about specific AWS details (API parameters, permissions,
limits, error codes), verify against documentation rather than guessing.
State uncertainty explicitly if you cannot confirm.
- When creating infrastructure, prefer infrastructure-as-code (AWS CDK or
CloudFormation) over direct CLI commands.
- When working with infrastructure, follow AWS Well-Architected Framework
principles.
- Do not use em dashes in AWS resource names or descriptions. Use
hyphens instead.

## Secret Safety

- MUST load the `aws-secrets-manager` skill first for any secret,
credential, API key, token, or password task. MUST NOT call
`secretsmanager get-secret-value` or `batch-get-secret-value`, and MUST
NOT hit the Secrets Manager Agent daemon directly. MUST use
`{{resolve:secretsmanager:secret-id:SecretString:json-key}}` with
`asm-exec` so the secret resolves at runtime without entering context.
Loading