This is an API for transfer money between two accounts using GOLang.
- Database Design(Used in-memory DS to mimic database)
account
table: id (int, PK), name (string), balance (decimal), created_at (timestamp), updated_at (timestamp).transaction
table: id (int, PK), from_account_id (int, FK -> account.id), to_account_id (int, FK -> account.id), amount (decimal), created_at (timestamp).
- Models
- Built Structs for
Account
andTransaction
corresponding to the database tables. - Expose Only interfaces instead of the actual structs.
- Data Store
- Mimic models and indices using DSA(Datastructures and Algorithms).
- Built
shardedMap
for more concurrency performance. - Handled concurrency (read and write locks)
- Services
- Splited bulks into chunks and assign goroutine to increase the performance.
- Used goroutine for inserting each element in chunk(As it now sharded).
- Handled Concurrent Transfering by
deadlock avoidance technique
.- always
sort
IDs of both accounts to ensure consistancy behavior and locking. - always lock the account with minimum ID value to avoid deadlock.
REF:
services/account.go:111
- always
- APIs
- Split the API into two resources
/accounts
and/transactions
. - Each one handle it's own flow.
- Wrote Integration tests for all endpoints.
- you can run it using
go test -v ./api/api_tests
- you can run the server using
go run main.go
- you can run it using
- Documented the API HERE
TODO:
- add getting transactions between two dates(Range Search) we can do that with 3 different options.
- AVL, Balanced BSTs.
- B-Trees.
- Interval trees.
- setting a monitoring service for the API (Performance and Error).
- Deactivate Accounts. As we could use the transactions' data history in training Ai Models to create a new AI-based features.
- Enhance data ingestion by using background jobs and queues.