Skip to content

Commit f0948a2

Browse files
committed
feat: ability to retrieve a single vehicle
1 parent 9c419b5 commit f0948a2

File tree

3 files changed

+194
-0
lines changed

3 files changed

+194
-0
lines changed

src/main/kotlin/com/ctrlhub/core/assets/vehicles/VehiclesRouter.kt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,14 @@ class VehiclesRouter(httpClient: HttpClient) : Router(httpClient) {
5353
): List<Vehicle> {
5454
return fetchJsonApiResources("/v3/orgs/$organisationId/assets/vehicles", requestParameters.toMap())
5555
}
56+
57+
suspend fun one(
58+
organisationId: String,
59+
vehicleId: String,
60+
requestParameters: VehicleRequestParameters = VehicleRequestParameters()
61+
): Vehicle {
62+
return fetchJsonApiResource("/v3/orgs/$organisationId/assets/vehicles/$vehicleId", requestParameters.toMap())
63+
}
5664
}
5765

5866
val Api.vehicles: VehiclesRouter

src/test/kotlin/com/ctrlhub/core/assets/vehicles/VehiclesRouterTest.kt

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,28 @@ class VehiclesRouterTest {
3939
}
4040
}
4141

42+
@Test
43+
fun `can retrieve one vehicle`() {
44+
val jsonFilePath = Paths.get("src/test/resources/assets/vehicles/one-vehicle-response.json")
45+
val jsonContent = Files.readString(jsonFilePath)
46+
47+
val mockEngine = MockEngine { request ->
48+
respond(
49+
content = jsonContent,
50+
status = HttpStatusCode.OK,
51+
headers = headersOf(HttpHeaders.ContentType, "application/json")
52+
)
53+
}
54+
55+
val vehiclesRouter = VehiclesRouter(httpClient = HttpClient(mockEngine).configureForTest())
56+
57+
runBlocking {
58+
val response = vehiclesRouter.one(organisationId = "123", vehicleId = "123")
59+
assertIs<Vehicle>(response)
60+
assertNotNull(response.id)
61+
}
62+
}
63+
4264
@Test
4365
fun `can retrieve all vehicles with includes`() {
4466
val jsonFilePath = Paths.get("src/test/resources/assets/vehicles/all-vehicles-response-with-includes.json")
Lines changed: 164 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,164 @@
1+
{
2+
"data": {
3+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
4+
"type": "vehicles",
5+
"attributes": {
6+
"colour": "grey",
7+
"description": null,
8+
"registration": "XXXXXXX",
9+
"status": "active",
10+
"vin": null
11+
},
12+
"relationships": {
13+
"assignee": {
14+
"data": {
15+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
16+
"type": "users"
17+
}
18+
},
19+
"equipment": {
20+
"data": []
21+
},
22+
"specification": {
23+
"data": {
24+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
25+
"type": "vehicle-specifications"
26+
}
27+
}
28+
},
29+
"meta": {
30+
"counts": {
31+
"equipment": 0
32+
},
33+
"created_at": "2025-02-06T15:39:00Z",
34+
"modified_at": "2025-02-06T15:39:00Z",
35+
"sorn": false,
36+
"mot": {
37+
"is_valid": true,
38+
"records": 7,
39+
"last": {
40+
"at": "2024-07-30T11:45:46Z",
41+
"id": "xxxxxxxxxxxx"
42+
}
43+
},
44+
"tax": {
45+
"is_valid": true,
46+
"due": "2025-10-01"
47+
},
48+
"last_odometer_reading": 43595,
49+
"checks": {
50+
"inventory": {
51+
"count": 0,
52+
"last": {
53+
"at": null,
54+
"id": ""
55+
}
56+
},
57+
"inspection": {
58+
"count": 0,
59+
"last": {
60+
"at": null,
61+
"id": ""
62+
}
63+
}
64+
},
65+
"dvla": {
66+
"mot": {
67+
"exists": true,
68+
"data": {
69+
"make": "REDACTED",
70+
"model": "REDACTED",
71+
"first_used": "2017-03-31T00:00:00Z",
72+
"fuel_type": "Diesel",
73+
"colour": "Grey",
74+
"registration_date": "2017-03-31T00:00:00Z",
75+
"manufacture_date": "2017-03-31T00:00:00Z",
76+
"engine_size": "1499",
77+
"has_outstanding_recall": "unknown"
78+
},
79+
"last_sync": "2025-02-11T16:00:12.384Z"
80+
},
81+
"ves": {
82+
"exists": true,
83+
"data": {
84+
"art_end_date": "",
85+
"co2_emissions": 94,
86+
"colour": "GREY",
87+
"date_of_last_v5c_issued": "2022-09-30",
88+
"engine_capacity": 1499,
89+
"euro_status": "",
90+
"fuel_type": "DIESEL",
91+
"make": "REDACTED",
92+
"marked_for_export": false,
93+
"month_of_first_registration": "2017-03",
94+
"mot_status": "Valid",
95+
"real_driving_emissions": "",
96+
"registration_number": "XXXXXXX",
97+
"revenue_weight": 1575,
98+
"tax_due_date": "2025-10-01",
99+
"tax_status": "Taxed",
100+
"type_approval": "M1",
101+
"wheelplan": "2 AXLE RIGID BODY",
102+
"year_of_manufacture": 2017
103+
},
104+
"last_sync": "2025-02-11T16:00:15.324Z"
105+
}
106+
}
107+
}
108+
},
109+
"meta": {},
110+
"jsonapi": {
111+
"version": "1.0",
112+
"meta": {}
113+
},
114+
"links": {
115+
"self": "https://api.example.com/v3/orgs/xxxxxx/assets/vehicles/xxxxxx?include=specification.model.manufacturer"
116+
},
117+
"included": [
118+
{
119+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
120+
"type": "vehicle-specifications",
121+
"attributes": {
122+
"documentation": [],
123+
"emissions": 94,
124+
"engine_capacity": 1499,
125+
"fuel_type": "diesel",
126+
"wheelplan": "2 AXLE RIGID BODY",
127+
"year": 2017
128+
},
129+
"relationships": {
130+
"model": {
131+
"data": {
132+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
133+
"type": "vehicle-models"
134+
}
135+
}
136+
}
137+
},
138+
{
139+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
140+
"type": "vehicle-models",
141+
"attributes": {
142+
"name": "REDACTED"
143+
},
144+
"relationships": {
145+
"categories": {
146+
"data": []
147+
},
148+
"manufacturer": {
149+
"data": {
150+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
151+
"type": "vehicle-manufacturers"
152+
}
153+
}
154+
}
155+
},
156+
{
157+
"id": "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
158+
"type": "vehicle-manufacturers",
159+
"attributes": {
160+
"name": "REDACTED"
161+
}
162+
}
163+
]
164+
}

0 commit comments

Comments
 (0)