Skip to main content

Web and Service Layers

Overview​

In this lab, you will:

  • Create a new Spring Boot project using Spring Initializr.
  • Build the controller and service layers of a basic REST API.
  • Implement a simple GET endpoint to list all items.
  • Plan and define additional endpoints for common CRUD operations.

This lab is the foundation of a growing application. You will connect the database later, but for now your service will return hardcoded or placeholder data.

If working with MongoDB later all ids should be of type String and not Long

Project Setup​

  • Use Spring Initializr
  • Group: com.neueda
  • Artifact/Name: item-api
  • Dependencies:
    • Spring Web
    • Spring Boot DevTools (optional)
  • Build Tool: Use your preferred tool (Maven or Gradle)

Folder Structure​

src/main/java/com/neueda/item-api/
├── controller
├── service
└── YourApplication.java

Step 1: Create Your Controller and Service Layers​

1. Create the Controller​

  • File: ItemController.java
  • Package: controller
  • Annotation: @RestController
  • Base Path: /items
  • Inject the service class
  • Implement a GET /items endpoint that returns a list of placeholder items (e.g., strings or simple item objects)
Click here to view the example solution
import java.util.List;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.neueda.service.ItemService;

@RestController
@RequestMapping("/items")
public class ItemController {

private final ItemService itemService;

public ItemController(ItemService itemService) {
this.itemService = itemService;
}

@GetMapping
public List<String> getItems() {
// This method would typically return a list of items.
return itemService.getAllItems();
}
}

2. Create the Service Layer​

  • File: ItemService.java (interface)
  • File: ItemServiceImpl.java (implementation)
  • Package: service
Click here to view the example solution
import java.util.List;

import org.springframework.stereotype.Service;

@Service
public class ItemService {

public List<String> getAllItems() {
// This method would typically interact with a repository to fetch items.
// For now, we return an empty list as a placeholder.
return List.of("Item1", "Item2", "Item3");
}
}

Test it: Run the application and visit http://localhost:8080/items to see the list.

Step 2: Add More Endpoints​

Now that the structure is in place:

Add support for the following HTTP operations and call the matching service method for each:

HTTP RoutePurposeSuggested Controller MethodService Method to Call
GET /items/{id}Get a single item by IDgetItemById(@PathVariable String id)ItemService.getItemById(String id)
POST /itemsAdd a new itemcreateItem(@RequestBody String item)ItemService.createItem(String item)
PUT /items/{id}Update part of an itemupdateItem(@PathVariable String id, @RequestBody String item)ItemService.updateItem(String id, String item)
DELETE /items/{id}Delete an itemdeleteItem(@PathVariable String id)ItemService.deleteItem(String id)

You must:

  • Define the appropriate controller functions in your ItemController class
  • Add these service method signatures to your service interface
  • Implement dummy logic in the service class (e.g., simulate item creation or return placeholder values)
  • Add matching methods in the controller and ensure each one calls the appropriate service method
  • At this point don't get too worried about the type of response from the controller method. It's enough at this stage to have the ItemService return String values.

Do NOT connect a database yet --- we will do that in a later section.

Complete ItemController (first implementation)​

Click here to view the example solution
import java.util.List;

import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.neueda.service.ItemService;

@RestController
@RequestMapping("/items")
public class ItemController {

private final ItemService itemService;

public ItemController(ItemService itemService) {
this.itemService = itemService;
}

@GetMapping
public List<String> getItems() {
// This method would typically return a list of items.
return itemService.getAllItems();
}

@GetMapping("/{id}")
public List<String> getItemById(@PathVariable String id) {
// This method would typically return a single item by its ID.
return itemService.getItemById(id);
}

@PostMapping
public List<String> createItem(@RequestBody String item) {
// This method would typically create a new item.
return itemService.createItem(item);
}

@PutMapping("/{id}")
public List<String> updateItem(@PathVariable String id, @RequestBody String item) {
// This method would typically update an existing item.
return itemService.updateItem(id, item);
}

@DeleteMapping("/{id}")
public List<String> deleteItem(@PathVariable String id) {
// This method would typically delete an item by its ID.
return itemService.deleteItem(id);
}
}

First ItemService (first implementation)​

Click here to view the example solution
import java.util.List;

import org.springframework.stereotype.Service;

@Service
public class ItemService {

public List<String> getAllItems() {
// This method would typically interact with a repository to fetch items.
// For now, we return an empty list as a placeholder.
return List.of("Item1", "Item2", "Item3");
}

public List<String> getItemById(String id) {
// This method would typically fetch a single item by its ID.
// For now, we return a placeholder list.
return List.of("Item with ID: " + id);
}

public List<String> createItem(String item) {
// This method would typically save a new item to the repository.
// For now, we return a placeholder list indicating the item was created.
return List.of("Created item: " + item);
}

public List<String> updateItem(String id, String item) {
// This method would typically update an existing item in the repository.
// For now, we return a placeholder list indicating the item was updated.
return List.of("Updated item with ID: " + id + " to " + item);
}

public List<String> deleteItem(String id) {
// This method would typically delete an item by its ID from the repository.
// For now, we return a placeholder list indicating the item was deleted.
return List.of("Deleted item with ID: " + id);
}
}