1 line
72 KiB
Plaintext
1 line
72 KiB
Plaintext
{"code":"(window.webpackJsonp=window.webpackJsonp||[]).push([[7],{363:function(t,s,a){\"use strict\";a.r(s);var n=a(42),e=Object(n.a)({},(function(){var t=this,s=t.$createElement,a=t._self._c||s;return a(\"ContentSlotsDistributor\",{attrs:{\"slot-key\":t.$parent.slotKey}},[a(\"h1\",{attrs:{id:\"echo-开源社区系统\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#echo-开源社区系统\"}},[t._v(\"#\")]),t._v(\" Echo — 开源社区系统\")]),t._v(\" \"),a(\"hr\"),t._v(\" \"),a(\"h2\",{attrs:{id:\"📚-从本项目你能学到什么\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#📚-从本项目你能学到什么\"}},[t._v(\"#\")]),t._v(\" 📚 从本项目你能学到什么\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"学会主流的 Java Web 开发技术和框架\")]),t._v(\" \"),a(\"li\",[t._v(\"积累一个真实的 Web 项目开发经验\")]),t._v(\" \"),a(\"li\",[t._v(\"掌握本项目中涉及的常见面试题的答题策略\")])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"💻-核心技术栈\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#💻-核心技术栈\"}},[t._v(\"#\")]),t._v(\" 💻 核心技术栈\")]),t._v(\" \"),a(\"p\",[t._v(\"后端:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"Spring\")]),t._v(\" \"),a(\"li\",[t._v(\"Spring Boot 2.1.5 RELEASE\")]),t._v(\" \"),a(\"li\",[t._v(\"Spring MVC\")]),t._v(\" \"),a(\"li\",[t._v(\"ORM:MyBatis\")]),t._v(\" \"),a(\"li\",[t._v(\"数据库:MySQL 5.7\")]),t._v(\" \"),a(\"li\",[t._v(\"日志:SLF4J(日志接口) + Logback(日志实现)\")]),t._v(\" \"),a(\"li\",[t._v(\"分布式缓存:Redis\")]),t._v(\" \"),a(\"li\",[t._v(\"本地缓存:Caffeine\")]),t._v(\" \"),a(\"li\",[t._v(\"消息队列:Kafka 2.13-2.7.0\")]),t._v(\" \"),a(\"li\",[t._v(\"搜索引擎:Elasticsearch 6.4.3\")]),t._v(\" \"),a(\"li\",[t._v(\"安全:Spring Security\")]),t._v(\" \"),a(\"li\",[t._v(\"邮件:Spring Mail\")]),t._v(\" \"),a(\"li\",[t._v(\"分布式定时任务:Spring Quartz\")])]),t._v(\" \"),a(\"p\",[t._v(\"前端:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"Thymeleaf\")]),t._v(\" \"),a(\"li\",[t._v(\"Bootstrap 4.x\")]),t._v(\" \"),a(\"li\",[t._v(\"Jquery\")]),t._v(\" \"),a(\"li\",[t._v(\"Ajax\")])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🔨-开发环境\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🔨-开发环境\"}},[t._v(\"#\")]),t._v(\" 🔨 开发环境\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"操作系统:Windows 10\")]),t._v(\" \"),a(\"li\",[t._v(\"构建工具:Apache Maven\")]),t._v(\" \"),a(\"li\",[t._v(\"集成开发工具:Intellij IDEA\")]),t._v(\" \"),a(\"li\",[t._v(\"数据库:MySQL 5.7\")]),t._v(\" \"),a(\"li\",[t._v(\"应用服务器:Apache Tomcat\")]),t._v(\" \"),a(\"li\",[t._v(\"接口测试工具:Postman\")]),t._v(\" \"),a(\"li\",[t._v(\"压力测试工具:Apache JMeter\")]),t._v(\" \"),a(\"li\",[t._v(\"版本控制工具:Git\")])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🎨-功能列表\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🎨-功能列表\"}},[t._v(\"#\")]),t._v(\" 🎨 功能列表\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208222403.png\",alt:\"\"}})]),t._v(\" \"),a(\"ul\",[a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"注册\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"用户注册成功,将用户信息存入 MySQL,但此时该用户状态为未激活\")]),t._v(\" \"),a(\"li\",[t._v(\"向用户发送激活邮件,用户点击链接则激活账号(Spring Mail)\")])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"登录 | 登出\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[a(\"p\",[t._v(\"进入登录界面,动态生成验证码,并将验证码短暂存入 Redis(60 秒)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登录成功(验证用户名、密码、验证码),生成登录凭证且设置状态为有效,并将登录凭证存入 Redis\")]),t._v(\" \"),a(\"p\",[t._v(\"注意:登录凭证存在有效期,在所有的请求执行之前,都会检查凭证是否有效和是否过期,只要该用户的凭证有效并在有效期时间内,本次请求就会一直持有该用户信息(使用 ThreadLocal 持有用户信息)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"勾选记住我,则延长登录凭证有效时间\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登录成功,将用户信息短暂存入 Redis(1 小时)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登出,将凭证状态设为无效,并更新 Redis 中该用户的登录凭证信息\")])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"账号设置\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"修改头像\\n\"),a(\"ul\",[a(\"li\",[t._v(\"将用户选择的头像图片文件上传至七牛云服务器\")])])]),t._v(\" \"),a(\"li\",[t._v(\"修改密码\")])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"帖子模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"发布帖子(过滤敏感词),将其存入 MySQL\")]),t._v(\" \"),a(\"li\",[t._v(\"分页显示所有的帖子\\n\"),a(\"ul\",[a(\"li\",[t._v(\"支持按照 “发帖时间” 显示\")]),t._v(\" \"),a(\"li\",[t._v(\"支持按照 “热度排行” 显示(Spring Quartz)\")])])]),t._v(\" \"),a(\"li\",[t._v(\"查看帖子详情\")]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security + Thymeleaf Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法发帖\")]),t._v(\" \"),a(\"li\",[t._v(\"“版主” 可以看到帖子的置顶和加精按钮并执行相应操作\")]),t._v(\" \"),a(\"li\",[t._v(\"“管理员” 可以看到帖子的删除按钮并执行相应操作\")]),t._v(\" \"),a(\"li\",[t._v(\"“普通用户” 无法看到帖子的置顶、加精、删除按钮,也无法执行相应操作\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"评论模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"发布对帖子的评论(过滤敏感词),将其存入 MySQL\")]),t._v(\" \"),a(\"li\",[t._v(\"分页显示评论\")]),t._v(\" \"),a(\"li\",[t._v(\"发布对评论的回复(过滤敏感词)\")]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法使用评论功能\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"私信模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"发送私信(过滤敏感词)\")]),t._v(\" \"),a(\"li\",[t._v(\"私信列表\\n\"),a(\"ul\",[a(\"li\",[t._v(\"查询当前用户的会话列表\")]),t._v(\" \"),a(\"li\",[t._v(\"每个会话只显示一条最新的私信\")]),t._v(\" \"),a(\"li\",[t._v(\"支持分页显示\")])])]),t._v(\" \"),a(\"li\",[t._v(\"私信详情\\n\"),a(\"ul\",[a(\"li\",[t._v(\"查询某个会话所包含的所有私信\")]),t._v(\" \"),a(\"li\",[t._v(\"访问私信详情时,将显示的私信设为已读状态\")]),t._v(\" \"),a(\"li\",[t._v(\"支持分页显示\")])])]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法使用私信功能\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"统一处理 404 / 500 异常\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"普通请求异常\")]),t._v(\" \"),a(\"li\",[t._v(\"异步请求异常\")])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"统一记录日志\")])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"点赞模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[a(\"p\",[t._v(\"支持对帖子、评论/回复点赞\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"第 1 次点赞,第 2 次取消点赞\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"首页统计帖子的点赞数量\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"详情页统计帖子和评论/回复的点赞数量\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"详情页显示当前登录用户的点赞状态(赞过了则显示已赞)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"统计我的获赞数量\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"权限管理(Spring Security)\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法使用点赞相关功能\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"关注模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"关注功能\")]),t._v(\" \"),a(\"li\",[t._v(\"取消关注功能\")]),t._v(\" \"),a(\"li\",[t._v(\"统计用户的关注数和粉丝数\")]),t._v(\" \"),a(\"li\",[t._v(\"我的关注列表(查询某个用户关注的人),支持分页\")]),t._v(\" \"),a(\"li\",[t._v(\"我的粉丝列表(查询某个用户的粉丝),支持分页\")]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法使用关注相关功能\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"系统通知模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"通知列表\\n\"),a(\"ul\",[a(\"li\",[t._v(\"显示评论、点赞、关注三种类型的通知\")])])]),t._v(\" \"),a(\"li\",[t._v(\"通知详情\\n\"),a(\"ul\",[a(\"li\",[t._v(\"分页显示某一类主题所包含的通知\")]),t._v(\" \"),a(\"li\",[t._v(\"进入某种类型的系统通知详情,则将该页的所有未读的系统通知状态设置为已读\")])])]),t._v(\" \"),a(\"li\",[t._v(\"未读数量\\n\"),a(\"ul\",[a(\"li\",[t._v(\"分别显示每种类型的系统通知的未读数量\")]),t._v(\" \"),a(\"li\",[t._v(\"显示所有系统通知的未读数量\")])])]),t._v(\" \"),a(\"li\",[t._v(\"导航栏显示所有消息的未读数量(未读私信 + 未读系统通知)\")]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"未登录用户无法使用系统通知功能\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"搜索模块\")])]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"发布事件\\n\"),a(\"ul\",[a(\"li\",[t._v(\"发布帖子时,通过消息队列将帖子异步地提交到 Elasticsearch 服务器\")]),t._v(\" \"),a(\"li\",[t._v(\"为帖子增加评论时,通过消息队列将帖子异步地提交到 Elasticsearch 服务器\")])])]),t._v(\" \"),a(\"li\",[t._v(\"搜索服务\\n\"),a(\"ul\",[a(\"li\",[t._v(\"从 Elasticsearch 服务器搜索帖子\")]),t._v(\" \"),a(\"li\",[t._v(\"从 Elasticsearch 服务器删除帖子(当帖子从数据库中被删除时)\")])])]),t._v(\" \"),a(\"li\",[t._v(\"显示搜索结果\")])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] \"),a(\"strong\",[t._v(\"网站数据统计\")]),t._v(\"(管理员专属)\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"独立访客 UV\\n\"),a(\"ul\",[a(\"li\",[t._v(\"存入 Redis 的 HyperLogLog\")]),t._v(\" \"),a(\"li\",[t._v(\"支持单日查询和区间日期查询\")])])]),t._v(\" \"),a(\"li\",[t._v(\"日活跃用户 DAU\\n\"),a(\"ul\",[a(\"li\",[t._v(\"存入 Redis 的 Bitmap\")]),t._v(\" \"),a(\"li\",[t._v(\"支持单日查询和区间日期查询\")])])]),t._v(\" \"),a(\"li\",[t._v(\"权限管理(Spring Security)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"只有管理员可以查看网站数据统计\")])])])])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"[x] 优化网站性能\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"使用本地缓存 Caffeine 缓存热帖列表以及所有用户帖子的总数\")])])])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🔐-待实现及优化\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🔐-待实现及优化\"}},[t._v(\"#\")]),t._v(\" 🔐 待实现及优化\")]),t._v(\" \"),a(\"p\",[t._v(\"以下是我个人发现的本项目存在的问题,但是暂时没有头绪无法解决,集思广益,欢迎各位小伙伴提 PR 解决:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"[ ] 注册模块无法正常跳转到操作提示界面(本地运行没有问题)\")]),t._v(\" \"),a(\"li\",[t._v(\"[ ] 评论功能的前端显示部分存在 Bug\")]),t._v(\" \"),a(\"li\",[t._v(\"[ ] 查询我的评论(未完善)\")])]),t._v(\" \"),a(\"p\",[t._v(\"以下是我觉得本项目还可以添加的功能,同样欢迎各位小伙伴提 issue 指出还可以增加哪些功能,或者直接提 PR 实现该功能:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"[ ] 忘记密码(发送邮件找回密码)\")]),t._v(\" \"),a(\"li\",[t._v(\"[ ] 查询我的点赞\")]),t._v(\" \"),a(\"li\",[t._v(\"[ ] 管理员对帖子的二次点击取消置顶功能\")]),t._v(\" \"),a(\"li\",[t._v(\"[ ] 管理员对已删除帖子的恢复功能(本项目中的删除帖子并未将其从数据库中删除,只是将其状态设置为了拉黑)\")])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🎀-界面展示\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🎀-界面展示\"}},[t._v(\"#\")]),t._v(\" 🎀 界面展示\")]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🌱-本地运行\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🌱-本地运行\"}},[t._v(\"#\")]),t._v(\" 🌱 本地运行\")]),t._v(\" \"),a(\"p\",[t._v(\"各位如果需要将项目部署在本地进行测试,以下环境请提前备好:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"Java 8\")]),t._v(\" \"),a(\"li\",[t._v(\"MySQL 5.7\")]),t._v(\" \"),a(\"li\",[t._v(\"Redis\")]),t._v(\" \"),a(\"li\",[t._v(\"Kafka 2.13-2.7.0\")]),t._v(\" \"),a(\"li\",[t._v(\"Elasticsearch 6.4.3\")])]),t._v(\" \"),a(\"p\",[t._v(\"然后\"),a(\"strong\",[t._v(\"修改配置文件中的信息为你自己的本地环境,直接运行是运行不了的\")]),t._v(\",而且相关私密信息我全部用 xxxxxxx 代替了。\")]),t._v(\" \"),a(\"p\",[t._v(\"本地运行需要修改的配置文件信息如下:\")]),t._v(\" \"),a(\"p\",[t._v(\"1)\"),a(\"code\",[t._v(\"application-develop.properties\")]),t._v(\":\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"MySQL\")]),t._v(\" \"),a(\"li\",[t._v(\"Spring Mail(邮箱需要开启 SMTP 服务)\")]),t._v(\" \"),a(\"li\",[t._v(\"Kafka:consumer.group-id(该字段见 Kafka 安装包中的 consumer.proerties,可自行修改, 修改完毕后需要重启 Kafka)\")]),t._v(\" \"),a(\"li\",[t._v(\"Elasticsearch:cluster-name(该字段见 Elasticsearch 安装包中的 elasticsearch.yml,可自行修改)\")]),t._v(\" \"),a(\"li\",[t._v(\"七牛云(需要新建一个七牛云的对象存储空间,用来存放上传的头像图片)\")])]),t._v(\" \"),a(\"p\",[t._v(\"2)\"),a(\"code\",[t._v(\"logback-spring-develop.xml\")]),t._v(\":\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"LOG_PATH:日志存放的位置\")])]),t._v(\" \"),a(\"p\",[t._v(\"每次运行需要打开:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"MySQL\")]),t._v(\" \"),a(\"li\",[t._v(\"Redis\")]),t._v(\" \"),a(\"li\",[t._v(\"Elasticsearch\")]),t._v(\" \"),a(\"li\",[t._v(\"Kafka\")])]),t._v(\" \"),a(\"h2\",{attrs:{id:\"📜-数据库设计\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#📜-数据库设计\"}},[t._v(\"#\")]),t._v(\" 📜 数据库设计\")]),t._v(\" \"),a(\"p\",[t._v(\"用户 \"),a(\"code\",[t._v(\"user\")]),t._v(\":\")]),t._v(\" \"),a(\"div\",{staticClass:\"language-sql extra-class\"},[a(\"pre\",{pre:!0,attrs:{class:\"language-sql\"}},[a(\"code\",[a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DROP\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"IF\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"EXISTS\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"user\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"SET\")]),t._v(\" character_set_client \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\" utf8mb4 \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CREATE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"user\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"NOT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"username\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"50\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"password\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"50\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"salt\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"50\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"email\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"100\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"type\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'0-普通用户; 1-超级管理员; 2-版主;'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"status\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'0-未激活; 1-已激活;'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"activation_code\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"100\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"header_url\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"200\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"create_time\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"timestamp\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"PRIMARY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_username\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"username\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"20\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_email\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"email\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"20\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"ENGINE\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"InnoDB\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"101\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CHARSET\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\"utf8\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\")])])]),a(\"p\",[t._v(\"讨论帖 \"),a(\"code\",[t._v(\"discuss_post\")]),t._v(\":\")]),t._v(\" \"),a(\"div\",{staticClass:\"language-sql extra-class\"},[a(\"pre\",{pre:!0,attrs:{class:\"language-sql\"}},[a(\"code\",[a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DROP\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"IF\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"EXISTS\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"discuss_post\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"SET\")]),t._v(\" character_set_client \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\" utf8mb4 \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CREATE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"discuss_post\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"NOT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"title\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"100\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"content\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"text\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"type\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'0-普通; 1-置顶;'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"status\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'0-正常; 1-精华; 2-拉黑;'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"create_time\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"timestamp\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"comment_count\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"score\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"double\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"PRIMARY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"ENGINE\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"InnoDB\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CHARSET\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\"utf8\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\")])])]),a(\"p\",[t._v(\"评论(回复)\"),a(\"code\",[t._v(\"comment\")]),t._v(\":\")]),t._v(\" \"),a(\"div\",{staticClass:\"language-sql extra-class\"},[a(\"pre\",{pre:!0,attrs:{class:\"language-sql\"}},[a(\"code\",[a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CREATE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"comment\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"NOT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"entity_type\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'评论目标的类别:1 帖子;2 评论 '\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"entity_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'评论目标的 id'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"target_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'指明对谁进行评论'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"content\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"text\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"status\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'状态:0 正常;1 禁用'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"create_time\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"timestamp\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"PRIMARY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"user_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_entity_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"entity_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"ENGINE\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"InnoDB\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"247\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CHARSET\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\"utf8\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\")])])]),a(\"p\",[t._v(\"私信 \"),a(\"code\",[t._v(\"message\")]),t._v(\":\")]),t._v(\" \"),a(\"div\",{staticClass:\"language-sql extra-class\"},[a(\"pre\",{pre:!0,attrs:{class:\"language-sql\"}},[a(\"code\",[a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DROP\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"IF\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"EXISTS\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"message\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"SET\")]),t._v(\" character_set_client \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\" utf8mb4 \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CREATE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"TABLE\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"message\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"NOT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"AUTO_INCREMENT\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"from_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"to_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"conversation_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"varchar\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"45\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"NOT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"content\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"text\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"status\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"int\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"11\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"COMMENT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token string\"}},[t._v(\"'0-未读;1-已读;2-删除;'\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"create_time\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"timestamp\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token boolean\"}},[t._v(\"NULL\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"PRIMARY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_from_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"from_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_to_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"to_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"KEY\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"index_conversation_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),t._v(\"conversation_id\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"`\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"ENGINE\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"InnoDB\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"DEFAULT\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"CHARSET\")]),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\"utf8\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\")])])]),a(\"h2\",{attrs:{id:\"🎯-功能逻辑图\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🎯-功能逻辑图\"}},[t._v(\"#\")]),t._v(\" 🎯 功能逻辑图\")]),t._v(\" \"),a(\"p\",[t._v(\"画了一些不是那么严谨的图帮助各位小伙伴理清思绪。\")]),t._v(\" \"),a(\"blockquote\",[a(\"p\",[t._v(\"单向绿色箭头:\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"前端模板 -> Controller:表示这个前端模板中有一个超链接是由这个 Controller 处理的\")]),t._v(\" \"),a(\"li\",[t._v(\"Controller -> 前端模板:表示这个 Controller 会像该前端模板传递数据或者跳转\")])]),t._v(\" \"),a(\"p\",[t._v(\"双向绿色箭头:表示 Controller 和前端模板之间进行参数的相互传递或使用\")]),t._v(\" \"),a(\"p\",[t._v(\"单向蓝色箭头: A -> B,表示 A 方法调用了 B 方法\")]),t._v(\" \"),a(\"p\",[t._v(\"单向红色箭头:数据库或缓存操作\")])]),t._v(\" \"),a(\"h3\",{attrs:{id:\"注册\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#注册\"}},[t._v(\"#\")]),t._v(\" 注册\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"用户注册成功,将用户信息存入 MySQL,但此时该用户状态为未激活\")]),t._v(\" \"),a(\"li\",[t._v(\"向用户发送激活邮件,用户点击链接则激活账号(Spring Mail)\")])]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210204222249.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"登录-登出\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#登录-登出\"}},[t._v(\"#\")]),t._v(\" 登录 | 登出\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[a(\"p\",[t._v(\"进入登录界面,动态生成验证码,并将验证码短暂存入 Redis(60 秒)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登录成功(验证用户名、密码、验证码),生成登录凭证且设置状态为有效,并将登录凭证存入 Redis\")]),t._v(\" \"),a(\"p\",[t._v(\"注意:登录凭证存在有效期,在所有的请求执行之前,都会检查凭证是否有效和是否过期,只要该用户的凭证有效并在有效期时间内,本次请求就会一直持有该用户信息(使用 ThreadLocal 持有用户信息)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"勾选记住我,则延长登录凭证有效时间\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登录成功,将用户信息短暂存入 Redis(1 小时)\")])]),t._v(\" \"),a(\"li\",[a(\"p\",[t._v(\"用户登出,将凭证状态设为无效,并更新 Redis 中该用户的登录凭证信息\")])])]),t._v(\" \"),a(\"p\",[t._v(\"下图是登录模块的功能逻辑图,并没有使用 Spring Security 提供的认证逻辑(我觉得这个模块是最复杂的,这张图其实很多细节还没有画全)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210204233233.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"分页显示所有的帖子\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#分页显示所有的帖子\"}},[t._v(\"#\")]),t._v(\" 分页显示所有的帖子\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"支持按照 “发帖时间” 显示\")]),t._v(\" \"),a(\"li\",[t._v(\"支持按照 “热度排行” 显示(Spring Quartz)\")]),t._v(\" \"),a(\"li\",[t._v(\"将热帖列表和所有帖子的总数存入本地缓存 Caffeine(利用分布式定时任务 Spring Quartz 每隔一段时间就刷新计算帖子的热度/分数 — 见下文,而 Caffeine 里的数据更新不用我们操心,它天生就会自动的更新它拥有的数据,给它一个初始化方法就完事儿)\")])]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210204222822.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"账号设置\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#账号设置\"}},[t._v(\"#\")]),t._v(\" 账号设置\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"修改头像(异步请求)\\n\"),a(\"ul\",[a(\"li\",[t._v(\"将用户选择的头像图片文件上传至七牛云服务器\")])])]),t._v(\" \"),a(\"li\",[t._v(\"修改密码\")])]),t._v(\" \"),a(\"p\",[t._v(\"此处只画出修改头像:\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210206121201.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"发布帖子-异步请求\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#发布帖子-异步请求\"}},[t._v(\"#\")]),t._v(\" 发布帖子(异步请求)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210206122521.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"显示评论及相关信息\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#显示评论及相关信息\"}},[t._v(\"#\")]),t._v(\" 显示评论及相关信息\")]),t._v(\" \"),a(\"blockquote\",[a(\"p\",[t._v(\"评论部分前端的名称显示有些缺陷,有兴趣的小伙伴欢迎提 PR 解决~\")])]),t._v(\" \"),a(\"p\",[t._v(\"关于评论模块需要注意的就是评论表的设计,把握其中字段的含义,才能透彻了解这个功能的逻辑。\")]),t._v(\" \"),a(\"p\",[t._v(\"评论 Comment 的目标类型(帖子,评论) entityType 和 entityId 以及对哪个用户进行评论/回复 targetId 是由前端传递给 DiscussPostController 的\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207150925.png\",alt:\"\"}})]),t._v(\" \"),a(\"p\",[t._v(\"一个帖子的详情页需要封装的信息大概如下:\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207151328.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"添加评论-事务管理\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#添加评论-事务管理\"}},[t._v(\"#\")]),t._v(\" 添加评论(事务管理)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207122908.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"私信列表和详情页\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#私信列表和详情页\"}},[t._v(\"#\")]),t._v(\" 私信列表和详情页\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207161130.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"发送私信-异步请求\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#发送私信-异步请求\"}},[t._v(\"#\")]),t._v(\" 发送私信(异步请求)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207161500.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"点赞-异步请求\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#点赞-异步请求\"}},[t._v(\"#\")]),t._v(\" 点赞(异步请求)\")]),t._v(\" \"),a(\"p\",[t._v(\"将点赞相关信息存入 Redis 的数据结构 set 中。其中,key 命名为 \"),a(\"code\",[t._v(\"like:entity:entityType:entityId\")]),t._v(\",value 即点赞用户的 id。比如 key = \"),a(\"code\",[t._v(\"like:entity:2:246\")]),t._v(\" value = \"),a(\"code\",[t._v(\"11\")]),t._v(\" 表示用户 11 对实体类型 2 即评论进行了点赞,该评论的 id 是 246\")]),t._v(\" \"),a(\"p\",[t._v(\"某个用户的获赞数量对应的存储在 Redis 中的 key 是 \"),a(\"code\",[t._v(\"like:user:userId\")]),t._v(\",value 就是这个用户的获赞数量\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207165837.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"我的获赞数量\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#我的获赞数量\"}},[t._v(\"#\")]),t._v(\" 我的获赞数量\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207170003.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"关注-异步请求\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#关注-异步请求\"}},[t._v(\"#\")]),t._v(\" 关注(异步请求)\")]),t._v(\" \"),a(\"ul\",[a(\"li\",[t._v(\"若 A 关注了 B,则 A 是 B 的粉丝 Follower,B 是 A 的目标 Followee\")]),t._v(\" \"),a(\"li\",[t._v(\"关注的目标可以是用户、帖子、题目等,在实现时将这些目标抽象为实体(目前只做了关注用户)\")])]),t._v(\" \"),a(\"p\",[t._v(\"将某个用户关注的实体相关信息存储在 Redis 的数据结构 zset 中:key 是 \"),a(\"code\",[t._v(\"followee:userId:entityType\")]),t._v(\" ,对应的 value 是 \"),a(\"code\",[t._v(\"zset(entityId, now)\")]),t._v(\" ,以关注的时间进行排序。比如说 \"),a(\"code\",[t._v(\"followee:111:3\")]),t._v(\" 对应的value \"),a(\"code\",[t._v(\"(20, 2020-02-03-xxxx)\")]),t._v(\",表明用户 111 关注了实体类型为 3 即人(用户),该帖子的 id 是 20,关注该帖子的时间是 2020-02-03-xxxx\")]),t._v(\" \"),a(\"p\",[t._v(\"同样的,将某个实体拥有的粉丝相关信息也存储在 Redis 的数据结构 zset 中:key 是 \"),a(\"code\",[t._v(\"follower:entityType:entityId\")]),t._v(\",对应的 value 是 \"),a(\"code\",[t._v(\"zset(userId, now)\")]),t._v(\",以关注的时间进行排序\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207174046.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"关注列表\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#关注列表\"}},[t._v(\"#\")]),t._v(\" 关注列表\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207175621.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"发送系统通知\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#发送系统通知\"}},[t._v(\"#\")]),t._v(\" 发送系统通知\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210207182917.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"显示系统通知\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#显示系统通知\"}},[t._v(\"#\")]),t._v(\" 显示系统通知\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208153059.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"搜索\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#搜索\"}},[t._v(\"#\")]),t._v(\" 搜索\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208161936.png\",alt:\"\"}})]),t._v(\" \"),a(\"p\",[t._v(\"类似的,置顶、加精也会触发发帖事件,就不再图里面画出来了。\")]),t._v(\" \"),a(\"h3\",{attrs:{id:\"置顶加精删除-异步请求\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#置顶加精删除-异步请求\"}},[t._v(\"#\")]),t._v(\" 置顶加精删除(异步请求)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208171729.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"网站数据统计\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#网站数据统计\"}},[t._v(\"#\")]),t._v(\" 网站数据统计\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208170801.png\",alt:\"\"}})]),t._v(\" \"),a(\"h3\",{attrs:{id:\"帖子热度计算\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#帖子热度计算\"}},[t._v(\"#\")]),t._v(\" 帖子热度计算\")]),t._v(\" \"),a(\"p\",[t._v(\"每次发生点赞(给帖子点赞)、评论(给帖子评论)、加精的时候,就将这些帖子信息存入缓存 Redis 中,然后通过分布式的定时任务 Spring Quartz,每隔一段时间就从缓存中取出这些帖子进行计算分数。\")]),t._v(\" \"),a(\"p\",[t._v(\"帖子分数/热度计算公式:分数(热度) = 权重 + 发帖距离天数\")]),t._v(\" \"),a(\"div\",{staticClass:\"language-java extra-class\"},[a(\"pre\",{pre:!0,attrs:{class:\"language-java\"}},[a(\"code\",[a(\"span\",{pre:!0,attrs:{class:\"token comment\"}},[t._v(\"// 计算权重\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"double\")]),t._v(\" w \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"wonderful \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"?\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"75\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\":\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"0\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"+\")]),t._v(\" commentCount \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"*\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"10\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"+\")]),t._v(\" likeCount \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"*\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"2\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token comment\"}},[t._v(\"// 分数 = 权重 + 发帖距离天数\")]),t._v(\"\\n\"),a(\"span\",{pre:!0,attrs:{class:\"token keyword\"}},[t._v(\"double\")]),t._v(\" score \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"=\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token class-name\"}},[t._v(\"Math\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\".\")]),a(\"span\",{pre:!0,attrs:{class:\"token function\"}},[t._v(\"log10\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token class-name\"}},[t._v(\"Math\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\".\")]),a(\"span\",{pre:!0,attrs:{class:\"token function\"}},[t._v(\"max\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"w\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\",\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"1\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\"\\n \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"+\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),t._v(\"post\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\".\")]),a(\"span\",{pre:!0,attrs:{class:\"token function\"}},[t._v(\"getCreateTime\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\".\")]),a(\"span\",{pre:!0,attrs:{class:\"token function\"}},[t._v(\"getTime\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"-\")]),t._v(\" epoch\"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\".\")]),a(\"span\",{pre:!0,attrs:{class:\"token function\"}},[t._v(\"getTime\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"/\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\"(\")]),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"1000\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"*\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"3600\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token operator\"}},[t._v(\"*\")]),t._v(\" \"),a(\"span\",{pre:!0,attrs:{class:\"token number\"}},[t._v(\"24\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\")\")]),a(\"span\",{pre:!0,attrs:{class:\"token punctuation\"}},[t._v(\";\")]),t._v(\"\\n\")])])]),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208173636.png\",alt:\"\"}})]),t._v(\" \"),a(\"h2\",{attrs:{id:\"🌌-理想的部署架构\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#🌌-理想的部署架构\"}},[t._v(\"#\")]),t._v(\" 🌌 理想的部署架构\")]),t._v(\" \"),a(\"p\",[t._v(\"我只部署了一台服务器,以下是理想的部署架构:\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210206215827.png\",alt:\"\"}})]),t._v(\" \"),a(\"h2\",{attrs:{id:\"📖-常见面试题\"}},[a(\"a\",{staticClass:\"header-anchor\",attrs:{href:\"#📖-常见面试题\"}},[t._v(\"#\")]),t._v(\" 📖 常见面试题\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210208221333.png\",alt:\"\"}})]),t._v(\" \"),a(\"p\",[t._v(\"有意愿拿着这个项目去面试(校招/社招)的小伙伴,可以扫描下方二维码关注公众号**『飞天小牛肉』**,获取我整理的关于本项目涉及的常见面试题及解析(尚在更新中)\")]),t._v(\" \"),a(\"p\",[a(\"img\",{attrs:{src:\"https://gitee.com/veal98/images/raw/master/img/20210206220907.png\",alt:\"\"}})])])}),[],!1,null,null,null);s.default=e.exports}}]);","extractedComments":[]} |