포스팅의 목차는 다음과 같이 정리하였다.
1. 서블릿
1) 서블릿의 개요
2) 서블릿이란?
3) 서블릿 컨테이너
4) 서블릿활용 예제
2. JSP기본문법
1) page 지시어_errorPage
2) include 지시어
3) action태그_include, forward
4) 선언문, 스크립틀릿, 표현식
1. 서블릿
1) 서블릿의 개요_서블릿을 왜 알아야하는가?
JSP가 생성되기 이전에는 서블릿을 작성하여 서버프로그래밍을 진행했다. JSP에 제대로 들어가기 전에 JSP의 고마움에 대해 알아보자.
html에 로직을 추가하고싶을때, 즉 java를 html에 심기 위해서는 JSP을 사용한다. 이말은 JSP 컴파일 파일이 존재한다는 의미이고, 이전 포스팅에서 경로를 따라 파일을 확인해보았을때 "jsp파일명.java"라고 명명되어있는 파일을 찾을 수 있었다. 해당 파일은 servlet이며, 결국 JSP는 컴파일되어서 서블릿이 되는것임을 알아야한다.
2) 서블릿이란?
POJO(Plain Old Java Object : 기본 자바 객체)라는 개념이 존재한다. POJO는 가볍고 빠른 프로그램이며, 반대로 POJO가 아니라면 무겁다는 것을 알 수 있다. POJO가 아닌 것들은 class를 제외한 필터, 리스너, 서블릿이 있다. class파일 생성시와 다르게 서블릿, 필터, 리스너를 생성할때는 특정 클래스의 상속 등과 같이 필수적으로 강제되는 내용들이 존재한다.
디폴트를 피하기 위해 다른 패키지에 생성하였다. 클래스명이 대문자로 시작하며, .java임을 보아 그냥 자바 파일과 크게 다를 것이 없다. 하지만 기본으로 어떤 클래스를 상속받는 것을 확인할 수 있다.
* 서블릿파일의 기본 내용에 대한 분석 *
package day041;
import jakarta.servlet.http.HttpServlet;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@WebServlet("/Test")//사용자의 "/test"라는 url요청에 대해 다음의 서블릿(아래의 내용들)을 수행
public class Test extends HttpServlet {
private static final long serialVersionUID = 1L; //객체직렬화
//!기본생성자:서블릿은 무조건 기본생성자가 있어야해서 화면에 표시한다!
public Test() {
super();
}
//데이터를 보내는 방식 중 get방식은 아래와 같이 하자! + 요청(사용자의)과 응답(서버의)은 메서드가 기본 인자로 가지고 다닌당
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//응답을 "확인"이라는 글로 한당
response.getWriter().append(" <HTML>\r\n"
+ " <HEAD><TITLE>제목</TITLE></HEAD>\r\n"
+ " <BODY><H1>서블릿으로 만드는 웹 페이지"+new Date()+"</H1></BODY>\r\n"
+ " </HTML>").append(request.getContextPath());
}
//데이터를 보내는 방식 중 post방식은 아래와 같이 하자!->doGet으로 가라는데..? 어차피 위의 함수를 호출할거임
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
서블릿파일은 다음과 같은 특징이 존재한다.
1. 기본생성자 필수
2. get,post방식에 대한 반응 설정가능
3. 사용자의 "/test"라는 url요청에 대해 다음의 서블릿(아래의 내용들)을 수행할 수 있는 명령어 존재
* 서블릿의 장단점 *
서블릿을 통해 html파일에서 new Date를 사용하려면 사진같은 동작이 필요하다. 웹페이지에서 자바 로직을 추가하게 됐지만 장점빼고 다 별로..... jsp를 사용하면 서블릿 파일을 기본적으로 생성해준다. 그니까 우리 그냥 jsp쓰자!^^
3) 서블릿 컨테이너
간단하게 설명될 예정이며 자세한 내용은 다루지 않았다.
위의 서블릿 파일을 동작시켜보면 doGet메서드가 객체 없이 동작하는 것을 볼 수 있다.(static메서드가 아님에 유의)
이는 서블릿 컨테이너(톰캣)가 존재하기에 가능하다. 서블릿 컨테이너는 서블릿파일을 컴파일해주는 역할과 동시에 객체관리자이다.(객체의 생성 및 관리를 담당) 기본 생성자의 존재의 이유가 이때 발생한다.
사용자의 url(get)요청에 의해 서블릿(웹페이지)이 제공된다. -> 서버가 응답한다는 의미
서블릿이 제공되려면(doGet( )이실행되려면) 객체인 서블릿 컨테이너(톰캣)이 필요하다. -> new 어쩌구 하려니까 기본 생성자가 필요하다.
서블릿은 요청에 대해 어떻게 응답할지 결정하는 역할을 하므로 MVC중 C의 역할을 수행하게 될 예정이다.
전체적 내용이 잘 정리되어있는 블로그 포스팅의 링크를 첨부해보았다. 두 포스팅을 전부 봐두면 본 블로그의 이전 포스팅 내용과 해당 포스팅의 내용을 이해하는데 도움이 된다.
https://m.blog.naver.com/shb1833/221128940361?referrerCode=1
https://m.blog.naver.com/shb1833/221747758686?referrerCode=1
4) 서블릿 활용 예제
① 계산기
* html파일 *
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<form action="/day041/Test3" method="get">
<input type="text" name="num1">
<select name="op">
<option selected="selected">+</option>
<option>-</option>
<option>*</option>
</select>
<input type="text" name="num2">
<input type="submit" name="계산하기">
</form>
</body>
</html>
* 로직이 들어갈 Bean파일 *
유지보수의 용이를 위해 서블릿 파일에서 계산 로직 메서드를 별도로 구현하게 될텐데, 이때 메서드 별도 구현보다 유지보수를 더 좋게 하는 방법이 두가지 존재한다.
1. 스테틱메서드로 생성하기 2. 클래스(BEAN) 별도 생성하여 로직 객체화 하기
이때 static메서드를 사용하게 되면 프로그램 종료시까지 해당 메서드가 동작하기 때문에 메모리에 좋지 않은 영향을 미친다. 따라서 2번의 방법으로 유지보수를 더욱 용이하게 할 수 있다.
package day041;
public class CalcBean {
//멤버변수
private int result;
//private에 접근하기 위한 get
public int getResult() {
return result;
}
//생성자를 활용하여 로직 구현
public CalcBean(int num1,int num2,String op) {
if(op.equals("+")){
result=num1+num2;
}
else if(op.equals("-")){
result=num1-num2;
}
else if(op.equals("*")){
result=num1*num2;
}
else if(op.equals("/")){
result=num1/num2;
}
else{
System.out.println("없는 연산자를 이용중입니다!");
// Console은 로그확인용 view
}
}
}
* 서블릿파일 *
package day041;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Servlet implementation class Test01
*/
@WebServlet("/Test3") // 사용자(클라이언트,브라우저)의 URL요청에 대해 다음의 서블릿 수행!
public class Test3 extends HttpServlet {
private static final long serialVersionUID = 1L; // 객체직렬화
/**
* @see HttpServlet#HttpServlet()
*/
public Test3() { // 서블릿은 무조건 기본생성자를 필요로합니다!!!!!★★★★★
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request,response);
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
int num1=Integer.parseInt(request.getParameter("num1"));
int num2=Integer.parseInt(request.getParameter("num2"));
String op=request.getParameter("op");
//타 클래스를 불러와 생성자를 통해 result를 생성하고,
//input에 따라 값이 지정된 result를 불러온다.
CalcBean cb=new CalcBean(num1,num2,op);
int res=cb.getResult();
//한글이 페이지에 표시될 수 있도록 하기 위함
response.setContentType("text/html;charset=UTF-8");
//아래는 response.getWriter().append(?).append(request.getContextPath());의 역할과 동일하다
PrintWriter out=response.getWriter();
out.println("<HTML>");
out.println("<HEAD><TITLE>계산기</TITLE></HEAD>");
out.println("<BODY>");
out.println("<H1>계산결과: "+num1+" "+op+" "+num2+" = "+res);
out.println("</H1>");
out.println("</BODY>");
out.println("</HTML>");
}
}
* 결과 *
② 숫자에 따른 이름결과 조회
* html파일 *
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>캐릭터이름출력</title>
</head>
<body>
<form action="/day041/Test4" method="post">
<h1>숫자를 골라보세요</h1>
<input type="number" min="1" max="5" value="1" name="num">
<input type="submit" value="결과">
</form>
</body>
</html>
유지보수를 용이하게 하기 위해서는 화면에서 유효성 체크를 하는 것 보다 자바스크립트를 별도로 활용하는 것이 더 좋다.
여기서 input의 name을 지정하지 않아 다음과 같은 오류가 발생하였다. name을 지정하고, 해당 num을 서블릿파일에 호출하여 정상적으로 값이 전달될 수 있도록 하였다. 오류 사진은 다음과 같다.
* Bean파일 *
package day041;
public class NameBean {
private String name;
public String getName() {
return name;
}
public NameBean(int num) {
if(num==1) {
name="아무무";
}else if(num==2) {
name="티모";
}else if(num==3) {
name="아리";
}else if(num==4) {
name="가렌";
}else if(num==5) {
name="세트";
}
}
}
* 서블릿파일 *
package day041;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Servlet implementation class Test4
*/
@WebServlet("/Test4")
public class Test4 extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public Test4() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doPost(request, response);
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("text/html;charset=UTF-8");
int num=Integer.parseInt(request.getParameter("num"));
NameBean nb=new NameBean(num);
String name=nb.getName();
PrintWriter out=response.getWriter();
out.println("<HTML>");
out.println("<HEAD><TITLE>이름 결과</TITLE></HEAD>");
out.println("<BODY>");
out.println("<H1>번호"+num+"에 해당하는 캐릭터는 "+name+"입니다.");
out.println("</H1>");
out.println("</BODY>");
out.println("</HTML>");
}
}
* 결과 *
위의 풀이방법 이외로 Bean파일의 추가 없이 ArrayList를 활용한 방법도 있다. 해당하는 코드만 하단에 첨부해보았다.
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("text/html;charset=UTF-8");
int num=Integer.parseInt(request.getParameter("num"));
ArrayList<String> al= new ArrayList<String>();
al.add("아무무");
al.add("티모");
al.add("아리");
al.add("가렌");
al.add("세트");
PrintWriter out=response.getWriter();
out.println("<HTML>");
out.println("<HEAD><TITLE>이름 결과</TITLE></HEAD>");
out.println("<BODY>");
out.println("<H1>번호"+num+"에 해당하는 캐릭터는 "+al.get(num-1)+"입니다.");
out.println("</H1>");
out.println("</BODY>");
out.println("</HTML>");
}
2. JSP기본문법
1) page 지시어_errorPage
page지시어는 JSP 페이지를 컨테이너에서 처리하는 데 필요한 속성을 기술하는 부분이며, 대부분 소스코드 맨 앞에 위치한다. 아래의 코드가 페이지 지시어 코드이다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
이 페이지 지시어에는 다양한 속성들이 존재하는데, 그 중 오류 페이지 처리와 관련된 두가지의 속성에 대해 알아보았다.
① errorPage
현재 페이지에서 에러가 발생했을경우 이동할 페이지를 지정해주는 속성이다. 사용예시는 다음과 같다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" errorPage="error.jsp"%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<title>일부러 에러를 발생시킬 예정!</title>
</head>
<body>
<% //스크립틀릿(scritlet)! 자바 코드를 사용할때사용
int num=10/0;
%>
</body>
</html>
② isErrorPage
현재 페이지가 예외를 처리하는 페이지임을 지정할때사용한다. 기본값은 "false"이며 해당 페이지가 예외(Exception)을 처리하는 페이지일 경우 "true"로 설정해주면 된다. 사용예시는 다음과 같다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" isErrorPage="true"%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<h1>페이지 처리중 문제가 발생함</h1>
<%=//표현식! 화면에 출력하고싶을때 사용
exception //오류 내용출력
%>
</body>
</html>
이때 서블릿의 내장객체가 생성되어 exception이 사용 가능해진다.
출력 결과는 다음과 같다.
2) include 지시어
외부 페이지를 해당 페이지에 끌고올 수 있는 행동을 해주는 지시어이다. 예시는 다음과 같다.
① 외부 페이지(끌고올 페이지의) 내용 작성
1. header.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
[메일] [카페] [블로그] [뉴스]
2. news.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
[책방]
매일 한 장씩 따라쓰는 루이스 헤이의 긍정 확언 어쩌구
3. aside.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
[트렌드 쇼핑]
쿠팡
봄이니까! 르니몰
르니앤맥코이SALE
② 현재 페이지(NewFile1.jps)에 삽입하기
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>include 지시어</title>
</head>
<body>
<table border="1">
<tr>
<td colspan="2"><%@ include file="header.jsp" %></td>
</tr>
<tr>
<td><%@ include file="news.jsp" %></td>
<td><%@ include file="aside.jsp" %></td>
</tr>
</table>
</body>
</html>
출력화면 첨부
외부의 파일을 인클루드 지시어를 사용한 현재 jsp파일 페이지에 포함시키는 것을 가장 먼저 처리한 후 컴파일을 진행하게 된다.
인클루드 지시어를 많이 사용할수록 컴파일을 해야할 파일들이 많아지므로, 현재 파일의 부담이 증가하게 된다.
해당 방법으로 외부 파일의 내용을 가져오는 행동은 변화가 별로 없는 정적인 페이지(nav, footer등)에 유리하다.
* 지시어에 대한 내용이 잘 정리되어있는 블로그의 링크 첨부 *
https://m.blog.naver.com/shb1833/221750455018
3) action태그
기존의 HTML 태그에는 없는 기능으로 Java의 코드 없이 태그를 이용해 실행하기 위해 사용된다. Web 컨테이너가 제공하여 따로 설정할 필요가 없이 이용할 수 있다. 그 중에서도 외부 페이지를 해당 페이지로 끌고오는데에 있어 자주 사용되는 태그에 대해 정리해보았다.
① include 액션
include지시어와 다르게, 컴파일을 진행 한 후 파일을 포함시키는 순서로 진행되며 뉴스나, 광고처럼 동적인 페이지에 유리하다.
1. 현재페이지(NewFile2.jsp)
<jsp : include page="포함시킬 페이지">를 지정하였다. 추가로 <jsp:param>을 통해 변수를 전달할 수 있다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>include 액션</title>
</head>
<body>
<h1>include 액션 페이지입니다.</h1>
<hr>
<jsp:include page="content.jsp">
<jsp:param value="timo" name="name"/>
<jsp:param value="010-0000-0000" name="phone"/>
</jsp:include>
</body>
</html>
2. 외부페이지(content.jsp)
전달받은 변수를 출력하는 내용을 담도록 하였다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<h5>content.jsp 페이지입니다</h5>
<hr>
<%= request.getParameter("name") %>
<%= request.getParameter("phone") %>
</body>
</html>
출력 결과는 다음과 같다.
② forward 액션
현재 페이지를 완전히 다른 페이지로 전환할 때 사용된다. 서버에 전달되는 요청이나 그 정보들을 은닉할때 많이 사용되는 경향이 있다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>forward 액션</title>
</head>
<body>
<h1>forward 액션 페이지입니다.</h1>
<hr>
<jsp:forward page="content.jsp">
<jsp:param value="timo" name="name"/>
<jsp:param value="010-0000-0000" name="phone"/>
</jsp:forward>
</body>
</html>
출력결과는 다음과 같다.
NewFile3.jsp파일을 실행했음에도 content.jsp의 내용만이 출력되었음을 확인할 수 있다.
* 액션태그에 대한 내용이 잘 정리되어있는 블로그의 링크 첨부 *
https://m.blog.naver.com/shb1833/221758638442
4) 선언문, 스크립틀릿, 표현식
아래 코드에서 주석을 통해 설명을 확인할 수 있다.
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>표현식, 스크립트릿, 선언식</title>
</head>
<body>
<%! //선언부(선언식) : 멤버변수, 함수의 내용을 담는다.
int num=0;
public void func(){
return;
}
%>
<% //스크립트릿: 자바코드를 담는다.
if(request.getParameter("act")!=null){
out.println(request.getParameter("act"));
//자바코드 내부에서 브라우저로 출력하고싶을때, 내장객체 out의 도움을 받아야한다.
}
%>
<%=//표현식: 멤버변수나 함수를 출력하기 위해 사용된다.
request.getParameter("act")//20번라인과 26번라인의 수행은 동일하다.
%>
</body>
</html>
* 예제 *
1. 1~10까지의 수를 브라우저에 출력
2. 1~100까지의 수 중 3의 배수만 브라우저에 출력
3. 5가지의 색상을 저장하고, 랜덤으로 화면에 출력
<%@page import="java.util.Random"%>
<%@page import="java.util.ArrayList"%>
<%@page import="javax.security.auth.message.callback.PrivateKeyCallback.Request"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<title>예제</title>
<style type="text/css">
div{
width: 100px;
height: 100px;
}
</style>
</head>
<body>
<h1>문제1</h1>
<%
for(int i=1; i<=10; i++){
out.println(i);
//브라우저에 전달할 Document를 작성한다.
//즉, 브라우저화면에는 ln이 적용되지 않았으나
//페이지 소스코드에는 ln이 적용되어있음이 확인 가능하다.
}
%>
<br>
<h1>문제2</h1>
<%
for(int i=1; i<=100; i++){
if(i%3==0){
out.println(i);
}
}
%>
<br>
<h1>문제3</h1>
<%
ArrayList<String> color = new ArrayList<String>();
color.add("red");
color.add("orange");
color.add("yellow");
color.add("green");
color.add("blue");
Random rand = new Random();
int index=rand.nextInt(color.size());
%>
<div style="background-color:<%= color.get(index) %>; "></div>
</body>
</html>
출력결과는 다음과 같다.
* 선언문, 스크립틀릿, 표현식에 대한 내용이 잘 정리되어있는 블로그의 링크 첨부 *
https://m.blog.naver.com/shb1833/221757561876
'JSP' 카테고리의 다른 글
[View업그레이드] EL & JSTL (0) | 2022.03.03 |
---|---|
[JDBC] MVC나누기_1 : 게시글 (0) | 2022.03.02 |
[JDBC] Bean & JDBC연결 (0) | 2022.03.01 |
[JSP] 내장객체 (0) | 2022.02.25 |
[JSP] 서버프로그래밍의 기초 (0) | 2022.02.23 |