본문 바로가기
공부/Trouble Shooting

웹 파일 리팩토링

by son_i 2023. 9. 10.
728x90

1. 맨 처음 index.jsp 페이지가 열리도록 하기 위해서 FrontController 파일 생성. -> servlet으로 생성하고 doget, dopost체

extends HttpServlet implements javax.servlet.Servlet 클래스에 상속

 

import가 안돼서 찾아보니까 서버가 Path에 잘 들어가있지 않아 생기는 문제

 

오류나는 파일 우클릭 -> properties -> java build Path에 server runtime이 없었음.

Add Library -> server runtime에서 tomcat 선택.

정상적으로 import 가 가능해졌다 !

-> 수정 그냥 class 파일이 아니라 servlet 파일로 생성해줌.

 

2. index.jsp가 웹브라우저에서 열리도록 컨트롤러에 코드 작성.

처음 페이지는 get 방식, doGet 메소드에 작성

 

주소 찾기 해 url과 contextPath 불러온 후 주소만 가져오기 위해 substring 사용.

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String requestURI = request.getRequestURI();
		String contextPath = request.getContextPath();
		String command = request.getRequestURI().substring(contextPath.length());

 

3. 주소 가져온 후 주소가 /home 인지 확인할 수 있게 조건문 사용

근데 RequestDispatcher에 오류가 나고 import도 안 돼서 

프로젝트 우클릭 -> Project Facets에 Dynamin web Module 체크 되어있는지 확인. 

체그 되어있어서 우측 Runtimes 탭에 tomcat확인. 체크 안 돼있어서 해주니까 import 가능해짐.

 

* RequestDispatcher
RequestDispatcher는 클라이언트로부터 최초에 들어온 요청을 JSP/Servlet 내에서 원하는 자원으로 요청을 넘기는(보내는) 역할을 수행하거나, 특정 자원에 처리를 요청하고 처리 결과를 얻어오는 기능을 수행하는 클래스.
즉 /a.jsp 로 들어온 요청을 /a.jsp 내에서 RequestDispatcher를 사용하여 b.jsp로 요청을 보낼 수 있습니다. 또는 a.jsp에서 b.jsp로 처리를 요청하고 b.jsp에서 처리한 결과 내용을 a.jsp의 결과에 포함시킬 수 있다.

-출처
https://dololak.tistory.com/502

3. web.xml에 servlet 추가 (src - webapp - WEB-INF - web.xml)

<servlet>
//등록
  <servlet-name>homestart</servlet-name> //변수이름
  <servlet-class>controller.FrontController></servlet-class> //생성할 객체
</servlet>
//매핑
//서버 시작시 url에 home 요청되면 homestart라는 서블릿을 실행시켜주세요
<servlet-mapping>
  <servlet-name>homestart</servlet-name>
  <url-pattern>*.home<url-pattern>

4. 위치 히스토리버튼

기존 loc-history.jsp 에서 history만 적어줌.

loc-history.jsp 파일은 만들어 놓음.

 

이제 FrontController 에서 loc-history.jsp파일을 웹 브라우저에 전송하는 코드 작성

 

5. open API 와이파이 정보 가져오기 버튼

기존 load-wifi.jsp 에서 load로 변경

이 버튼을 누르면 단순 뷰 화면만 띄워주는 것이 아니라 db에 접근해서 저장된 wifi 갯수를 가져오는 작업이 필요하다.

LoadWifiController를 만들고

 

6. 내 위치 가져오기 버튼

x, y 좌표 값을 입력하고 버튼을 누르면 내가 입력한 값과 db에 저장된 데이터들의 거리를 계산하고 db에 저장도 해주고 위치 히스토리 테이블에 정보 저장도 해주고 다시 메인화면으로 돌아와야 한다.

-> x, y값을 보내주는게 아직 이게 맞는지는 모르겠음  ajax 통해 해결 !

 

FrontController에서 데이터 전달할 수 있게 DistUpdateContoller 객체를 생성하고 메서드를 실행시켜준다.

다시 홈 화면으로 갈 수 있도록 response.sendRedirect 작성.

<FrontController>

Front에서 전송된 데이터를 저장하기 위한 컨트롤러 생성. DistUpdateController

DistUpdateController에 전달된 값을 받을 수 있게 변수 정의하고 각 변수에는 index.jsp에서 input으로 전송된 값을 request.getParameter() 메서드를 이용해서 받는다.

<DistUpdateDAO>

기존에 APIService에 있던 calDist 함수등등 DAO로 옮겨줌.

 

<index.jsp>

x,y값을 넘기는 방법으로 ajax를 해봤다가 실패했었는데 다시 시도했다 !

<button onclick="calDist_()">내 위치 가져오기</button> 
		<script src="https://code.jquery.com/jquery-3.4.1.js"></script>
		<script>
		var flag = 0;
    		function calDist_() {
    			var xv = document.getElementById('x').value;
			var yv = document.getElementById('y').value;
			//location.href='distUpdate.jsp?xvalue='+xv+'&yvalue='+yv;
    			//location.href='distupdate?xvalue='+xv+'&yvalue='+yv;
    		$.ajax({
    			url:"distupdate",
    			type:'get',
    			data: { x: xv, y: yv}
    			success: function(data) {
    				flag = 1;
    			}
    		});
    		}
    		
  		</script>

ajax요청 페이지에 로직 더 자세히 적어놓음.

 

7. 내 위치 가져오기로 wifi-history 테이블도 업데이트, wifi-list 테이블도 거리 항목 계산되어 업데이트.

근처와이파이 정보보기 누르면 원래의 index.jsp화면에서 따로 페이지 이동하지 않고 dist 작은 순 20개 보여줘야함.

 

<index.jsp>

<input type="button" onclick="loadWifi_()" value="근처 WIPI 정보 보기">
		<script>
		function loadWifi_() {
			location.href='showwifi';
		}
		</script>

<web.xml>

<servlet>
  <servlet-name>showwifi</servlet-name>
  <servlet-class>controller.FrontController</servlet-class>
  <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  <servlet-name>showwifi</servlet-name>
  <url-pattern>/showwifi</url-pattern>
</servlet-mapping>

<FrontController>

else if(command.equals("/showwifi")) {
			ShowWifiController action = new ShowWifiController();
			action.execute(request);
			response.sendRedirect("/home");
		}

 

<ShowWifiController> //여기서는 요청을 받아서 dao를 호출해 dto리스트를 세팅을 다시 프론트로 내보내야함.

package controller;

import java.io.UnsupportedEncodingException;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import dao.ShowWifiDAO;
import dto.WifiList;

public class ShowWifiController{
	public void execute(HttpServletRequest request) {
		System.out.println(request);
		try {
			request.setCharacterEncoding("utf-8");
		} catch(UnsupportedEncodingException e) {	}
		
		ShowWifiDAO dao = new ShowWifiDAO();
		List<WifiList>list = dao.showWifi();
		request.setAttribute("lists", list);
	}
}

 

<showWifiDAO>

package dao;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import dto.WifiList;

public class ShowWifiDAO {
	//controller에서 호출되어 DB를 접근할 dao
	//db 정보를 적어줌.
	public List<WifiList> showWifi() {
		List<WifiList> wifiListResult = new ArrayList<>();
			try {
				Class.forName("org.sqlite.JDBC");
			} catch (ClassNotFoundException e) {
				e.printStackTrace();
			}
			
			Connection connection = null;
			PreparedStatement preparedStatement = null;
			ResultSet rs = null;

			String url_value = "jdbc:sqlite:C:\\dev_web\\sqlite-tools-win32-x86-3430000\\wifi.db";

			try {
				connection = DriverManager.getConnection(url_value);

				String sql = "select * from wifi_list"
						+ " order by dist limit 0,20;";

				preparedStatement = connection.prepareStatement(sql);

				rs = preparedStatement.executeQuery();

				while(rs.next()) {
					WifiList wifiList = new WifiList();
					wifiList.setManageNo(rs.getString("manage_no"));
					 wifiList.setDist(rs.getDouble("dist"));
					wifiList.setGugun(rs.getString("gugun"));
					wifiList.setWifiName(rs.getString("wifi_name"));
					wifiList.setAddress(rs.getString("address"));
					wifiList.setDetailAddress(rs.getString("detail_address"));
					wifiList.setSetFloor(rs.getString("set_floor"));
					wifiList.setSetType(rs.getString("set_type"));
					wifiList.setSetOrgan(rs.getString("set_organ"));
					wifiList.setServiceDivision(rs.getString("service_division"));
					wifiList.setNetworkKind(rs.getString("network_kind"));
					wifiList.setSetYear(rs.getInt("set_year"));
					wifiList.setInOutdoor(rs.getString("in_outdoor"));
					wifiList.setWificonnectEnvirionment(rs.getString("wificonnect_environment"));
					wifiList.setX(rs.getDouble("x"));
					wifiList.setY(rs.getDouble("y"));
					wifiList.setWorkDate(rs.getString("work_date"));
					
					wifiListResult.add(wifiList);
				}
			} catch (SQLException e) {
				e.printStackTrace();
			} finally {
				try {
					if (rs != null && !rs.isClosed()) {
						rs.close();
					}
				} catch (SQLException e) {
					e.printStackTrace();
				}
				try {
					if (preparedStatement != null && !preparedStatement.isClosed()) {
						preparedStatement.close();
					}
				} catch (SQLException e) {
					e.printStackTrace();
				}
				try {
					if (connection != null && !connection.isClosed()) {
						connection.close();
					}
				} catch (SQLException e) {
					e.printStackTrace();
				}
			}
			return wifiListResult;
	}
}

 

이젠 front 부분에서 받아와서 화면에 보여주는 부분 구성

<index.jsp>

<tbody>
		<c:if test="items==null" var="result">
			위치정보를 입력한 후에 조회해주세요.
		</c:if>
		<c:forEach items= "${lists }" var="dto">
			<td>${dto.manageNo }</td>
			<td>${dto.dist }</td>
			<td>${dto.gugun }</td>
			<td>${dto.wifiName }</td>
			<td>${dto.address }</td>
			<td>${dto.detailAddress }</td>
			<td>${dto.setFloor }</td>
			<td>${dto.setType }</td>
			<td>${dto.setOrgan }</td>
			<td>${dto.serviceDivision }</td>
			<td>${dto.networkKind }</td>
			<td>${dto.setYear }</td>
			<td>${dto.inOutdoor }</td>
			<td>${dto.wificonnectEnvirionment }</td>
			<td>${dto.x }</td>
			<td>${dto.y }</td>
			<td>${dto.workDate }</td>
			
		</c:forEach>
		</tbody>

jstl 문법 사용하기 위해 상단에 추가

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>

오류발생 !

 

pom.xml에 dependency 추가해서 해결

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

 

<index.jsp>

<input type="button" onclick="loadWifi_()" value="근처 WIPI 정보 보기">
		<script>
		function loadWifi_() {
			location.href='showwifi';
		}
		</script> 
	</div>
	<table>
		<thead>
			<tr>
				<th>거리</th>
				<th>관리번호</th>
				<th>자치구</th>
				<th>와이파이명</th>
				<th>도로명주소</th>
				<th>상세주소</th>
				<th>설치위치(층)</th>
				<th>설치유형</th>
				<th>설치기관</th>
				<th>서비스구분</th>
				<th>망종류</th>
				<th>설치년도</th>
				<th>실내외구분</th>
				<th>WIFI접속환경</th>
				<th>X좌표</th>
				<th>Y좌표</th>
			</tr>
		</thead>
		<tbody>
		<c:if test="${lists eq null}" var="result">
		</table>
			<p style="text-align: center;">위치정보를 입력한 후에 조회해주세요.</p>
	
		</c:if>
		<c:forEach items= "${lists }" var="dto">
		<tr>
			<td>${dto.dist }</td>
			<td>${dto.manageNo }</td>
			<td>${dto.gugun }</td>
			<td>${dto.wifiName }</td>
			<td>${dto.address }</td>
			<td>${dto.detailAddress }</td>
			<td>${dto.setFloor }</td>
			<td>${dto.setType }</td>
			<td>${dto.setOrgan }</td>
			<td>${dto.serviceDivision }</td>
			<td>${dto.networkKind }</td>
			<td>${dto.setYear }</td>
			<td>${dto.inOutdoor }</td>
			<td>${dto.wificonnectEnvirionment }</td>
			<td>${dto.x }</td>
			<td>${dto.y }</td>
			<td>${dto.workDate }</td>
			</tr>
		</c:forEach>
		</tbody>
	</table>

 

showWifiController에서 request.setArribute한 lists객체가 없으면 (jstl if문으로 조건)위치정보를 입력한 후에 조회하라는 문구 출력함

request.setParameter()와 request.getParameter()이용하면 String 값만 주고 받을 수 있음.

Action으로 넘어온 값 변경후 jsp로 넘길때 requset.setAttribute() , jsp페이지에서는 request.getAttribute써서 받음.

근데 나는 getAttribute대신 foreach이용해서 ${} 안에 객체명 입력해줘서 받음.

https://sun-p.tistory.com/20

 

request.setAttribute / request.getAttribute

request.setParameter() 와 request.getParameter()를 이용하면 String의 값 밖에는 주고 받을 수 없다. 그럼 Action으로 넘어온 값을 변경시킨후 JSP 페이지로 넘겨주기 위해서는 request.setAttribute() 를 써서 넘겨주

sun-p.tistory.com

뭐 이제 자잘한 것들이랑 추가기능만 하면 된다 !


문제 해결

 

흠 근데 실컷 만들다가 서버 실행을 먼저 시켜봤는데 404에러가 나고 index.jsp에서는 run on server도 되지 않는다..

음..... 이클립스 껐다 키고 일단 web.xml 없애봤는데 프로젝트 우클릭해서 run on server 하면 index.jsp페이지 잘 열림.

다시 아래 servlet 코드 추가해도 잘 열림 !!!!! ㅎㅎ

<servlet>

<servlet-name>homestart</servlet-name>

<servlet-class>controller.FrontController</servlet-class>

<load-on-startup>1</load-on-startup>

</servlet>

<servlet-mapping>

<servlet-name>homestart</servlet-name>

<url-pattern>/home<url-pattern>

</servlet-mapping>

그리고 인제 모든 요청에 대해서 servlet도 만들어줘야함.

<servlet>
  <servlet-name>homestart</servlet-name>
  <servlet-class>controller.FrontController</servlet-class>
  <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  <servlet-name>homestart</servlet-name>
  <url-pattern>/home</url-pattern>
</servlet-mapping>
<servlet>
  <servlet-name>history</servlet-name>
  <servlet-class>controller.FrontController</servlet-class>
  <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  <servlet-name>history</servlet-name>
  <url-pattern>/history</url-pattern>
</servlet-mapping>
<servlet>
  <servlet-name>load</servlet-name>
  <servlet-class>controller.FrontController</servlet-class>
  <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  <servlet-name>load</servlet-name>
  <url-pattern>/load</url-pattern>
</servlet-mapping>