194 lines
6.7 KiB
Markdown
194 lines
6.7 KiB
Markdown
아래는 **"스프링부트 웹플럭스 시리즈"**의 **6장: 리액티브 데이터베이스 연동"**에 대한 초안입니다. MariaDB를 예시로 사용하며, R2DBC를 통해 리액티브 방식으로 연동합니다. 설정은 `application.yaml`을 사용하고, 간단한 실습 코드를 포함했습니다. 초보자도 따라 할 수 있도록 단계별로 설명하며 친근한 문체를 유지했습니다.
|
|
|
|
---
|
|
|
|
## 6. 리액티브 데이터베이스 연동
|
|
|
|
이제 웹플럭스의 리액티브 특성을 데이터베이스와 연결해볼 시간입니다. 이번 장에서는 MariaDB를 리액티브하게 다루는 방법을 배워보겠습니다. 전통적인 JDBC 대신 R2DBC(Reactive Relational Database Connectivity)를 사용하며, 설정은 `application.yaml`로 깔끔하게 정리하겠습니다. 데이터 조회와 저장 예제도 함께 해보며 실습을 진행할게요. 준비되셨죠?
|
|
|
|
### R2DBC와 리액티브 리포지토리 설정
|
|
|
|
R2DBC는 관계형 데이터베이스를 비동기/논블로킹 방식으로 접근하게 해주는 드라이버입니다. 웹플럭스와 찰떡궁합이죠. 먼저, MariaDB와 R2DBC를 사용하기 위해 Gradle에 의존성을 추가합니다. `build.gradle`에 아래를 추가하세요:
|
|
|
|
```gradle
|
|
dependencies {
|
|
implementation 'org.springframework.boot:spring-boot-starter-data-r2dbc'
|
|
implementation 'io.r2dbc:r2dbc-mariadb:1.1.3'
|
|
runtimeOnly 'org.mariadb.jdbc:mariadb-java-client'
|
|
}
|
|
```
|
|
|
|
- `spring-boot-starter-data-r2dbc`: R2DBC와 스프링 데이터 통합을 위한 스타터.
|
|
- `r2dbc-mariadb`: MariaDB용 R2DBC 드라이버.
|
|
|
|
의존성을 추가한 뒤, `./gradlew build`로 빌드해줍니다.
|
|
|
|
다음으로, `application.yaml`을 설정합니다. `src/main/resources`에 `application.yaml` 파일을 만들고 아래 내용을 입력하세요:
|
|
|
|
```yaml
|
|
spring:
|
|
r2dbc:
|
|
url: r2dbc:mariadb://localhost:3306/webflux_db
|
|
username: root
|
|
password: yourpassword
|
|
data:
|
|
r2dbc:
|
|
repositories:
|
|
enabled: true
|
|
```
|
|
|
|
- `url`: MariaDB 데이터베이스 연결 정보 (예: `webflux_db`라는 데이터베이스 사용).
|
|
- `username`, `password`: MariaDB 접속 계정 정보 (환경에 맞게 수정하세요).
|
|
|
|
MariaDB에 `webflux_db` 데이터베이스를 미리 만들어야 합니다. MariaDB 클라이언트에서 다음 명령어를 실행하세요:
|
|
|
|
```sql
|
|
CREATE DATABASE webflux_db;
|
|
```
|
|
|
|
### MariaDB와의 연동 예제
|
|
|
|
이제 간단한 사용자(User) 데이터를 저장하고 조회하는 예제를 만들어보겠습니다. 먼저, 테이블을 생성합니다. MariaDB에서 아래 SQL을 실행하세요:
|
|
|
|
```sql
|
|
USE webflux_db;
|
|
CREATE TABLE users (
|
|
id BIGINT AUTO_INCREMENT PRIMARY KEY,
|
|
name VARCHAR(255) NOT NULL,
|
|
email VARCHAR(255) NOT NULL
|
|
);
|
|
```
|
|
|
|
#### 엔티티 클래스 작성
|
|
|
|
`src/main/java/com/example/demo`에 `User` 클래스를 추가합니다:
|
|
|
|
```java
|
|
package com.example.demo;
|
|
|
|
import lombok.Data;
|
|
import org.springframework.data.annotation.Id;
|
|
|
|
@Data
|
|
public class User {
|
|
@Id
|
|
private Long id;
|
|
private String name;
|
|
private String email;
|
|
}
|
|
```
|
|
|
|
- `@Id`: 기본 키를 나타냅니다.
|
|
- `@Data`: Lombok으로 getter/setter 등을 자동 생성.
|
|
|
|
#### 리포지토리 인터페이스 생성
|
|
|
|
`src/main/java/com/example/demo`에 `UserRepository` 인터페이스를 만듭니다:
|
|
|
|
```java
|
|
package com.example.demo;
|
|
|
|
import org.springframework.data.r2dbc.repository.R2dbcRepository;
|
|
import reactor.core.publisher.Mono;
|
|
|
|
public interface UserRepository extends R2dbcRepository<User, Long> {
|
|
Mono<User> findByEmail(String email);
|
|
}
|
|
```
|
|
|
|
- `R2dbcRepository`: 리액티브 CRUD 작업을 지원.
|
|
- `findByEmail`: 이메일로 사용자 조회 메서드 추가.
|
|
|
|
#### 데이터 저장 및 조회 실습
|
|
|
|
컨트롤러를 만들어 데이터를 다뤄봅시다. `src/main/java/com/example/demo`에 `UserController`를 추가합니다:
|
|
|
|
```java
|
|
package com.example.demo;
|
|
|
|
import org.springframework.web.bind.annotation.*;
|
|
import reactor.core.publisher.Flux;
|
|
import reactor.core.publisher.Mono;
|
|
|
|
@RestController
|
|
@RequestMapping("/users")
|
|
public class UserController {
|
|
|
|
private final UserRepository userRepository;
|
|
|
|
public UserController(UserRepository userRepository) {
|
|
this.userRepository = userRepository;
|
|
}
|
|
|
|
@PostMapping
|
|
public Mono<User> createUser(@RequestBody User user) {
|
|
return userRepository.save(user);
|
|
}
|
|
|
|
@GetMapping("/{id}")
|
|
public Mono<User> getUserById(@PathVariable Long id) {
|
|
return userRepository.findById(id);
|
|
}
|
|
|
|
@GetMapping("/email/{email}")
|
|
public Mono<User> getUserByEmail(@PathVariable String email) {
|
|
return userRepository.findByEmail(email);
|
|
}
|
|
|
|
@GetMapping
|
|
public Flux<User> getAllUsers() {
|
|
return userRepository.findAll();
|
|
}
|
|
}
|
|
```
|
|
|
|
- `createUser`: 새 사용자를 저장.
|
|
- `getUserById`: ID로 사용자 조회.
|
|
- `getUserByEmail`: 이메일로 사용자 조회.
|
|
- `getAllUsers`: 모든 사용자 목록 반환.
|
|
|
|
#### 테스트해보기
|
|
|
|
애플리케이션을 실행한 뒤, Postman이나 curl로 테스트해봅시다.
|
|
|
|
1. **사용자 추가**:
|
|
```
|
|
POST http://localhost:8080/users
|
|
Content-Type: application/json
|
|
{"name": "Alice", "email": "alice@example.com"}
|
|
```
|
|
응답으로 저장된 사용자 객체가 반환됩니다.
|
|
|
|
2. **사용자 조회 (ID)**:
|
|
```
|
|
GET http://localhost:8080/users/1
|
|
```
|
|
ID가 1인 사용자가 반환됩니다.
|
|
|
|
3. **사용자 조회 (이메일)**:
|
|
```
|
|
GET http://localhost:8080/users/email/alice@example.com
|
|
```
|
|
이메일로 조회한 결과가 나옵니다.
|
|
|
|
4. **모든 사용자 조회**:
|
|
```
|
|
GET http://localhost:8080/users
|
|
```
|
|
저장된 모든 사용자가 리스트로 표시됩니다.
|
|
|
|
### 잠깐 정리
|
|
|
|
- **R2DBC**: MariaDB를 리액티브하게 연결.
|
|
- **`application.yaml`**: 간단한 설정으로 데이터베이스 연결 완료.
|
|
- **리포지토리**: 비동기 CRUD 작업을 쉽게 처리.
|
|
|
|
이 과정에서 `Mono`와 `Flux`가 데이터베이스 작업에 자연스럽게 녹아든 걸 느끼셨을 겁니다. 전통적인 JDBC와 달리 스레드가 블록되지 않아 더 많은 요청을 효율적으로 처리할 수 있죠.
|
|
|
|
### 마무리
|
|
|
|
MariaDB와의 리액티브 연동을 성공적으로 해냈습니다! 데이터베이스 작업이 웹플럭스의 비동기 흐름과 어떻게 맞물리는지 실감 나셨나요? 다음 장에서는 이 데이터를 기반으로 REST API를 설계하며, 실무에서 더 유용한 기능을 추가해보겠습니다. 이번 실습이 재미있으셨길 바랍니다!
|
|
|
|
---
|
|
|
|
이 장은 MariaDB와 R2DBC를 활용한 실습 중심으로 구성했으며, `application.yaml` 설정과 간단한 코드를 포함했습니다. 추가 예제나 수정이 필요하면 말씀해주세요! |