Mr丶冷文

文章 分类 评论
115 10 5698

站点介绍

冷文学习者(KEVINLU98.COM),记录一个北漂小码农的日常业余生活
友链申请地址(直接评论即可): 传送门

(十九)评论功能及评论局部刷展示

MR丶冷文 2022-10-14 205 3条评论 个人博客项目视频教程 javaspringboot个人博客博客系统

首页 / 正文
Freewind主题v1.5版本已发布,下载请移步Freewind 1.5,同时还有主题伴生插件Freewind Markdown,下载请移步 Freewind Markdown,有问题请在留言板,交换友链请直接在友链留言,我创建了一个主题交流群,有兴趣可以加下: 点此加入
报毒我说明一下,是因为我把主题的版权信息做了加密,其中用了eval,杀毒软件认为eval函数是一个危险的操作,这点介意的话请勿下载,我也没有强迫任何人去下载,也没有向大家收取一分钱的主题费用,所以也犯不着因为这些事情来喷我,喜欢就用,不喜欢就不用,就这么简单

发布于2022-10-28

说明

经过前面的学习,我们博客的功能是越来越完善了,这节课我们来说下评论功能的实现

我们希望我们的评论完成之后页面不进行刷,只刷新评论部分,然后评论的翻页也是如此

普通评论实现

  • 定义评论接口

    • 路由:/comment
    • 方式:POST
    • 参数:Comment对象
    • 返回:公共返回对象
//Service    
@PostMapping("/comment")
public void save(Comment comment) {
  //新评论
  if (Objects.isNull(comment.getId())) {
    comment.setCreated(new Date());
    comment.setView(false);
  }
  mapper.save(comment);
}
//Controller
@PostMapping("/comment")
@ResponseBody
public Result<String> comment(Comment comment) {
  if (StringUtils.equals(comment.getEmail(), webSite.getMail())) {
    return Result.error(ResultEnum.RESULT_MAIL_FAIL);
  }
  commentService.save(comment);
  return Result.success();
}
  • 完善评论表单的name属性
<form id="lw-comment-form">
  <input type="hidden" name="article.id" th:value="${article.id}">
  <input type="hidden" name="pid" value="0">
  <div class="col-md-12 lw-p0" style="padding-right: 10px;">
    <textarea required name="content" placeholder="请输入你的评论..."></textarea>
  </div>
  <div class="col-md-4 col-xs-12 lw-comment-input lw-posr">
    <input name="nickname" required type="text" placeholder="请输入昵称...">
    <i class="fa fa-user  lw-comment-input  lw-posa"></i>
  </div>
  <div class="col-md-4 col-xs-12   lw-comment-input lw-posr">
    <input name="email" required type="email" placeholder="请输入电子邮件...">
    <i class="fa fa-envelope lw-posa"></i>
  </div>
  <div class="col-md-4 col-xs-12  lw-comment-input  lw-posr">
    <input name="url" type="url" placeholder="请输入主页地址...">
    <i class="fa fa-link fa-link lw-posa"></i>
  </div>
  <div class="col-md-12 col-xs-12  lw-comment-input  lw-posr" style="text-align: right">
    <button class="lw-comment-submit" type="submit">提交按钮</button>
  </div>
</form>
  • 拦截表单提交改为Ajax提交表单
$('#lw-comment-form').on('submit', function () {
  let data = $(this).serialize();
  $.ajax({
    url: '/comment',
    method: 'POST',
    data: data,
    dataType: 'json',
    success: res => {
      if (res.code === 200) {
        layer.msg('评论成功', {icon: 1})
        // todo 局部刷新评论列表
      } else {
        layer.msg(res.message, {icon: 2})
      }
    }
  })
  return false;
})

局部刷新展示

我们其实可以写个获取评论列表的接口返回一个JSON数据,然后前端把这个JSON拼接到一段HTML代码再展示出来,这过这样太麻烦了,我们可以直接利用Thymeleaf返回一个fragment,然后得用Jqueryload方法将其加载到对应容器中

  • 在获取文章详情时也获取文章下的第一页评论
//Mapper
Page<Comment> findAllByArticleOrderByCreatedDesc(Article article, Pageable pageable);
//Service
public PageHelper<Comment> list(Integer id, int pageNum) {
  Page<Comment> page = mapper.findAllByArticleOrderByCreatedDesc(Article.builder().id(id).build(), PageRequest.of(pageNum - 1, 5));
  return PageHelper.<Comment>builder()
    .rows(page.getContent())
    .current(pageNum)
    .total(page.getTotalElements())
    .totalPage(page.getTotalPages())
    .build();
}
//Controller
@GetMapping("/{id}.html")
public String detail(@PathVariable Integer id, Model model, HttpServletRequest request, HttpServletResponse response) {
  Article article = articleService.detail(id);
  if (Objects.isNull(CookieUtil.getCookie(request, Article.VIEW_PREFIX + id))) {
    articleService.viewArticle(id);
    CookieUtil.setCookie(response, Article.VIEW_PREFIX + id, "true");
  }
  //todo 当文章不存在时的处理
  model.addAttribute("article", article);
  PageHelper<Comment> commentPage = commentService.list(id, 1);
  model.addAttribute("commentPage", commentPage);
  return "detail";
}
public String avatar(String mail) {
  Pattern pattern = Pattern.compile("(\\d{5,10})@qq.com");
  Matcher matcher = pattern.matcher(mail);
  if (matcher.find()) {
    String qq = matcher.group(1);
    return String.format("https://q1.qlogo.cn/g?b=qq&nk=%s&s=100", qq);
  }
  return avatars.get((int) (Math.random() * avatars.size()));
}
  • 将页面的评论列表改为fragment并做渲染
<div id="lw-comment-list">
  <th:block th:fragment="comments">
    <div class="lw-comment-list">
      <ul th:each="comment:${commentPage.rows}">
        <li class="lw-posr">
          <div class="lw-comment-avatar lw-posa">
            <img th:src="${@defaultImage.avatar(comment.email)}" alt="">
          </div>
          <div class="lw-comment-content">
            <p><b th:text="${comment.nickname}"></b> <span
                                                           th:text="${#dates.format(comment.created,'yyyy-MM-dd HH:mm')}"></span> <a
                                                                                                                                     href="">回复</a></p>
            <p class="lw-comment-info" th:text="${comment.content}"></p>
          </div>
          <ul>
            <li class="lw-posr">
              <div class="lw-comment-avatar lw-posa">
                <img src="https://q1.qlogo.cn/g?b=qq&nk=1518228633&s=100" alt="">
              </div>
              <div class="lw-comment-content">
                <p><b>VOODOO</b> <span>2022-09-28 19:53</span> <a href="">回复</a></p>
                <p class="lw-comment-info">
                  @xpboy
                  <br>
                  谢谢</p>
              </div>
            </li>
          </ul>
        </li>
      </ul>
    </div>
    <ul th:if="${commentPage.totalPage>1}" id="lw-page-list" class="lw-pagenation">
      <li th:if="${commentPage.current != 1}"><a href="javascript:void(0)" data-page="1">首页</a></li>
      <li th:each="num:${#numbers.sequence((commentPage.current < 3?1: commentPage.current -2) ,(commentPage.current < commentPage.totalPage -2?commentPage.current+2: commentPage.totalPage))}">
        <a th:class="${commentPage.current eq num}?'lw-active':''"
           href="javascript:void(0)"
           th:data-page="${num}"
           th:text="${num}"></a>
      </li>
      <li th:if="${commentPage.current != commentPage.totalPage}">
        <a href="javascript:void(0)" th:data-page="${commentPage.totalPage}">尾页</a>
      </li>
      <li th:text="${'共 '+ commentPage.totalPage +' 页'}"></li>
    </ul>
  </th:block>
</div>
  • 在分页及评论成功时调用load方法请求评论区域的数据并加载到容器
@GetMapping("/comment/{id}")
public String comments(@PathVariable Integer id, @RequestParam(required = false, defaultValue = "1") Integer pn, Model model) {
  pn = Math.max(1, pn);
  PageHelper<Comment> commentPage = commentService.list(id, pn);
  model.addAttribute("commentPage", commentPage);
  return "detail::comments";
}
//评论成功
$('#lw-comment-list').load('/comment/' + articleId)
//分页
$('#lw-comment-list').on('click', '#lw-page-list a', function () {
  let page = $(this).data('page')
  $('#lw-comment-list').load(`/comment/${articleId}?pn=${page}`)
})

对不起,作者设置了附件 回复可见

评论(3)

  1. jzl 游客 2022-10-29 16:28 回复

    支持

  2. 遇见你真好 游客 2022-10-27 21:45 回复

    看看

  3. 小丑 游客 2022-10-22 01:13 回复

    来看看

最新评论

  •  hh

  •  hh

  • 蝌蚪

    支持大佬

  • SURELY

    下载支持一下大佬

  • SURELY

    大佬支持啊,下载了试一下

日历

2022年12月

    123
45678910
11121314151617
18192021222324
25262728293031

文章目录

站点公告
Freewind主题v1.5版本已发布,下载请移步Freewind 1.5,同时还有主题伴生插件Freewind Markdown,下载请移步 Freewind Markdown,有问题请在留言板,交换友链请直接在友链留言,我创建了一个主题交流群,有兴趣可以加下: 点此加入
报毒我说明一下,是因为我把主题的版权信息做了加密,其中用了eval,杀毒软件认为eval函数是一个危险的操作,这点介意的话请勿下载,我也没有强迫任何人去下载,也没有向大家收取一分钱的主题费用,所以也犯不着因为这些事情来喷我,喜欢就用,不喜欢就不用,就这么简单
点击小铃铛关闭