코딩하는 오징어

intellij에서 Spring 4 초기 환경 세팅에서 디비연동까지 한 번에 하기 (Maven & Mysql & Mybatis) 본문

Framework/Spring

intellij에서 Spring 4 초기 환경 세팅에서 디비연동까지 한 번에 하기 (Maven & Mysql & Mybatis)

코딩하는 오징어 2018. 3. 9. 00:30
반응형

이번 글은 조금 길어 질 수 있겠네요. 항상 레퍼런스 용도로 글을 작성하다보니 최대한 간단하게 포스팅하였는데 초기환경 세팅은 중요하니까요!! spring boot를 이용하여 개발할 때는 초기환경 세팅이 정말 쉬웠는데 spring 4 mvc를 사용하려다 보니 설정해야할 것들이 꽤 있더라구요. 하지만!! 한번 간단하게 따라해보면 절대 어렵지않습니다. 그럼 시작 해봅시다! spring 4!!!


일단 여러분의 환경이 jdk1.8, maven이 세팅되어있다고 생각하고 진행하겠습니다.


먼저 spring은 의존성을 특징으로 갖고있기 때문에 spring을 이용하려면 여러 모듈들을 주입해야합니다. 예를 들어 spring-context만 있다고 해서 컨테이너를 관리 할 수 있는 것이아니라 spring-context를 이용하기 위해 spring-beans, spring-core등이 필요합니다. 스프링의 특징인 DI(Dependency Injection : 의존성 주입)때문입니다. 이 부분에 대해서는 따로 포스팅을 하겠습니다. 이번 글은 초기 환경세팅이 주 목적이니까요!! 먼저 intellij에서 maven프로젝트를 만들어 봅시다.



maven을 선택한 후 Create from archetype을 해제한 후 프로젝트를 생성합니다.



원하시는 GroupId 와 ArtifactId를 설정한 후 next를 누릅니다.



Finish를 누르면 기본 프로젝트가 생성됩니다. 프로젝트가 생성되면 기본 구조만 잡혀있게됩니다. 여러분의 입맛에 맞게 디렉토리를 구성하면 되지만 저는 이렇게 구성했습니다.



자 골격을 이렇게 갖추고 난 후에 세부 설정 사항들은 긴말 없이 코드로 보여드리겠습니다. 이 글은 오로지 초기 환경 설정 세팅에만 관심이 있으므로 동작이 어떻게 되는지는 따로따로 상세하게 포스팅 할 생각입니다. 일단은 이렇게하면 동작이 되는구나 라고 생각하고 따라해 봅시다.

 여기서 중요한 포인트만 알고가면됩니다. 스프링이 war파일로 패키징돼서 톰캣으로 올라가서 실행 될 때 제일 먼저 web.xml의 설정 값들을 싹 훑습니다. 여기서 dispatcher-servlet들과 context설정 파일을 읽게되고 스프링의 빈 객체들을 설정대로 생성해서 스프링 컨테이너가 관리하게됩니다. dispatcher-servlet은 클라이언트들의 요청들을 알맞은 컨트롤러로 매핑시켜주는 역할을 하게 되는 건데 자세한 건 따로 포스팅하겠습니다. 하나하나 설명하게되면 글이 너무 길어져 조금 지루하게 느껴질 수 있기 때문입니다. 일단 해보고 잘 동작 하는거 확인되면 그다음 부터 하나하나 찾아보면서 공부하시면 도움이 크게 되실겁니다.


pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>com.codingsquid</groupId>
<artifactId>spring4Tutorial</artifactId>
<packaging>war</packaging>
<version>1.0-SNAPSHOT</version>

<dependencies>
<!-- spring context 묶음 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<!-- databind for json -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.3</version>
</dependency>

<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.9.3</version>
</dependency>

<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.9.3</version>
</dependency>

<!-- spring mvc -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>

<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>

<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.2</version>
<scope>provided</scope>
</dependency>

<dependency>
<groupId>cglib</groupId>
<artifactId>cglib</artifactId>
<version>2.2.2</version>
</dependency>

<!-- lombok -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.18</version>
<scope>provided</scope>
</dependency>

<!-- junit test -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>

<!-- database -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.31</version>
</dependency>

<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.2.7</version>
</dependency>

<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>1.2.2</version>
</dependency>

<dependency>
<groupId>commons-dbcp</groupId>
<artifactId>commons-dbcp</artifactId>
<version>1.4</version>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>4.3.14.RELEASE</version>
</dependency>

</dependencies>

<repositories>
<repository>
<id>spring-libs-release</id>
<name>Spring Releases</name>
<url>https://repo.spring.io/libs-release</url>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
</repositories>

<build>
<finalName>spring4Tutorial</finalName>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
<encoding>utf-8</encoding>
</configuration>
</plugin>
</plugins>
</build>
</project>

web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://java.sun.com/xml/ns/javaee"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
version="3.0">

<display-name>Hello Spring MVC</display-name>

<!-- application config -->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/applicationContext.xml</param-value>
</context-param>

<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

<!-- rest dispatcher config -->
<servlet>
<servlet-name>rest</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/rest-servlet.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>

<servlet-mapping>
<servlet-name>rest</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>

<!-- dispatcher config -->
<servlet>
<servlet-name>dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/dispatcher-servlet.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>

<servlet-mapping>
<servlet-name>dispatcher</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>

<!-- encoding filter -->
<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>


</web-app>


dispatcher-servlet.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">

<!-- This tag registers the DefaultAnnotationHandlerMapping and
AnnotationMethodHandlerAdapter beans that are required for Spring MVC -->
<mvc:annotation-driven />
<!-- This tag allows for mapping the DispatcherServlet to "/" -->
<mvc:default-servlet-handler />

<!-- Process annotations on registered beans like @Autowired... -->
<context:annotation-config/>
<!-- 컴포넌트 스캔 -->
<context:component-scan base-package="com.codingsquid.spring4Tutorial.web_controller" />

<bean id="viewResolver"
class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/views/" />
<property name="suffix" value=".jsp" />
</bean>

</beans>


rest-servlet.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:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd">

<!-- This tag registers the DefaultAnnotationHandlerMapping and
AnnotationMethodHandlerAdapter beans that are required for Spring MVC -->
<mvc:annotation-driven />
<!-- This tag allows for mapping the DispatcherServlet to "/" -->
<mvc:default-servlet-handler />

<!-- Process annotations on registered beans like @Autowired... -->
<context:annotation-config/>
<!-- 컴포넌트 스캔 -->
<context:component-scan base-package="com.codingsquid.spring4Tutorial.rest_controller" />

</beans>


저는 restful 서비스를 위한 서블릿과 spring mvc를 위한 서블릿을 나누어서 설정하였습니다. 이부분에 대해서는 dispatcher-servlet나누기 글을 보시면 되겠습니다.


applicationContext.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:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-4.2.xsd">

<context:property-placeholder location="classpath:application.properties" />
<context:component-scan base-package="com.codingsquid.spring4Tutorial" />

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
<property name="driverClassName" value="${spring.database.class}" />
<property name="url" value="${spring.database.host}" />
<property name="username" value="${spring.database.username}" />
<property name="password" value="${spring.database.password}" />
</bean>

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="mapperLocations" value="classpath*:database/**" />
</bean>

<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
<constructor-arg ref="sqlSessionFactory" />
</bean>

</beans>

mybatis를 이용하여 데이터를 뽑아올 것이므로 빈을 설정해주어야합니다.


application.properties

spring.database.class=com.mysql.jdbc.Driver
spring.database.host=jdbc:mysql://127.0.0.1:3306/springMybatisTest
spring.database.username=root
spring.database.password=1234


어플리케이션에 필요한 여러 설정 값들을 이 파일에 저장합니다. 다음은 database폴더 안에 있는 query.xml내용입니다. mybatis를 이용하게되면 쿼리문을 xml파일로 관리할 수 있습니다.


query.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="database">
<select id="getStudentByName" resultType="com.codingsquid.spring4Tutorial.model.Student" parameterType="String">
SELECT *
FROM students
WHERE students.name=#{name}
LIMIT 1
</select>
</mapper>


그럼 이제 web_controller폴더와 rest_controller안에있는 컨트롤러 클래스와 dao와 model에있는 클래스들을 보겠습니다.


WebController.java

package com.codingsquid.spring4Tutorial.web_controller;

import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
public class WebControllerTest {

@RequestMapping(value = "/webController.do")
public String helloWorld(ModelMap modelMap) {
modelMap.addAttribute("author", "CodingSquid");
return "index";
}

}

index.jsp

<%--
Created by IntelliJ IDEA.
User: codingsquid
Date: 2018. 3. 4.
Time: PM 11:59
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h1>${author}</h1>
Hello World! Spring 4 By CodingSquid
</body>
</html>


Student.java (model)

package com.codingsquid.spring4Tutorial.model;

import lombok.Data;

@Data
public class Student {

private int id;
private String name;
private int age;
private int identifierNum;

}

StudentRepository.java (dao)

package com.codingsquid.spring4Tutorial.dao;

import com.codingsquid.spring4Tutorial.model.Student;
import org.apache.ibatis.session.SqlSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

@Repository
public class StudentRepository {

private SqlSession sqlSession;

@Autowired
public StudentRepository(SqlSession sqlSession) {
this.sqlSession = sqlSession;
}

public Student findStudentByName(String name) {
return sqlSession.selectOne("database.getStudentByName", name);
}

}

RestController.java

package com.codingsquid.spring4Tutorial.rest_controller;

import com.codingsquid.spring4Tutorial.dao.StudentRepository;
import com.codingsquid.spring4Tutorial.model.Student;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class RestControllerTest {

private StudentRepository studentRepository;

@Autowired
public RestControllerTest(StudentRepository studentRepository) {
this.studentRepository = studentRepository;
}

@RequestMapping(value = "/restControllerTest", method = RequestMethod.GET)
public Student restAPITest(@RequestParam("name") String name) {
return studentRepository.findStudentByName(name);
}

}


자 여기까지 필요한 모든 코딩을 한 것입니다. 이제 톰캣에 이 스프링 프로젝트의 빌드결과인 war파일을 올려서 돌려야겠죠??? 먼저 오른쪽 상단에 있는 EditConfigurations...를 누릅니다. 그 다음부터는 밑에 캡쳐화면 순서대로 진행하시면 됩니다.



톰캣이 있는 폴더를 지정해주세요



여기까지 톰캣을 등록시켰으면



이렇게 프로젝트가 활성화가 됩니다. 그럼 이제 실행시켜서 결과를 확인해 봅시다.



Mvc 부분과 Restful서비스 모두 잘 작동되는 걸 확인할 수 있습니다~

반응형
Comments