Bean Treasure community project actual combat tutorial introduction
This project is equipped with a free video tutorial, the supporting code is completely open source. Build from scratch the most widely used Springboot+Vue front-end and back-end separation multi-user community project. This project is of moderate difficulty. For your convenience, each video tutorial will correspond to each submission on Github.
Screenshot of project Home Page
Open source code address
The front end
Video Tutorial Address
Video tutorial
Front-end technology stack
Vue Vuex Vue Router Axios Bulma Buefy Element Vditor DarkReader
Back-end technology stack
Spring Boot Mysql Mybatis MyBatis-Plus Spring Security JWT Lombok
Post list backend implementation
Entity class
BmsPost
import com.baomidou.mybatisplus.annotation.*;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.NotBlank;
import java.io.Serializable;
import java.util.Date;
@Data
@Builder
@TableName("bms_post")
@AllArgsConstructor
@NoArgsConstructor
public class BmsPost implements Serializable {
private static final long serialVersionUID = 1L;
/** * primary key */
@TableId(value = "id", type = IdType.ASSIGN_ID)
private String id;
/** ** title */
@notblank (message = "header must not be empty ")
@TableField(value = "title")
private String title;
/** * markdown */
@notblank (message = "The content must not be empty ")
@TableField("`content`")
private String content;
/** * author ID */
@TableField("user_id")
private String userId;
/** * number of comments */
@TableField("comments")
@Builder.Default
private Integer comments = 0;
/** * select */
@TableField("collects")
@Builder.Default
private Integer collects = 0;
/** * Number of views */
@TableField("view")
@Builder.Default
private Integer view = 0;
/** * column ID, default is no column */
@TableField("section_id")
@Builder.Default
private Integer sectionId = 0;
/** ** top */
@TableField("top")
@Builder.Default
private Boolean top = false;
/** ** */
@TableField("essence")
@Builder.Default
private Boolean essence = false;
/** * create time */
@TableField(value = "create_time", fill = FieldFill.INSERT)
private Date createTime;
/** * Change the time */
@TableField(value = "modify_time", fill = FieldFill.UPDATE)
private Date modifyTime;
/** * description */
@TableField("summary")
private String summary;
}
Copy the code
BmsPostTag
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import lombok.experimental.Accessors;
import java.io.Serializable;
@Data
@TableName("bms_post_tag")
@Accessors(chain = true)
public class BmsPostTag implements Serializable {
private static final long serialVersionUID = -5028599844989220715L;
@TableId(type = IdType.AUTO)
private Integer id;
@TableField("tag_id")
private String tagId;
@TableField("post_id")
private String postId;
}
Copy the code
BmsTag
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Builder;
import lombok.Data;
import lombok.experimental.Accessors;
import java.io.Serializable;
@Data
@Builder
@TableName("bms_tag")
@Accessors(chain = true)
public class BmsTag implements Serializable {
private static final long serialVersionUID = 3257790983905872243L;
@TableId(type = IdType.ASSIGN_ID)
private String id;
@TableField("name")
private String name;
/** * Number of topics under the current tag */
@TableField("post_count")
@Builder.Default
private Integer postCount = 1;
}
Copy the code
Vo
package com.notepad.blog.domain.vo;
import com.notepad.blog.domain.BmsTag;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class PostVO implements Serializable {
private static final long serialVersionUID = -261082150965211545L;
/** * article ID */
private String id;
/** * user ID */
private String userId;
/** ** avatar */
private String avatar;
/** * User name */
private String alias;
/** * account */
private String username;
/** ** title */
private String title;
/** * comment statistics */
private Integer comments;
/** ** top */
private Boolean top;
/** ** */
private Boolean essence;
/** * select */
private Integer collects;
/** * topic tag */
private List<BmsTag> tags;
/** * views */
private Integer view;
/** * create time */
private Date createTime;
/** * Change the time */
private Date modifyTime;
/** ** **
private String summary;
}
Copy the code
mapper.xml
<! DOCTYPEmapper PUBLIC "- / / mybatis.org//DTD Mapper / 3.0 / EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="com.notepad.blog.mapper.BmsPostMapper">
<resultMap id="postVo" type="com.notepad.blog.domain.vo.PostVO">
<id column="id" property="id"/>
<result column="title" property="title"/>
<result column="user_id" property="userId"/>
<result column="comments" property="comments"/>
<result column="view" property="view"/>
<result column="collects" property="collects"/>
<result column="top" property="top"/>
<result column="essence" property="essence"/>
<result column="create_time" property="createTime"/>
<result column="modify_time" property="modifyTime"/>
<result column="username" property="username"/>
<result column="alias" property="alias"/>
<result column="avatar" property="avatar"/>
<result column="summary" property="summary"/>
<collection property="tags" ofType="com.notepad.blog.domain.BmsTag">
<result column="tag_id" property="id"/>
<result column="name" property="name"/>
<result column="post_count" property="postCount"/>
</collection>
</resultMap>
<select id="selectListAndPage" resultMap="postVo">
SELECT
p.id,
p.title,
<! -- p.user_id, -->
p.comments,
p.VIEW,
p.collects,
p.top,
p.essence,
p.create_time,
p.modify_time,
u.username,
u.alias,
u.avatar,
pt.tag_id,
t.`name`,
t.post_count
FROM
bms_post p
LEFT JOIN ums_user u ON p.user_id = u.id
LEFT JOIN bms_post_tag pt ON p.id = pt.post_id
LEFT JOIN bms_tag t ON t.id = pt.tag_id
<if test="tab == 'hot'">
<where>
date(p.create_time) <= date_add(curdate(), interval 1 day)
and date(p.create_time) >= date_sub(curdate(), interval 7 day)
</where>
order by p.view desc, p.create_time desc
</if>
<if test="tab == 'atest'">
order by p.create_time desc
</if>
<if test="tab == 'update'">
<where>
p.modify_time is NOT null
</where>
order by p.modify_time desc
</if>
</select>
</mapper>
Copy the code
The mapper layer
public interface BmsPostMapper extends BaseMapper<BmsPost> {
Page<PostVO> selectListAndPage(@Param("page") Page<PostVO> page, @Param("tab") String tab);
}java
Copy the code
controller
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.notepad.blog.common.api.ApiResult;
import com.notepad.blog.domain.vo.PostVO;
import com.notepad.blog.service.BmsPostService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/post")
public class BmsPostController {
@Autowired
private BmsPostService postService;
@GetMapping("/list")
public ApiResult<Page<PostVO>> list(@RequestParam(value = "tab", defaultValue = "latest") String tab,
@RequestParam(value = "pageNo", defaultValue = "1") Integer pageNo,
@RequestParam(value = "size", defaultValue = "10") Integer pageSize) {
Page<PostVO> list = postService.getList(pageNo,pageSize, tab);
returnApiResult.success(list); }}Copy the code
service
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.notepad.blog.domain.BmsPost;
import com.notepad.blog.domain.BmsPostTag;
import com.notepad.blog.domain.BmsTag;
import com.notepad.blog.domain.vo.PostVO;
import com.notepad.blog.mapper.BmsPostMapper;
import com.notepad.blog.mapper.BmsPostTagMapper;
import com.notepad.blog.mapper.BmsTagMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.stream.Collectors;
@Service
public class BmsPostService extends ServiceImpl<BmsPostMapper.BmsPost> {
@Autowired
private BmsPostMapper postMapper;
public Page<PostVO> getList(Integer pageNo, Integer pageSize, String tab) {
Page<PostVO> page = new Page(pageNo, pageSize);
// query the article
Page<PostVO> iPage = postMapper.selectListAndPage(page, tab);
returniPage; }}Copy the code