- Download and install Node.js (LTS recommended).
- Clone this repository locally. (
git clone git@github.com:westy92/fr-exercise.git
) - Navigate to this repository and run
npm i
to install dependencies. - Run
npm run build
to transpile the TypeScript source code into JavaScript. - Run
node dist/index.js
to start the web service. The defaultport
is3000
, but that can be changed by instead runningPORT=8080 node dist/index.js
with a port of your choosing.
- Run
npm run test
to run the unit test suite.
Adds a transaction for a specific payer and date.
Endpoint: POST /points/transaction
Body:
(All fields are required)
payer
- the name of the payerpoints
- the points valuetimestamp
- the timestamp the transaction occurred
Example Request Body:
{
"payer": "DANNON",
"points": 1000,
"timestamp": "2020-11-02T14:00:00Z"
}
Example Response Body:
(none)
Notes:
points
cannot be 0.- A user's total
points
cannot go negative.
Possible Responses:
Status Code | Error Message |
---|---|
201 (Created) |
(none) |
400 (Bad Request) |
Points cannot be zero. |
400 (Bad Request) |
User points cannot go negative. |
Spend a user's points. The user's oldest points are deducted first.
Endpoint: POST /points/spend
Body:
(All fields are required)
points
- the points value
Example Request Body:
{
"points": 5000
}
The corresponding points that are deducted from each payer are returned.
Example Response Body:
[
{
"payer": "DANNON",
"points": -100
},
{
"payer": "UNILEVER",
"points": -200
},
{
"payer": "MILLER COORS",
"points": -4700
},
]
Notes:
points
to spend must be greater than 0.- A user's total
points
cannot go negative.
Possible Responses:
Status Code | Error Message |
---|---|
200 (Ok) |
(none) |
400 (Bad Request) |
Points must be positive. |
400 (Bad Request) |
Not enough points available. |
Gets the user's points balances, separated by payer.
Endpoint: GET /points/balances
Body: Example Response Body:
{
"DANNON": 1000,
"UNILEVER": 0,
"MILLER COORS": 5300
}
Possible Responses:
Status Code | Error Message |
---|---|
200 (Ok) |
(none) |
Since the database and cache are in-memory, this endpoint provides an easy way to clear them for testing purposes. This endpoint should be removed once an actual database and cache are added. This endpoint should not be exposed in production.
Endpoint: DELETE /points/clear
Body: There is no request or response body.
Possible Responses:
Status Code | Error Message |
---|---|
200 (Ok) |
(none) |
- Add additional unit tests to test more complex scenarios and increase code coverage.
- Set up a continuous integration environment like GitHub Actions.
- Add input validation. Ensure points are integers, fields aren't missing, etc.
- Use an actual database and cache instead of application memory. Possible options are PostgreSQL and Redis, respectively.
- Add logging throughout the application. (winston is a popular choice.)
- Add user authentication and keep track of points on a per-user basis.
- Add rate limiting.
- Containerize this app with a Dockerfile, using
node:18-alpine
.