일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | |||||
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
- 페이코 추천인코드
- programmers
- php 프로그래밍 입문
- Flutter
- php 프로그래밍 입문 솔루션
- JAVA SPRING
- php 프로그래밍 입문 문제풀이
- php 프로그래밍 입문 예제
- 페이코 추천인
- Java
- 페이코 초대코드
- php 프로그래밍 입문 3판
- 자바
- SWEA
- 배열
- php
- 플러터
- php 프로그래밍 입문 연습문제
- 파이썬
- 스프링
- 한정 분기
- 백준
- spring
- 플러터 개발환경 설정
- C
- 자바 스프링
- C언어
- php 프로그래밍
- 최단 경로
- 페이코 친구코드
- Today
- Total
ImJay
[Java Spring] 1-19. 순수 JDBC 본문
[Java Spring] 1-19. 순수 JDBC
1. 이제 어플리케이션과 DB를 연동해서 어플리케이션에서 SQL 문을 작성하여 DB에 데이터를 저장해보는 작업을 수행해보자.
2. 주의! 이렇게 JDBC API로 직접 코딩하는 것은 15년 전의 이야기이다. 따라서 고대 개발자들이 이렇게 고생하고 살았구나 생각하고, 참고만 하며 넘어가자.
3. bundle.gradle dependencies 에 아래 코드를 추가하자.
implementation 'org.springframework.boot:spring-boot-starter-jdbc'
runtimeOnly 'com.h2database:h2'
4. src > resources > application.properties 에 해당 코드를 작성한다.
spring.datasoruce.url=jdbc:h2:~/test
spring.datasource.driver-class-name=org.h2.Driver
- url 은 H2 콘솔의 JDBC URL 이다.
5. 그리고 코끼리 버튼을 클릭한다.
6. 빌드가 정상적으로 되는지 확인한다.
7. 빌드에 성공했다면 연동에 성공한 것이다. 이제 어플리케이션을 통해 작업을 수행해보자.
src > main > java > repository > 새로 만들기 > java 클래스
8. JdbcMemberRepository 클래스 생성
9. 코드 작성
package hello.hellospring.repository;
import hello.hellospring.domain.Member;
import org.springframework.jdbc.datasource.DataSourceUtils;
import javax.sql.DataSource;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
public class JdbcMemberRepository implements MemberRepository {
private final DataSource dataSource;
public JdbcMemberRepository(DataSource dataSource) {
this.dataSource = dataSource;
}
@Override
public Member save(Member member) {
String sql = "insert into member(name) values(?)";
Connection conn = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
conn = getConnection();
pstmt = conn.prepareStatement(sql,
Statement.RETURN_GENERATED_KEYS);
pstmt.setString(1, member.getName());
pstmt.executeUpdate();
rs = pstmt.getGeneratedKeys();
if (rs.next()) {
member.setId(rs.getLong(1));
} else {
throw new SQLException("id 조회 실패");
}
return member;
} catch (Exception e) {
throw new IllegalStateException(e);
} finally {
close(conn, pstmt, rs);
}
}
@Override
public Optional<Member> findById(Long id) {
String sql = "select * from member where id = ?";
Connection conn = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
conn = getConnection();
pstmt = conn.prepareStatement(sql);
pstmt.setLong(1, id);
rs = pstmt.executeQuery();
if(rs.next()) {
Member member = new Member();
member.setId(rs.getLong("id"));
member.setName(rs.getString("name"));
return Optional.of(member);
} else {
return Optional.empty();
}
} catch (Exception e) {
throw new IllegalStateException(e);
} finally {
close(conn, pstmt, rs);
}
}
@Override
public List<Member> findAll() {
String sql = "select * from member";
Connection conn = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
conn = getConnection();
pstmt = conn.prepareStatement(sql);
rs = pstmt.executeQuery();
List<Member> members = new ArrayList<>();
while(rs.next()) {
Member member = new Member();
member.setId(rs.getLong("id"));
member.setName(rs.getString("name"));
members.add(member);
}
return members;
} catch (Exception e) {
throw new IllegalStateException(e);
} finally {
close(conn, pstmt, rs);
}
}
@Override
public Optional<Member> findByName(String name) {
String sql = "select * from member where name = ?";
Connection conn = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
try {
conn = getConnection();
pstmt = conn.prepareStatement(sql);
pstmt.setString(1, name);
rs = pstmt.executeQuery();
if(rs.next()) {
Member member = new Member();
member.setId(rs.getLong("id"));
member.setName(rs.getString("name"));
return Optional.of(member);
}
return Optional.empty();
} catch (Exception e) {
throw new IllegalStateException(e);
} finally {
close(conn, pstmt, rs);
}
}
private Connection getConnection() {
return DataSourceUtils.getConnection(dataSource);
}
private void close(Connection conn, PreparedStatement pstmt, ResultSet rs)
{
try {
if (rs != null) {
rs.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
try {
if (pstmt != null) {
pstmt.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
try {
if (conn != null) {
close(conn);
}
} catch (SQLException e) {
e.printStackTrace();
}
}
private void close(Connection conn) throws SQLException {
DataSourceUtils.releaseConnection(conn, dataSource);
}
}
- 데이터를 가져오려면 sql.DataSource 라이브러리가 필요하다.
10. SpringConfig 수정
package hello.hellospring;
import hello.hellospring.domain.Member;
import hello.hellospring.repository.JdbcMemberRepository;
import hello.hellospring.repository.MemberRepository;
import hello.hellospring.repository.MemoryMemberRepository;
import hello.hellospring.service.MemberService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.sql.DataSource;
@Configuration
public class SpringConfig {
private DataSource dataSource;
@Autowired
public SpringConfig(DataSource dataSource) {
this.dataSource = dataSource;
}
@Bean
public MemberService memberService() {
return new MemberService(memberRepository());
}
@Bean
public MemberRepository memberRepository() {
// return new MemoryMemberRepository();
return new JdbcMemberRepository(dataSource);
}
}
11. 빌드 후 회원 목록 확인
- 정상적으로 DB가 연동된 것을 확인할 수 있다.
12. H2 콘솔로 새로운 데이터를 추가해보자.
13. 다시 한번 회원목록을 확인해보자.
- 정상적으로 추가되었음을 확인할 수 있다.
14. 작동 원리
14-1. 현재 우리가 구성한 클래스는 다음과 같다.
14-2. 스프링 컨테이너에서는 우리가 반환해준 객체를 토대로 스프링에서 빈 등록을 교체했다.
- 스프링의 장점이 다른 걸 건들 필요 없이 간단하게 레포지토리만 변경하면 된다는 점이다.
15. 우리가 지금 사용한 객체지향 원리는 5원칙(SOLID) 중 OCP(개방 폐쇄 원칙 : 확장에는 열려있고, 변경에는 닫혀있다.)이다.
16. 스프링의 DI (Dependencies Injection)을 사용하면 기존 코드를 전혀 손대지 않고, 설정만으로 구현 클래스를 변경할 수 있다.
'Java Spring > 스프링 입문' 카테고리의 다른 글
[Java Spring] 1-21. JDBC Template (0) | 2023.01.30 |
---|---|
[Java Spring] 1-20. 스프링 통합 테스트 (0) | 2023.01.30 |
[Java Spring] 1-18. H2 데이터베이스 설치 (0) | 2023.01.30 |
[Java Spring] 1-17. 회원 웹 기능 - 조회 (0) | 2023.01.30 |
[Java Spring] 1-16. 화면 웹 기능 - 등록 (0) | 2023.01.30 |