Skip to content

Bahati-Patrick/car-management

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

20 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Car Management & Fuel Tracking System

A Java application for managing cars and tracking fuel consumption, built with plain Java, embedded Jetty server, and manual servlet implementation.

Project Structure

car-management/
├── pom.xml (parent)
├── backend/
│   ├── pom.xml
│   └── src/main/java/com/codehills/carmanagement/
│       ├── Server.java (main class)
│       ├── domain/
│       │   ├── Car.java
│       │   ├── FuelEntry.java
│       │   └── FuelStats.java
│       ├── repository/
│       │   ├── CarRepository.java
│       │   └── FuelRepository.java
│       ├── service/
│       │   ├── CarService.java
│       │   └── FuelService.java
│       ├── servlet/
│       │   ├── CarServlet.java
│       │   ├── FuelServlet.java
│       │   └── FuelStatsServlet.java
│       ├── exception/
│       │   ├── CarNotFoundException.java
│       │   └── InvalidInputException.java
│       └── util/
│           ├── JsonUtil.java
│           └── ServiceLocator.java
└── cli/
    ├── pom.xml
    └── src/main/java/com/codehills/cli/
        ├── CarManagementCli.java
        ├── client/
        │   └── ApiClient.java
        └── parser/
            └── CommandParser.java

Prerequisites

  • Java 11 or higher
  • Maven 3.6 or higher

Building the Project

Build all modules:

mvn clean install

This will:

  • Compile all modules
  • Create executable JARs in backend/target/ and cli/target/

Running the Backend Server

Option 1: Using Executable JAR (Recommended)

After building, run:

cd backend
java -jar target/backend-1.0-SNAPSHOT.jar

The server will start on port 8080 by default. You can specify a custom port:

java -jar target/backend-1.0-SNAPSHOT.jar 9090

Option 2: Using Maven Exec Plugin

cd backend
mvn exec:java -Dexec.mainClass=com.codehills.carmanagement.Server

Running the CLI Client

Option 1: Using Executable JAR (Recommended)

After building, run:

cd cli
java -jar target/cli-1.0-SNAPSHOT.jar <command> [options]

Option 2: Using Maven Exec Plugin

cd cli
mvn exec:java -Dexec.mainClass=com.codehills.cli.CarManagementCli -Dexec.args="create-car --brand Toyota --model Corolla --year 2018"

CLI Commands

Create Car

create-car --brand <brand> --model <model> --year <year>

Example:

java -jar target/cli-1.0-SNAPSHOT.jar create-car --brand Toyota --model Corolla --year 2018

Add Fuel Entry

add-fuel --carId <id> --liters <liters> --price <price> --odometer <odometer>

Note: The price parameter represents the total cost for this fill-up, not price per liter.

Example:

java -jar target/cli-1.0-SNAPSHOT.jar add-fuel --carId 1 --liters 40 --price 50.0 --odometer 43125
java -jar target/cli-1.0-SNAPSHOT.jar add-fuel --carId 1 --liters 40 --price 52.5 --odometer 44000
java -jar target/cli-1.0-SNAPSHOT.jar add-fuel --carId 1 --liters 40 --price 52.5 --odometer 45000

Get Fuel Statistics

fuel-stats --carId <id>

Example:

java -jar target/cli-1.0-SNAPSHOT.jar fuel-stats --carId 1

Expected Output:

Total fuel: 120.0 L
Total cost: 155.00
Average consumption: 6.4 L/100km

REST API Endpoints

Create Car

POST /api/cars

Request Body:

{
  "brand": "Toyota",
  "model": "Corolla",
  "year": 2018
}

Response: 201 Created

{
  "id": 1,
  "brand": "Toyota",
  "model": "Corolla",
  "year": 2018
}

List All Cars

GET /api/cars

Response: 200 OK

[
  {
    "id": 1,
    "brand": "Toyota",
    "model": "Corolla",
    "year": 2018
  }
]

Add Fuel Entry

POST /api/cars/{id}/fuel

Request Body:

{
  "liters": 40,
  "price": 52.5,
  "odometer": 45000
}

Note: The price field represents the total cost for this fill-up, not price per liter.

Response: 201 Created

{
  "id": 1,
  "carId": 1,
  "liters": 40.0,
  "price": 52.5,
  "odometer": 45000,
  "timestamp": "2024-01-01T10:00:00"
}

Get Fuel Statistics

GET /api/cars/{id}/fuel/stats

Response: 200 OK

{
  "totalFuel": 120.0,
  "totalCost": 155.0,
  "averageConsumption": 6.4
}

Manual Servlet Endpoint

Get Fuel Statistics (Manual Servlet)

GET /servlet/fuel-stats?carId={id}

This endpoint demonstrates manual servlet implementation with:

  • Manual query parameter parsing
  • Explicit content type setting
  • Manual status code handling

Response: 200 OK

{
  "totalFuel": 120.0,
  "totalCost": 155.0,
  "averageConsumption": 6.4
}

Fuel Statistics Calculation

  • Total Fuel: Sum of all liters from fuel entries
  • Total Cost: Sum of all prices (total cost per fill-up)
  • Average Consumption: (Total Fuel / Total Distance) * 100 in L/100km
    • Requires at least 2 fuel entries
    • Total Distance = maxOdometer - minOdometer

Error Handling

The API returns appropriate HTTP status codes:

  • 200 OK: Successful GET request
  • 201 Created: Successful POST request
  • 400 Bad Request: Invalid input or validation error
  • 404 Not Found: Car not found
  • 500 Internal Server Error: Server error

Error responses follow this format:

{
  "error": "Error message",
  "status": 400
}

Technology Stack

  • Backend: Plain Java 11+ with embedded Jetty server
  • Dependencies:
    • Jetty Server & Servlet API (embedded)
    • Jackson (for JSON)
    • SLF4J + Logback (logging)
  • CLI: Plain Java with java.net.http.HttpClient
  • Build: Maven multi-module

Key Features

  • ✅ In-memory storage (thread-safe using ConcurrentHashMap)
  • ✅ Manual servlet implementation (demonstrates servlet lifecycle knowledge)
  • ✅ RESTful API endpoints
  • ✅ CLI client using HttpClient
  • ✅ Comprehensive error handling
  • ✅ Proper HTTP status codes
  • ✅ JSON serialization/deserialization

Testing

Test the Backend API

  1. Start the server:

    cd backend
    java -jar target/backend-1.0-SNAPSHOT.jar
  2. Create a car:

    curl -X POST http://localhost:8080/api/cars \
      -H "Content-Type: application/json" \
      -d '{"brand":"Toyota","model":"Corolla","year":2018}'
  3. Add fuel entries:

    curl -X POST http://localhost:8080/api/cars/1/fuel \
      -H "Content-Type: application/json" \
      -d '{"liters":40,"price":52.5,"odometer":45000}'
  4. Get fuel statistics:

    curl http://localhost:8080/api/cars/1/fuel/stats

Test the CLI

  1. Ensure the backend server is running

  2. Create a car:

    cd cli
    java -jar target/cli-1.0-SNAPSHOT.jar create-car --brand Toyota --model Corolla --year 2018
  3. Add fuel entries:

    java -jar target/cli-1.0-SNAPSHOT.jar add-fuel --carId 1 --liters 40 --price 52.5 --odometer 45000
  4. Get fuel statistics:

    java -jar target/cli-1.0-SNAPSHOT.jar fuel-stats --carId 1

Notes

  • The price field in fuel entries represents the total cost for the fill-up, not price per liter
  • Fuel consumption calculation requires at least 2 fuel entries
  • All data is stored in-memory and will be lost when the server stops
  • The server runs on port 8080 by default

License

This project is part of a technical assignment.

About

Car Management & Fuel Tracking System

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages