基於SSM框架的簡單問答社區

前言:學習了Spring、SpringMVC、MyBatis框架後,開發了一套簡單的問答社區,前端採用Bootstrap開發框架。

版本資訊

IDEA:2020.1.2

JDK:14.0.1

Maven:3.6.3

Tomcat:9.0.36

MySql:8.0.20

Bootstrap:3.3.7

JQuery:3.5.1

 

本文目錄

一、需求分析

1、社區功能

2、數據表

3、數據表關係

二、功能實現

1、用戶註冊、登錄、註銷

2、提出問題、修改問題、刪除問題

3、對問題進行回答、修改回答、刪除回答

4、對回答進行評論、修改評論、刪除評論

5、用戶關注(取消關注)用戶、用戶關注(取消關注)問題、用戶贊同(取消贊同)回答

三、程式碼介紹

1、項目結果

2、部分程式碼

四、效果演示

1、登錄

2、註冊

3、用戶主頁面

4、提出問題

5、查看所有問題

6、根據條件查詢問題

7、問題及回答資訊

8、回答及評論資訊

9、用戶資訊

10、個人資料

11、關注的用戶、粉絲、關注的問題、贊同的回答、提出的問題、做出的回答、做出的評論

12、修改、刪除問題,修改、刪除回答

五、程式碼/功能優化

六、開發經驗

 

一、需求分析

1、社區功能

①用戶註冊、登錄、註銷;

②提出問題、修改問題、刪除問題;

③對問題進行回答、修改回答、刪除回答;

④對回答進行評論、修改評論、刪除評論;

⑤用戶關注(取消關注)用戶、用戶關注(取消關注)問題,用戶贊同(取消贊同)回答。

2、數據表

(1)用戶表

user 用戶表
user_id 用戶編號
user_name 用戶名
user_nickname 用戶昵稱
user_avatar 用戶頭像
user_sex 用戶性別
user_email 用戶郵箱
user_password 用戶密碼
user_register_time 用戶註冊時間
user_last_login_time 用戶最近一次登錄的時間
user_last_login_ip 用戶最近一次登錄的IP地址
user_status 用戶狀態

(2)問題表

question 問題表 外鍵
question_id 問題編號  
question_user_id 問題的提問者用戶編號(關聯用戶表) user表user_id
question_title 問題標題  
question_content 問題內容  
question_view_count 問題瀏覽量  
question_follow_count 問題關注量  
question_answer_count 問題回答量  
question_update_time 問題更新時間  
question_create_time 問題創建時間  
question_status 問題狀態  

(3)回答表

answer 回答表 外鍵
answer_id 回答編號  
answer_user_id 回答的回答者用戶編號(關聯用戶表) user表user_id
answer_question_id 回答所對應的問題編號(關聯問題表) question表question_id
answer_content 回答內容  
answer_view_count 回答瀏覽量  
answer_agree_count 回答贊同量  
answer_update_time 回答更新時間  
answer_create_time 回答創建時間  
answer_status 回答狀態  

(4)評論表

comment 評論表 外鍵/備註
comment_id 評論編號  
comment_user_id 評論的評論者用戶編號(關聯用戶表) user表user_id
comment_answer_id 評論所對應的回答編號(關聯回答表) answer表answer_id
comment_last_id 評論上一條評論編號 為Null表示一級評論,否則為二級及以上評論(對評論的評論)
comment_content 評論內容  
comment_time 評論時間  

comment_last_id本打算用作辨別回答下的一級評論(對回答的評論)和二級及以下評論(即對評論進行回復的評論),但感覺過於複雜,所有目前並未使用該欄位

(5)用戶與用戶關係表

user_relation_user 用戶關注用戶關係表 外鍵
from_user_id 發起用戶編號 user表user_id
to_user_id 關注用戶編號 user表user_id

(6)用戶與問題關係表

user_relation_question 用戶關注問題關係表 外鍵
from_user_id 發起用戶編號 user表user_id
to_question_id 關注問題編號 question表question_id

(7)用戶與回答關係表

user_relation_answer 用戶與回答關係表 外鍵
from_user_id 發起用戶編號 user表user_id
to_answer_id 贊同回答編號 answer表answer_id

3、數據表關係

(1)user表、question表、answer表、comment表之間的關係

(2)user表、question表、answer表、user_relation_user表、user_relation_question表、user_relation_answer表之間的關係

 

(3)由於有外鍵約束

①當刪除用戶時,user_relation_user表、user_relation_question表、user_relation_answer表的該用戶關係均會刪除,question表、answer表、comment表也會刪除該用戶的問題、回答及評論;

②當刪除問題時,user_relation_question表的用戶關係會刪除,question表、answer表也會刪除問題及回答;

③當刪除回答時,user_relation_answer表的用戶關係會刪除,answer表、comment表也會刪除回答及評論。

二、功能實現

1、用戶註冊、登錄、註銷

①用戶註冊時,查找資料庫中是否已經存在註冊的用戶名,如果不存在,則將用戶填入的註冊資訊,以及設置當前時間為用戶註冊時間、最近一次登錄時間,存入資料庫;

②用戶登錄時,首先前端先進行限制數據的輸入格式,密碼與確認密碼相同,進入後端查找資料庫中是否存在該用戶,不存在則顯示用戶名不存在。若存在該用戶名,再將密碼和資料庫中密碼進行匹配,匹配成功則登錄成功,反之失敗;

③用戶登錄後,可點擊註銷按鈕,根據存入session域中的登錄用戶編號刪除資料庫中用戶。

注意:記錄最近一次登錄IP功能還未實現,user_last_login_ip一直默認為null。user_status用來判斷用戶狀態或身份,比如1為普通用戶,0為管理員,2為禁用等,目前未開通這些功能,一直默認user_status=1。

2、提出問題、修改問題、刪除問題

①提出問題,根據session域中的登錄用戶編號及輸入的問題資訊,以及設置當前時間為問題創建時間、更新時間,存入資料庫;

②修改問題,根據問題編號查出資料庫中的該問題資訊,根據輸入修改問題資訊,以及設置當前時間為問題更新時間,再存入資料庫;

③刪除問題,根據問題編號刪除資料庫中的問題。

3、對問題進行回答、修改回答、刪除回答

①進行回答,根據登錄用戶編號、問題編號、輸入的回答資訊,以及設置當前時間為回答創建時間、更新時間,存入資料庫;

②修改回答,根據回答編號查出資料庫中的該回答資訊,根據輸入修改回答資訊,以及設置當前時間為回答更新時間,再存入資料庫;

③刪除回答,根據回答編號刪除資料庫中的回答。

4、對回答進行評論、修改評論、刪除評論

①進行評論,根據登錄用戶編號、回答編號、輸入的評論資訊,以及設置當前時間為評論時間,存入資料庫;

②修改評論,根據評論編號查出資料庫中的該評論資訊,根據輸入修改評論資訊,以及設置當前時間為評論時間,再存入資料庫;

③刪除評論,根據評論編號刪除資料庫中的評論。

注意:評論時間及最新的評論時間,修改後立即更新時間,查看不到首次評論時間

5、用戶關注(取消關注)用戶、用戶關注(取消關注)問題,用戶贊同(取消贊同)回答

①用戶關注用戶、問題,用戶贊同回答,首先查詢資料庫中是否存在對應關係,如果有則提示關注(贊同)失敗,如果沒有則將關係存入資料庫;

②用戶取消關注用戶、問題,用戶取消贊同回答,首先查詢資料庫中是否存在對應關係,如果有則提示取消關注(贊同)成功,如果有則將資料庫中的對應關係刪除。

三、程式碼介紹

1、項目結構

 

2、部分程式碼

(1)實體類

(2)dao層

java

xml

(3)service層

介面

 

實現類

(4)controller層

 

(5)測試類

 

(6)前端

JavaScript

 

HTML

四、效果演示

1、登錄

 

2、註冊

3、用戶主頁面

4、提出問題

5、查看所有問題

6、根據條件查詢問題

 

7、問題及回答資訊(點擊所有問題或者查詢問題得到的頁面的問題標題鏈接)

 

在頁面可以關注、取消關注問題,僅展示關注問題

①點擊關注,如果已經關注,彈出「您已經關注該問題,不能重複關注」,如果沒關注,彈出「關注成功」

②點擊取消關注,如果已經關注,彈出「取消關注成功」,如果沒關注,彈出「您還未關注該問題,不可取消關注」

關注成功

關註失敗

回答問題

8、回答及評論資訊(點擊問題及回答資訊頁面的回答的詳細內容鏈接)

 

在此頁面可以贊同及取消贊同該回答,其顯示效果與關注與取消關注問題類型類似,故不展示

評論回答

9、用戶資訊(在問題及回答頁面可點擊問題標題右下側名字鏈接,在回答及評論頁面可點擊回答或評論者的名字鏈接,進入用戶詳情資訊頁面)

以上圖的回答及評論頁面為例,點擊評論者周伯通

在此頁面可以關注或取消關注用戶,與對問題和回答的操作同理,如果已經關注再點擊關注、未關注點擊取消關注會失敗,未關注點擊取消關注、已關注點擊關注會失敗

10、個人資料(在用戶頁面可進入個人資料)

 

此頁面可點擊修改用戶資訊

輸入框內容默認為用戶資訊,用戶名不可更改,修改成功會返回個人頁面

註銷用戶會刪除資料庫內用戶資訊,直接退出到登錄頁面,此處不再展示

11、用戶頁面的個人資料及退出登錄按鈕下有7個鏈接,分別可進入對應頁面,此處僅挑部分頁面展示

①關注的用戶

②贊同的回答

③提出的問題

④做出的評論

12、修改、刪除問題,修改、刪除回答,修改、刪除評論

可在用戶頁面「提出的問題」、「做出的回答」、「做出的評論」鏈接進入後的頁面點擊問題標題、回答內容、評論內容鏈接進入對應資訊頁面,然後對其進行修改、刪除,此處僅以做出的回答舉例

①用戶頁面,點擊做出的回答鏈接

②進入回答頁面,點擊回答內容的鏈接

③進入回答詳細頁面,點擊修改回答按鈕

④進入修改回答頁面,顯示原回答內容

⑤修改回答內容

 ⑥點擊確認修改

⑦點擊返回回答頁面

⑧點擊刷新回答按鈕,即可查看更新後的回答

五、程式碼/功能優化

1、question表可不需要question_answer_count欄位,直接從answer表查詢某問題下有多少回答即可,本項目因為多次需要查詢問題時顯示問題有多少評論量,故也作為一個屬性。但因為question表內question_answer_count值在新增answer時加1,在刪除answer時減1,此過程在service層實現,如果直接對資料庫操作,question表的question_answer_count欄位的值可能不正確;

2、對問題、回答、評論等進行新增、更新、刪除時有時會進入一個成功或失敗提示頁面,可以進行程式碼優化讓其直接返回之前的資訊頁面,然後進行彈窗提示成功或失敗資訊,不需要單獨進入一個提示頁面;

3、user表的user_avtar(用戶頭像)、user_last_login_ip(用戶最近一次登錄的IP地址)、user_status(用戶狀態)等欄位並未使用,可以在後續開發中加上這些欄位對應的功能;

4、comment表中的comment_last_id欄位表示評論的上一條評論編號,利用該欄位可以實現對評論進行評論, 此目的主要是想實現回復功能,考慮到有些複雜本項目並未實現此功能

六、開發經驗

在開發過程中,熟悉了許多過程,也在一些細節的地方浪費了許多時間,經過不斷學習測試得出了一些經驗,現挑一些印象深刻的進行歸納

1、Dao層的類的方法傳入參數為多個時,需要用到@Parma

比如對user_relation_user表進行新增某用戶關注某用戶時,對應的UserRelationDao的類的方法為

1 void saveUserFollowUser(Integer from_user_id,Integer to_user_id);

UserRelationMapper.xml對應的xml語句

1 <!-- 新增某用戶關注某用戶 -->
2 <insert id="saveUserFollowUser" parameterType="java.lang.Integer" >
3     INSERT INTO user_relation_user (from_user_id,to_user_id)
4     VALUES (#{from_user_id},#{to_user_id})
5 </insert>

此時會報錯,因為找不到from_user_id與to_user_id

此時需要用到@Parma,修改後的UserRelationDao的類的方法為

1 void saveUserFollowUser(@Param("from_user_id") Integer from_user_id,@Param("to_user_id") Integer to_user_id);

2、JSP頁面發送url請求時要用<%=path%>加上後續路徑(JSP頭部加上<% String path = request.getContextPath();%>)

此處的內容關於JSP文件的絕對路徑與相對路徑,相關介紹網上已經很詳細了

如在用戶頁面查看所有問題

1  <a href="Question/DisplayAllQuestionList"><button type="button" class="btn btn-success btn-lg" style="width: 150px;">查看所有問題</button></a>

對應的Controller類的方法為

 1 /**
 2  * 表現層 問題
 3  */
 4 @Controller
 5 @RequestMapping(value = "/Question")
 6 public class QuestionController {
 7     
 8     ······
 9     
10     /**
11     * 進入所有問題列表頁面
12     * @param model
13     * @return
14     */
15     @RequestMapping(value = "/DisplayAllQuestionList")
16     public String DisplayAllQuestionList(Model model) {
17     ......
18     }   
19     
20     ······
21 }

此時的請求可能會出錯,我在運行過程中出現了404的問題,如圖所示

此時修改為如下方式即可

1 <% String path = request.getContextPath();%>
2 
3 ......
4 
5 <a href="<%=path%>/Question/DisplayAllQuestionList"><button type="button" class="btn btn-success btn-lg" style="width: 150px;">查看所有問題</button></a>
6 ·····

3、在JSP頁面顯示時間的格式問題

如果在java中用java.util.Date接收MySQL中的datetime,然後直接在JSP頁面顯示,會輸出以下格式

此時的程式碼為

1 ······
2 <td>
3     <p>${question.question_create_time}</p>
4 </td>
5 ······

使用Jstl語句的格式化輸出

1 <%@ taglib prefix="fmt" uri="//java.sun.com/jsp/jstl/fmt" %>
2     
3     ······
4     
5 <td>
6     <fmt:formatDate value="${question.question_create_time}" pattern="yyyy-MM-dd HH:mm:ss"/>
7 </td>
8     
9     ······

此時會輸出以下格式

4、在之前發表過的隨筆有過以下總結

(1)@Controller類的方法如何解析ajax請求發送的請求體中的多個參數

//www.cnblogs.com/huskysir/p/13295631.html

(2)關於在JSP頁面識別不了EL表達式的情況

//www.cnblogs.com/huskysir/p/13283569.html

(3)JSP頁面中同時遍歷多個List集合

//www.cnblogs.com/huskysir/p/13282191.html

(4)如何從默認的index.jsp頁面跳轉到其他頁面

//www.cnblogs.com/huskysir/p/13273734.html

(5)SSM前後端資訊交互

//www.cnblogs.com/huskysir/p/13308418.html

 七、GitHub程式碼地址

//github.com/HuskySir/JAVA

Tags: