Money transactions service

24 Oct 2020

Hello! Today I'm going to share experience of development simple money transactions service. This service is not ready for production usage. I created similar service as a software engineer test assignment. There were such requirements:

  • Implement a backend application that would allow users to transfer funds between wallets.
  • Commission of 1.5% for each operation
  • Database should be populated with sample data
  • The system should support two currency: BTC and ETH
  • Create a REST endpoint that can be used to transfer funds
  • Provide a docker-compose configuration

It wasn't described in requirements, but recommended implementing tests. All this task was estimated for 3-4 hours. Finally, it took about 8 hours for me.

General

Project built with Symfony 5.1 using Doctrine, FOSRestBundle and PHPUnit.

I created 3 entities Wallet, Transaction, User. Transaction has source and destination wallets. Wallet attached to user. User can have several wallets. Currency specified for the wallet and transaction. Currencies should match for them. Database schema looks like that:

https://dbdiagram.io/d/5f45434e7b2e2f40e9deb90a

Currencies and commissions values are stored in Enum.

REST API Implemented with FOSRestBundle. TransactionRequest is used for requests handling. Incoming transactions handled with TransactionController and TransactionCreator. ValidationErrorResponse and ExceptionListener used for displaying errors in a beautiful format.

Authorization of users works with login and password. I thought to use bearer tokens, but decided to skip it for this project. Authorization built using EventSubscriber mechanism.

Sample data

Sample data can be created with console command. Probably, it would be better to use fixtures, but it requires additional actions and configuration. Finally, I decided to use console command.

Tests

Implemented test for transactions creation.

Positive cases:

Negative cases:

Docker

I prepared Docker configuration based on this tutorial. Docker compose includes nginx, php-fpm and mysql containers.

Install

Project runs with Docker. Need to clone repository, run docker-compose, then load sample data.

git clone https://github.com/antonshell/money-transactions-service.git
cd money-transactions-service
docker-compose up
docker-compose exec php-fpm php bin/console sample-data:load

Usage

1 . There is health check request:

curl --request GET \
  --url http://127.0.0.1:18680/

2 . Create transaction from user #1 to user #2:

curl --request POST \
  --url http://127.0.0.1:18680/transaction \
  --header 'content-type: application/json' \
  --header 'password: user1' \
  --header 'username: user1@test.com' \
  --data '{
    "source": 1,
    "destination": 3,
    "amount": 1
}'

3 . From user #2 to user #1:

curl --request POST \
  --url http://127.0.0.1:18680/transaction \
  --header 'content-type: application/json' \
  --header 'password: user2' \
  --header 'username: user2@test.com' \
  --data '{
    "source": 3,
    "destination": 1,
    "amount": 1
}'

4 . List of users and wallets. In real project this method should be available for admin only.

curl --request GET \
  --url http://127.0.0.1:18680/dashboard

Project available on github. That's all for today. Thank you for your attention!