BBS论坛-跟帖添加与查询

本文档详述了一个论坛跟帖系统的实现细节,包括如何通过主贴ID查询跟帖,跟帖的添加及分页展示,以及如何在前端页面上进行富文本编辑和展示。系统采用Spring框架,JdbcTemplate进行数据库操作,实现主贴和跟帖的关联查询,并通过JSTL标签在JSP页面上展示数据。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在这里插入图片描述## 通过主贴的id查询跟帖
mrbbs=>myresource=>com.mrkj.ygl.controller=>SecondPageController.java

package com.mrkj.ygl.controller;

import java.util.HashMap;
import java.util.Map;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

import com.mrkj.ygl.service.SecondPageService;

@Controller
public class SecondPageController {
     //注入Service
	@Resource
	SecondPageService sps;
	
	@RequestMapping(value="/secondPageContent")
	public ModelAndView goSecondPage(String mainId,
	    @RequestParam(name="page",defaultValue="1") Integer page,
	    @RequestParam(name="row",defaultValue="3")Integer row){
			ModelAndView mav = new ModelAndView("myJSP/secondPage");
			//根据传递过来的mainId查找my_main与my_second表
			Map<String, Object> mainAndSecond = sps.getMainAndSeconds(mainId,(page-1)*row, row);
			//将返回值传递给JSP
			//mav.addObject("mainAndSeconds", mainAndSecond);
			mav.addObject("mainAndSeconds", mainAndSecond);
			
			Long count = sps.getSecondCount(mainId);
			Map<String,String> parm = new HashMap<> ();
			parm.put("mainId", mainId);
			String pageHtml = sps.getPage(count, page, row,parm);
			mav.addObject("pageHtml", pageHtml);
			
			return mav;
	}

	
	
	
	
	
	
	//接收JSP传递过来的参数main_id与富文本content,保存至数据库my_second表中
@RequestMapping(value="/saveSecondPage")
public ModelAndView saveSecondPage(HttpServletRequest request,
                                       String mainId,String content){
	ModelAndView mav = new ModelAndView();
	String mainCreatuser = request.getRemoteAddr();
	int result = sps.saveSecondPage(mainId, content, mainCreatuser);
	if (result == 1){
		mav.setViewName("redirect:/secondPageContent?mainId="+mainId);
	}else{
		mav.setViewName("404");
	}
	return mav;
}
	
}

查询主贴链接跟帖的数据

mrbbs=>myresource=>com.mrkj.ygl.service=>SecondPageService.java

package com.mrkj.ygl.service;

import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import java.util.UUID;

import javax.annotation.Resource;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Service;
//@service注解声明通知Spring该层为服务层,如果服务层不使用@Service注解声明
//导致控制层无法注入
@Service
public class SecondPageService {

	//注入Spring JdbcTemplate,在resource资源包下
 	//“com.mrkj.ygl.config.RootConfig.java”文件下配置JdbcTemplate,否则无法注入
	@Resource
	JdbcTemplate jdbc;
	//获取帖子详细信息包括主贴跟帖
	public Map<String,Object> getMainAndSeconds(String mainId,Integer start,Integer offset){
 		//定义SQL语句,查询主贴
		String sql_select_mymain = "select main_id,main_title,"
				+ "main_content,DATE_FORMAT(main_creatime,'%Y年%m月%d日 %h点%i分%s秒') "
				+ "as main_creatime,main_creatuser,"
				+ "main_commend from my_main where main_id = ?";
 		//定义SQL语句,查询跟帖
		String sql_select_mysecond = "select sec_id,main_id,"
				+ "sec_content,DATE_FORMAT(sec_creatime,'%Y年%m月%d日 %h点%i分%s秒') "
				+ "as sec_creatime,sec_creatuser,sec_sequence"
				+ " from my_second where main_id = ? ORDER BY sec_creatime"
				+ " LIMIT ?,?";
		//执行SQL语句,获取主贴信息
		Map<String, Object> mainContent = jdbc.queryForMap(sql_select_mymain,mainId);
		//判断主贴是否存在,如果存在查找跟帖
		if (mainContent != null){
			List<Map<String, Object> > seconds
 			= jdbc.queryForList(sql_select_mysecond,mainId,start,offset);
			mainContent.put("seconds", seconds);
		}
		//返回帖子模型
		return mainContent;
	}
	
	
	public int saveSecondPage (String main_id,String content,String creatuser){
		String sql_insert_mysecond = "insert INTO my_second "
		+ "(sec_id,main_id,sec_content,sec_creatime,sec_creatuser,sec_sequence) "
		+ "VALUES (?,?,?,now(),?,'1')";
		
		return jdbc.update(sql_insert_mysecond,UUID.randomUUID().toString(),
				main_id,content,creatuser);
	}
	
	public Long getSecondCount(String mainId){
		//是用count关键字,查询总条数
		String sql_select_mymain = "select count(sec_id) as count from my_second where main_id=?";
		//执行SQL语句,返回总条数
		return (Long)jdbc.queryForMap(sql_select_mymain,mainId).get("count");
	}
		//count:数据库当中数据总条数
	 	//currentPage:当前页数
	 	//offset:每页显示多少条数护具
	 	//parm:附加参数	
	public String getPage (Long count,Integer currentPage,
	                                  Integer offset,Map<String,String> parm){
			//将当前页数转换为Long类型,统一类型方便计算
			Long currentLong = Long.parseLong(currentPage+"");
	 		//记录总页数,初始化给定值为0L。因为是长整形所以要在数字后面加L 
			Long countPage = 0L;
			//计算总页数,根据数据库数据总条数与每页显示数,计算总页数
	 		//使用求余运算,判断是否整除,如果整除,使用总条数除以每页记录数,得出总页数
	 		//如果没有整除那么证明有余数,使用总条数除以每页记录数加一得出总页数
			if(count%offset!=0){
				countPage = count/offset+1;
			}else{
				countPage = count/offset;
			}
			//将parm里的参数拼接成URL参数
			StringBuffer sbParm = new StringBuffer("");

			//判断parm是否为空,设置额外附加参数
			if (parm!=null){
	 			//从Map类型获取entrySet,Entry是Map的一个元素,以键值对呈现
				Set<Entry<String, String>>  entrySet = parm.entrySet();
				//迭代Set获取Entry元素,将键作为参数名,值作为参数值拼接成URL参数
				for (Entry<String, String>  entry : entrySet){
					sbParm.append("&"+entry.getKey()+"="+entry.getValue());
				}
				
			}
			
			StringBuffer sb = new StringBuffer();
	 		//前一页,判断当前页数是否大于1
			if (currentPage> 1){
	 			//大于1的话,前一页就等于当前页减1
				sb.append("<span class=\"page\"> <a href=\"?page="+(currentPage-1));
				sb.append(sbParm);
				sb.append("\"> «</a> </span> ");
			}else{
	 			//不大于1的话,证明是第一页
				sb.append("<span class=\"page\"> <a href=\"?page=1");
	 			//增加URL参数
				sb.append(sbParm);
				sb.append("\"> «</a> </span> ");
			}
	 		//第一页
			sb.append("<span class=\"page\" style=\"width: 50px !important;\"> ");
			//连接永远指向第一页
			sb.append("<a href=\"?page=1");
	 		//增加URL参数
			sb.append(sbParm);
			sb.append("\"> start</a> ");
			sb.append("</span> ");
			//如果总页数减去当前页数大于5,那么证明可以显示5个分页
			if ((countPage-currentLong+1) >=5){
				for (Long i = currentLong ; i<currentPage+5;i++){
					sb.append("<span class=\"page\"> ");
					sb.append("<a href=\"?page="+i);
	 				//增加URL参数
					sb.append(sbParm);
					sb.append("\"> "+i+"</a> ");
					sb.append("</span> ");
				}
			}
	 		//如果总页数减4大于0那么证明从总页数任然够5页
	 		else if (countPage-4 >  0){
				for (long i = countPage-4 ; i<= countPage;i++){
	 				//顺序迭代页面 
					sb.append("<span class=\"page\"> ");
					sb.append("<a href=\"?page="+i);
	 				//增加URL参数
					sb.append(sbParm);
					sb.append("\"> "+i+"</a> ");
					sb.append("</span> ");
				}
			}
	 		//否则总页数不够5页
	 		else{
				for (long i = 1 ; i<= countPage;i++){
	 				//顺序迭代页面
					sb.append("<span class=\"page\"> ");
					sb.append("<a href=\"?page="+i);
	 				//增加URL参数
					sb.append(sbParm);
					sb.append("\"> "+i+"</a> ");
					sb.append("</span> ");
				}
			}
			//增加最后一页
			sb.append("<span class=\"page\" style=\"width: 40px !important;\"> ");
	 		//这里使用了三目表达式,判断总页数是否为0,如果是0返回1否则返回总页数
			sb.append("<a href=\"?page="+(countPage==0?1:countPage));
	 		//增加URL参数
			sb.append(sbParm);
			sb.append("\"> end</a> ");
			sb.append("</span> ");
			//判断是否拥有下一页
			if (currentLong<countPage){
				sb.append("<span class=\"page\"> ");
	 			//如果满足条件下一页为当前页加1
				sb.append("<a href=\"?page="+currentLong+1);
				sb.append(sbParm);
				sb.append("\"> »</a> ");
				sb.append("</span> ");
			}else{
				sb.append("<span class=\"page\"> ");
	 			//为满足条件,下一页为当前页
				sb.append("<a href=\"?page="+currentLong);
				sb.append(sbParm);
				sb.append("\"> »</a> ");
				sb.append("</span> ");
			}
			
			sb.append("<span> ");
			sb.append("共"+countPage+"页");
			sb.append("</span> ");

			return sb.toString();
		}
}

跟帖的添加以及查询分页

mrbbs=>WebContent=>WEB-INF=>view=>myJSP=>secondPage.jsp

<%@page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPEhtml> 
<html> 
<head> 
<%@include file="/../../../jspHead.jsp" %>	
	<!--  分页样式  -->
 	<style type="text/css"> 
	.page{
		display:inline-block;			/*  内联对象  */
		border: 1px solid ;			/*  1像素边框  */
		font-size: 20px;				/*  文字大小20像素  */
		width: 30px;					/*  宽度30像素  */
		height: 30px;				/*  高度30像素  */
		background-color: #1faeff;	/*  设置背景色  */
		text-align: center;			/*  居中对齐  */
	}
	a,a:hover{ text-decoration:none; color:#333}
 	</style> 
</head> 
<body> 
<!--  以下代码使用JSTL标签迭代出主帖与跟帖  --> 
<div class="container-fluid" > 
	<table class="table table-bordered"> 
		<tr> 
 		<!--  td标签,该单元格定义了发帖人信息与身份  -->
		<td class="tbl"> 
		<div style="text-align: center;"> 
		<p> 楼主</p> 
		<a> <img alt="" src="<%=basePath %>image/ico_000.gif" /> </a> 
		</div>
		<!--  table标签,该表格用户展示发帖人信息  -->
		<table class="table" style="background-color:#e5edf2; "> 
		<tr> 
		<td> 昵称:</td> 
 		<!--  使用EL表达式获取发帖人  -->
		<td> ${mainAndSeconds.main_creatuser }</td> 
		</tr> 
		<tr> 52
		<td> 性别:</td> 
		<td> 男</td> 
		</tr> 
		<tr> 
		<td> 年龄:</td> 
		<td> 18</td> 
		</tr> 
		<tr> 
		<td> 发帖数:</td> 
		<td> 10</td> 
		</tr> 
		<tr> 
		<td> 回帖数:</td> 
		<td> 10</td> 
		</tr> 
		</table> 
		</td> 
 		<!--  td标签,该单元格定义了帖子详细内容  -->
		<td class="tbr"> 
		<div style="height: 65px;padding-left: 20px;padding-top: 1px;"> 
		<h3>
 		<!--  使用EL表达式获取帖子标题  -->
 		<a style="color: #ifaeff"> ${mainAndSeconds.main_title }</a>
 		</h3> 
		</div> 
 		<!-- 下面这是画出一条横线 --> 
 		<div style="width:98%;height:1px;margin-bottom:10px;
 			padding:0px;background-color:#D5D5D5;overflow:hidden;"> 
 		</div> 
		<p class="text-right" style="padding-right: 90px;"> 
		<span style="padding-right: 30px;"> 
 		<!--  EL表达式获取发帖时间  -->
		<a style="color: #78BA00;">
 		发表于:${mainAndSeconds.main_creatime }
 		</a> 
		</span> 
		<span> </span> 
		</p> 
 		<!-- 下面这是画出一条横线 --> 
 		<div style="width:98%;height:1px;margin-bottom:10px;
                        padding:0px;background-color:#D5D5D5;overflow:hidden;"> 
 		</div> 
		<div style="padding-top: 12px;min-height: 380px;"> 
 		<!--  EL表达式获取帖子内容  -->
		${mainAndSeconds.main_content }
		</div> 
 		<!-- 下面这是画出一条横线 --> 
 		<div style="width:98%;height:1px;margin-bottom:10px;
                       padding:0px;background-color:#D5D5D5;overflow:hidden;"> 
 		</div> 
		<!--  上下间隙90像素  --> 
		<div style="padding-right: 90px;"> 
					
		</div> 
				
		</td> 
		</tr> 
		<!--  choose标签相当于Java代码当中switch case语句 -->
		<c:choose> 
 		<%--  when标签相当于Java当中switch case语句当中的case,属性test设置条件 --%>
		<c:when test="${not empty mainAndSeconds.seconds }"> 
 		<!--  forEach相当于Java代码当中的循环  -->
 		<!--  属性items为要迭代元素  -->
 		<!--  属性item为迭代出来的元素  -->
 		<!--  属性varStatus为迭代状态  -->
		<c:forEach	items="${mainAndSeconds.seconds}" var="item" varStatus="vs"> 
		<tr> 
		<td class="tbl"> 
		<div style="text-align: center;"> 
 		<!--  利用vs获取迭代序号,vs索引从0开始  -->
		<p> 第${vs.index+1 }楼</p> 
		<a> 
 		<img alt="" src="<%=basePath%>image/ico_000.gif" /> 
 		</a> 
		</div> 
		<table class="table" style="background-color:#e5edf2; "> 
		<tr> 
		<td> 昵称:</td>
 		<!--  获取跟帖人  --> 
		<td> ${item.creatuser }</td> 
		</tr> 
		<tr> 
		<td> 性别:</td> 
		<td> 男</td> 
		</tr> 
		<tr> 
		<td> 年龄:</td> 
		<td> 18</td> 
		</tr> 
		<tr> 
		<td> 发帖数:</td> 
		<td> 10</td> 
		</tr> 
		<tr> 
		<td> 回帖数:</td> 
		<td> 10</td> 
		</tr> 
		</table> 
		</td> 
						
		<td class="tbr"> 
		<span style="padding-right: 30px;"> 
 		<!--  获取跟帖时间  -->
		<a style="color: #78BA00;"> 回复于:${item.sec_creatime } 
 		</a> 
		</span> 
 		<div style="width:98%;height:1px;margin-bottom:10px;
                                    padding:0px; background-color:#D5D5D5;overflow:hidden;"> 
 		</div> 
		<div style="padding-top: 12px;min-height: 380px;"> 
 		<!--  获取跟帖内容  -->
		${item.sec_content }
		</div> 
 		<div style="width:98%;height:1px;margin-bottom:10px;
                                    padding:0px; background-color:#D5D5D5;overflow:hidden;"> 
 		</div> 

		</td> 
		</tr> 
		</c:forEach> 
		</c:when> 
		</c:choose> 
	</table> 
	
	<!-- *******************************分页***************************** -->
	
	<div style="padding: 10px 5px;text-align: right;"> ${pageHtml }</div> 
	
	<!-- *********************************富文本******************************* -->
	 
	<form action="<%=basePath %>saveSecondPage" method="post"> 
 		<!--  隐藏字段,记录主帖id,发帖表跟帖时,将该字段传递之后台,将主帖与跟帖关系绑定 -->
 		<input name="mainId" type="hidden" value="${mainAndSeconds.main_id }"> 
		<p class="text-right" style="padding-right: 90px;"> 
			<button type="submit" class="btn btn-primary btn-xs text-right" > 
			<span class="glyphicon glyphicon-edit" aria-hidden="true"> </span> 
				回复帖子
 			</button> 
		</p> 
 		<!-- 加载编辑器的容器 --> 
 		<script id="container" name="content" type="text/plain"> 

 		</script> 
</form>
	<!-- 配置文件 -->
    <script type="text/javascript" src="<%=basePath %>uedit/js/ueditor.config.js"></script>
    <!-- 编辑器源码文件 -->
    <script type="text/javascript" src="<%=basePath %>uedit/js/ueditor.all.js"></script>
    <!-- 实例化编辑器 -->
    <script type="text/javascript">
   		 var editor = UE.getEditor('container');
    </script>
</div> 

</body> 
</html> 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值