#10 pin bowling API
-
Start a new game - ./api/new (POST)
-
Record a player's frame result - ./api/result/:gameId/:playerId (PATCH)
-
Fetch a player's current score and frame by frame history - ./api/score/:gameId/:playerId (GET)
-
Fetch the results/scores for a given game - ./api/history/:gameId (GET)
This has been implemented within Node.js
-
MongoDB - In this implementation the database name is tenpin and the collection is games
-
Node.js dependencies
$ yarn add
$ yarn test
Requires jest to be installed
The test includes 3 unit tests in an attempt to provide some confidence on the ten pin scoring calculation object Scoring
- Average Game
- Perfect Game
- Tragic Game
Also the testing suite includes 2 end-to-end tests
- Game Creation
- Game Simulation
The completion of the end-to-end tests will tear-down the test data
$ yarn start
The server will start on port 3900 as set within ./config/default.json
-
Header - Content-Type: application/json
-
Body - for 2 players
{ "1": "A. Player", "2": "B. Player2" }
- Body - for 1 player
{ "1": "A. Player" }
- Server response
{
"_id": "5cf64bfca7695f365b0b6b5f",
"players": [
{
"id": 1,
"name": "A. Player"
}
]
}
Where the value given under "_id" is the game's id.
-
URL: /api/result/5cf64bfca7695f365b0b6b5f/1
-
Where the first request parameter is the game's id 5cf64bfca7695f365b0b6b5f and the second request parameter is the player's id
-
Header - Content-Type: application/json
-
Body
{ "result": "3/" }
- Where the results for the first 9 frames may be entered in the pattern
/^[XxFf0-9-]{1}[Ff0-9-/]?$/
and the 10th frame takes the form
/^[XxFf0-9-]{1}[XxFf0-9-/]?[XxFf0-9-/]?$
-
"Ff0"- => The ball has missed one or more of the standing pins or has ended up in the gutter
-
"Xx" => A STRIKE
-
"/" => the second ball in the frame has knocked down the reming pins - SPARE
-
Server response
{
"_id": "5cf64bfca7695f365b0b6b5f",
"players": {
"id": 1,
"name": "A. Player"
},
"results": {
"id": 1,
"results": ["3/"]
}
}
-
URL: /api/score/5cf64bfca7695f365b0b6b5f/1
-
Server response
[{ "frameScore": 20, "runningTotal": 20, "status": "spare", "totalThrows": 2 }]
-
URL: /api/history/5cf64bfca7695f365b0b6b5f
-
Server response
-
The response is given in the format of the data structure as shown below
Each game is stored within it own document inside the games collection and has the following structure
{
"players": [
{
"id": 1,
"name": "A. Player"
}
],
"results": [
{
"id": 1,
"results": []
}
],
"scores": [
{
"id": 1,
"scores": []
}
],
"ballValues": [
{
"id": 1,
"ballValues": []
}
],
"_id": "hex * 24",
"__v": 0
}
Where "id" equates to a player and "_id" equates to a single game.
In the case of 2 players, each parent array - players results scores and ballValues will have 2 items. For example:
"players": [
{
"id": 1,
"name": "A. Player1"
},
{
"id": 2,
"name": "B. Player2"
}
]
The child arrays results scores and ballValues per player will build as the game progresses as shown in the following forms
"results":["3/","x","45","x","ff","7/","x","34","6/","2/x"]
"scores":[
{"frameScore": 20,"runningTotal": 20,"status": "spare","totalThrows": 2},
{"frameScore": 19,"runningTotal": 39,"status": "strike","totalThrows": 3},
{"frameScore": 9,"runningTotal": 48,"status": "open","totalThrows": 5},
{"frameScore": 10,"runningTotal": 58,"status": "strike","totalThrows": 6},
{"frameScore": 0,"runningTotal": 58,"status": "open","totalThrows": 8},
{"frameScore": 20,"runningTotal": 78,"status": "spare","totalThrows": 10},
{"frameScore": 17,"runningTotal": 95,"status": "strike","totalThrows": 11},
{"frameScore": 7,"runningTotal": 102,"status": "open","totalThrows": 13},
{"frameScore": 12,"runningTotal": 114,"status": "spare","totalThrows": 15},
{"frameScore": 20,"runningTotal": 134,"status": "tenthFrame","totalThrows": 18}
]
"ballValues": [3,7,10,4,5,10,0,0,7,3,10,3,4,6,4,2,8,10]