4 ๋ถ„ ์†Œ์š”

๐Ÿ“š SPRING


๐Ÿ“š SPRING_SUMMARY

Mybatis ๋ฅผ ์ด์šฉํ•œ Spring Project๋ฅผ ์ง„ํ–‰ํ•  ๋•Œ ํ•ด์•ผํ•  ๊ฒƒ์„ ๋‚ด๊ฐ€ ์•Œ์•„๋ณผ ์ˆ˜ ์žˆ๊ฒŒ ์ •๋ฆฌํ•ด๋ณด๊ณ ์ž ํ•œ๋‹ค. (spring boot ์•„๋‹˜)
spring + mybatis_spring + tomcat ..

Project ์ƒ์„ฑ

  • STS์—์„œ ๋จผ์ € Server ( tomcat 9.0 )๋ฅผ ์—ฐ๊ฒฐํ•œ๋‹ค.
  • Spring Legact Project ์ƒ์„ฑ ( Spring MVC Project -> package๋ช… ์ƒ์„ฑ )
  • pom.xml ์„ค์ • ( ๋ฒ„์ „ ํ™•์ธ - ํ”„๋กœ์ ํŠธ์—์„œ mybatis, spring โ€ฆ ์„ ์“ฐ๋ ค๊ณ ํ•˜๋Š” ๊ฒƒ๋“ค์„ ์„ค์ •ํ•ด์ฃผ๋Š” xml -> dependency, maven ์œผ๋กœ ๋ฒ„์ „ ์„ค์ • )
  • Maven Update ( force ์ฒดํฌ ) -> java 1.8๋กœ ๋ฐ”๋€ ๊ฒƒ ํ™•์ธ

DB ๊ด€๋ จ ์—…๋ฌด

  • project/res ํด๋” ์ƒ์„ฑ -> DB ์ •๋ณด ์ €์žฅ ( sql, mwb .. ) , res ๋Š” ๋ถ€๊ฐ€์ ์ธ ํŒŒ์ผ์ด๋ผ๋Š” ๋œป์„ ๊ฐ€์ง„๋‹ค.
  • webapp ์— META-INF ํด๋” ๋งŒ๋“ค๊ธฐ
  • context.xml ์ƒ์„ฑ : DB์—ฐ๊ฒฐ์„ค์ • - ์ด๋ฆ„ ์•ฝ์†
username ์—๋Š” ๋‚ด DB ์ด๋ฆ„, password ๋Š” ๋‚ด DB ๋น„๋ฒˆ
url์—์„œ '&'๋ฅผ '&amp'๋กœ ์ž‘์„ฑํ•ด์•ผํ•œ๋‹ค.
testweb์€ DB ์Šคํ‚ค๋งˆ ๋ช…์ด๋‹ค.
๋งˆ์ง€๋ง‰ ๊ตฌ๋ฌธ์€ ๋‹ค์Œ์œผ๋กœ web.xml์„ ๋ณธ๋‹ค๋Š” ๋œป
<?xml version="1.0" encoding="UTF-8"?>
<Context>
	<Resource name="jdbc/practice" auth="Container" type="javax.sql.DataSource" 
			maxTotal="100" maxIdle="30" maxWaitMillis="10000" 
			username="root" password="1234" driverClassName="com.mysql.cj.jdbc.Driver" 	
			url="jdbc:mysql://localhost:3306/testweb?serverTimezone=UTC&amp;useUniCode=yes&amp;characterEncoding=UTF-8"/> 
    <WatchedResource>WEB-INF/web.xml</WatchedResource>
</Context>

web ์„ค์ •

web.xml

web.xml
ํ•œ๊ธ€ ํ•„ํ„ฐ ์„ค์ •, throwException ์ฒ˜๋ฆฌ๋ฅผ ํ•ด์ค€๋‹ค.

  • ํ•œ๊ธ€ ํ•„ํ„ฐ ์„ค์ •
	<!-- POST ๋ฐฉ์‹์˜ ํ•œ๊ธ€ ์ฒ˜๋ฆฌ. -->
	 <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>
     </filter>
     
     <filter-mapping>
        <filter-name>encodingFilter</filter-name>
        <url-pattern>/*</url-pattern>
     </filter-mapping>
  • throwException ์ฒ˜๋ฆฌ
	<!-- DispatcherServlet์ด ํ•ด๋‹น mapping์„ ์ฐพ์ง€ ๋ชปํ•  ๊ฒฝ์šฐ NoHandlerFoundException๋ฅผ throwํ•˜๊ฒŒ ์„ค์ • -->
		<init-param>
			<param-name>throwExceptionIfNoHandlerFound</param-name>
			<param-value>true</param-value>
		</init-param>

web ํ™˜๊ฒฝ์ด ๋…๋ฆฝ์ ์ธ bean ( ๋น„ ์›น )

root-context.xml
service, mapper(dao), mybatis, aop. transaction ๋“ฑ ๊ด€๋ จ bean์„ ๋“ฑ๋กํ•œ๋‹ค.
์„ค์ •์— ํ•„์š”ํ•œ ๊ฒƒ๋“ค์„ namespace์—์„œ ์ž˜ ์ฒดํฌํ•ด์ฃผ์–ด์•ผ ํ•œ๋‹ค. ๊ทธ๋ž˜์•ผ ์„ค์ • ๊ฐ€๋Šฅ.

  • mybatis ์„ค์ •
	<!-- mybatis-config.xml ์—์„œ enviornments ๋ถ€๋ถ„ -->
    <!-- Connection pool์„ ์‚ฌ์šฉํ•œ๋‹ค. -->
    <!-- ์œ„์— DB ์„ค์ •ํ• ๋•Œ ๋งŒ๋“ค์–ด์ค€ webapp/META-INF/context.xml ์„ ์ฐธ์กฐํ•œ๋‹ค. -->
	<bean id="ds" class="org.springframework.jndi.JndiObjectFactoryBean">
		<property name="jndiName" value="java:comp/env/jdbc/practice"></property>
	</bean>


	<!-- mybatis -->
	<!-- SqlMapConfig.java ๋ถ€๋ถ„ ์ƒ์„ฑ -->
	<!-- factory ๋งŒ๋“ค์–ด์ฃผ๊ธฐ -->
	<bean id="sqlSessionFactoryBean" class="org.mybatis.spring.SqlSessionFactoryBean">
		<!-- ์œ„์— ์„ ์–ธํ•œ ds ์ฐธ์กฐ -->
		<property name="dataSource" ref="ds" />
		<!-- mybatis-config.xml ์—์„œ mappers ๋ถ€๋ถ„ -->
		<!-- mapper๋ผ๋Š” ํด๋” ๋ฐ‘์— ๋ชจ๋“  xml์„ ์ฝ์–ด ์˜ค๊ฒ ๋‹ค 	mapper๊ฐ€ ์–ด๋”จ๋Š๋ƒ~	-->
		<property name="mapperLocations" value="classpath:mapper/*.xml" />
		
		<!-- mybatis-config.xml ์—์„œ typeAliases ๋ถ€๋ถ„ -->
		<!-- config๊ฐ€ ์–ด๋”จ๋Š๋ƒ~  -->
		<!-- ํด๋” ๊ฒฝ๋กœ ์ง€์ •ํ•ด์„œ ์—ฐ๊ฒฐ -->
		<!-- <property name="configLocation" value="classpath:mybatis-config.xml"/> -->
		<!-- ์—ฌ๊ธฐ์„œ package ์„ ์–ธ -> mybatis-config.xml๊ฐ€ ์—†์–ด๋„๋œ๋‹ค -->
		<property name="typeAliasesPackage" value="com.practice.guestbook.model"/>
	</bean>
	
	<!-- SqlMapConfig.java ๋ถ€๋ถ„ ์ƒ์„ฑ -->
	<!-- default ๊ฐ’์ด ์—†์–ด์„œ ๋ฐ˜๋“œ์‹œ ์ƒ์„ฑ์ž๋ฅผ ๊ฐ€์ ธ๊ฐ€์•ผํ•œ๋‹ค -->
	<!-- factory๋ฅผ ๊ฐ€์ง€๊ณ  SqlSession์„ ๋งŒ๋“ค์–ด๋ผ -->
	<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
		<constructor-arg ref="sqlSessionFactoryBean"/>
	</bean>


  • component-scan ์„ค์ •
    model ( service, mapper ( dao )) , aop
    service๋Š” @Service , dao๋Š” @Repository ๋ฅผ ์ ์–ด์ค˜์•ผํ•˜๊ณ  mapper๋Š” interface๋ผ์„œ annotation์ด ์—†๋‹ค.
	<context:component-scan
		base-package="com.ssafy.practice.model, com.ssafy.practice.aop" />
  • aop ์„ค์ •
	<aop:aspectj-autoproxy></aop:aspectj-autoproxy>
  • transaction ์„ค์ •
	<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
		<property name="dataSource" ref="ds"/>
	</bean>
	
	<tx:annotation-driven transaction-manager="transactionManager"/>

web ๊ด€๋ จ bean ( ์›น )

servlet-context.xml ViewResolver , interceptors, file ๋“ฑ ์„ค์ •

  • annotataion ํ™œ์„ฑํ™”
    <annotation-driven />
  • component-scan ์„ค์ •
    controller
    Controller๋Š” @Controller๋ฅผ ์ ์–ด์ค˜์•ผํ•œ๋‹ค.
	<context:component-scan base-package="com.practice.guestbook.controller" />
  • ViewResolver ์„ค์ •
    ๊ธฐ๋ณธ์ ์œผ๋กœ ๊ตฌํ˜„๋œ ๋ถ€๋ถ„์ด ์žˆ๋‹ค.
	<!-- viewResolver -->
    <!-- ํŒŒ์ผ๋ช… ์•ž ( prefix )์— /WEB-INF/views/ ๊ฒฝ๋กœ๊ฐ€ ๋ถ™๊ณ  
         ํŒŒ์ผ๋ช… ๋’ค ( suffix )์— .jsp ๊ฐ€ ๋ถ™๋Š”๋‹ค.
    -->
	<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>
  • ๊ฒฝ๋กœ ๋งคํ•‘
    img, css, js ๋Š” DispatcherServlet์„ ๊ฑฐ์น˜๋ฉด์„œ ๋งคํ•‘ํ•  ํ•„์š”๊ฐ€ ์—†๋‹ค. ( ๋‹จ์ง€ ํ™”๋ฉด๋‹จ์—์„œ๋งŒ ๋ณด์—ฌ์ฃผ๋Š” ๊ฒƒ์ด๊ธฐ ๋•Œ๋ฌธ - Controller๊ฐ€ ํ•„์š”๊ฐ€ ์—†๋‹ค. )
    ๊ทธ๋ž˜์„œ resources์— ์ €์žฅํ•ด์„œ ๊ฒฝ๋กœ๋ฅผ ์„ค์ •ํ•˜๋Š” ๊ฒƒ์€ ๋งคํ•‘์„ ์•ˆํ•ด์ฃผ๋Š”๋‹ค๋Š” ์˜๋ฏธ์ด๋‹ค.
    ์‹คํ–‰๋˜๋ฉด ๋งคํ•‘์•ˆํ•ด์ฃผ๊ณ  ๋ฐ”๋กœ ์ „์†กํ•ด์ค€๋‹ค.
    ์—ฌ๊ธฐ์„œ webapp์— resources ํด๋”๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ์•ˆ์— img, css, js ํด๋”๋ฅผ ๋งŒ๋“ค์–ด์ค˜์•ผํ•œ๋‹ค.
	<!-- <resources mapping="/resources/**" location="/resources/" /> -->
    <!-- mapping ๊ฐ’์œผ๋กœ ๋“ค์–ด์˜ค๋ฉด location์œผ๋กœ ์—ฐ๊ฒฐ์‹œ์ผœ๋‹ฌ๋ผ๋Š” ์˜๋ฏธ์ด๋‹ค. -->
	<resources mapping="/img/**" location="/resources/img/" />
	<resources mapping="/css/**" location="/resources/css/" />
	<resources mapping="/js/**" location="/resources/js/" />

  • interceptor
	<beans:bean id="confirm" class="com.practice.interceptor.ConfirmInterceptor"/>

	<interceptors>
		<interceptor>
			<!-- <mapping path="/guestbook/*"/> -->
            <!-- ๋งคํ•‘ ๊ฒฝ๋กœ ์„ค์ • -->
			<mapping path="/guestbook/register"/>
			<mapping path="/guestbook/modify"/>
			<mapping path="/guestbook/delete"/>
			<!-- <exclude-mapping path="/user/log*"/> -->
			
			<!-- <beans:bean class="com.ssafy.interceptor.ConfirmInterceptor"/> -->
			<beans:ref bean="confirm"/>
		</interceptor>
	</interceptors>
  • file
<!-- fileUpload -->
	<beans:bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
		<beans:property name="defaultEncoding" value="UTF-8"/>
		<beans:property name="maxUploadSize" value="52428800"/> 
		<beans:property name="maxInMemorySize" value="1048576"/> 
	</beans:bean>

	<!-- fileDownload -->
	<beans:bean id="fileDownLoadView" class="com.practice.guestbook.view.FileDownLoadView"/>
	<beans:bean id="fileViewResolver" class="org.springframework.web.servlet.view.BeanNameViewResolver">
		<beans:property name="order" value="0" />
	</beans:bean> 

์‘์šฉ ์—…๋ฌด ๊ตฌํ˜„

์ด์ œ ์„ค์ •๋“ค์„ ๋‹ค ๋งˆ์น˜๊ณ  ๊ธฐ๋Šฅ๋“ค์„ ๊ตฌํ˜„ํ•˜๋ฉด ๋œ๋‹ค.
.jsp -> controller -> service -> mapper -> .xml
๊ตฌ์กฐ๋กœ ๋ฐ์ดํ„ฐ๊ฐ€ ์ด๋™ํ•˜๋ฉฐ ์ฒ˜๋ฆฌ๋œ๋‹ค.

๋””๋ฒ„๊น…์„ ์œ„ํ•œ Log4j ์ •์˜

log4j๋Š” Apache ์—์„œ ๋งŒ๋“  ์˜คํ”ˆ์†Œ์Šค ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋กœ ํ”„๋กœ๊ทธ๋žจ์„ ์ž‘์„ฑํ•˜๋Š” ๋„์ค‘์— ๋กœ๊ทธ๋ฅผ ๋‚จ๊ธฐ๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉ๋˜๋Š” ์ž๋ฐ” ๊ธฐ๋ฐ˜ ๋กœ๊น… ์œ ํ‹ธ๋ฆฌํ‹ฐ๋กœ ๋””๋ฒ„๊ทธ์šฉ ๋„๊ตฌ ๋กœ ์ฃผ๋กœ ์‚ฌ์šฉ๋œ๋‹ค.

  • pom.xml์— log4j ์ถ”๊ฐ€, ํ™•์ธ
	<!-- Logging -->
		<dependency>
			<groupId>org.slf4j</groupId>
			<artifactId>slf4j-api</artifactId>
			<version>${org.slf4j-version}</version>
		</dependency>
		<dependency>
			<groupId>org.slf4j</groupId>
			<artifactId>jcl-over-slf4j</artifactId>
			<version>${org.slf4j-version}</version>
			<scope>runtime</scope>
		</dependency>
		<dependency>
			<groupId>org.slf4j</groupId>
			<artifactId>slf4j-log4j12</artifactId>
			<version>${org.slf4j-version}</version>
			<scope>runtime</scope>
		</dependency>
		<dependency>
			<groupId>log4j</groupId>
			<artifactId>log4j</artifactId>
			<version>${log4j-version}</version>
			<exclusions>
				<exclusion>
					<groupId>javax.mail</groupId>
					<artifactId>mail</artifactId>
				</exclusion>
				<exclusion>
					<groupId>javax.jms</groupId>
					<artifactId>jms</artifactId>
				</exclusion>
				<exclusion>
					<groupId>com.sun.jdmk</groupId>
					<artifactId>jmxtools</artifactId>
				</exclusion>
				<exclusion>
					<groupId>com.sun.jmx</groupId>
					<artifactId>jmxri</artifactId>
				</exclusion>
			</exclusions>
			<scope>runtime</scope>
		</dependency>
  • Log4j.xml ์ž‘์„ฑ
    src/main/resources๋ฐ‘์— log4j.xml์„ ๋งŒ๋“ ๋‹ค.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE log4j:configuration PUBLIC "-//APACHE//DTD LOG4J 1.2//EN" "log4j.dtd">
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">

	<!-- Appenders -->
	<appender name="console" class="org.apache.log4j.ConsoleAppender">
		<param name="Target" value="System.out" />
		<layout class="org.apache.log4j.PatternLayout">
			<param name="ConversionPattern" value="%d %5p [%c] %m%n" />
		</layout>
	</appender>
	
	<!-- Application Loggers -->
	<logger name="com.ssafy.guestbook">
		<level value="debug" />
	</logger>
	
	<!-- 3rdparty Loggers -->
	<logger name="org.springframework.core">
		<level value="info" />
	</logger>
	
	<logger name="org.springframework.beans">
		<level value="info" />
	</logger>
	
	<logger name="org.springframework.context">
		<level value="info" />
	</logger>

	<logger name="org.springframework.web">
		<level value="info" />
	</logger>

	<!-- Root Logger -->
	<root>
		<priority value="warn" />
		<appender-ref ref="console" />
	</root>
	
</log4j:configuration>
  • Log4j.xml ์‚ฌ์šฉ
    Controller ์—์„œ ์„ ์–ธ
	private static final Logger logger = LoggerFactory.getLogger(MemberController.class);

์‚ฌ์šฉ

	logger.debug("map : {}", map.get("userId"));

๊ฒฐ๊ณผ

DEBUG [com.ssafy.guestbook.controller.MemberController] map : 1234

console ์ฐฝ์— ์ด๋ ‡๊ฒŒ ๋œฌ๋‹ค.

Log4j ์„ค์ • ์™„๋ฃŒ !!

package ์ƒ์„ฑ, class ์ƒ์„ฑ, xml ์ƒ์„ฑ

๋‚ด๊ฐ€ ํ•˜๊ณ ์žˆ๋Š” project๋ฅผ ๋”ฐ์™€์„œ ์˜ˆ์‹œ๋กœ ๋“  ๊ฒƒ์ด๋‹ค.

src/main/java

  • com.practice.guestbook.controller
    • controller
  • com.practice.guestbook.model
    • dto
  • com.practice.guestbook.model.mapper
    • mapper
  • com.practice.guestbook.model.service
    • service
    • serviceImpl
  • com.practice.guestbook.view
    • file ๊ด€๋ จ
  • com.practice.interceptor
    • interceptor
  • com.practice.util -page ์ฒ˜๋ฆฌ

src/main/resources/mapper sql๋ฌธ ์ฒ˜๋ฆฌ xml

  • member.xml
  • guestbook.xml

src/main/webapp/resources

  • img
    • img
  • css
    • css ์ž‘์„ฑ
  • js
    • js ์ž‘์„ฑ

src/main/webapp/WEB-INF/spring

  • servlet-context.xml
  • root-context.xml

src/main/webapp/WEB-INF/views ํ™”๋ฉด ๋‹จ ( jsp )