仿9GAG製做過程(五)

有話要說:

在作完了數據展現功能以後,就想着完善整個APP。發現如今後臺很是的混亂,有好多點都不具有,比方說:圖片應該有略縮圖和原圖,段子、評論、點贊應該聯動起來,段子應該有建立時間等。數據庫

因而就從新設計了數據庫,從新爬取了數據,從新設計了後臺接口。json

此次主要講此次重構的主要內容。框架

數據庫設計:

 

一共設計了六張表,分別爲數據庫設計

  1. 段子表,主要存放每個段子的圖片等信息
  2. 評論表,主要存放評論信息,評論能夠上傳圖片
  3. 用戶表
  4. 標籤表,每條段子發表以前會自定義標籤,該表存放的就是這些標籤
  5. 點贊記錄表,由於用戶點贊與段子之間是多對多的關係,所以要加一張表用來存放點贊記錄
  6. 段子標籤關聯表,由於段子和標籤是多對多的,所以須要多一張表存放關聯關係

接口設計:

橙色的爲表,咖啡色爲接口。工具

目前設計了十四個接口,上圖寫明瞭各接口和相關的表之間的關係。post

後臺結構:

bean包下爲基本實體類;this

implement包下爲消息實體類的子類;spa

dao包爲涉及到數據庫的具體實現類;設計

servlet爲接口類;code

util爲過程當中用到的工具類。

具體例子:

下面以查詢段子接口爲例,介紹具體的結構。

bean類:

消息實體類:

 1 public class MessageEntity {  2 
 3     // 返回信息描述
 4     private String reason;  5     // 返回碼
 6     private int errorCode;  7 
 8     public String getReason() {  9         return reason; 10  } 11 
12     public void setReason(String reason) { 13         this.reason = reason; 14  } 15 
16     public int getErrorCode() { 17         return errorCode; 18  } 19 
20     public void setErrorCode(int errorCode) { 21         this.errorCode = errorCode; 22  } 23 
24 }

 

段子消息實體類:

 1 public class TopicMessageEntity extends MessageEntity {  2 
 3     // 獲取段子的結果
 4     private List<TopicEntity> result;  5 
 6     public List<TopicEntity> getResult() {  7         return result;  8  }  9 
10     public void setResult(List<TopicEntity> result) { 11         this.result = result; 12  } 13 
14 }

 

 段子實體類:

 1 public class TopicEntity {  2 
 3     // 段子標識
 4     private int id;  5     // 段子做者
 6     private String author = "";  7     // 段子標題
 8     private String title = "";  9     // 段子點贊數
10     private int upvote; 11     // 段子評論數
12     private int commentCount; 13     // 段子略縮圖地址
14     private String thumbNail = ""; 15     // 段子原圖地址
16     private String orgPicture = ""; 17     // 段子發表時間
18     private String postTime = ""; 19     
20     // 點的是贊仍是踩,0表明沒點,1表明贊,-1表明踩
21     private int like = 0; 22 
23     public int getId() { 24         return id; 25  } 26 
27     public void setId(int id) { 28         this.id = id; 29  } 30 
31     public String getAuthor() { 32         return author; 33  } 34 
35     public void setAuthor(String author) { 36         this.author = author; 37  } 38 
39     public String getTitle() { 40         return title; 41  } 42 
43     public void setTitle(String title) { 44         this.title = title; 45  } 46 
47     public int getUpvote() { 48         return upvote; 49  } 50 
51     public void setUpvote(int upvote) { 52         this.upvote = upvote; 53  } 54 
55     public int getCommentCount() { 56         return commentCount; 57  } 58 
59     public void setCommentCount(int commentCount) { 60         this.commentCount = commentCount; 61  } 62 
63     public String getThumbNail() { 64         return thumbNail; 65  } 66 
67     public void setThumbNail(String thumbNail) { 68         this.thumbNail = thumbNail; 69  } 70 
71     public String getOrgPicture() { 72         return orgPicture; 73  } 74 
75     public void setOrgPicture(String orgPicture) { 76         this.orgPicture = orgPicture; 77  } 78 
79     public String getPostTime() { 80         return postTime; 81  } 82 
83     public void setPostTime(String postTime) { 84         this.postTime = postTime; 85  } 86 
87     public int getLike() { 88         return like; 89  } 90 
91     public void setLike(int like) { 92         this.like = like; 93  } 94 
95 }

 

這裏和數據庫表略有不一樣,主要是like字段。

like字段表明的是當前獲取數據的人對該段子是否點了贊。

dao層:

查詢段子方法:

 1 public List<TopicEntity> query(int topicId, int count, boolean after) {  2         List<TopicEntity> topicList = new ArrayList<TopicEntity>();  3 
 4         if (topicId <= 0) {  5             topicId = 0;  6  }  7 
 8         if (count <= 0) {  9             count = 10; 10  } 11 
12         if (after) { 13  queryAfter(topicId, count, topicList); 14         } else { 15  queryBefore(topicId, count, topicList); 16  } 17 
18         return topicList; 19     }
 1 private void queryAfter(int topicId, int count, List<TopicEntity> topicList) {  2         String queryAfter = "SELECT * FROM 9gag_topics WHERE id > ? LIMIT ?";  3 
 4         Connection conn = DatabaseUtil.getConnection();  5         PreparedStatement pstmt = null;  6         ResultSet rs = null;  7 
 8         try {  9             pstmt = conn.prepareStatement(queryAfter); 10             pstmt.setInt(1, topicId); 11             pstmt.setInt(2, count); 12             rs = pstmt.executeQuery(); 13 
14             while (rs.next()) { 15                 TopicEntity topicEntity = new TopicEntity(); 16                 topicEntity.setId(rs.getInt("id")); 17                 topicEntity.setAuthor(rs.getString("author")); 18                 topicEntity.setTitle(rs.getString("title")); 19                 topicEntity.setUpvote(rs.getInt("upvote")); 20                 topicEntity.setCommentCount(rs.getInt("commentcount")); 21                 topicEntity.setThumbNail(rs.getString("thumbnail")); 22                 topicEntity.setOrgPicture(rs.getString("orgpicture")); 23                 topicEntity.setPostTime(rs.getString("posttime")); 24  topicList.add(topicEntity); 25  } 26         } catch (SQLException e) { 27  e.printStackTrace(); 28         } finally { 29  DatabaseUtil.close(conn, pstmt, rs); 30  } 31     }
 1 private void queryBefore(int topicId, int count, List<TopicEntity> topicList) {  2         String queryBefore = "SELECT * FROM 9gag_topics WHERE id < ? ORDER BY id DESC LIMIT ?";  3 
 4         Connection conn = DatabaseUtil.getConnection();  5         PreparedStatement pstmt = null;  6         ResultSet rs = null;  7 
 8         try {  9             pstmt = conn.prepareStatement(queryBefore); 10             pstmt.setInt(1, topicId); 11             pstmt.setInt(2, count); 12             rs = pstmt.executeQuery(); 13 
14             while (rs.next()) { 15                 TopicEntity topicEntity = new TopicEntity(); 16                 topicEntity.setId(rs.getInt("id")); 17                 topicEntity.setAuthor(rs.getString("author")); 18                 topicEntity.setTitle(rs.getString("title")); 19                 topicEntity.setUpvote(rs.getInt("upvote")); 20                 topicEntity.setCommentCount(rs.getInt("commentcount")); 21                 topicEntity.setThumbNail(rs.getString("thumbnail")); 22                 topicEntity.setOrgPicture(rs.getString("orgpicture")); 23                 topicEntity.setPostTime(rs.getString("posttime")); 24  topicList.add(topicEntity); 25  } 26         } catch (SQLException e) { 27  e.printStackTrace(); 28         } finally { 29  DatabaseUtil.close(conn, pstmt, rs); 30  } 31 
32         // 獲取完數據以後逆序,由於查找的時候是逆序
33  Collections.reverse(topicList); 34     }

 

這三個方法實現了查詢指定段子前(或者後)count條記錄。

 servlet層:

 1 protected void doPost(HttpServletRequest request, HttpServletResponse response)  2             throws ServletException, IOException {  3         response.setContentType("text/json; charset=utf-8");  4         PrintWriter out = response.getWriter();  5 
 6         TopicMessageEntity message = new TopicMessageEntity();  7         TopicDAO topicDao = new TopicDAO();  8         UpvoteDAO upvoteDao = new UpvoteDAO();  9         Gson gson = GsonUtil.getGson(); 10 
11         request.setCharacterEncoding("utf-8"); 12         response.setCharacterEncoding("utf-8"); 13 
14         int topicId = Integer.parseInt(request.getParameter("topicId")); 15         int count = Integer.parseInt(request.getParameter("count")); 16         boolean after = Boolean.parseBoolean(request.getParameter("after")); 17         String author = request.getParameter("author"); 18 
19         if (count <= 0) { 20             message.setErrorCode(-1); 21             message.setReason("count值不能爲負數!"); 22  out.print(gson.toJson(message)); 23             return; 24  } 25 
26         try { 27             List<TopicEntity> topics = topicDao.query(topicId, count, after); 28             
29             // 判斷做者是否點過贊
30             if (author != null) { 31                 List<UpvoteEntity> upvoteList = upvoteDao.findUpvoteByAuthor(author, true); 32                 if (upvoteList != null) { 33                     for (TopicEntity topic : topics) { 34                         for (UpvoteEntity upvote : upvoteList) { 35                             if (upvote.getLikedId() == topic.getId()) { 36                                 int like = upvote.isLiked() ? 1 : -1; 37  topic.setLike(like); 38  } 39  } 40  } 41  } 42  } 43             
44  Collections.reverse(topics); 45             message.setErrorCode(0); 46             message.setReason("success"); 47  message.setResult(topics); 48         } catch (Exception e) { 49             message.setErrorCode(-1); 50  message.setReason(e.getMessage()); 51         } finally { 52  out.print(gson.toJson(message)); 53  } 54 
55     }

主要邏輯:查找到須要的段子→遍歷段子→若是段子被點過贊或者踩,就把段子相應字段更改成贊或者踩→因爲查出來的數據時順序的,要改成逆序展現。

反思:

此次主要重構了後臺的設計邏輯,其實還有好多不完備的地方。

經過此次重構,明白了一個要點。要作一件事情首先要規劃好,首先是設計,把一切的流程,框架設計好以後循序漸進的作。這樣作出來的東西纔會比較好。

不然在過程當中會很混亂,嚴重影響效率。

預告:

下一章準備講述點讚的邏輯,由於點讚的邏輯比較複雜。

 

你們若是有什麼疑問或者建議能夠經過評論或者郵件的方式聯繫我,歡迎你們的評論~

相關文章
相關標籤/搜索