The task is to implement stopwatch React application satisfying functional requirements listed below. The applicant is provided with github repository containing minimal application framework and backend implementation providing REST API. Documentation for the API endpoints can be found in this document.
Base application framework has following tools preconfigured:
- React (with server-side rendering);
- React Router;
- Vanilla CSS (used via
import './path-to-css-file.css'
); - CSS-in-JS (via Emotion).
The applicant is free to choose any additional third-party modules if needed to complete the task. The applicant is free to use any other CSS-in-JS library instead of Emotion.
FLUKENESS
environment variable to control it if needed.
FLUKENESS=5 yarn start
It accepts integer in range from 0 to 100, where 0 is normally functioning API, 1 to 99 — slowed down (the higher number, the slower the API is) and 100 — not working API.
By default (if no environment variable provided — yarn start
) API behaviour is randomised.
- Application consists of two screens: list and single stopwatch view.
- Stopwatch list and each stopwatch state is preserved on BE.
- BE errors are handled gracefully (how errors are handled and presented is up to applicant)
- Active items are updated in realtime (i.e. showing current time since start).
- User is able to navigate to single stopwatch view by clicking desired item.
- User is not able to control any other properties of items in stopwatch list view.
- Items are paginated (3 per page).
- User is able to create new stopwatch.
- User is redirected to single stopwatch view after creation.
- Stopwatch is formatted as
<hours>:<minutes>:<seconds>.<milliseconds>
(i.e.00:02:26.081
) wherehours
,minutes
andseconds
is minimum two digits with preceding zero andmilliseconds
is minimum three digits with preceding zeroes. - User is able to pause stopwatch.
- User is able to unpause stopwatch.
- User is able to reset stopwatch.
- User is able to return to stopwatch list view (UI is up to applicant).
- User is able to remove stopwatch. (optional)
- User is redirected to stopwatch list view after removal.
- User is able to create “lap” mark. (optional)
- Shortest and longest laps are highlighted. (optional)
To start the app, intall dependencies and run npm start
or yarn start
. Server will start and listen on http://localhost:3000/
Solution to be implemented in src/app
folder, but you may edit any files if needed.
Environment comes with React, React Router and Emotion installed. You may also use *.css
files if needed by importing them in your components.
GET /api/stopwatches
POST /api/stopwatches
GET /api/stopwatches/:id
POST /api/stopwatches/:id
DELETE /api/stopwatches/:id
POST /api/stopwatches/:id/toggle
POST /api/stopwatches/:id/lap
__id
— database record unique ID.laps
— array of timestamps for lap marks.started
— timestamp for stopwatch start time.toggles
— array of timestamps when stopwatch was toggled (paused or restarted)
Returns paginated list of stopwatches.
Page number to fetch.
// curl /api/stopwatches?page=2
{
"meta": {
"currentPage": 2,
"totalPages": 2
},
"result": [
{
"__id": 3,
"laps": [
1587807696286
],
"started": 1587807510806,
"toggles": []
},
{
"__id": 2,
"laps": [],
"started": 1587807410626,
"toggles": [
1587807620331,
1587807760877,
1587807709934,
1587807785664
]
},
{
"__id": 1,
"laps": [],
"started": 1587807345496,
"toggles": [
1587807652309,
1587807686826
]
}
]
}
Create new stopwatch with given start time.
Timestamp (in milliseconds) of stopwatch start.
// curl -X POST -d '{ "started": 1587807686826 }' /api/stopwatches
{
"meta": {},
"result": {
"__id": 5,
"laps": [],
"started": 1587807345496,
"toggles": []
}
}
Returns single stopwatch.
Stopwatch ID to get.
// curl /api/stopwatches/1
{
"meta": {},
"result": {
"__id": 1,
"laps": [],
"started": 1587807345496,
"toggles": [
1587807652309,
1587807686826
]
}
}
Reset given stopwatch to given start time.
Stopwatch ID to reset.
Timestamp (in milliseconds) of stopwatch start.
// curl -X POST -d '{ "started": 1587807686826 }' /api/stopwatches/5
{
"meta": {},
"result": {
"__id": 5,
"laps": [],
"started": 1587807345496,
"toggles": []
}
}
Remove given stopwatch.
Stopwatch ID to remove.
Reponds with HTTP 204
on success.
Add toggle time for given stopwatch
Stopwatch ID to store toggle for.
Timestamp (in milliseconds) of stopwatch toggle.
// curl -X POST -d '{ "time": 1587807760877 }' /api/stopwatches/2/toggle
{
"meta": {},
"result": {
"__id": 2,
"laps": [],
"started": 1587807410626,
"toggles": [
1587807620331,
1587807760877
]
}
}
Add lap time for given stopwatch
Stopwatch ID to store lap for.
Timestamp (in milliseconds) of lap mark.
// curl -X POST -d '{ "time": 1587807760877 }' /api/stopwatches/2/lap
{
"meta": {},
"result": {
"__id": 2,
"laps": [
1587807760877
],
"started": 1587807410626,
"toggles": []
}
}