【JavaWeb】头条新闻项目实现 基本增删改查 分页查询 登录注册校验 业务功能实现 第二期

文章目录

  • 一、为什么使用token口令
  • 二、登录注册功能
    • 2.1 登录表单提交
      • 后端代码:
    • 2.2 根据token获取完整用户信息
      • 代码实现:
    • 2.3 注册时用户名占用校验
      • 代码实现:
    • 2.4 注册表单提交
      • 代码实现:
  • 三、头条首页功能
    • 3.1 查询所有头条分类
    • 3.2 分页带条件查询所有头条
      • 代码实现:
    • 3.3 查看头条详情
      • 代码实现:
  • 四、头条发布修改和删除
    • 4.1 登录校验
      • 代码实现:
    • 4.2 提交发布头条(新增
      • 代码实现:
    • 4.3 修改头条回显
    • 4.4 保存修改
      • 代码实现:
    • 4.5 删除头条
  • 总结
    • 2.1 登录表单提交


一、为什么使用token口令

为什么使用 token 口令 而不使用 cookie和session

  • cookie和session 对于高并发项目不合适
    1
  • token:
    1

二、登录注册功能

gif

2.1 登录表单提交

需求描述:
输入 用户名 密码 验证登录,根据输入的用户名 和 密码 提示不同的响应信息

URI:
user/login

请求方式:
POST

请求参数:
{ "username":"dougwake", //用户名 "userPwd":"123456" //明文密码 }
1
响应示例:

  • 登录成功
    1
  • 用户名输入有误:
    在这里插入图片描述
  • 密码错误:
    在这里插入图片描述

后端代码:

2.1.1 Controller 层

package com.doug.headline.controller;import com.doug.headline.common.Result;
import com.doug.headline.common.ResultCodeEnum;
import com.doug.headline.dao.NewsUserDao;
import com.doug.headline.pojo.NewsUser;
import com.doug.headline.service.NewsUserService;
import com.doug.headline.service.impl.NewsUserServiceImpl;
import com.doug.headline.util.JwtHelper;
import com.doug.headline.util.MD5Util;
import com.doug.headline.util.WebUtil;
import jakarta.servlet.ServletException;
import jakarta.servlet.annotation.WebServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;import java.io.IOException;
import java.util.HashMap;
import java.util.Map;@WebServlet("/user/*")
public class NewsUserController extends BaseController {private NewsUserService newsUserService = new NewsUserServiceImpl();/*** 接收前端请求参数 进行登录校验** @param req* @param resp* @throws ServletException* @throws IOException*/protected void login(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// 接收前端传递过来的JSON串 (即请求参数)NewsUser newsUser = WebUtil.readJson(req, NewsUser.class);// 调用业务层代码 查找用户名是否存在NewsUser loginNewsUser = newsUserService.findByUsername(newsUser.getUsername());Result result = null;if (null != loginNewsUser) {// 用户名存在 -> 进一步判断 密码是否正确(先将明文密码转成MD5 再与已存密码对比)if (loginNewsUser.getUserPwd().equals(MD5Util.encrypt(newsUser.getUserPwd()))) {// 响应结果 是键值对形式 所以用mapMap<String, Object> data = new HashMap<>();// 创建token String token = JwtHelper.createToken(loginNewsUser.getUid().longValue());data.put("token", token);result = Result.ok(data);} else {// 密码有误result = Result.build(null, ResultCodeEnum.PASSWORD_ERROR);}} else {// 查找为空 用户名不存在 返回自定义用户名错误业务码result = Result.build(null, ResultCodeEnum.USERNAME_ERROR);}// 响应结果WebUtil.writeJson(resp, result);}
}

2.1.2 service

public interface NewsUserService {/*** 根据用户名,获得查询的用户信息* @param username 要查找的用户名* @return 如果找到返回NewsUser对象,找不到返回null*/NewsUser findByUsername(String username);
}
public class NewsUserServiceImpl implements NewsUserService {private NewsUserDao newsUserDao = new NewsUserDaoImpl();@Overridepublic NewsUser findByUsername(String username) {return newsUserDao.findByUsername(username);}
}

2.1.3 dao

public interface NewsUserDao {/*** 根据用户名,获得查询的用户信息* @param username 要查找的用户名* @return 如果找到返回NewsUser对象,找不到返回null*/NewsUser findByUsername(String username);
}
public class NewsUserDaoImpl  extends BaseDao implements NewsUserDao {@Overridepublic NewsUser findByUsername(String username) {String sql = """selectuid,username,user_pwd userPwd,nick_name nickNamefromnews_userwhereusername = ?;""";List<NewsUser> newsUserList = baseQuery(NewsUser.class, sql, username);// 如果找到,返回集合中的第一个数据(其实就一个)if(null != newsUserList && newsUserList.size() > 0){return newsUserList.get(0);}return null;}
}

2.2 根据token获取完整用户信息

需求描述:
客户端发送请求,提交token请求头,后端根据token请求头获取登录用户的详细信息并响应给客户端进行存储

URI:
user/getUserInfo

请求方式:
GET

请求头
token: ...

响应示例

  • 成功获取
    1
  • 获取失败
    504

代码实现:

2.2.1 Controller

    private NewsUserService newsUserService = new NewsUserServiceImpl();/*** 接收token,根据token查询完整用户信息* @param req* @param resp* @throws ServletException* @throws IOException*/protected void getUserInfo(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {String token = req.getHeader("token");Result result = Result.build(null, ResultCodeEnum.NOTLOGIN);// token 存在if(null != token){// token 没有到期if(!JwtHelper.isExpiration(token)){Integer uid = JwtHelper.getUserId(token).intValue();// 通过token的uid 找对象NewsUser newsUser = newsUserService.findByUid(uid);newsUser.setUserPwd("");HashMap<String, Object> data = new HashMap<>();data.put("loginUser",newsUser);result = Result.ok(data);}}WebUtil.writeJson(resp,result);}

2.2.2 Service

    /*** 根据用户id查询用户信息* @param uid 要查询的用户id* @return 找到返回NewsUser对象,找不到返回null*/NewsUser findByUid(Integer uid);
    @Overridepublic NewsUser findByUid(Integer uid) {return newsUserDao.finByUid(uid);}

2.2.3 Dao

    NewsUser finByUid(Integer uid);
    @Overridepublic NewsUser finByUid(Integer uid) {String sql = """selectuid,username,user_pwd userPwd,nick_name nickNamefromnews_userwhereuid = ?;""";List<NewsUser> newsUserList = baseQuery(NewsUser.class, sql, uid);// 如果找到,返回集合中的第一个数据(其实就一个)return null != newsUserList && newsUserList.size() > 0 ? newsUserList.get(0):null;}

2.3 注册时用户名占用校验

用户在注册时输入用户名时,立刻将用户名发送给后端,后端根据用户名查询用户名是否可用并做出响应

URI
user/checkUserName

请求方式: POST

请求参数: username=DougWake

响应示例:

  • 用户名校验通过
    2
  • 用户名被占用
    2

代码实现:

    /*** 注册时校验用户名是否占用* @param req* @param resp* @throws ServletException* @throws IOException*/protected void checkUserName(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {String username = req.getParameter("username");NewsUser newsUser = newsUserService.findByUsername(username);Result result = null;if(null == newsUser){result = Result.ok(null);}else{result = Result.build(null,ResultCodeEnum.USERNAME_USED);}WebUtil.writeJson(resp,result);}

2.4 注册表单提交

客户端将新用户信息发送给服务端,服务端将新用户存入数据库,存入之前做用户名是否被占用校验,校验通过响应成功提示,否则响应失败提示

URI : user/regist

请求方式: POST

请求参数 :

{"username":"GavinGroves","userPwd":"0123456","nickName":"加文"
}

响应示例:

  • 注册成功:
    1
  • 用户名占用:(第二次注册)
    2

代码实现:

2.4.1 Controller

    /*** 用户注册* @param req* @param resp* @throws ServletException* @throws IOException*/protected void regist(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {NewsUser newsUser = WebUtil.readJson(req, NewsUser.class);NewsUser usedUser = newsUserService.findByUsername(newsUser.getUsername());Result result = null;if(null != usedUser){result = Result.build(null,ResultCodeEnum.USERNAME_USED);}else{newsUserService.registUser(newsUser);result = Result.ok(null);}WebUtil.writeJson(resp,result);}

2.4.2 Service

    /*** 注册用户信息,注册成功返回大于0的整数,失败返回0* @param newsUser 要添加的新对象* @return*/int registUser(NewsUser newsUser);
    @Overridepublic int registUser(NewsUser newsUser) {// 密码明文转密文newsUser.setUserPwd(MD5Util.encrypt(newsUser.getUserPwd()));return newsUserDao.insertNewsUser(newsUser);}

2.4.3 Dao

    /*** 将用户信息存入数据库* @param newsUser 插入新的用户对象* @return*/int insertNewsUser(NewsUser newsUser);
    public int insertNewsUser(NewsUser newsUser) {String sql = "insert into news_user values(DEFAULT,?,?,?)";return baseUpdate(sql, newsUser.getUsername(), newsUser.getUserPwd(), newsUser.getNickName());}

result

三、头条首页功能

2

3.1 查询所有头条分类

进入新闻首页,查询所有分类并动态展示新闻类别栏位

URI: portal/findAllTypes
请求方式: GET

  • 响应示例:
{"code": 200,"message": "success","data": [{"tid": 1,"tname": "新闻"},{"tid": 2,"tname": "体育"},{"tid": 3,"tname": "娱乐"},{"tid": 4,"tname": "科技"},{"tid": 5,"tname": "其他"}]
}
  • Controller
package com.doug.headline.controller;import com.doug.headline.common.Result;
import com.doug.headline.pojo.NewsType;
import com.doug.headline.service.NewsTypeService;
import com.doug.headline.service.impl.NewsTypeServiceImpl;
import com.doug.headline.util.WebUtil;
import jakarta.servlet.ServletException;
import jakarta.servlet.annotation.WebServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;import java.io.IOException;
import java.util.List;/*** @Author: Gavin* @Date: 2024-02-02 17:10* @Description: 门户 控制器 即 当用户没有登录时候 所看到的页面(首页)*/
@WebServlet("/portal/*")
public class PortalController extends BaseController {private NewsTypeService typeService = new NewsTypeServiceImpl();/*** 查询所有头条类型 业务接口实现** @param req* @param resp* @throws ServletException* @throws IOException*/protected void findAllTypes(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {List<NewsType> newsTypeList = typeService.findAllTypes();WebUtil.writeJson(resp,Result.ok(newsTypeList));}
}
  • service
public interface NewsTypeService {/*** 查询全部新闻类型* @return 新闻类型数据*/List<NewsType> findAllTypes();
}
public class NewsTypeServiceImpl implements NewsTypeService {private NewsTypeDao typeDao= new NewsTypeDaoImpl();@Overridepublic List<NewsType> findAllTypes() {return typeDao.findAllTypes();}
}
  • dao
public interface NewsTypeDao {/*** 查询全部新闻类型* @return 新闻类型数据*/List<NewsType> findAllTypes();
}
public class NewsTypeDaoImpl extends BaseDao implements NewsTypeDao {@Overridepublic List<NewsType> findAllTypes() {String sql = "select tid,tname from news_type";return baseQuery(NewsType.class,sql);}
}

3.2 分页带条件查询所有头条

  • 客户端向服务端发送查询关键字,新闻类别,页码数,页大小
  • 服务端根据条件搜索分页信息,返回含页码数,页大小,总页数,总记录数,当前页数据等信息,并根据时间降序,浏览量降序排序

uri: portal/findNewsPage

请求方式:POST

  • 请求参数:
{"keyWords":"马斯克", // 搜索标题关键字"type":0,           // 新闻类型"pageNum":1,        // 页码数(当前页码)"pageSize":"10"     // 页大小(一页10条显示数据
}
  • 响应示例:
{"code":"200","message":"success""data":{"pageInfo":{"pageData":[                           // 本页的数据{"hid":"1",                     // 新闻id "title":"尚硅谷宣布 ... ...",   // 新闻标题"type":"1",                    // 新闻所属类别编号"pageViews":"40",              // 新闻浏览量"pastHours":"3" ,              // 发布时间已过小时数"publisher":"1"                // 发布用户ID},{"hid":"1",                     // 新闻id "title":"尚硅谷宣布 ... ...",   // 新闻标题"type":"1",                    // 新闻所属类别编号"pageViews":"40",              // 新闻浏览量"pastHours":"3",              // 发布时间已过小时数"publisher":"1"                // 发布用户ID},{"hid":"1",                     // 新闻id "title":"尚硅谷宣布 ... ...",   // 新闻标题"type":"1",                    // 新闻所属类别编号"pageViews":"40",              // 新闻浏览量"pastHours":"3",               // 发布时间已过小时数"publisher":"1"                // 发布用户ID}],"pageNum":1,    //页码数"pageSize":10,  // 页大小"totalPage":20, // 总页数"totalSize":200 // 总记录数}}
}

detial

代码实现:

3.2.1 controller

@WebServlet("/portal/*")
public class PortalController extends BaseController {private NewsTypeService typeService = new NewsTypeServiceImpl();private NewsHeadlineService headlineService = new NewsHeadlineServiceImpl();/*** 分页带条件查询新闻* @param req* @param resp* @throws ServletException* @throws IOException*/protected void findNewsPage(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {HeadlineQueryVo headlineQueryVo = WebUtil.readJson(req, HeadlineQueryVo.class);//查询分页五项数据Map<String,Object> pageInfo =  headlineService.findPage(headlineQueryVo);//将分页五项数据放入Map<String, Object> pageInfoMap = new HashMap<>();pageInfoMap.put("pageInfo",pageInfo);WebUtil.writeJson(resp,Result.ok(pageInfoMap));}

3.2.2 service

public interface NewsHeadlineService {/*** 分页查询头条新闻方法* @param headlineQueryVo* @return*/Map<String, Object> findPage(HeadlineQueryVo headlineQueryVo);
}
public class NewsHeadlineServiceImpl implements NewsHeadlineService {private NewsHeadLineDao headLineDao = new NewsHeadlineDaoImpl();@Overridepublic Map<String, Object> findPage(HeadlineQueryVo headlineQueryVo) {// 准备一个map,用于装分页的五项数据Map<String, Object> pageInfo = new HashMap<>();// 分页查询本页数据新闻List<HeadlinePageVo> pageData = headLineDao.findPageList(headlineQueryVo);// 当前 页码数int pageNum = headlineQueryVo.getPageNum();// 页大小int pageSize = headlineQueryVo.getPageSize();// 总记录数int totalSize = headLineDao.findPageCount(headlineQueryVo);// 总页数(多出一条数据的情况 +1页上去int totalPage = totalSize % pageSize == 0 ? totalSize / pageSize : totalSize / pageSize + 1;pageInfo.put("pageData",pageData);pageInfo.put("pageNum",pageNum);pageInfo.put("pageSize",pageSize);pageInfo.put("totalPage",totalPage);pageInfo.put("totalSize",totalSize);return pageInfo;}
}

3.2.3 dao

public interface NewsHeadLineDao {/*** 根据查询条件,查询当前页数据* @param headlineQueryVo* @return*/List<HeadlinePageVo> findPageList(HeadlineQueryVo headlineQueryVo);/*** 根据查询条件,查询满足条件的记录数* @param headlineQueryVo* @return*/int findPageCount(HeadlineQueryVo headlineQueryVo);}
package com.doug.headline.dao.impl;import com.doug.headline.dao.BaseDao;
import com.doug.headline.dao.NewsHeadLineDao;
import com.doug.headline.pojo.vo.HeadlinePageVo;
import com.doug.headline.pojo.vo.HeadlineQueryVo;import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;public class NewsHeadlineDaoImpl extends BaseDao implements NewsHeadLineDao {@Overridepublic List<HeadlinePageVo> findPageList(HeadlineQueryVo headlineQueryVo) {List params = new ArrayList();String sql = """selecthid,title,type,page_views pageViews,TIMESTAMPDIFF(HOUR,create_time,now()) pastHours,publisherfromnews_headlinewhereis_deleted = 0""";if(headlineQueryVo.getType() != 0){sql = sql.concat(" and type = ? ");params.add(headlineQueryVo.getType());}if(headlineQueryVo.getKeyWords() != null && !headlineQueryVo.getKeyWords().equals("")){sql = sql.concat(" and title like ? ");params.add("%"+headlineQueryVo.getKeyWords()+"%");}// 按时间升序 浏览量降序sql = sql.concat(" order by pastHours ASC , page_views DESC ");// 分页显示sql = sql.concat(" limit ?,? ");params.add((headlineQueryVo.getPageNum()-1)*headlineQueryVo.getPageSize());params.add(headlineQueryVo.getPageSize());return baseQuery(HeadlinePageVo.class,sql,params.toArray());}@Overridepublic int findPageCount(HeadlineQueryVo headlineQueryVo) {//  拼接动态 SQL,拼接参数List args = new LinkedList<>();String sql = "select count(1) from news_headline where is_deleted = 0";StringBuilder sqlBuffer = new StringBuilder(sql);String keyWords = headlineQueryVo.getKeyWords();//判断并动态拼接条件if(null != keyWords && keyWords.length() > 0){sqlBuffer.append(" and title like ? ");args.add("%" + keyWords + "%");}//  判断并动态拼接条件Integer type = headlineQueryVo.getType();if(null != type && type!=0){sqlBuffer.append(" and type = ? ");args.add(type);}// 参数转数组Object[] argsArr = args.toArray();System.out.println(sqlBuffer.toString());Long totalSize = baseQueryObject(Long.class, sqlBuffer.toString(), argsArr);return totalSize.intValue();}
}

3.3 查看头条详情

1

  • 用户点击"查看全文"时,向服务端发送新闻id
  • 后端根据新闻id查询完整新闻文章信息并返回
  • 后端要同时让新闻的浏览量+1

URI : portal/showHeadlineDetail
请求方式 : POST
请求参数:hid = 1
响应示例:

{"code":"200","message":"success","data":{"headline":{"hid":"1",                     // 新闻id "title":"马斯克宣布 ... ...",   // 新闻标题"article":"... ..."            // 新闻正文"type":"1",                    // 新闻所属类别编号"typeName":"科技",             // 新闻所属类别"pageViews":"40",              // 新闻浏览量"pastHours":"3" ,              // 发布时间已过小时数"publisher":"1" ,               // 发布用户ID"author":"张三"                 // 新闻作者}}
}

代码实现:

3.3.1 controller

    /*** 查询单个新闻详情* @param req* @param resp* @throws ServletException* @throws IOException*/protected void showHeadlineDetail(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// 获取要查询的详情新闻idInteger hid = Integer.valueOf(req.getParameter("hid"));// 封装data内容HashMap<String, Object> headlineInfo = new HashMap<>();// 查询新闻详情的voHeadlineDetailVo headlineDetailVo = headlineService.findHeadlineByHid(hid);Result result = null;if(null != headlineDetailVo){headlineInfo.put("headline",headlineDetailVo);result = Result.ok(headlineInfo);}WebUtil.writeJson(resp,result);}

3.3.2 service

    /*** 根据hid 查看单个新闻详情* @param hid* @return*/HeadlineDetailVo findHeadlineByHid(Integer hid);
    @Overridepublic HeadlineDetailVo findHeadlineByHid(Integer hid) {// 修改新闻信息浏览量+1headLineDao.increasePageViews(hid);// 查询新闻详情return headLineDao.findHeadlineInfoByHid(hid);}

3.3.3 dao

    /*** 根据 hid 查看详细新闻* @param hid 新闻对应ID* @return*/HeadlineDetailVo findHeadlineInfoByHid(Integer hid);/*** 新闻浏览量+1* @param hid* @return*/int increasePageViews(Integer hid);
    @Overridepublic HeadlineDetailVo findHeadlineInfoByHid(Integer hid) {String sql = """selecth.hid,h.title,h.article,h.type,h.page_views as pageViews,TIMESTAMPDIFF(HOUR,create_time,now()) pastHours,h.publisher,t.tname as typeName,u.nick_name as authorfromnews_headline hleft joinnews_type tonh.type = t.tidleft joinnews_user uonh.publisher = u.uidwhereh.hid = ?""";List<HeadlineDetailVo> headlineDetailVoList = baseQuery(HeadlineDetailVo.class, sql, hid);if (null != headlineDetailVoList && headlineDetailVoList.size() > 0) {return headlineDetailVoList.get(0);}return null;}@Overridepublic int increasePageViews(Integer hid) {String sql = "update news_headline set page_views = page_views +1 where hid = ?";return baseUpdate(sql, hid);}

四、头条发布修改和删除

4.1 登录校验

  • 客户端在进入发布页前、发布新闻前、进入修改页前、修改前、删除新闻前先向服务端发送请求携带token请求头
  • 后端接收token请求头后,校验用户登录是否过期并做响应
  • 前端根据响应信息提示用户进入登录页还是进入正常业务页面

URI : user/checkLogin
请求 : GET
请求头: token: … …

  • 响应:
    • 登录未过期
{"code":"200","message":"success","data":{}
}
    • 登录已过期
{"code":"504","message":"loginExpired","data":{}
}

代码实现:

4.1.1 controller

    /*** 前端自行校验token登录是否过期* @param req* @param resp* @throws ServletException* @throws IOException*/protected void checkLogin(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {String token = req.getHeader("token");Result result = Result.build(null, ResultCodeEnum.NOTLOGIN);//token 不等于空 且 没有过期if(null != token){if(!JwtHelper.isExpiration(token)){result = Result.ok(null);}}WebUtil.writeJson(resp,result);}

4.1.2 登录过滤器

/*** @Author: Gavin* @Date: 2024-02-07 21:58* @Description: 过滤器自动校验请求是否过期(过滤所有/headline/*下的方法*/
@WebFilter("/headline/*")
public class LoginFilter implements Filter {@Overridepublic void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {HttpServletRequest request = (HttpServletRequest)servletRequest;String token = request.getHeader("token");//boolean flag = false;// token 不为空 且 没有过期//if(null != token){//    boolean expiration = JwtHelper.isExpiration(token);//    if(!expiration){//        flag = true;//    }//}boolean flag = null != token && (!JwtHelper.isExpiration(token));if(flag){//放行 请求响应filterChain.doFilter(servletRequest,servletResponse);}else{WebUtil.writeJson((HttpServletResponse) servletResponse, Result.build(null, ResultCodeEnum.NOTLOGIN));}}
}

4.1.3 web.xml中配置登录校验过滤器

    <!--登录校验过滤器--><filter><filter-name>loginFilter</filter-name><filter-class>com.doug.headline.filters.LoginFilter</filter-class></filter><filter-mapping><filter-name>loginFilter</filter-name><url-pattern>/headline/*</url-pattern></filter-mapping>

4.2 提交发布头条(新增

1

  • 用户在客户端输入发布的新闻信息完毕后
  • 发布前先请求后端的登录校验接口验证登录
  • 登录通过则提交新闻信息
  • 后端将新闻信息存入数据库

URI : headline/publish
请求方式 : POST
请求头 : token: … …

  • 请求参数:
{"title":"道格维克 ... ...",   // 文章标题"article":"... ...",          // 文章内容"type":"1"                    // 文章类别
}
  • 响应示例:
    • 响应发布
{"code":"200","message":"success","data":{}
}
    • 失去登录状态发布失败
{"code":"504","message":"loginExpired","data":{}
}

代码实现:

4.2.1 controller

package com.doug.headline.controller;import com.doug.headline.common.Result;
import com.doug.headline.pojo.NewsHeadline;
import com.doug.headline.service.NewsHeadlineService;
import com.doug.headline.service.impl.NewsHeadlineServiceImpl;
import com.doug.headline.util.JwtHelper;
import com.doug.headline.util.WebUtil;
import jakarta.servlet.ServletException;
import jakarta.servlet.annotation.WebServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;import java.io.IOException;@WebServlet("/headline/*")
public class NewsHeadlineController extends BaseController {private NewsHeadlineService headlineService = new NewsHeadlineServiceImpl();/*** 发布新闻** @param req* @param resp* @throws ServletException* @throws IOException*/protected void publish(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// 读取新闻信息NewsHeadline newsHeadline = WebUtil.readJson(req, NewsHeadline.class);// 通过token获取发布者IDString token = req.getHeader("token");Long userId = JwtHelper.getUserId(token);newsHeadline.setPublisher(userId.intValue());// 将新闻存入数据库headlineService.addNewsHeadline(newsHeadline);WebUtil.writeJson(resp, Result.ok(null));}
}

4.2.2 seriver

    /*** 新增头条新闻* @param newsHeadline* @return*/int addNewsHeadline(NewsHeadline newsHeadline);
    /*** 发布新闻** @param req* @param resp* @throws ServletException* @throws IOException*/protected void publish(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// 读取新闻信息NewsHeadline newsHeadline = WebUtil.readJson(req, NewsHeadline.class);// 通过token获取发布者IDString token = req.getHeader("token");Long userId = JwtHelper.getUserId(token);newsHeadline.setPublisher(userId.intValue());// 将新闻存入数据库headlineService.addNewsHeadline(newsHeadline);WebUtil.writeJson(resp, Result.ok(null));}

4.2.3 dao

    /*** 增加新闻头条* @param newsHeadline* @return*/int addNewsHeadline(NewsHeadline newsHeadline);
    @Overridepublic int addNewsHeadline(NewsHeadline newsHeadline) {String sql = """insert intonews_headlinevalues(DEFAULT,?,?,?,?,0,NOW(),NOW(),0)  """;return baseUpdate(sql,newsHeadline.getTitle(),newsHeadline.getArticle(),newsHeadline.getType(),newsHeadline.getPublisher());}

添加成功:
1

4.3 修改头条回显

1

  • 前端先调用登录校验接口,校验登录是否过期
  • 登录校验通过后 ,则根据新闻id查询新闻的完整信息并响应给前端

URI : headline/findHeadlineByHid
请求方式:POST
请求参数:hid=1

  • 响应实例:
    • 查询成功
{"code":"200","message":"success","data":{"headline":{"hid":"1","title":"马斯克宣布","article":"... ... ","type":"2"}}
}

4.3.1 controller

    /*** 修改新闻信息** @param req* @param resp* @throws ServletException* @throws IOException*/protected void findHeadlineByHid(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {Integer hid = Integer.valueOf(req.getParameter("hid"));HeadlineDetailVo headlineByHid = headlineService.findHeadlineByHid(hid);HashMap<String, Object> headlineMap = new HashMap<>();Result result = null;if(null != headlineByHid){headlineMap.put("headline",headlineByHid);result = Result.ok(headlineMap);}WebUtil.writeJson(resp,result);}

4.4 保存修改

1

  • 客户端将新闻信息修改后,提交前先请求登录校验接口校验登录状态
  • 登录校验通过则提交修改后的新闻信息,后端接收并更新进入数据库

URI:headline/update
请求方式:post

  • 请求参数:
{"hid":"1","title":"道格维克 ... ...","article":"... ...","type":"2"
}
  • 响应实例:

修改成功:

{"code":"200","message":"success","data":{}
}

修改失败:

{"code":"504","message":"loginExpired","data":{}
}

代码实现:

4.4.1 controller

    /*** 修改新闻信息* @param req* @param resp* @throws ServletException* @throws IOException*/protected void update(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {NewsHeadline newsHeadline = WebUtil.readJson(req, NewsHeadline.class);headlineService.updateHeadline(newsHeadline);WebUtil.writeJson(resp,Result.ok(null));}

4.4.2 service

    /*** 修改新闻信息* @param newsHeadline* @return*/int updateHeadline(NewsHeadline newsHeadline);
    @Overridepublic int updateHeadline(NewsHeadline newsHeadline) {return headLineDao.updateHeadlineInfo(newsHeadline);}

4.4.3 dao

    /*** 修改新闻信息* @param newsHeadline* @return*/int updateHeadlineInfo(NewsHeadline newsHeadline);
    @Overridepublic int updateHeadlineInfo(NewsHeadline newsHeadline) {String sql = "update news_headline set title = ?,article = ?,type = ? ,update_time = now() where hid = ?";return baseUpdate(sql, newsHeadline.getTitle(),newsHeadline.getArticle(),newsHeadline.getType(),newsHeadline.getHid());}

4.5 删除头条

2

  • 将要删除的新闻id发送给服务端
  • 服务端校验登录是否过期,未过期则直接删除,过期则响应登录过期信息

URI : headline/removeByHid
请求方式:POST
请求参数:hid=1

  • 响应实例:

删除成功

{"code":"200","message":"success","data":{}
}

删除失败

{"code":"504","message":"loginExpired","data":{}}
  • controller:
    /*** 删除对应Hid的新闻* @param req* @param resp* @throws ServletException* @throws IOException*/protected void removeByHid(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {Integer hid = Integer.parseInt(req.getParameter("hid"));headlineService.removeByHid(hid);WebUtil.writeJson(resp,Result.ok(null));}
  • service
    /*** 删除单个新闻* @param hid 新闻hid* @return*/int removeByHid(Integer hid);
    @Overridepublic int removeByHid(Integer hid) {return headLineDao.removeByHid(hid);}
  • dao
    /*** 删除对应hid的新闻* @param hid* @return*/int removeByHid(Integer hid);
    @Overridepublic int removeByHid(Integer hid) {String sql = "update news_headline set is_deleted = 1, update_time = NOW() where hid = ?";return baseUpdate(sql, hid);}

总结

2.1 登录表单提交

controller

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/2775468.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

第三讲 多重背包问题①——转化

【题目来源】AcWing 4. 多重背包问题 I 【题意分析】和完全背包问题类似&#xff0c;但是区别在于每一种物品的数量是有限的。 【解决方法】 1.转化为 0 / 1 0/1 0/1 背包问题 因为每一种物品数量有限&#xff0c;所以将每个物品看作单独的种类&#xff0c;可转化为 0 / 1 0/…

掌握Vue,开启你的前端开发之路!

介绍&#xff1a;Vue.js是一个构建数据驱动的Web应用的渐进式框架&#xff0c;它以简洁和轻量级著称。 首先&#xff0c;Vue.js的核心在于其视图层&#xff0c;它允许开发者通过简单的模板语法将数据渲染进DOM&#xff08;文档对象模型&#xff09;。以下是Vue.js的几个重要特点…

Git中为常用指令配置别名

目录 1 前言 2 具体操作 2.1 创建.bashrc文件 2.2 添加指令 2.3 使其生效 2.4 测试 1 前言 在Git中有一些常用指令比较长&#xff0c;当我们直接输入&#xff0c;不仅费时费力&#xff0c;还容易出错。这时候&#xff0c;如果能给其取个简短的别名&#xff0c;那么事情就…

力扣102. 二叉树的层序遍历 (复习vector和queue的常见用法

目录 题目描述 题目解析 题目答案 题目所用知识点 最后 题目描述 给你二叉树的根节点 root &#xff0c;返回其节点值的 层序遍历 。 &#xff08;即逐层地&#xff0c;从左到右访问所有节点&#xff09;。力扣&#xff08;LeetCode&#xff09;官网 - 全球极客挚爱的技术…

K8S之运用节点选择器指定Pod运行的节点

node节点选择器的使用 使用场景实践使用nodeName使用nodeSelectornodeName和nodeSelector混合使用1、设置了nodeName 和 设置 Node上都不存在的标签。看调度情况2、设置nodeName 为node1 和 设置 node2上才有的标签。看调度情况 实践总结 使用场景 默认情况&#xff0c;在创建…

c++二叉树寒假特训题目(2)

hello&#xff0c;我是Joseph&#xff0c;今天推出第二期c二叉树寒假特训题目。 第一期传送门 第一期答案传送门 这期有7题&#xff0c;目录如下。 目录 题目 二叉树结点查找 二叉树是否对称 ​编辑 二叉排序树 层次遍历 根据前序中序求后序 二叉树高度 ​编辑 二…

【通讯录案例-偏好设置 Objective-C语言】

一、刚才,我们plist存储,讲完了,这个plist,我直接,右键,打开 打开 不用xcode,我就用文本文档打开,打开方式:其他 选择:文本编辑 打开 好,这个里边儿啊,就是我们刚才存的一个Key:Value 它本质上,是一个xml 这是一种文件的格式, 等你们讲到网络的时候,实际上,…

MGIE官网体验入口 苹果多模态大语言模型AI图像编辑工具在线使用地址

MGIE是一项由苹果开源的技术&#xff0c;利用多模态大型语言模型&#xff08;MLLMs&#xff09;生成图像编辑指令&#xff0c;通过端到端训练&#xff0c;捕捉视觉想象力并执行图像处理操作&#xff0c;使图像编辑更加智能、直观。 MGIE官网体验入口https://github.com/apple/M…

上市公司人工智能转型指数及55个工具变量汇总数据集(2024.2月更新)

一、“智能化转型”发文趋势和主题分布 二、数据来源 上市公司年报、官网&#xff0c;中国知网及各期刊官网等三、时间跨度 工具变量&#xff1a;2022-2024年&#xff1b; 上市公司人工智能转型指数&#xff1a;2007-2021年四、数据范围 中国A股上市公司五、数据展示 序号…

单片机学习笔记---串口向电脑发送数据电脑通过串口控制LED

目录 串口向电脑发送数据 每隔一秒串口就发送一个递增的数给电脑 电脑通过串口控制LED 波特率的具体计算 HEX模式和文本模式 前两节是本节的理论基础&#xff0c;这节开始代码演示&#xff01; 串口向电脑发送数据 接下来先开始演示一下串口单向发送一个数字给电脑&…

ShardingSphere 5.x 系列【3】分库分表中间件技术选型

有道无术,术尚可求,有术无道,止于术。 本系列Spring Boot 版本 3.1.0 本系列ShardingSphere 版本 5.4.0 源码地址:https://gitee.com/pearl-organization/study-sharding-sphere-demo 文章目录 1. 前言2. My Cat3. ShardingSphere4. Dble5. Vitess6. 大厂开源6.1 Cobar6.…

[HTTP协议]应用层的HTTP 协议介绍

目录 1.前言 2.使用fiddler抓包来观察HTTP协议格式 3.HTTP协议的基本格式 2.1请求 2,1.1首行 2.1.2请求头 2.1.3空行 2.2响应 2.2.1首行 2.2.2响应头 键值对 ​编辑2.2.3空行 2.2.4载荷(响应正文) 3.认识URL 3.1关于URL encode 1.前言 我们在前面的博客中,简单的…

火星文:网络时代下的语言

引言 在互联网时代&#xff0c;网络语言的发展日新月异。火星文作为一种特殊的网络表达方式&#xff0c;近年来逐渐兴起并成为了网络文化的一部分。 火星文生成器 | 一个覆盖广泛主题工具的高效在线平台(amd794.com) https://amd794.com/huoxingwen 火星文的兴起时代 火星…

请手写几种js排序算法

什么是排序算法 冒泡排序选择排序插入排序快速排序归并排序&#xff08;Merge Sort&#xff09; 思想实现测试分析动画 快速排序 &#xff08;Quick Sort&#xff09; 思想实现测试分析动画 思考&#xff1a;快排和归并用的都是分治思想&#xff0c;递推公式和递归代码也非常相…

深度学习在知识图谱问答中的革新与挑战

目录 前言1 背景知识2 基于深度学习改进问句解析模型2.1 谓词匹配2.2 问句解析2.3 逐步生成查询图 3 基于深度学习的端到端模型3.1 端到端框架3.2 简单嵌入技术 4 优势4.1 深入的问题表示4.2 实体关系表示深挖4.3 候选答案排序效果好 5 挑战5.1 依赖大量训练语料5.2 推理类问句…

MacOS上怎么把格式化成APFS的U盘或者硬盘格式化回ExFAT?

一、问题 MacOS在更新MacOS Monterey后或者更高系统后发现&#xff0c;格式U盘或者硬盘只有4个APFS选项&#xff0c;那么我们该如何将APFS格式成ExFAT&#xff1f; 二、解答 将APFS的U盘或者硬盘拓展成MacOS的拓展格式即可&#xff0c;操作步骤如下 1、电脑接入U盘或者硬盘 2…

深度学习入门笔记(八)可以不断思考的模型:RNN与LSTM

8.1 循环神经网络RNN 之前学到的 CNN 和全连接&#xff0c;模型的输入数据之间是没有关联的&#xff0c;比如图像分类&#xff0c;每次输入的图片与图片之间就没有任何关系&#xff0c;上一张图片的内容不会影响到下一张图片的结果。但在自然语言处理领域&#xff0c;这就成了…

158基于matlab的用于分析弧齿锥齿轮啮合轨迹的程序

基于matlab的用于分析弧齿锥齿轮啮合轨迹的程序&#xff0c;输出齿轮啮合轨迹及传递误差。程序已调通&#xff0c;可直接运行。 158 matlab 弧齿锥齿轮啮合轨迹 传递误差 (xiaohongshu.com)

利用路由懒加载和CDN分发策略,对Vue项目进行性能优化

目录 一、Vue项目 二、路由懒加载 三、CDN分发策略 四、如何对Vue项目进行性能优化 一、Vue项目 Vue是一种用于构建用户界面的JavaScript框架&#xff0c;它是一种渐进式框架&#xff0c;可以用于构建单页应用&#xff08;SPA&#xff09;和多页应用。Vue具有简单易学、灵…

C++:二叉搜索树模拟实现(KV模型)

C&#xff1a;二叉搜索树模拟实现&#xff08;KV模型&#xff09; 前言模拟实现KV模型1. 节点封装2、前置工作&#xff08;默认构造、拷贝构造、赋值重载、析构函数等&#xff09;2. 数据插入&#xff08;递归和非递归版本&#xff09;3、数据删除&#xff08;递归和非递归版本…