SpringBoot Fundamentals
Getting Started with SpringBoot
Project Initialization
SpringBoot simplifies the setup of Spring applications by providing an auto-configuration approach. To create a new SpringBoot project:
- Use Spring Initializr to generate a project structure
- Select appropriate dependencies (Spring Web for web applications)
- Configure project metadata (group, artifact, name, etc.)
- Set Java version to 8 or higher
Basic Application Structure
The main application class serves as the entry point:
@SpringBootApplication
public class ApplicationRunner {
public static void main(String[] args) {
SpringApplication.run(ApplicationRunner.class, args);
}
}
Creating a REST Controller
@RestController
@RequestMapping("/api/items")
public class ItemController {
@GetMapping("/{itemId}")
public ResponseEntity<String> retrieveItem(@PathVariable Integer itemId) {
System.out.println("Requested item ID: " + itemId);
return ResponseEntity.ok("Item retrieved successfully");
}
}
Understanding SpringBoot's Core Features
Dependency Management
SpringBoot uses parent POM to manage dependancy versions:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.7.8</version>
</parent>
Web Server Configuration
By default, SpringBoot uses Tomcat as the embedded server. To switch to Jetty:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jetty</artifactId>
</dependency>
Configuration Management
Configuration File Types
SpringBoot supports multiple configuration file formats with the following priority order:
- application.properties
- application.yml
- application.yaml
YAML Configuration Syntax
YAML provides a human-readable format for configuration data:
# Application settings
app:
name: inventory-system
version: 1.0.0
debug: false
# Server configuration
server:
port: 8080
servlet:
context-path: /inventory
# Database settings
database:
host: localhost
port: 3306
name: inventory_db
credentials:
username: admin
password: secret123
connection-pool:
initial-size: 5
max-size: 20
Reading Configuration Values
Using @Value Annotation
@RestController
public class ConfigController {
@Value("${app.name}")
private String applicationName;
@Value("${database.port}")
private Integer dbPort;
@GetMapping("/config")
public String getConfigInfo() {
return "App: " + applicationName + ", DB Port: " + dbPort;
}
}
Using Environment Object
@RestController
public class ConfigController {
@Autowired
private Environment environment;
@GetMapping("/all-config")
public Map<String, Object> getAllConfig() {
Map<String, Object> configMap = new HashMap<>();
configMap.put("app.name", environment.getProperty("app.name"));
configMap.put("server.port", environment.getProperty("server.port"));
return configMap;
}
}
Configuraton Properties Binding
@Component
@ConfigurationProperties(prefix = "database")
public class DatabaseSettings {
private String host;
private int port;
private String name;
private Credentials credentials;
private ConnectionPool connectionPool;
// Getters and Setters
}
@RestController
public class ConfigController {
@Autowired
private DatabaseSettings dbSettings;
@GetMapping("/db-config")
public DatabaseSettings getDbConfig() {
return dbSettings;
}
}
Multi-Environment Configuration
Using YAML Profiles
# Common configuration
app:
name: inventory-system
version: 1.0.0
---
# Development profile
spring:
profiles: dev
server:
port: 8080
database:
host: dev-db.example.com
---
# Production profile
spring:
profiles: prod
server:
port: 80
database:
host: prod-db.example.com
Using Properties Files
Create separate files for different environments:
- application-dev.properties
- application-prod.properties
Specify the active profile in application.properties:
spring.profiles.active=dev
Testing with SpringBoot
Unit Testing Setup
@SpringBootTest
public class InventoryServiceTest {
@Autowired
private InventoryService inventoryService;
@Test
public void testItemRetrieval() {
Item item = inventoryService.getItemById(1);
assertNotNull(item);
assertEquals("Sample Item", item.getName());
}
}
Database Integration with MyBatis
Project Dependencies
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-mybatis</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
Database Configuration
spring:
datasource:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/inventory_db?useSSL=false&serverTimezone=UTC
username: root
password: password
type: com.alibaba.druid.pool.DruidDataSource
Data Access Object
@Mapper
public interface ItemRepository {
@Select("SELECT * FROM items WHERE id = #{id}")
Item findById(Long id);
@Insert("INSERT INTO items(name, category, price) VALUES(#{name}, #{category}, #{price})")
@Options(useGeneratedKeys = true, keyProperty = "id")
void save(Item item);
@Update("UPDATE items SET name = #{name}, category = #{category}, price = #{price} WHERE id = #{id}")
void update(Item item);
@Delete("DELETE FROM items WHERE id = #{id}")
void deleteById(Long id);
}
Service Layer
@Service
public class ItemServiceImpl implements ItemService {
private final ItemRepository itemRepository;
@Autowired
public ItemServiceImpl(ItemRepository itemRepository) {
this.itemRepository = itemRepository;
}
@Override
public Item getItemById(Long id) {
return itemRepository.findById(id);
}
@Override
public Item createItem(Item item) {
itemRepository.save(item);
return item;
}
}
Complete SSM Integration Example
Project Structure
- Controller: Handles HTTP requests
- Service: Contains business logic
- Repository: Manages database operations
- Model: Data entities
- Config: Configuration classes
Controller Implementation
@RestController
@RequestMapping("/api/items")
public class ItemController {
private final ItemService itemService;
@Autowired
public ItemController(ItemService itemService) {
this.itemService = itemService;
}
@GetMapping("/{id}")
public ResponseEntity<Item> getItem(@PathVariable Long id) {
Item item = itemService.getItemById(id);
if (item != null) {
return ResponseEntity.ok(item);
}
return ResponseEntity.notFound().build();
}
@PostMapping
public ResponseEntity<Item> createItem(@RequestBody Item item) {
Item createdItem = itemService.createItem(item);
return ResponseEntity.status(HttpStatus.CREATED).body(createdItem);
}
}
Service Implementation
@Service
public class ItemServiceImpl implements ItemService {
private final ItemRepository itemRepository;
@Autowired
public ItemServiceImpl(ItemRepository itemRepository) {
this.itemRepository = itemRepository;
}
@Override
public Item getItemById(Long id) {
return itemRepository.findById(id);
}
@Override
public Item createItem(Item item) {
// Business logic validation
if (item.getPrice() == null || item.getPrice().compareTo(BigDecimal.ZERO) < 0) {
throw new IllegalArgumentException("Price must be positive");
}
itemRepository.save(item);
return item;
}
}
Repository Implementation
@Mapper
public interface ItemRepository {
@Select("SELECT * FROM items WHERE id = #{id}")
Item findById(Long id);
@Insert("INSERT INTO items(name, category, price) VALUES(#{name}, #{category}, #{price})")
@Options(useGeneratedKeys = true, keyProperty = "id")
void save(Item item);
}
Configuration Setup
SpringBoot eliminates the need for extensive configuration files. The application is configured through:
- application.yml for basic settings
- @ConfigurationProperties for custom configuration
- Conditional beans for environment-specific settings
Static Resources
Place static resources in the src/main/resources/static directory:
- CSS, JavaScript, images
- HTML templates
Running the Application
To run the application:
- Use the main ApplicationRunner class
- Package as a JAR with Maven: mvn clean package
- Run the JAR file: java -jar your-application.jar
For different environments, specify the profile:
java -jar your-application.jar --spring.profiles.active=prod