반응형
1) model2의 script추가 (writeForm을 위해)
1-1) writeForm수정(글에 이미지업로드를위해)
1-2) updateForm과 replyForm도 수정
2) 웹크롤링
2-1)테이블데이터가져오기(연습)
2-2) 키움히어로즈(야구선수단) 웹에 들어가 선수사진만 가져와보자
1) model2의 script추가 (writeForm을 위해)
해당부분에 밑의 코드 넣자
summernote를 위해 jqery와 bootstarp의 버전을 바꾸는거임 (기존꺼를 지우지않아도됨)
<script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/summernote/0.8.18/summernote.min.js"></script>
1-1) writeForm수정(글에 이미지업로드를위해)
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<c:set var="path" value="${pageContext.request.contextPath }" scope="application"></c:set>
<!-- /webapp/view/board/writeForm.jsp -->
<!--
1. boardid가 1인경우 , 관리자가아니면 관리자만 공지사항 글쓰기가 가능합니다
공지사항 목록 페이지이동
-->
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>게시글등록</title>
</head>
<body>
<form action="write" method="post" enctype="multipart/form-data"
name="f">
<h2 class="text-center">게시판 글쓰기</h2>
<table class="table">
<tr>
<td>글쓴이</td>
<td><input type="text" name="writer" class="form-control"></td>
</tr>
<tr>
<td>비밀번호</td>
<td><input type="password" name="pass" class="form-control"></td>
</tr>
<tr>
<td>제목</td>
<td><input type="text" name="title" class="form-control"></td>
</tr>
<tr>
<td>내용</td>
<td><textarea rows="15" name="content" id="summernote"
class="form-control"></textarea></td>
</tr>
<tr>
<td>첨부파일</td>
<td><input type="file" name="file1"></td>
</tr>
<tr>
<td colspan="2"><a href="javascript:inputcheck()" class="btn btn-outline-secondary">[게시물등록]</a></td>
</tr>
</table>
</form>
<script type="text/javascript">
function inputcheck() {
f = document.f;
if (f.writer.value == "") {
alert("글쓴이 입력");
f.writer.focus();
return;
}
if (f.pass.value == "") {
alert("비밀번호입력");
f.pass.focus();
return;
}
if (f.title.value == "") {
alert("제목입력");
f.title.focus();
return;
}
f.submit(); //모두아니라면 submit발생
}
</script>
<%--summernote관련 구현 --%>
<script type="text/javascript">
$(function(){
$("#summernote").summernote({ //summernote에디터로변환
height:300,
callbacks:{
//이미지업로드이벤트발생
//files : 한개이상의 이미지업로드가능(배열)
onImageUpload : function(files){
for(let i=0;i<files.length;i++){
sendFile(files[i]); //하나씩 ajax이용해 서버로파일 전송
}
}
}
})
})
function sendFile(file){
let data = new FormData(); //폼데이터수집하고 전송가능한 객체, 파일업로드에사용
data.append("file",file); //이미지파일
$.ajax({
//${path}를 사용하기위해서는 layout부분에 path를 설정한곳에
//scope="application"추가
url : "${path}/board/uploadImage", //업로드의기능만가진서블릿
type:"post",
data: data,
processData : false,
contentType:false,
success: function(url){
//url : 업로드된 이미지의 접근url정보
$("#summernote").summernote("insertImage",url);
},
error : function(e){
alert("이미지업로드실패 : "+e.status);
}
})
}
</script>
</body>
</html>
/java/controller/UploadImageServlet 생성
(servlet파일로 생성할것)
package controller;
import java.io.File;
import java.io.IOException;
import java.util.UUID;
import javax.servlet.ServletException;
import javax.servlet.annotation.MultipartConfig;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.Part;
/**
* Servlet implementation class UploadImageServlet
*/
@WebServlet("/board/uploadImage")
@MultipartConfig //업로드된 파일 처리
public class UploadImageServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
public UploadImageServlet() {
super();
}
private static final String UPLOAD_DIR = "uploaded_images";
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
Part filePart = request.getPart("file"); //file이름의 데이터를가져옴
String fileName = getFileName(filePart); //파일명추출
String originalFileName = getFileName(filePart);
// UUID로 고유한 파일명 생성(중복방지)
String savedFileName = UUID.randomUUID().toString() + getFileExtension(originalFileName);
//file.separator : window : \
// 리눅스 : /
String uploadPath = //파일업로드되는폴더
//C:/java/workspace/.metadata/.plugins/org.eclipse.wst.server.core/tmp0/wtpwebapps/model2Study/uploaded_images
getServletContext().getRealPath("")+File.separator+UPLOAD_DIR;
File uploadDir = new File(uploadPath);
if(!uploadDir.exists()) {
uploadDir.mkdirs();
}
//filePath : 이미지파일이 업로드된 절대경로
String filePath = uploadPath+File.separator+savedFileName;
filePart.write(filePath); //파일업로드 @MultipartConfig 필수
//request.getContextPath() : 프로젝트명
//fileUrl 톰캣이접근할수있는 url정보
String fileUrl = request.getContextPath()+"/"+UPLOAD_DIR+"/"+savedFileName;
response.setContentType("text/plain");
response.getWriter().write(fileUrl); // 클라이언트(summernote)에게 url정보 전달(출력)
}
private String getFileName(Part part) {
//content-disposition : form-data; name="file"; filename="iz.jpg"
System.out.println("content-disposition : "+part.getHeader("content-disposition"));
for(String content : part.getHeader("content-disposition").split(";")) {
if(content.trim().startsWith("filename")) {
return content.substring(content.indexOf("=")+1).trim().replace("\"", "");
//오직filename만 반환
}
}
return "unkown.jpg";
}
// 파일 확장자 추출 메서드
private String getFileExtension(String fileName) {
return fileName.substring(fileName.lastIndexOf("."));
}
}
1-2) updateForm과 replyForm도 수정
둘다 동일하게 가장 상단에 밑에 코드 추가 후
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<c:set var="path" value="${pageContext.request.contextPath }" ></c:set>
내용을 담는 태그의 id를 summernoter로 변경하자
그 후 스크립트에 해당코드 추가
<script type="text/javascript">
$(function(){
$("#summernote").summernote({
height:300,
callbacks:{
//onImageUpload : 이미지업로드이벤트발생
//files : 한개이상의 이미지업로드가능(배열)
onImageUpload : function(files){
for(let i=0;i<files.length;i++){
sendFile(files[i]); //파일 하나씩 ajax이용해 서버로파일 전송
}
}
}
})
})
function sendFile(file){
let data = new FormData(); //폼데이터수집하고 전송가능한 객체, 파일업로드에사용
data.append("file",file); //이미지파일
$.ajax({
//${path}를 사용하기위해서는 layout부분에 path를 설정한곳에
//scope="application"추가
url : "${path}/board/uploadImage", //업로드의기능만가진서블릿
type:"post",
data: data, //data = 전송받은 이미지파일들
processData : false,
contentType:false,
success: function(url){
//url : 업로드된 이미지의 접근url정보
//insertImage : image삽입
$("#summernote").summernote("insertImage",url);
},
error : function(e){
alert("이미지업로드실패 : "+e.status);
}
})
}
</script>
2)크롤링(jsoup이용)
JsoupStudy라는 이름의 Dynamic프로젝트생성
해당 jar파일을 가져오자
2-1) 테이블데이터 가져오기
수출입은행 -> 환율정보의 url
https://www.koreaexim.go.kr/wg/HPHKWG057M01
/webapp/ex01_exchange.jsp
(자바파일을 사용하려면 꼭 import해줘야함)
(스크립트릿으로사용해도무관하지만 난 자바파일을 따로만들었음)
<%@page import="org.jsoup.select.Elements"%>
<%@page import="java.io.IOException"%>
<%@page import="org.apache.jasper.tagplugins.jstl.core.Catch"%>
<%@page import="org.jsoup.nodes.Element"%>
<%@page import="org.jsoup.nodes.Document"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ page import="org.jsoup.Jsoup" %>
<%@ page import="jsoup.Ex01_exchange" %>
<%--
1.jsoupStudy 프로젝트생성
2.ex01_exchange.jsp 생성
3.3개의 jar파일넣기
4.브라우저에서 한국수출입은행 사이트에서
업무안내--> 환율정보 클릭
환율정보url : https://www.koreaexim.go.kr/wg/HPHKWG057M01
(주소는 매번바뀔수있음 주의)
--%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>수출입은행 환율 정보조회</title>
<style type="text/css">
table{border-collapse: collapse;}
table,td,th{border:2px solid grey;}
</style>
</head>
<body>
<%
/*String url = "https://www.koreaexim.go.kr/wg/HPHKWG057M01";
String line = "";
Document doc = null;
try{
doc = Jsoup.connect(url).get();
Elements el = doc.select("table");
for(Element ele : el){
String temp = ele.html();
line += temp;
}
}
catch(IOException e){
e.printStackTrace();
} EX01_exchange.java파일로 옮겨놨음
*/
String line = Ex01_exchange.Ex01();
%>
<table><%=line %></table>
</body>
</html>
/java/jsoup/Ex01_exchange.java
테이블을 통쨰로 크롤링
package jsoup;
import java.io.IOException;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
public class Ex01_exchange {
public static String Ex01() {
String url = "https://www.koreaexim.go.kr/wg/HPHKWG057M01";
String line = "";
Document doc = null;
try{
doc = Jsoup.connect(url).get(); //url접속후 DOM트리 취상위문서
Elements el = doc.select("table");//doc하위태그중 table태그선택
for(Element ele : el){
//ele : table태그 1개
String temp = ele.html();
System.out.println(temp);
line += temp;
return line;
}
}
catch(IOException e){
e.printStackTrace();
}
return null;
}
}
3-2) 웹크롤링 후 내가 구조를 바꿈
활용예제 ( 수출입 은행 환율정보중 EUR,JPY(100),CNH,USD통화만 출력)
<%@page import="java.io.IOException"%>
<%@page import="org.jsoup.nodes.Element"%>
<%@page import="org.jsoup.select.Elements"%>
<%@page import="org.jsoup.Jsoup"%>
<%@page import="org.jsoup.nodes.Document"%>
<%@page import="java.util.Arrays"%>
<%@page import="java.util.ArrayList"%>
<%@page import="java.util.List"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<%--수출입은행 환율 정보중 EUR,JPY(100),CNH,USD 통화만
ex02_exchange.jsp형태로출력--%>
<html>
<head>
<meta charset="UTF-8">
<title>EXAM1</title>
<style type="text/css">
table{border-collapse: collapse;}
tabel,td,th{border: 3px solid purple;}
</style>
</head>
<body>
<%
String url = "https://www.koreaexim.go.kr/wg/HPHKWG057M01";
String line = "";
Document doc = null;
List<List<String>> trlist = new ArrayList<List<String>>();
List<String> title = Arrays.asList("전신환받으실때","전신환보내실때","매매기준율","장부가격","중개매매기준율","중개장부 가격");
List<String> list = Arrays.asList("EUR","JPY(100)","CNH","USD");
try{
doc = Jsoup.connect(url).get(); //DOM트리 최상위문서
Elements trs = doc.select("tr"); //tr태그들
for(Element tr : trs) {//tr : tr태그 1개
List<String> tdlist = new ArrayList<String>();
Elements tds = tr.select("td"); // td태그들
for(Element td : tds){ // td : td태그 1개
tdlist.add(td.html());//td의 내용
}
//tdlist가 비어있지않고 통화코드가들어있는리스트(list)에 tdlist의0번째인덱스가 존재한다면
if(tdlist.size()>0 && list.contains(tdlist.get(0))){
trlist.add(tdlist);
}
}
}catch(IOException e) {
e.printStackTrace();
}
pageContext.setAttribute("trlist", trlist);//el,jstl사용위해 속성등록
pageContext.setAttribute("title", title);
%>
<table>
<c:forEach items="${trlist}" var="tdlist">
<c:forEach items="${tdlist}" var="td" varStatus="stat">
<c:choose>
<c:when test="${stat.index % 8 == 0}"> <%--1번쨰 td(통화코드) --%>
<tr><td rowspan="6">${td}</td>
</c:when>
<c:when test="${stat.index % 8 == 1}"><%--2번쨰 td(통화명) --%>
<td rowspan="6">${td}</td>
</c:when>
<c:when test="${stat.index % 8 == 2}"><%--3번쨰 td : 전신환받으실때의 환율 --%>
<td>${title[0]}</td><td>${td}</td></tr>
</c:when>
<c:otherwise>
<tr><td>${title[stat.index -2]}</td><td>${td}</td></tr>
</c:otherwise>
</c:choose>
</c:forEach>
</c:forEach>
</table>
</body>
</html>
2-2) 키움히어로즈(야구선수단) 웹에 들어가 선수사진만 가져와보자
https://heroesbaseball.co.kr/players/infielder/list.do
선수단
heroesbaseball.co.kr
크롤링코드
/webapp/exam2_Img.jsp
<%@page import="org.apache.catalina.tribes.transport.MultiPointSender"%>
<%@page import="java.io.IOException"%>
<%@page import="org.jsoup.nodes.Element"%>
<%@page import="org.jsoup.select.Elements"%>
<%@page import="org.jsoup.Jsoup"%>
<%@page import="org.jsoup.nodes.Document"%>
<%@page import="java.util.Arrays"%>
<%@page import="java.util.ArrayList"%>
<%@page import="java.util.List"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>이미지추출</title>
<style type="text/css">
img{
border:30px;
width:100px;
height:100px;
}
td{
border: 1px solid purple;
width:200px;
}
</style>
</head>
<body>
<%
String url = "https://heroesbaseball.co.kr/players/infielder/list.do";
Document doc = null;
List<String> html = new ArrayList<>();
try{
doc = Jsoup.connect(url).get(); //최상위DOM트리 최상위문서
Elements ele = doc.select("a"); // a태그들 꺼내기
for(Element el : ele){
//id가position인 태그가져와
Element positionElement = el.select(".position").first();
//태그가있고 태그내의 이름이 내야수인 태그만!!!!
if(positionElement!=null && positionElement.text().equals("내야수")){
Elements img = el.select("img");//img태그들
for(Element im : img){
if(img!=null){
String ab = im.absUrl("src");//src를 가져와 절대경로로바꿈
img.attr("src", ab); // 바꾼경로를 해당 src에 넣음
}
}
html.add(el.html()); // a태그의 html을 List에넣기
}
}
}
catch(Exception e){
e.printStackTrace();
}
request.setAttribute("list",html);
%>
<table>
<tr>
<c:forEach items="${list}" var="s" varStatus="i">
<td>${s}</td>
<c:if test="${i.count%4==0}"></tr><tr></c:if>
</c:forEach>
</tr>
</table>
</body>
</html>
3) 나만의 예제
해당사이트의 사진들을 모두 가져와볼게요
Nareum.java
package jsoup;
import java.util.ArrayList;
import java.util.List;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
public class Nareum {
public static List<String> nareum() {
String url = "https://nareum.co.kr/product/list.html?cate_no=28";
Document doc = null;
ArrayList<String> list = new ArrayList<>();
try {
doc = Jsoup.connect(url).get();
Elements div= doc.select("img");
for (Element im : div) {
if(im!=null ) {
String src = im.absUrl("src");
System.out.println(src);
if(!src.contains("wish") && !src.contains("cate_no")) {
list.add(src);
}
}
}
return list;
}
catch(Exception e) {
e.printStackTrace();
}
return null;
}
}
nareum.jsp
<%@page import="java.util.List"%>
<%@page import="jsoup.Nareum"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<style type="text/css">
img{
height:100px;
width:100px;
}
td{
width:50px;
}
</style>
<meta charset="UTF-8">
<title>나름SHOP</title>
</head>
<body>
<%
List<String> list = Nareum.nareum();
request.setAttribute("list", list);
%>
<table>
<tr>
<c:forEach items="${list}" var="s" varStatus="i">
<td><img src="${s}"></td>
<c:if test="${i.count%8==0}"></tr><tr></c:if>
</c:forEach>
</tr>
</table>
</body>
</html>
'JSP' 카테고리의 다른 글
부트캠프59일차(크롤링, model2적용) (0) | 2025.04.25 |
---|---|
부트캠프57일 (차트 ,DB연동, 차트를 model2에 사용 , (0) | 2025.04.23 |
부트캠프56일차(jqeury이용한DB연결 , XML분석 , model2의 시,구,동 설정) (0) | 2025.04.22 |
부트캠프56일차(ajax설명,fetch , jquery , json 설명) (0) | 2025.04.22 |
54일차의 내용추가(book 관련) (1) | 2025.04.19 |