Skip to content

About

Coinly is a crypto exchange app. In simple words, it lets a person turn their normal money (USD) into crypto (like ETH), and also turn crypto back into normal money. To make this safe, people first log in, verify who they are, connect their crypto wallet, and then buy or sell.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Latest commit

 

History

24 Commits

Folders and files

Repository files navigation

Coinly

Coinly is a crypto exchange app. In simple words, it lets a person turn their normal money (USD) into crypto (like ETH), and also turn crypto back into normal money. To make this safe, people first log in, verify who they are, connect their crypto wallet, and then buy or sell.

This is a personal (pet) project, built mainly to learn and get hands-on experience with Web3 — things like smart contracts, wallets, and how a real app connects to the blockchain. It's not a production business, just a way to genuinely understand how these pieces fit together by actually building one.

Under the hood, this project has a few moving pieces working together:

  • A website (frontend) where people actually use the app.
  • A couple of backend services written in Go, which handle logins, user accounts, and the buy/sell logic.
  • Some smart contracts written in Solidity, which live on the blockchain and actually hold/move the crypto.

You don't need to understand blockchain deeply to run this project locally. Just follow the steps below.

1. Running the smart contracts locally (using Anvil)

Anvil is just a fake local blockchain that runs on your own computer, so you can test contracts without spending real money.

cd contracts

# install/build the contracts
forge build

# run the test suite (optional, but good to check everything still works)
forge test

# start a local blockchain in its own terminal window, and leave it running
anvil

Once Anvil is running, if you actually want to deploy the contracts to it (first time only), copy contracts/.env.example to contracts/.env, fill in the values, then run:

forge script script/Deploy.s.sol:Deploy --rpc-url http://localhost:8545 --broadcast

That's it — you now have a local blockchain with the contracts deployed on it.

2. Running the backend + frontend together with Docker

This is the easiest way to get the whole app (both backend services and the website) running together on your machine.

# from the root of the project
docker compose up -d --build

This starts Postgres, Redis, the two backend services (core-service and finance), and the frontend, all together.

⚠️ Before you run this, please set up your environment variables properly — otherwise things will not work.

Each service reads its settings from its own .env file, and these files are not committed to git (they hold real secrets like Auth0 and Stripe keys). You need to create them yourself:

  • backend/core-service/.env — copy from backend/core-service/.env.example
  • backend/finance/.env — copy from backend/finance/.env.example
  • frontend/.env.local — copy from frontend/.env.example

Fill in every value in those files (Auth0 credentials, Stripe keys, etc.) before starting Docker. If a .env file is missing or has empty/wrong values, the affected service will fail to start or will crash right after starting — so it's worth double-checking these files first.

Once everything is up, you can check that things are healthy:

curl http://localhost:8080/healthz   # core-service
curl http://localhost:8081/healthz   # finance

And the website itself will be available at http://localhost:5173.

System design

This project is being built as a set of small services (microservices) instead of one big service, so each piece can grow on its own. Some of these services already exist, and some are still just planned for later — this section covers the full picture.

Planned microservices:

  • core-service (Go) — the identity service. Owns user accounts and KYC status, and is the one place that actually checks if a login token is valid.
  • finance (Go) — the money/crypto service. Handles currencies, wallets, bank accounts, Stripe payments, and (soon) the actual buy/sell orders.
  • auth-service (Go, planned) — would take over authentication/token issuance and role-based permissions as a dedicated service.
  • notification-service (Go, planned) — would send emails/push notifications in the background (e.g. "your purchase is complete").
  • ai-intelligence-service (Python, planned) — an AI support agent that can answer user questions and raise support tickets on its own.

How they talk to each other:

  • For things that need an instant answer (like "is this user's login valid?"), services call each other directly and synchronously using gRPC.
  • For things that can happen a little later and shouldn't block the user (like "send a receipt email after a purchase"), services publish events to Kafka, and whichever service cares about that event picks it up whenever it's ready.
  • All services share one Postgres database for now (kept simple on purpose), and use Redis for caching and to make sure things like Stripe webhooks don't get processed twice.

How login works (Auth0):

  1. A user logs in through Auth0 on the frontend (this handles passwords, MFA, etc. — we don't build our own login system).
  2. Auth0 gives the frontend an access token.
  3. The frontend sends that token to whichever backend service it's calling.
  4. core-service is the only service that actually talks to Auth0 to verify a token is real and fetch who the user is.
  5. Every other service (like finance) doesn't re-check the token itself — it just asks core-service over gRPC, "is this token valid, and is this user allowed to do this?", and trusts the answer.

This way, login/identity logic lives in exactly one place, and every other service can stay simple.

flowchart LR
    User((User)) --> Frontend[Frontend - Next.js]
    Frontend -- login --> Auth0[(Auth0)]
    Frontend -- access token --> CoreService[core-service]
    Frontend --> Finance[finance]

    Finance -- "is this token valid?" --> CoreService
    CoreService -- verifies token --> Auth0

    CoreService --> Postgres[(Postgres)]
    CoreService --> Redis[(Redis)]
    Finance --> Postgres
    Finance --> Redis[(Redis)]
    Finance --> Contracts[Smart contracts on-chain]

    Finance -. events .-> Kafka[[Kafka]]
    Kafka -. events .-> Notification[notification-service]
    Kafka -. events .-> AI[ai-intelligence-service]
Loading

About

Coinly is a crypto exchange app. In simple words, it lets a person turn their normal money (USD) into crypto (like ETH), and also turn crypto back into normal money. To make this safe, people first log in, verify who they are, connect their crypto wallet, and then buy or sell.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages