일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
- 자바의 정석
- 멀티프로세싱
- 혼공얄코
- 입출력
- 자바의정석
- 달리기 경주 자바
- authenticationprovider 설정
- 캡슐화
- 객체지향
- hackerrank
- spring security
- 멀티태스킹
- over()
- 티스토리챌린지
- userdetailsservice 설정
- 공원 산책 자바
- SQL Mapper
- 리눅스
- 오버로딩
- java
- 개인정보 수집 유효기간 자바
- CPU
- 다형성
- 오버라이딩
- 바탕화면 정리 자바
- 로그인 핸들러 구현
- 오블완
- spring security 설정
- 프로그래머스
- 쿠키
- Today
- Total
쉽게 쉽게
[프로젝트 설정] XML과 Java Configuration 설정 방식 본문
▤ 목차
Spring 프로젝트에서 애플리케이션의 설정을 구현하는 방식은 XML과 Java Configuration이 있다.
이 둘의 장단점과 xml을 java configuration 방식으로 변환하는 방법을 알아보고자 한다.
1. XML 설정 (XML-based Configuration)
이 방식은 XML 파일 내에 태그를 사용하여 애플리케이션의 빈과 의존성을 선언한다.
<bean id="ExBean" class="com.example.ExClass">
<property name="name" value="bob" />
</bean>
1. 장점
- 수정 및 배포 용이: 설정이 Java 코드와 분리되어 있어, 설정 파일을 수정하더라도 애플리케이션 코드를 수정하지 않고도 배포가 가능하다.
- 코드와 분리된 설정: 코드가 아닌 XML 파일을 통해 설정을 관리하므로, 개발자 외에 다른 관리자도 설정 파일을 쉽게 수정할 수 있다. (중앙에서 관리하기 용이)
- 가독성이 좋음: XML 파일은 사람이 읽고 쓰기 쉬운 형태로 되어 있어, 구성 정보의 가독성이 높다. 이는 특히 애플리케이션의 구성이 복잡하지 않은 경우에 유리할 수 있다.
- 기존 프로젝트와의 호환성: Spring 2.x 이전부터 사용되던 방식으로, 레거시 시스템과의 호환성을 유지하는 데 유리하다.
2. 단점
- 빈약한 정보: XML은 모든 설정을 명시적으로 나타내야 하므로, 클래스를 지정하는 것도 상당히 번거롭다. 또한 XML은 단순 텍스트이기 때문에 해당 클래스가 다른 클래스와 어떤 관계를 갖는지 알 수 없다.
- 타입 안전성 부족: XML 설정에서는 컴파일 타임에 오류를 확인할 수 없으며, 설정 오류는 런타임 시점에만 확인된다. (즉 BreakPoint를 찍어볼 수 없고 어디서 오류가 났는지 확인하기 어렵다.)
- 유지보수 어려움: 설정이 복잡해지면 관리가 어려워지고, 특히 대규모 프로젝트에서 XML 파일이 길어지면 가독성이 떨어질 수 있다.
2. Java Configuration (Java-based Configuration)
이 방식은 애플리케이션의 구성 정보를 자바 클래스를 사용하여 정의하는 방법이다.
@Configuration 어노테이션을 사용하여 구성 클래스를 선언하고, @Bean 어노테이션을 사용하여 빈(Bean)을 정의한다.
@Configuration
public class AppConfig {
@Bean
public ExClass ExBean() {
return new ExClass("bob");
}
}
1. 장점
- 타입 안전성: 자바 코드를 사용하기 때문에 컴파일 시점에서 오류를 발견할 수 있으며, IDE의 지원을 받아 리팩토링과 코드 탐색이 용이하다. (즉 BreakPoint를 찍어볼 수 있고 구동 전에 오류를 알려준다.)
- 유연성: 조건부 로직을 적용(@Conditional), 환경 설정(@Profile), AOP 설정 등 복잡한 설정을 Java 코드로 더 쉽게 작성할 수 있다.
- 많은 정보: Java 코드로 작성된 클래스의 정보들(패키지, 클래스 이름, 접근 제한자, 상속/구현 등)까지 얻을 수 있다.
2. 단점
- 코드와 설정의 결합: 설정이 코드에 포함되므로 설정 변경을 위해서는 코드 수정을 해야 하며, 이는 배포 과정에서 코드를 다시 컴파일해야 할 수 있다.
- 학습 곡선: 기존 XML 설정에 익숙한 개발자에게는 적응하는 데 시간이 필요할 수 있다.
3. 요약
유연하고 타입 안전한 설정이 필요한 경우 Java Configuration을 사용하는 것이 더 유리하며,
기존 레거시 프로젝트와의 호환성이 중요한 경우 XML 설정을 사용할 수 있다.
3. XML 설정 --> Java Configuration으로 전환
변경 전 web.xml 파일
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://Java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee https://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
<!-- 한글설정 -->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class> org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/root-context.xml</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener
</listener-class>
</listener>
<servlet>
<servlet-name>appServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet
</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/appServlet/servlet-context.xml
</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>appServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
xml 방식에서는 web.xml에 다양한 설정들이 정의되어 있는 것이 보통이다.
살펴보면 인코딩, DispatcherServlet, servletMapping 등의 설정이 정의되어 있는 것을 알 수 있다.
이를 Java Configuration 방식으로 변경하기 위해서는 web.xml처럼 각 설정 정보를 담고 있는 java 클래스를 만들어 관리하면 된다.
xml 파일로 구성되어 있는 설정을 Java 방식으로 바꿔주는 단계는 이렇다.
- pom.xml을 수정하여 web.xml를 사용하지 않겠다는 설정 추가(web.xml을 제거해도 무방)
- web.xml 설정 파일에 대응되는 java 클래스 생성
- 각각의 클래스를 세팅
1. pom.xml 설정 추가(web.xml 설정 사용 금지)
필자는 web.xml을 남겨놓고 싶어서 이런 설정을 했다.
특별한 이유가 없다면 web.xml을 제거해도 무방하다.
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>3.2.0</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
2. WebConfig 생성 (java 설정을 모아놓는 곳 = web.xml)
변경 후 WebConfig 파일
package kr.board.config;
import javax.servlet.Filter;
import org.springframework.web.filter.CharacterEncodingFilter;
import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
//web.xml을 대신해서 만드는 config
public class WebConfig extends AbstractAnnotationConfigDispatcherServletInitializer{
@Override
protected Class<?>[] getRootConfigClasses() {
// TODO Auto-generated method stub
return new Class[] {RootConfig.class};
}
@Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] {ServletConfig.class};
}
@Override
protected String[] getServletMappings() {
return new String[] {"/"};
}
//web.xml의 인코딩 대체
@Override
protected Filter[] getServletFilters() {
CharacterEncodingFilter encodingFilter = new CharacterEncodingFilter();
encodingFilter.setEncoding("UTF-8");
encodingFilter.setForceEncoding(true);
return new Filter[]{encodingFilter};
}
}
web.xml에서 사용하던 설정들을 java 클래스로 바꿔서 각각 설정해주면 된다.
필자는 servlet-context.xml에 viewResolver 설정했었기 때문에 그에 맞는 ServletConfig 클래스를 생성했다.
root-context.xml에 DB 커넥션 정보를 설정했었기 때문에 그에 맞는 RootConfig 클래스를 생성했다.
3. RootConfig와 ServletConfig 생성
변경 전 root-context.xml 파일
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:mybatis-spring="http://mybatis.org/schema/mybatis-spring"
xsi:schemaLocation="http://mybatis.org/schema/mybatis-spring http://mybatis.org/schema/mybatis-spring-1.2.xsd
http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- mysql -->
<bean id="hikariConfig" class="com.zaxxer.hikari.HikariConfig">
<property name="driverClassName" value="com.mysql.jdbc.Driver"/>
<property name="jdbcUrl" value="jdbc:mysql://localhost:3306/com?serverTimezone=UTC"/>
<property name="username" value="사용자 저의"/>
<property name="password" value="사용자 정의"/>
</bean>
<bean id="dataSource" class="com.zaxxer.hikari.HikariDataSource" destroy-method="close">
<constructor-arg ref="hikariConfig" />
</bean>
<mybatis-spring:scan base-package="사용하는 Mapper 경로"/>
<bean class="org.mybatis.spring.SqlSessionFactoryBean">
<!-- connection pool 연결 -->
<property name="dataSource" ref="dataSource" />
</bean>
</beans>
변경 후 RootConfig(DB 설정) 생성
package kr.board.config;
import javax.sql.DataSource;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.PropertySource;
import org.springframework.core.env.Environment;
import com.zaxxer.hikari.HikariConfig;
import com.zaxxer.hikari.HikariDataSource;
//root-context.xml 대신 만들어짐
@Configuration
@MapperScan(basePackages = {"사용하는 mapper 경로 입력"})
@PropertySource({ "classpath:persistence-mysql.properties"})
public class RootConfig {
//properties 불러오려면 사용해야하는 클래스
@Autowired
private Environment env;
@Bean
public DataSource myDataSource() {
HikariConfig hikariConfig=new HikariConfig();
hikariConfig.setDriverClassName(env.getProperty("jdbc.driver"));
hikariConfig.setJdbcUrl(env.getProperty("jdbc.url"));
hikariConfig.setUsername(env.getProperty("jdbc.user"));
hikariConfig.setPassword(env.getProperty("jdbc.password"));
HikariDataSource myDataSource=new HikariDataSource(hikariConfig);
return myDataSource;
}
@Bean
public SqlSessionFactory sessionFactory() throws Exception{
SqlSessionFactoryBean sessionFactory=new SqlSessionFactoryBean();
sessionFactory.setDataSource(myDataSource());
return (SqlSessionFactory)sessionFactory.getObject();
}
}
변경전 servlet-context.xml 파일
<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/mvc"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:beans="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/mvc https://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<annotation-driven />
<resources mapping="/resources/**" location="/resources/" />
<beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<beans:property name="prefix" value="/WEB-INF/views/" />
<beans:property name="suffix" value=".jsp" />
</beans:bean>
<context:component-scan base-package="사용하는 컨트롤러 경로" />
</beans:beans>
변경 후 ServletConfig(ViewResolver 설정) 생성
package kr.board.config;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.ViewResolverRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.springframework.web.servlet.view.InternalResourceViewResolver;
//servlet-context.xml 대신 만들어짐
@Configuration
@EnableWebMvc
@ComponentScan(basePackages = {"사용하는 컨트롤러 경로 입력"})
public class ServletConfig implements WebMvcConfigurer{
@Override
public void configureViewResolvers(ViewResolverRegistry registry) {
InternalResourceViewResolver bean=new InternalResourceViewResolver();
bean.setPrefix("/WEB-INF/views/");
bean.setSuffix(".jsp");
registry.viewResolver(bean);
}
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/resources/**").addResourceLocations("/resources/");
}
}
이런 식으로 web.xml에 존재하는 설정들을 java 클래스에 맞게 만들어주면 된다.
이외의 설정도 대응되는 java 클래스를 활용하여 config를 구현해 나가면 될 것이다.
잘못된 내용이 있다면 지적부탁드립니다. 방문해주셔서 감사합니다. |
'CS > CS' 카테고리의 다른 글
SQL Mapper와 ORM이란? (0) | 2023.05.14 |
---|---|
멀티태스킹, 멀티프로세싱, 멀티스레딩 (1) | 2023.05.07 |
컴퓨터 구성요소 (0) | 2023.05.07 |
XML, JSON (0) | 2023.04.05 |
API, REST, REST API (0) | 2023.04.01 |