工程搭建及首页功能
# 工程搭建及首页功能
# 依赖安装
# 前端项目
先安装依赖再运行
npm install
npm run build
npm run dev
2
3
# maven 工程安装
创建父工程 mashen-blog
pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.example</groupId>
<artifactId>mashen-blog</artifactId>
<version>1.0-SNAPSHOT</version>
<modules>
<module>blog-api</module>
</modules>
<packaging>pom</packaging>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.0</version>
<relativePath/>
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.76</version>
</dependency>
<dependency>
<groupId>commons-collections</groupId>
<artifactId>commons-collections</artifactId>
<version>3.2.2</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.4.3</version>
</dependency>
<!-- https://mvnrepository.com/artifact/joda-time/joda-time -->
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time</artifactId>
<version>2.10.10</version>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
在父工程下创建一个新的子模块 blog-api
pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>mashen-blog</artifactId>
<groupId>org.example</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>blog-api</artifactId>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<!-- 排除 默认使用的logback -->
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- log4j2 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-log4j2</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-aop</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-mail</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.76</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
</dependency>
<dependency>
<groupId>commons-collections</groupId>
<artifactId>commons-collections</artifactId>
<version>3.2.2</version>
</dependency>
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.4.3</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time</artifactId>
<version>2.10.10</version>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>0.9.1</version>
</dependency>
<dependency>
<groupId>com.qiniu</groupId>
<artifactId>qiniu-java-sdk</artifactId>
<version>[7.7.0, 7.7.99]</version>
</dependency>
</dependencies>
</project>
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
在子模块中创建 application.properties
#server
server.port= 8888
spring.application.name=mszlu_blog
# datasource
spring.datasource.url=jdbc:mysql://localhost:3306/blog?useUnicode=true&characterEncoding=UTF-8&serverTimeZone=UTC
spring.datasource.username=root
spring.datasource.password=123456
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
#mybatis-plus
mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl
mybatis-plus.global-config.db-config.table-prefix=ms_
2
3
4
5
6
7
8
9
10
11
12
启动类
@SpringBootApplication
public class BlogApp {
public static void main(String[] args) {
SpringApplication.run(BlogApp.class, args);
}
}
2
3
4
5
6
# 配置类
在 blog-api 模块下创建 com.iekr.blog.config 包
创建 mybatisplus 配置类 MybatisPlusConfig
@Configuration
@MapperScan("com.iekr.blog.dao.mapper")
public class MybatisPlusConfig {
/**
* 分页插件
*/
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
interceptor.addInnerInterceptor(new PaginationInnerInterceptor());
return interceptor;
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
创建 webconfig 配置类 WebConfig
@Configuration
public class WebConfig implements WebMvcConfigurer {
@Override
public void addCorsMappings(CorsRegistry registry) {
//跨域配置
registry.addMapping("/**").allowedOrigins("http://localhost:8080");
}
}
2
3
4
5
6
7
8
9
10
# 文章列表
# 接口说明
接口 url:/articles
请求方式:POST
请求参数:
| 参数名称 | 参数类型 | 说明 |
|---|---|---|
| page | int | 当前页数 |
| pageSize | int | 每页显示的数量 |
返回数据:
{
"success": true,
"code": 200,
"msg": "success",
"data": [
{
"id": 1,
"title": "springboot介绍以及入门案例",
"summary": "通过Spring Boot实现的服务,只需要依靠一个Java类,把它打包成jar,并通过`java -jar`命令就可以运行起来。\r\n\r\n这一切相较于传统Spring应用来说,已经变得非常的轻便、简单。",
"commentCounts": 2,
"viewCounts": 54,
"weight": 1,
"createDate": "2609-06-26 15:58",
"author": "12",
"body": null,
"tags": [
{
"id": 5,
"avatar": null,
"tagName": "444"
},
{
"id": 7,
"avatar": null,
"tagName": "22"
},
{
"id": 8,
"avatar": null,
"tagName": "11"
}
],
"categorys": null
},
{
"id": 9,
"title": "Vue.js 是什么",
"summary": "Vue (读音 /vjuː/,类似于 view) 是一套用于构建用户界面的渐进式框架。",
"commentCounts": 0,
"viewCounts": 3,
"weight": 0,
"createDate": "2609-06-27 11:25",
"author": "12",
"body": null,
"tags": [
{
"id": 7,
"avatar": null,
"tagName": "22"
}
],
"categorys": null
},
{
"id": 10,
"title": "Element相关",
"summary": "本节将介绍如何在项目中使用 Element。",
"commentCounts": 0,
"viewCounts": 3,
"weight": 0,
"createDate": "2609-06-27 11:25",
"author": "12",
"body": null,
"tags": [
{
"id": 5,
"avatar": null,
"tagName": "444"
},
{
"id": 6,
"avatar": null,
"tagName": "33"
},
{
"id": 7,
"avatar": null,
"tagName": "22"
},
{
"id": 8,
"avatar": null,
"tagName": "11"
}
],
"categorys": null
}
]
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
# 表结构
文章表
CREATE TABLE `blog`.`ms_article` (
`id` bigint(0) NOT NULL AUTO_INCREMENT,
`comment_counts` int(0) NULL DEFAULT NULL COMMENT '评论数量',
`create_date` bigint(0) NULL DEFAULT NULL COMMENT '创建时间',
`summary` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '简介',
`title` varchar(64) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '标题',
`view_counts` int(0) NULL DEFAULT NULL COMMENT '浏览数量',
`weight` int(0) NOT NULL COMMENT '是否置顶',
`author_id` bigint(0) NULL DEFAULT NULL COMMENT '作者id',
`body_id` bigint(0) NULL DEFAULT NULL COMMENT '内容id',
`category_id` int(0) NULL DEFAULT NULL COMMENT '类别id',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 25 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
2
3
4
5
6
7
8
9
10
11
12
13
标签表
CREATE TABLE `blog`.`ms_tag` (
`id` bigint(0) NOT NULL AUTO_INCREMENT,
`article_id` bigint(0) NOT NULL,
`tag_id` bigint(0) NOT NULL,
PRIMARY KEY (`id`) USING BTREE,
INDEX `article_id`(`article_id`) USING BTREE,
INDEX `tag_id`(`tag_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
2
3
4
5
6
7
8
用户表
CREATE TABLE `blog`.`ms_sys_user` (
`id` bigint(0) NOT NULL AUTO_INCREMENT,
`account` varchar(64) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '账号',
`admin` bit(1) NULL DEFAULT NULL COMMENT '是否管理员',
`avatar` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '头像',
`create_date` bigint(0) NULL DEFAULT NULL COMMENT '注册时间',
`deleted` bit(1) NULL DEFAULT NULL COMMENT '是否删除',
`email` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '邮箱',
`last_login` bigint(0) NULL DEFAULT NULL COMMENT '最后登录时间',
`mobile_phone_number` varchar(20) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '手机号',
`nickname` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '昵称',
`password` varchar(64) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '密码',
`salt` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '加密盐',
`status` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '状态',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 16 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
# POJO
创建 com.iekr.blog.dao.pojo 包
Article
@Data
public class Article {
public static final int Article_TOP = 1;
public static final int Article_Common = 0;
private Long id;
private String title;
private String summary;
private int commentCounts;
private int viewCounts;
/**
* 作者id
*/
private Long authorId;
/**
* 内容id
*/
private Long bodyId;
/**
*类别id
*/
private Long categoryId;
/**
* 置顶
*/
private int weight = Article_Common;
/**
* 创建时间
*/
private Long createDate;
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
SysUser
@Data
public class SysUser {
private Long id;
private String account;
private Integer admin;
private String avatar;
private Long createDate;
private Integer deleted;
private String email;
private Long lastLogin;
private String mobilePhoneNumber;
private String nickname;
private String password;
private String salt;
private String status;
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
Tag
@Data
public class Tag {
private Long id;
private String avatar;
private String tagName;
}
2
3
4
5
6
7
8
9
10
# Dao
创建 com.iekr.blog.dao.pojo 包
ArticleMapper
public interface ArticleMapper extends BaseMapper<Article> {
}
2
TagMapper
public interface TagMapper extends BaseMapper<Tag> {
/**
* 根据文章id查询标签列表
* @param articleId
* @return
*/
List<Tag> findTagsByArticleId(Long articleId);
}
2
3
4
5
6
7
8
在 resources 目录下创建包 com.iekr.blog.dao.mapper
注意一个一个目录创建需要层次结构,否则 mybatis-plus 无法找自定义 xml 文件
创建 TagMapper.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!--MyBatis配置文件-->
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.iekr.blog.dao.mapper.TagMapper">
<sql id="all">
id,avatar,tag_name as tagName
</sql>
<select id="findTagsByArticleId" parameterType="long" resultType="com.iekr.blog.dao.pojo.Tag">
select <include refid="all" /> from ms_tag
<where>
id in
(select tag_id from ms_article_tag where article_id = #{articleId})
</where>
</select>
</mapper>
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
SysUserMapper
public interface SysUserMapper extends BaseMapper<SysUser> {
}
2
# VO
创建 com.iekr.blog.vo 包
创建 Result 类
@Data
@AllArgsConstructor
public class Result {
private boolean success;
private int code;
private String msg;
private Object data;
public static Result success(Object data) {
return new Result(true, 200, "success", data);
}
public static Result fail(int code, String msg) {
return new Result(false, code, msg, null);
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
创建 ArticleVo 类
@Data
public class ArticleVo {
private String id;
private String title;
private String summary;
private int commentCounts;
private int viewCounts;
private int weight;
/**
* 创建时间
*/
private String createDate;
private String author;
// private ArticleBodyVo body;
private List<TagVo> tags;
// private CategoryVo category;;
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
TagVo
@Data
public class TagVo {
private Long id;
private String tagName;
}
2
3
4
5
6
7
在 vo 包下创建 params 包再创建 PageParmas 类
@Data
public class PageParmas {
private int page = 1;
private int pageSize = 10;
}
2
3
4
5
# Service
创建 com.iekr.blog.service 包
ArticleService
public interface ArticleService {
/**
* 分页查询 文章列表
* @param pageParmas
* @return
*/
Result listArticle(PageParmas pageParmas);
}
2
3
4
5
6
7
8
ArticleServiceImpl
@Service
public class ArticleServiceImpl implements ArticleService {
@Autowired
private ArticleMapper articleMapper;
@Autowired
private TagService tagService;
@Autowired
private SysUserService sysUserService;
@Override
public Result listArticle(PageParmas pageParmas) {
Page<Article> page = new Page<>(pageParmas.getPage(), pageParmas.getPageSize());
LambdaQueryWrapper<Article> queryWrapper = new LambdaQueryWrapper<>();
//是否置顶以及根据创建日期倒序
queryWrapper.orderByDesc(Article::getWeight, Article::getCreateDate);
Page<Article> articlePage = articleMapper.selectPage(page, queryWrapper);
List<Article> records = articlePage.getRecords();
List<ArticleVo> articleVoList = copyList(records, true, true);
return Result.success(articleVoList);
}
private List<ArticleVo> copyList(List<Article> records, boolean isTag, boolean isAuthor) {
List<ArticleVo> articleVoList = new ArrayList<>();
for (Article record : records) {
articleVoList.add(copy(record, isTag, isAuthor));
}
return articleVoList;
}
private ArticleVo copy(Article article, boolean isTag, boolean isAuthor) {
ArticleVo articleVo = new ArticleVo();
//使用spring给我们提供的工具类进行相同属性相同类型的拷贝
BeanUtils.copyProperties(article, articleVo);
//不相同/不同类型的手动赋值
articleVo.setCreateDate(new DateTime(article.getCreateDate()).toString("yyyy-MM-dd HH:mm"));
if (isTag) {
Long articleId = article.getId();
articleVo.setTags(tagService.findTagsByArticleId(articleId));
}
if (isAuthor) {
Long authorId = article.getAuthorId();
articleVo.setAuthor(sysUserService.findUserById(authorId).getNickname());
}
return articleVo;
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
TagService
public interface TagService {
List<TagVo> findTagsByArticleId(Long articleId);
}
2
3
4
TagServiceImpl
@Service
public class TagServiceImpl implements TagService {
@Autowired
private TagMapper tagMapper;
@Override
public List<TagVo> findTagsByArticleId(Long articleId) {
//mybatisPlus 无法进行多表查询 需要我们手动写xml或sql语句
List<Tag> tags =tagMapper.findTagsByArticleId(articleId);
return copyList(tags);
}
public TagVo copy(Tag tag){
TagVo tagVo = new TagVo();
BeanUtils.copyProperties(tag,tagVo);
return tagVo;
}
public List<TagVo> copyList(List<Tag> tagList){
List<TagVo> tagVoList = new ArrayList<>();
for (Tag tag : tagList) {
tagVoList.add(copy(tag));
}
return tagVoList;
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
SysUserService
public interface SysUserService {
SysUser findUserById(Long id);
}
2
3
SysUserServiceImpl
@Service
public class SysUserServiceImpl implements SysUserService {
@Autowired
private SysUserMapper sysUserMapper;
@Override
public SysUser findUserById(Long id) {
SysUser sysUser = sysUserMapper.selectById(id);
if (sysUser == null) {
sysUser = new SysUser();
sysUser.setNickname("Iekr");
}
return sysUser;
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
# Controller
创建 com.iekr.blog.controller 包
ArticleController
@RestController
@RequestMapping("articles")
public class ArticleController {
@Autowired
private ArticleService articleService;
/**
* 首页 文章列表
*
* @param pageParmas
* @return
*/
@PostMapping
public Result listArticle(@RequestBody PageParmas pageParmas) {
return articleService.listArticle(pageParmas);
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# 首页 - 最热标签
# 接口说明
接口 url:/tags/hot
请求方式:GET
请求参数:无
返回数据:
{
"success": true,
"code": 200,
"msg": "success",
"data": [
{
"id":1,
"tagName":"4444"
}
]
}
2
3
4
5
6
7
8
9
10
11
# Controller
TagsController
@RestController
@RequestMapping("tags")
public class TagsController {
@Autowired
private TagService tagService;
@GetMapping("hot")
public Result hot() {
int limit = 6;
List<TagVo> tagVoList = tagService.hots(limit);
return Result.success(tagVoList);
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
# Service
TagService
List<TagVo> hots(int limit);
TagServiceImpl
@Override
public List<TagVo> hots(int limit) {
//查询拥有文章最多的标签
List<Long> tagIds = tagMapper.findHotsTagIds(limit);
// 根据tagIds查询 tag_id和tag_name
if (CollectionUtils.isEmpty(tagIds)) {
return Collections.emptyList();
}
List<Tag> tagList = tagMapper.findTagsByTagIds(tagIds);
return copyList(tagList);
}
2
3
4
5
6
7
8
9
10
11
# Dao
TagMapper
/**
* 查询最热门的标签前n条
* @param limit
* @return
*/
List<Long> findHotsTagIds(int limit);
/**
* 根据tag列表 查询tag_name
* @param tagIds
* @return
*/
List<Tag> findTagsByTagIds(List<Long> tagIds);
2
3
4
5
6
7
8
9
10
11
12
13
TagMapper.xml
<select id="findHotsTagIds" parameterType="int" resultType="java.lang.Long">
select tag_id
from ms_article_tag
group by tag_id
order by count(*) desc
limit #{limit}
</select>
<select id="findTagsByTagIds" parameterType="list" resultType="com.iekr.blog.dao.pojo.Tag">
select id,tag_name as tagName from ms_tag where id in
<foreach collection="tagIds" item="tagId" separator="," open="(" close=")">
#{tagId}
</foreach>
</select>
2
3
4
5
6
7
8
9
10
11
12
13
14
# 统一异常处理
不管是 controller 层还是 service,dao 层,都有可能报异常,如果是预料中的异常,可以直接捕获处理,如果是意料之外的异常,需要统一进行处理,进行记录,并给用户提示相对比较友好的信息。
创建 com.iekr.blog.handler 包
创建 AllExceptionHandler 类
@ControllerAdvice
public class AllExceptionHandler {
@ExceptionHandler(Exception.class)
@ResponseBody
public Result doException(Exception ex) {
ex.printStackTrace();
return Result.fail(-999, "系统异常");
}
}
2
3
4
5
6
7
8
9
10
# 首页 - 最热文章
# 接口说明
接口 url:/articles/hot
请求方式:POST
返回数据:
{
"success": true,
"code": 200,
"msg": "success",
"data": [
{
"id": 1,
"title": "springboot介绍以及入门案例",
},
{
"id": 9,
"title": "Vue.js 是什么",
},
{
"id": 10,
"title": "Element相关",
}
]
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# Controller
ArticleController
/**
* 首页 最热文章
*
* @return
*/
@PostMapping("hot")
public Result hotArticle() {
int limit = 5;
return articleService.hotArticle(limit);
}
2
3
4
5
6
7
8
9
10
# Service
ArticleService
/**
* 最热文章
* @param limit
* @return
*/
Result hotArticle(int limit);
2
3
4
5
6
ArticleServiceImpl
@Override
public Result hotArticle(int limit) {
LambdaQueryWrapper<Article> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.orderByDesc(Article::getViewCounts);
queryWrapper.select(Article::getId, Article::getTitle);
queryWrapper.last("limit " + limit);
//select id,title from article oder by view_counts desc limit 5;
List<Article> articles = articleMapper.selectList(queryWrapper);
return Result.success(copyList(articles, false, false));
}
2
3
4
5
6
7
8
9
10
# 首页 - 最新文章
# 接口说明
接口 url:/articles/new
请求方式:POST
返回数据:
{
"success": true,
"code": 200,
"msg": "success",
"data": [
{
"id": 1,
"title": "springboot介绍以及入门案例",
},
{
"id": 9,
"title": "Vue.js 是什么",
},
{
"id": 10,
"title": "Element相关",
}
]
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# Controller
ArticleController
/**
* 首页 最新文章
* @return
*/
@PostMapping("new")
public Result newArticles() {
int limit = 5;
return articleService.newArticles(limit);
}
}
2
3
4
5
6
7
8
9
10
# Service
ArticleService
/**
* 最新文章
* @param limit
* @return
*/
Result newArticles(int limit);
2
3
4
5
6
ArticleServiceImpl
@Override
public Result newArticles(int limit) {
LambdaQueryWrapper<Article> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.orderByDesc(Article::getCreateDate);
queryWrapper.select(Article::getId, Article::getTitle);
queryWrapper.last("limit " + limit);
//select id,title from article oder by create_date desc limit 5;
List<Article> articles = articleMapper.selectList(queryWrapper);
return Result.success(copyList(articles, false, false));
}
2
3
4
5
6
7
8
9
10
# 首页 - 文章归档
# 接口说明
接口 url:/articles/listArchives
请求方式:POST
返回数据:
{
"success": true,
"code": 200,
"msg": "success",
"data": [
{
"year": "2021",
"month": "6",
"count": 2
}
]
}
2
3
4
5
6
7
8
9
10
11
12
13
# Controller
ArticleController
/**
* 首页 文章归档
* @return
*/
@PostMapping("listArchives")
public Result listArchives() {
return articleService.listArchives();
}
2
3
4
5
6
7
8
# Service
ArticleService
/**
* 文章归档
* @return
*/
Result listArchives();
2
3
4
5
ArticleServiceImpl
@Override
public Result listArchives() {
// select YEAR(FROM_UNIXTIME(create_date/1000)) as year,MONTH(FROM_UNIXTIME(create_date/1000)) as month,count(*) as count from ms_article group by year,month
List<Archives> archivesList = articleMapper.listArchives();
return Result.success(archivesList);
}
2
3
4
5
6
# Dao
ArticleMapper
List<Archives> listArchives();
ArticleMapper.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!--MyBatis配置文件-->
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.iekr.blog.dao.mapper.ArticleMapper">
<select id="listArchives" resultType="com.iekr.blog.dao.dos.Archives">
select YEAR(FROM_UNIXTIME(create_date/1000)) as year,MONTH(FROM_UNIXTIME(create_date/1000)) as month,count(*) as count from ms_article group by year,month
</select>
</mapper>
2
3
4
5
6
7
8
9
# Do
创建 com.iekr.blog.dao.dos 包
创建 Archives 类
@Data
public class Archives {
private Integer year;
private Integer month;
private Long count;
}
2
3
4
5
6
7
8
9