Cloud 기반 웹 DevOps 프로젝트 개발자 과정

문이빈·2023년 7월 14일
0

어제 한 것 중에서 고침(이미 등록된 아이디여도 등록을 클릭하면 회원 목록으로 전송됨)

/**
 * 
 */
//$().ready(function(){
//	
//}) 아래와 같은 거임 ().ready 생략
$(function(){
chk1=false; // validate
chk2=false; // pw
$('#submit1').click(function(){
	var pw1 = $('.pw1').val();
	var pw2 = $('.pw2').val();

if(pw1 != "" && pw1.trim().length>0 && pw2 != "" && pw2.trim().length>0){

	  if(pw1 != pw2){
		  //alert('비밀번호가 일치하지 않습니다.');
		  $('font[class=pwMsg]').text('');
	 	  $('font[class=pwMsg]').attr('color','red');
		  $('font[class=pwMsg]').text('비밀번호가 일치하지 않습니다.');
		  $('.pw2').focus();
		  chk2 = false;
		  return false // 서브밋  불가
	  }else{
		  $('font[class=pwMsg]').text('');
	 	  $('font[class=pwMsg]').attr('color','blue');
		  $('font[class=pwMsg]').text('비밀번호가 일치합니다.');
		  chk2 = true;
	  }
	}

if(valichk( )){ // 누군가 빈칸 걸린것임
chk1 = false;
return false; // false는 리턴을 하니 else가 필요 없다.
}

	if(chk1 && chk2){
	$('form').submit();
	}else{
		return false;
	}
});
// id 중복체크 ajax

이미 등록된 아이디여도 이제는 등록으로 넘어가지 않음.


게시판

sql 테이블 만들기

----------index.html----------

HTML 코드로, 페이지를 새로고침하여 "list.to"로 리다이렉션(redirect)하는 역할을 합니다.

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta http-equiv="refresh" content="0; url=list.to">
</head>
<body>
</body>
</html>

<meta http-equiv="refresh" content="0; url=list.to"> 부분에서 content 속성은 0초 후에 리다이렉션을 수행하도록 지정되어 있습니다.
url 속성에는 리다이렉션할 주소인 "list.to"가 지정되어 있습니다.
이 코드를 사용하면 현재 페이지를 자동으로 "list.to"로 이동하게 됩니다.

----------BoardController----------

이 파일은 웹 애플리케이션에서 적절한 액션을 선택하여 처리하는 컨트롤러 역할을 수행합니다.
각 액션은 요청에 맞는 비즈니스 로직을 수행하고, 결과를 뷰로 전달하여 클라이언트에게 응답합니다.

package control;

import java.io.IOException;

import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import action.CommandAction;
import action.ListAction;
import action.WriteFormAction;
import action.WriteProAction;

/**
 * Servlet implementation class BoardController
 */
//@WebServlet("/member")
@WebServlet( // 확장자가 .do인 요청은 모두 이리로 와라.
        name = "BoardController",
        urlPatterns = {"*.to"})
public class BoardController extends HttpServlet {
    private static final long serialVersionUID = 1L;
   
/**
 * @see HttpServlet#HttpServlet()
 */
public BoardController() {
    super();
}

/**
 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
 */
protected void doGet(HttpServletRequest request, HttpServletResponse response) 
		throws ServletException, IOException {
//		response.getWriter().append("Served at: ").append(request.getContextPath());
	
	requestPro(request,response);
}

/**
 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
 */
protected void doPost(HttpServletRequest request, HttpServletResponse response) 
		throws ServletException, IOException {
	/* 
	 * 
	   Servlet에서 Ajax할 때 requestPro를 타는 것은 동기식 처리를 요청하는 것으로 하면 안된다.
	   Ajak url에 대해서는 PrintWriter out을 활용해서 출력하면 화면단에서 받을 수 있다.   
	*/
	requestPro(request,response);
}
protected void requestPro (HttpServletRequest request,HttpServletResponse response) 
		throws ServletException, IOException{
	String view = null;
	CommandAction com = null;  // 다형성을 위한 인터페이스 만들기
	
	//uri를 받아서 주소로 넘어온 것을 해당 비즈니스 로직으로 보내고 리턴받기
	String command = request.getRequestURI();
	if(command.indexOf(request.getContextPath())==0) {
		command = command.substring(request.getContextPath().length());
	}
//		System.out.println("comman :::"+command);
	switch(command) {
	case "/list.to":{
		// 페이지
		view = new ListAction().requestPro(request, response);
		break;
	}
	case "/writeForm.to":{
		view = new WriteFormAction().requestPro(request, response);
		break;
	}
	case "/writePro.to":{
		view = new WriteProAction().requestPro(request, response);
		break;
	}

	}
	// response의 redirect(주소가 변경되게 하고 싶을 때)이거나 forward(주소는 변화없고 제어만 넘길때)한다.
	RequestDispatcher dispatcher =request.getRequestDispatcher(view);
	if(view.contains(".to")) {     // 주소부분이 바뀌게 할때 - Redirect
		response.sendRedirect(view);
	}else {
	    dispatcher.forward(request, response); // 주소는 바뀌지 않고 결과만 받을 때
		}
	}
}

1. doGet(HttpServletRequest request, HttpServletResponse response) 메소드:

GET 요청을 처리하는 메소드입니다.
requestPro(request, response) 메소드로 요청을 전달하여 처리하고 있습니다.

2.doPost(HttpServletRequest request, HttpServletResponse response) 메소드:

POST 요청을 처리하는 메소드입니다.
현재는 requestPro(request, response) 메소드로 요청을 전달하여 처리하고 있습니다.

3. requestPro(HttpServletRequest request, HttpServletResponse response) 메소드:

실제 요청을 처리하는 메소드입니다.
request와 response 객체를 매개변수로 받아 처리합니다.
요청된 URI에 따라 적절한 비즈니스 로직을 수행하고, 처리 결과에 따라 뷰를 결정합니다.
해당 뷰로 포워딩 또는 리다이렉트를 수행합니다.

4. switch 문:

클라이언트로부터의 요청 URI에 따라 적절한 액션을 선택하는 역할을 합니다.
/list.to 요청인 경우 ListAction을 생성하고, requestPro 메소드를 호출합니다.
/writeForm.to 요청인 경우 WriteFormAction을 생성하고, requestPro 메소드를 호출합니다.
/writePro.to 요청인 경우 WriteProAction을 생성하고, requestPro 메소드를 호출합니다.

5. RequestDispatcher를 이용한 포워딩 또는 리다이렉트:

선택된 뷰로 포워딩 또는 리다이렉트를 수행합니다.
.to 확장자가 포함된 뷰인 경우 리다이렉트를 수행합니다.
그 외의 경우에는 포워딩을 수행하여 결과를 전달합니다.

----------ListAction----------

게시글 목록을 가져와서 화면에 표시하는 역할을 수행합니다.

package action;

import java.io.IOException;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import model.dao.BoardDAO;
import model.dto.BoardDTO;

public class ListAction implements CommandAction {

@Override
public String requestPro(HttpServletRequest request, HttpServletResponse response)
	   throws ServletException, IOException {
	// 데이터베이스 일하는 DAO 불러서
	// 시스트 갖고 오게 하고
	// 그걸 화면에서 볼 수 있게 저장
	List<BoardDTO> articles = null;
	int total = 0;
	try {
	    total = BoardDAO.getInstance().getTotCnt();
		articles = BoardDAO.getInstance().getArticles(1,100);
	}catch(Exception e) {
		System.out.println(e.getMessage());
		e.printStackTrace();
	}
	request.setAttribute("articles", articles);
	request.setAttribute("total", total);
	return "freeboard/list.jsp";
	}
}

1. requestPro(HttpServletRequest request, HttpServletResponse response) 메소드:

실제 요청을 처리하고 결과를 생성하는 메소드입니다.
request와 response 객체를 매개변수로 받아서 요청을 처리하고 결과를 생성합니다.
데이터베이스에서 게시글 목록을 가져와서 articles에 저장하고, 게시글 총 개수를 total에 저장합니다.
가져온 게시글 목록과 총 개수를 request 객체에 속성으로 저장합니다.
결과로 게시글 목록을 보여주는 freeboard/list.jsp 뷰를 반환합니다.

2. 데이터베이스 처리:

BoardDAO 클래스를 사용하여 데이터베이스 작업을 수행합니다.
BoardDAO.getInstance().getTotCnt() 메소드를 호출하여 게시글 총 개수를 가져옵니다.
BoardDAO.getInstance().getArticles(1, 100) 메소드를 호출하여 페이지 번호와 페이지 당 게시글 개수를 지정하여 게시글 목록을 가져옵니다.

3. 결과 반환:

가져온 게시글 목록과 총 개수를 request 객체에 속성으로 저장합니다.
freeboard/list.jsp 뷰로 결과를 반환합니다.

----------BoardDAO----------

데이터베이스와의 연결을 관리하고 게시판 데이터에 접근하여 필요한 작업을 수행합니다. 게시글 목록을 가져오고 작성하는 기능을 제공하며, 데이터베이스 연결과 SQL 문 실행을 처리합니다.

package model.dao;

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

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import model.dto.BoardDTO;

public class BoardDAO {
    private static BoardDAO instance = new BoardDAO();

private BoardDAO() {}

public static BoardDAO getInstance() {
	return instance;

}
// Connection을 얻기 위한 클래스를 따로 만들고 connection을 얻어와서 처리하기
public List<BoardDTO> getArticles(int start, int end)
               throws Exception{
	Connection conn = null;
	PreparedStatement pstmt = null;
	ResultSet rs = null;
	List<BoardDTO> articles = new ArrayList<>();
	try {			
		// 데이터베이스 연결하고
		conn = DBConnector.getInstance().getConnection();
		// 데이터베이스에 넘겨주는 rs 받아서 하나씩 읽어서 리스트에 담고 리스트 리턴
		
		String sql  = "select num, readcount, step, ref, level, writer, \n";	
	           sql += "subject, reg_date, content, ip, passwd, email \n";
	           sql += "from board \n";
	           sql += "where num >= ? and num <= ?";
		pstmt = conn.prepareStatement(sql);
		pstmt.setInt(1, start);
		pstmt.setInt(2, end);
		rs = pstmt.executeQuery();
		while(rs.next()) {
			BoardDTO article = new BoardDTO();
			article.setNum       (rs.getInt("num"));
			article.setReadcount((rs.getInt("readcount")));
			article.setStep      (rs.getInt("step"));
			article.setRef       (rs.getInt("ref"));
			article.setLevel     (rs.getInt("level"));
			article.setWriter    (rs.getString("writer"));
			article.setSubject   (rs.getString("subject"));
			article.setReg_date  (rs.getString("reg_date"));
			article.setContent   (rs.getString("content"));
			article.setIp        (rs.getString("ip"));
			article.setPasswd    (rs.getString("passwd"));
			article.setEmail     (rs.getString("email"));
			articles.add(article);
		}
	}catch (Exception e) {
		System.out.println(e.getMessage());
	}finally {
		if(rs != null)rs.close();
		if(pstmt != null)pstmt.close();
		if(conn != null)conn.close();
	}
	return articles;
}
public int getTotCnt() throws Exception{
	Connection conn = null;
	PreparedStatement pstmt = null;
	ResultSet rs = null;
	int cnt = 0;
	try {
		conn = DBConnector.getInstance().getConnection();
		String sql = "select count(num) from board";
		pstmt = conn.prepareStatement(sql);
		rs = pstmt.executeQuery();
		if(rs.next()) {
			cnt = rs.getInt(1);
		}
	}catch(Exception e) {
		System.out.println(e.getMessage());
	}finally {
		if(rs != null)rs.close();
		if(pstmt != null)pstmt.close();
		if(conn != null)conn.close();
	}
	return cnt;
}

public int writeArticle(HttpServletRequest request, HttpServletResponse response) 
    throws Exception{
	Connection conn = null;
	PreparedStatement pstmt = null;
	int r = 0;
	try {
		
	//내부 메소드 호출.. num의 번호를 확인하는 것\
	int newNm = generateNum();
	BoardDTO article = new BoardDTO();
	article.setNum(newNm);
	article.setSubject(request.getParameter("subject"));
	article.setWriter(request.getParameter("writer"));
	article.setContent(request.getParameter("content"));
	article.setEmail(request.getParameter("email"));
	article.setPasswd(request.getParameter("passwd"));
	article.setIp(request.getLocalAddr());

	// 만약 답글인 경우, num을 가져오므로 해당되는 num이 ref의 참조가 되어야 한다.
	if(request.getParameter("num")!=null){
		article.setRef(Integer.parseInt(request.getParameter("num")));
	}else {
		article.setRef(newNm);
	}
	
	String sql = "insert into board(num, subject, writer, content, "
  + "email, passwd, ip, reg_date, ref) values(?,?,?,?,?,?,?,sysdate(),?)";
	
	conn = DBConnector.getInstance().getConnection();
	pstmt = conn.prepareStatement(sql);
	pstmt.setInt(1, newNm);
	pstmt.setString(2, article.getSubject());
	pstmt.setString(3, article.getWriter());
	pstmt.setString(4, article.getContent());
	pstmt.setString(5, article.getEmail());
	pstmt.setString(6, article.getPasswd());
	pstmt.setString(7, article.getIp());
	pstmt.setInt(8, article.getRef());
	
	r = pstmt.executeUpdate();
	
	}catch (Exception e) {
		System.out.println(e.getMessage());
	}
	return r;
}

private int generateNum() throws Exception{
	Connection conn = null;
	PreparedStatement pstmt = null;
	ResultSet rs = null;
	int newNm = 0;
	try {
		String sql = "select ifnull(max(num),0)+1 as num from board";
		conn = DBConnector.getInstance().getConnection();
		pstmt = conn.prepareStatement(sql);
		rs = pstmt.executeQuery();
		if(rs.next()) {
			newNm = rs.getInt("num");
		}
	}catch (Exception e) {
	}finally {
		if(rs != null)rs.close();
		if(pstmt != null)pstmt.close();
		if(conn != null)conn.close();
	}
	
	return newNm;
	}
}

1. getArticles(int start, int end) 메소드:

게시글 목록을 가져오는 메소드입니다.
start와 end 매개변수를 이용하여 특정 범위의 게시글을 조회합니다.
데이터베이스 연결 후 SQL 문을 실행하여 결과를 ResultSet에 저장합니다.
ResultSet에서 각각의 게시글 정보를 BoardDTO 객체에 저장하고, 리스트에 추가합니다.
최종적으로 게시글이 담긴 리스트를 반환합니다.

2. getTotCnt() 메소드:

게시글의 총 개수를 가져오는 메소드입니다.
데이터베이스 연결 후 SQL 문을 실행하여 결과를 ResultSet에 저장합니다.
ResultSet에서 게시글 총 개수를 가져와서 반환합니다.

3. writeArticle(HttpServletRequest request, HttpServletResponse response) 메소드:

게시글을 작성하는 메소드입니다.
요청 파라미터에서 게시글 관련 정보를 추출하여 BoardDTO 객체에 저장합니다.
새로운 게시글 번호를 생성하기 위해 generateNum() 메소드를 호출합니다.
데이터베이스 연결 후 SQL 문을 실행하여 게시글 정보를 저장합니다.

4. generateNum() 메소드:

새로운 게시글 번호를 생성하는 메소드입니다.
데이터베이스 연결 후 SQL 문을 실행하여 최대 게시글 번호를 조회한 후 1을 증가시킵니다.
생성된 새로운 게시글 번호를 반환합니다.

----------DBConnector----------

데이터베이스에 접속하기 위한 기능을 제공하는 DAO(Database Access Object) 클래스입니다.
package model.dao;

import java.sql.Connection;

import javax.naming.Context;
import javax.naming.InitialContext;
import javax.sql.DataSource;

public class DBConnector {
  //데이터베이스 접속을 위한 connection singleton방식으로
    private static DBConnector instance = new DBConnector();
    private DBConnector() {}

public static DBConnector getInstance() {
	return instance;
}
public Connection getConnection() throws Exception{
	// 데이터베이스를 연결하기 위한 드라이버 호출
	Context initCtx = new InitialContext();
	DataSource ds =
			(DataSource)initCtx.lookup("java:comp/env/jdbc/bitdb");
	return ds.getConnection();
    }
}

1. instance 변수:

DBConnector 클래스의 유일한 인스턴스를 저장하는 정적 변수입니다.
Singleton 패턴을 구현하기 위해 사용됩니다.

2. getInstance() 메소드:

DBConnector 인스턴스를 반환하는 정적 메소드입니다.
Singleton 패턴을 구현하기 위해 사용됩니다.

3. getConnection() 메소드:

데이터베이스에 연결하기 위한 Connection 객체를 반환하는 메소드입니다.
JNDI(Java Naming and Directory Interface)를 사용하여 데이터베이스에 접근합니다.
InitialContext를 통해 DataSource 객체를 찾아와서 연결을 수행합니다.
반환된 Connection 객체를 호출한 곳으로 전달합니다.

----------BoardDTO----------

데이터베이스 연결을 담당하는 클래스입니다. Singleton 디자인 패턴을 사용하여 인스턴스를 한 번만 생성하고 공유합니다.

package model.dto;

public class BoardDTO {

private int rn;
private int num;
private int readcount;
private int step; 		
private int ref;		
private int level; 		
private String writer; 		
private String subject; 	
private String reg_date; 	
private String content;		
private String ip; 			
private String passwd; 		
private String email;

public int getRn() {
	return rn;
}

//setter
public void setRn(int rn) {
this.rn = rn;
}
public int getNum() {
return num;
}
public void setNum(int num) {
this.num = num;
}
public int getReadcount() {
return readcount;
}
public void setReadcount(int readcount) {
this.readcount = readcount;
}
public int getStep() {
return step;
}
public void setStep(int step) {
this.step = step;
}
public int getRef() {
return ref;
}
public void setRef(int ref) {
this.ref = ref;
}
public int getLevel() {
return level;
}
public void setLevel(int level) {
this.level = level;
}
public String getWriter() {
return writer;
}
public void setWriter(String writer) {
this.writer = writer;
}
//getter
public String getSubject() {
return subject;
}
public void setSubject(String subject) {
this.subject = subject;
}
public String getReg_date() {
return reg_date;
}
public void setReg_date(String reg_date) {
this.reg_date = reg_date;
}
public String getContent() {
return content;
}
public void setContent(String content) {
this.content = content;
}
public String getIp() {
return ip;
}
public void setIp(String ip) {
this.ip = ip;
}
public String getPasswd() {
return passwd;
}
public void setPasswd(String passwd) {
this.passwd = passwd;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}

1. getInstance() 메소드:

DBConnector 인스턴스를 반환하는 정적 메소드입니다.
Singleton 패턴을 구현하기 위해 private 생성자와 static 인스턴스 변수를 가지고 있습니다.

2. getConnection() 메소드:

데이터베이스 연결을 위한 Connection 객체를 반환하는 메소드입니다.
JNDI(Java Naming and Directory Interface)를 사용하여 데이터베이스에 연결합니다.
InitialContext를 통해 DataSource 객체를 얻어와 Connection을 생성합니다.
BoardDTO 클래스는 게시글 정보를 담는 DTO(Data Transfer Object) 클래스입니다.
게시글의 각 속성에 대한 getter와 setter 메소드가 있습니다.

----------WriteFormAction----------

게시글 작성 폼을 보여주기 위한 액션 클래스입니다.

package action;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class WriteFormAction implements CommandAction {

@Override
public String requestPro(HttpServletRequest request, HttpServletResponse response)
		throws ServletException, IOException {
	// 답글이냐 아니냐를 비교해서 화면을 좀 다르게 할 것임...
	// setting필요
	return "freeboard/writeForm.jsp";
    }
}

1. requestPro() 메소드:

CommandAction 인터페이스의 추상 메소드를 구현한 메소드입니다.
게시글 작성 폼을 보여주기 위해 호출됩니다.
HttpServletRequest와 HttpServletResponse 매개변수를 통해 요청과 응답을 처리합니다.
폼을 보여주기 위한 필요한 데이터나 설정을 수행합니다.
freeboard/writeForm.jsp로 포워딩하여 작성 폼을 보여줍니다.

----------WriteProAction----------

게시글을 저장하고, 저장 성공 여부에 따라 사용자에게 메시지를 보여주고 목록 페이지로 이동하도록 합니다.

package action;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import model.dao.BoardDAO;

public class WriteProAction implements CommandAction {

@Override
public String requestPro(HttpServletRequest request, HttpServletResponse response)
		throws ServletException, IOException {
	
	int r = 0;
	try {
		r = BoardDAO.getInstance().writeArticle(request, response);
	} catch (Exception e) {
		System.out.println(e.getMessage());
	}
	String msg = null;
	if(r>0)msg = "글 저장 성공";
	else msg = "글 저장 실패";
	request.setAttribute("msg", msg);
	request.setAttribute("url", "list.to");
	return "freeboard/Msg.jsp";
    }
}

requestPro 메소드

는 HttpServletRequest와 HttpServletResponse 객체를 매개변수로 받습니다.

BoardDAO.getInstance().writeArticle(request, response)

를 호출하여 게시글을 저장하는 기능을 수행합니다.

  • 저장 결과에 따라 메시지와 이동할 URL을 설정합니다.
  • request 객체에 메시지와 URL을 속성으로 설정합니다.
  • 최종적으로 freeboard/Msg.jsp로 포워딩되어 결과를 출력합니다.

----------WriteForm.jsp----------

게시글 작성 폼을 나타내는 JSP 페이지

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>글쓰기</title>
<style type="text/css">
table{
margin: 0 auto;
width: 695px;
border: 1px solid #4444;
}
th, td{
border: 1px solid #4444;
width: 10%;
}
textarea{
resize: none;
}
</style>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.7.0/jquery.min.js"></script>
<script type="text/javascript" src="/js/board.js"></script>
</head>
<%@include file="top.jsp" %>
<body>

<h3 style="text-align: center;">게시글 쓰기</h3>
<hr style="margin-bottom: 5px; margin-top: 5px;">
<form action="writePro.to" method="post">
  <table>
    <tbody>
      <tr><th>글제목</th>   <td><input name="subject" type="text" size="30" class="chk" title="글제목"></td></tr>
      <tr><th>글쓴이</th>   <td><input name="writer" type="text" size="30" class="chk" title="글쓴이"></td></tr>
      <tr><th>글내용</th><td><textarea name="content" rows="10" cols="40" class="chk" title="글내용"></textarea></td></tr>
      <tr><th>이메일</th>   <td><input name="email" type="text" size="20"></td></tr>
      <tr><th>비밀번호</th>  <td><input name="passwd" type="text" size="20" class="chk pw1" title="비밀번호"></td></tr>
      <tr><th>비밀번호확인</th>
        <td>
          <input name="passwd" type="text" size="20" class="chk pw2" title="비밀번호 확인">
          <font class="pwMsg" style="font-size: 0.8em"></font>
        </td>
      </tr>
    </tbody>
    </table>
    <table style="border: none;">
      <tbody style="border: none;">
        <tr style="border: 1px solid #fff;">
          <td style="border: none;">
            <input id="submit1" type="button" value="전송">&nbsp;&nbsp;&nbsp;
            <input type="button" value="글목록" onclick="javascript:location.href='list.to'">
          </td>
        </tr>
      </tbody>
  </table>
</form>
</body>
</html>

----------Msg.jsp----------

JSTL(Core) 태그 라이브러리를 사용하여 조건문을 처리하고, JavaScript를 통해 페이지 이동을 수행합니다.

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib uri ="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>

<c:if test="${msg != null}">
  <script type="text/javascript">
    var msg = '${msg}';
    alert("처리 결과: "+msg);
  </script>
</c:if>
<script type="text/javascript">
  document.location.href="${url}";
</script>

1. ${msg}

값이 존재하는 경우, JavaScript를 사용하여 알림창을 띄워 처리 결과 메시지를 표시합니다.

2. ${url}

값을 사용하여 페이지를 이동합니다.

----------list.jsp----------

게시글 목록을 표시하는 JSP 페이지

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<title>????</title>
</head>
<body>
<%@include file="top.jsp" %>
<div class="container">
<h3 style="text-align: center;">자유 게시판</h3>
  <hr style="margin-bottom: 5px; margin-top: 5px;">
    <c:choose>
      <c:when test="${articles ==null or fn:length(articles)==0}">
        <table>
          <tbody>
            <tr>
              <td>게시글이 없습니다.</td>
            </tr>
          </tbody>
        </table>
      </c:when>
      
      <c:when test="${articles !=null or fn:length(articles)>0}">
        <table>
          <tbody>
            <tr>
              <th>글제목</th>
              <th>작성자</th>
              <th>이메일</th>
              <th>조회수</th>
              <th>작성시각</th>
            </tr>
              <c:forEach var="article" items="${articles}">
                <tr>
                  <td>${article.subject}</td>
                  <td>${article.writer}</td>
                  <td>${article.email}</td>
                  <td>${article.readcount}</td>
                  <td>${article.reg_date}</td>
                </tr>
              </c:forEach>
          </tbody>
        </table>
      </c:when>  
    </c:choose>
</div>
</body>
</html>

1. ${articles}

값이 null이거나 길이가 0인 경우, "게시글이 없습니다."라는 메시지를 표시합니다.

2. ${articles}

값이 존재하고 길이가 0보다 큰 경우, 게시글 목록을 테이블 형태로 표시합니다.

3. forEach 태그

를 사용하여 ${articles}에 있는 각 게시글을 반복적으로 표시합니다. 각 게시글의 제목, 작성자, 이메일, 조회수, 작성 시각을 테이블의 행으로 표시합니다

----------top.jsp----------

게시판의 메뉴 및 상단 부분을 표시하는 JSP 페이지

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib uri ="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<style type="text/css">
ul{
list-style-type: none;
}
li{
display: inline-block;
margin: 12px 30px 0 50px;
font-size: 13px;
}
.container li a:link{
text-decoration: none;
color: black;
}
.container li a:visited{
text-decoration: none;
color: black;
}
.container li a:active{
text-decoration: none;
color: black;
}
.container{
width: 700;
margin: 0 auto;
}
table {
margin: 0 auto;
}
</style>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.7.0/jquery.min.js"></script>
<script type="text/javascript">
  $().ready(function(){
  	  }
  	);
  });
</script>
</head>
  <div class="container">
    <ul style="text-align: right;">
      <li><a href="/writeForm.to">게시글 글쓰기</a></li>
      <li><a href="/list.to">글 목록</a></li>
      <li>총 게시글(${total})</li>
    </ul>
  </div>
    <hr style="margin-top: 10px; margin-bottom: 10px;">
<body>

</body>
</html>
  1. JSTL(Core) 태그 라이브러리를 사용하여 동적인 링크를 생성합니다.
  2. ${total} 변수를 통해 총 게시글 수를 표시합니다.
    페이지의 구성은 다음과 같습니다:
  3. <ul> 태그를 사용하여 메뉴를 나열합니다.
    메뉴에는 "게시글 글쓰기"와 "글 목록" 링크가 있습니다.
  4. 상단 부분에는 ${total} 변수를 사용하여 총 게시글 수를 표시합니다.
    이 페이지는 주어진 스타일과 링크를 생성하여 게시판의 메뉴와 상단 부분을 보여줍니다.

----------board.js----------

폼의 유효성 검사와 비밀번호 일치 여부를 체크하여 서브밋 동작을 제어하는 기능을 구현합니다.

$(function(){
	chk1=false; // validate
	chk2=false; // pw
	$('#submit1').on('click', function(){
		var pw1 = $('.pw1').val();
		var pw2 = $('.pw2').val();
		  if(pw1 != "" && pw1.trim().length>0 && pw2 != "" && pw2.trim().length>0){
		  if(pw1 != pw2){
			  //alert('비밀번호가 일치하지 않습니다.');
			  $('font[class=pwMsg]').text('');
		 	  $('font[class=pwMsg]').attr('color','red');
			  $('font[class=pwMsg]').text('비밀번호가 일치하지 않습니다.');
			  $('.pw2').focus();
			  chk2 = false;
			  return false // 서브밋  불가
		  }else{
			  $('font[class=pwMsg]').text('');
		 	  $('font[class=pwMsg]').attr('color','blue');
			  $('font[class=pwMsg]').text('비밀번호가 일치합니다.');
			  chk2 = true;
		  }
		}
		if(valichk()){  // 누군가 빈칸 걸린것임
		    chk1 = false;
			return false; // false는 리턴을 하니 else가 필요 없다.
		}else{
			chk1=true;			
		}
		alert(chk1+"::"+chk2);
		if(chk1 && chk2){
		    $('form').submit();
		}else{
			return false;
		}
	});
});

function valichk(){
	var flen = $('form .chk').length;
	for(let i=0; i<flen; i++){
		if($('.chk').eq(i).val()== "" || 
		   $('.chk').eq(i).val()== null || 
		   $('.chk').eq(i).val().trim()==""){
			   alert($('.chk').eq(i).attr("title")+"은/는 필수 입력 항목입니다.");
			   $('.chk').eq(i).focus();
			   return true;
		   }
	}
	return false;
}

1. $('#submit1').on('click', function(){...});:

"submit1" ID를 가진 버튼이 클릭되었을 때 실행되는 함수입니다.

2. 입력된 비밀번호(pw1, pw2)를 가져와 비교하여 일치 여부를 확인합니다.

비밀번호가 일치하지 않을 경우, 경고 메시지를 표시하고 chk2 변수를 false로 설정합니다.
비밀번호가 일치할 경우, 일치함을 나타내는 메시지를 표시하고 chk2 변수를 true로 설정합니다.

3. valichk() 함수를 호출하여 폼의 입력 필드가 비어있는지 검사합니다.

입력 필드가 비어있는 경우, 해당 필드에 대한 경고 메시지를 표시하고 true를 반환합니다.

4. 유효성 검사와 비밀번호 일치 여부 검사 결과(chk1 및 chk2)에 따라 서브밋 동작을 제어합니다.

유효성 검사와 비밀번호 일치 여부 모두 true인 경우, 폼을 서브밋합니다.
그렇지 않은 경우, 서브밋을 방지합니다.




0개의 댓글