【博客系统】 一

该博客系统基于servlet和mysql数据库 , 并且通过xshell终端工具部署至云服务器. 实现的功能包括:

1.博客列表页

2.博客详情页

3.登陆页面

4.强制登陆检查

5.获取用户信息

6.退出登陆

7.发布博客

一.系统展示

登陆页面

博客列表页

博客详情页

博客编辑页


下面就开始编写代码了. (前端代码不提供) 接下来的操作主要是两个大的方面 . 

1.前端和服务器的交互

2.服务器和数据库的交互

二.服务器和数据库的交互

该系统涉及的表包括blog博客表和用户登陆的user表. 

一般需要把建库建表的操作,写成sql文件保留下来 , 后续如果把程序部署到别的机器上,建库操作直接赋值sql,然后执行就可以完全服务器数据库的建库建表操作.

dao层

Data Acess Object 数据访问对象 , 写一些类,通过这些类里的方法封装了数据库操作,此时数据库就是通过这样的对象来访问的

1.设计数据库

  • 根据需求,找出需要有哪些实体
  • 梳理清楚实体和实体之间的关系 一对一/一对多/多对多

2.封装DBUtil 实现建立连接和断开连接

package dao;


import com.mysql.cj.jdbc.MysqlDataSource;

import javax.sql.DataSource;
import javax.xml.transform.Result;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

/**
 * 通过这个类,把数据库建立连接的逻辑封装好
 */

public class DBUtil {
    //使用单例模式创建(懒汉模式线程不安全)
    private static volatile DataSource dataSource=null;

    //私有,只在类内使用
    private static DataSource getDataSource() {
        if (dataSource == null) {
            synchronized (DBUtil.class) {
                if (dataSource == null) {
                    dataSource = new MysqlDataSource();
                    ((MysqlDataSource) dataSource).setUrl("jdbc:mysql://127.0.0.1:13306/blogsystem?characterEncoding=utf8&useSSL=false");
                    ((MysqlDataSource) dataSource).setUser("root");
//                    ((MysqlDataSource) dataSource).setPassword("chenyafen");
                    ((MysqlDataSource) dataSource).setPassword("123456");
                }
            }
        }
        return dataSource;
    }


    //提供方法,和数据库建立连接
    public static Connection getConnection() throws SQLException {
        return getDataSource().getConnection();
    }

    //提供方法,和数据库断开连接
    public static void close(Connection connection, PreparedStatement statement, ResultSet resultSet) throws SQLException {


        if(resultSet!=null){
            resultSet.close();
        }

        if(statement!=null){
            statement.close();
        }

        if(connection!=null){
            connection.close();
        }
    }

}

3.创建实体类 后续数据库操作是围绕实体类展开的

三.服务器和数据库的交互

实现前后端交互逻辑 , 针对每个功能点的步骤都是一样的. 

1.设计前后端交互接口

2.开发后端代码

3.开发前端代码

4.调试

1.博客列表页

让博客列表页再加载的时候,发起一个ajax的http 请求,请求发送到服务器上,就能获取博客列表数据. 进一步的把博客数据展示到页面上 (拼接成一些html片段)

1.前端发起一个http请求,向后端索要博客列表数据

2.后端收到请求之后查询数据库获取到数据库中的博客列表,返回给前端

3.前端拿到响应之后,就依据这里的内容,构造出html片段,最终显示出来

在进行这三个操作之前,还需要约定前后端交互接口,后续前端和后端要进行很多不同的数据交互.每一种数据交互,都需要发送不同的请求,返回不同的响应 .

此处就需要把请求具体什么样? 响应具体什么样? 都约定好 !

约定前后端交互接口

以下是一种典型的约定方式

请求:

GET blog

响应:

HTTP/1.1 200 OK

Content-Type:application/json ( 返回的是json数据)

[

        {

                blodId:1,

                title:"第一篇",

                content:"dddd",

                userId:1,

                posttime:"ddddd"

        } ,

        {

                blodId:1,

                title:"第一篇",

                content:"dddd",

                userId:1,

                posttime:"ddddd"

        }

]

前端负责构造请求 , 解析响应 ;

后端负责解析请求, 构造响应 ;

编写后端代码

api应用编程接口

博客系统后续还会写一些servlet给前端提供功能的支持. 这些都可以理解成服务器给前端提供的api (或者也可以叫做Controller )

说明:

jackson看到blogs是一个list,就会构造出一个json数组; 针对list中每一个blog对象,分别构造出json对象 , 具体构造过程,就是根据Blog属性:属性的名字就是json的key,属性的值就是json的值

 

编写前端代码

让页面通过js ajax的方式发起http请求 . 

说明:

1.定义了一个函数,并调用这个函数 (不需要返回值)

2.构造这个html片段

相当于

<div> </div>

<div class="blog"> <div>

blog就是服务器返回的json数组里的一个元素 (这一个元素有五个属性)

浏览器访问该页面

 Fiddler抓包

上面的请求是获取列表页这个静态页面的

下面的请求是获取博客数据的

如果出现灰色的是因为触发了浏览器自带的缓存;

浏览器为了提高页面加载速度,就会把静态的资源在本地硬盘缓存一份,后续再访问统一资源,直接从本地获取 .

前后端交互过程:

当浏览器发起一个形如blog的http请求时,服务器就会调用查询数据库,并获取到数据库中的数据,然后转换为json格式的字符串,再返回给前端,前端拿到数据之后,回调函数进行遍历数据,依据返回的数据构造出html片段

问题:

1.更早发布的博文应该在下面 .

解决方法:给查询语句加上order by ,按照时间降序排序(大的在前, 小的在后)即可

2.时间格式不对

针对这个问题,要先明确问题出在前端还是后端 , 抓包查看后端返回的响应 , 发现是后端的问题

后端将从数据库读取到的对象转换为json字符串,转成的json字符串就是根据Blog对象的getter方法来完成的 ,jackson会自动调用getter方法把得到的结果作为json字符串中属性的值.  因此问题出在posttime的getter方法上,

使用simpleDateFormat方法:

2.博客详情页

2.1.约定前后端交互接口

请求:

GET  /blog?blodId=1     

如果是请求中不带query string, 此时就是查询博客列表

如果带有query string (blogId) , 此时就是查询指定博客的详细情况

响应:

HTTP/1.1 200 OK

Content-Typea:application/json

{

    blogId:1,

    title:"dfljf",

    content:"gjdsf",

    userId:1,

    posttime:"2023-12-4"

}

2.2实现后端代码

2.3实现前端代码

注意:

1.这里需要让博客详情页,把数据库的中的原始数据,渲染成md渲染后的数据

使用editor.md的线程的方法即可(阅读文档)

2.editor.md也依赖jquery,注意引入的顺序

3.登陆页面

3.1前后端交互接口

请求:

POST /login

Content-type:aaplication/x-www-form-urlencoded

使用form表单提交 使用ajax也可以

响应:

HTTP/1.1 302

Location:blog_list.html

3.2编写后端代码

注意:

1.不要对用户名和密码分别提示,容易造成不安全

2.创建会话,参数设为true.

不存在会话就创建,存在就查询 ;  并且会生成键值对 (sesesionid : httpsession对象 ), 并且会把session通过set-cookie返回到浏览器

3.3编写前端代码

注意:

1.构造sql语句的时候 , 先用preparestatement创建statement . 再设置占位符的值

否则会出现空指针异常

4.实现强制登陆

使得网站登陆后才能使用, 此处咱们要求我们的博客系统,必须登陆才能使用 ;

如果用户在未登陆情况下,访问博客列表页/详情页/编辑页,都会自动跳转到登录页

4.1约定前后端交互接口

在博客列表页/详情页/编辑页,再发起一个get的ajax请求,询问服务器时候登陆

4.2编写前后端代码


5.实现显示用户信息

在列表页,显示当前登陆用户的个人信息 ; 在详情页,显示这个文章的作者信息

实现方法:

在博客列表页和详情页分别发起ajax请求

列表页,就需要获取到当前登陆用户的信息 ; 详情页,就需要获取到文章作者的信息.

5.1约定前后端交互接口

列表页

请求:

GET /user

响应:

HTTP/1.1 200 ok

{

    userId:1,

    username:'zhangsan'

}

详情页

请求:

GET /user?blogId=1

响应:

HTTP/1.1 200 OK

{

    userId:1,

    username:'zhangsan'

}

注意:

对于登陆功能来说,依赖了session机制,tomcat是在内存中存储session的.

当重启了tomcat服务器之后,之前的session就没了,下一次访问就需要重新登陆

但是有些smart tomcat会把session放到硬盘中持久化存储 , 重启服务器也不需要重新登陆 ;

6.退出登陆(注销)

判定登陆状态逻辑中

1.会话存在

2.会话中存储的user对象存在

两个条件同时满足,才认为用户是已经登陆了

破坏上述任何一个条件都可以实现注销

但是servlet中,并没有提供一个api来直接删除会话,但是有api可以删除会话中的user

(Attribute)

6.1约定前后端交互接口

请求:

GET /logout 

响应:

HTTP/1.1 302

Location :login.html

6.2后端

6.3前端

点击页面的注销,实质上是一个a标签,通过a标签的href属性,指定要访问的请求路径即可 .

点击a标签,自然就能触发http get请求了

7.发布博客

本质上和登陆差不多, 核心都是通过form表单,把页面中用户输入的内容提高到服务器,服务器就会内容保存到数据库中.

7.1约定前后端交互接口

使用form提交数据到服务器

请求:

POST /blog

Conten-type:application/x-www-form-urlencoded (form表单格式)

body内容:

title=***&content=***** 

响应:

HTTP/1.1 302

Location:blog_list.html

提交成功跳转到博客列表页,来到页表页之后,就能够看到刚才新发布的博客了 .

7.2后端

7.3前端

把form表单补齐

注意:

md编辑器怎么添加name属性呢?

在此处写一个隐藏的textarea,就可以实现form表单提交的效果,就可以指定name的值.


部署请看这篇 【博客系统】 二-CSDN博客 ~~~ 

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【Linux】Linux进程间通信(一)

​ ​&#x1f4dd;个人主页&#xff1a;Sherry的成长之路 &#x1f3e0;学习社区&#xff1a;Sherry的成长之路&#xff08;个人社区&#xff09; &#x1f4d6;专栏链接&#xff1a;Linux &#x1f3af;长路漫漫浩浩&#xff0c;万事皆有期待 上一篇博客&#xff1a;【Linux】…

如何选择适合企业的数字化看板系统

数字化看板是一种数字化管理工具&#xff0c;它具有实时数据展示、任务分配与优先级管理、问题追踪与解决、供应链管理与协同以及数据分析与预测等功能。这些功能可以帮助企业提高生产效率、降低成本、优化资源配置并实现生产过程的透明化。 具体来说&#xff0c;数字化看板可以…

Navicat 使用

安装包请私信本人 软件安装 需要注意以下不要先运行navicat软件,先运行 在工具的第一个选项(1.Patch)里选择Backup&#xff0c;然后点击&#xff0c;Patch按钮&#xff0c;选择Navicat的安装位置中的navicat.exe文件 如果显示这样表示成功了 在这选择语言简体中文 点击Gener…

第五章 路由技术及应用

目录 5.1 直连路由概述 5.1.1 直连路由工作原理 5.1.2 直连路由配置 5.2 直连路由仿真 5.3 静态路由技术 5.3.1 静态路由定义 5.3.2 静态路由工作原理 5.3.3 静态路由配置 5.3.4 默认路由 (1) 默认路由概述 (2) 配置默认路由 (3) 默认路由应用场合&#xff1a;上网…

基于springboot实现疫苗接种管理系统项目【项目源码】计算机毕业设计

基于springboot实现疫苗接种管理系统演示 Java语言简介 Java是由SUN公司推出&#xff0c;该公司于2010年被oracle公司收购。Java本是印度尼西亚的一个叫做爪洼岛的英文名称&#xff0c;也因此得来java是一杯正冒着热气咖啡的标识。Java语言在移动互联网的大背景下具备了显著的…

3+差异分析+PPI+预后+实验的生信思路,简单直接容易上手

今天给同学们分享一篇生信文章“Identification of hub genes and pathways in lung metastatic colorectal cancer”&#xff0c;这篇文章发表在BMC Cancer期刊上&#xff0c;影响因子为3.8。 结果解读&#xff1a; 原发性和肺转移性CRC组织之间的差异表达基因的鉴定 使用在…

Spring Boot EasyPOI 使用指定模板导出Excel

相信大家都遇到过&#xff0c;用户提出要把界面上的数据导成一个Excel&#xff0c;还得是用户指定的Excel格式&#xff0c;用原生的POI&#xff0c;需要自己去实现&#xff0c;相信是比较麻烦的&#xff0c;所以我们可以使用开源的EasyPOI. 先上个图&#xff0c;看看是不是大家…

<Linux>(极简关键、省时省力)《Linux操作系统原理分析之进程管理2》(4)

《Linux操作系统原理分析之进程管理2》》&#xff08;4&#xff09; 3 进程管理3.5 P、V操作3.5.1 信号量3.5.2 信号量的应用3.5.3 进程同步机制 3.6 进程通信3.6.1 消息通信3.6.2 信箱通信 3.7 死锁3.7.1 死锁的定义3.7.2 死锁产生的必要条件3.7.3 死锁的预防3.7.4 死锁的避免…

如何使用Omniverse Kit开发元宇宙

最近我研究了一些潜在的元宇宙开发平台。尽管Facebook上个月引发了关于元宇宙的最新一轮炒作&#xff0c;但另一家公司英伟达&#xff08;Nvidia&#xff09;在开发实际元宇宙平台方面走得更远。Nvidia的Omniverse自2019年以来一直在运行&#xff0c;因此在今天的帖子中&#x…

vscode中Chinese (Simplified)汉化无效解决方法

问题复现 之前已经下载了 Chinese (Simplified)插件并启用了&#xff0c;都是正常的中文简体。有时候打开vscode的时候&#xff0c;会发现汉化失效了&#xff0c;如图&#xff1a; 解决方法 依次点击 扩展&#xff08;Extensions&#xff09;— Chinese (Simplified) — 选…

SpringBoot使用DevTools实现后端热部署

&#x1f4d1;前言 本文主要SpringBoot通过DevTools实现热部署的文章&#xff0c;如果有什么需要改进的地方还请大佬指出⛺️ &#x1f3ac;作者简介&#xff1a;大家好&#xff0c;我是青衿&#x1f947; ☁️博客首页&#xff1a;CSDN主页放风讲故事 &#x1f304;每日一句&…

WorkPlus移动数字化平台,助力企业全面掌控业务和生态

在移动化的时代&#xff0c;企业面临着将业务和生态纳入数字化平台的挑战。WorkPlus作为一款安全专属的移动数字化平台&#xff0c;成为企业业务和生态全面掌控的有力助手。它如同一艘强大的“航空母舰”&#xff0c;助力企业实现全面发展&#xff0c;从业务到生态&#xff0c;…

Linux安装Docker完整教程

Linux安装Docker完整教程 1.卸载旧版本的Docker&#xff08;可选&#xff09;2.安装Docker&#xff08;1&#xff09;yun安装&#xff08;2&#xff09;离线安装 3.启动Docker4.配置镜像加速5.Docker拉取镜像命令 参考链接 https://blog.csdn.net/m0_59196543/article/details/…

9.基于SpringBoot3+MybatisPlus定制化代码生成器类

我们在3.基于SpringBoot3集成MybatisPlus中讲到自定义代码生成器&#xff0c;但是往往遗留代码生成的类格式或者命名不符合要求&#xff0c;需要手工修改&#xff0c;但是当表很多时就比较头痛,所以我们自定义模板在进行代码生成 1. 新建MyTemplateEngine.java类 里面大多实现…

小型心仪什么牌子好又便宜?迷你洗衣机品牌推荐

相信不少人群为了方便清洗衣服&#xff0c;都会直接选择了大型的洗衣机。由于家里住的人多&#xff0c;所以对洗衣机的使用还是比较频繁&#xff0c;但内衣裤和其它衣服混合在一起清洗的话&#xff0c;或许大多数人都不太会接受的了&#xff0c;所以都是选择自己手工洗的&#…

【uniapp/uview1.x】u-upload 在 v-for 中的使用时, before-upload 如何传参

引入&#xff1a; 是这样一种情况&#xff0c;在接口获取数据之后&#xff0c;是一个数组列表&#xff0c;循环展示后&#xff0c;需要在每条数据中都要有图片上传&#xff0c;互不干扰。 分析&#xff1a; uview 官网中有说明&#xff0c;before-upload 是不加括号的&#xff…

springboot服务和python服务如何自定义启动banner

shigen日更文章的博客写手&#xff0c;擅长Java、python、vue、shell等编程语言和各种应用程序、脚本的开发。记录成长&#xff0c;分享认知&#xff0c;留住感动。 shigen最近在修改ruoyi的框架&#xff0c;看到了框架自带的banner图&#xff0c;就是一个不爽&#xff0c;于是…

AI大模型低成本快速定制法宝:RAG和向量数据库

文章目录 1. 前言2. RAG和向量数据库3. 论坛日程4. 购票方式 1. 前言 当今人工智能领域&#xff0c;最受关注的毋庸置疑是大模型。然而&#xff0c;高昂的训练成本、漫长的训练时间等都成为了制约大多数企业入局大模型的关键瓶颈。 这种背景下&#xff0c;向量数据库凭借其独特…

3.5 Windows驱动开发:应用层与内核层内存映射

在上一篇博文《内核通过PEB得到进程参数》中我们通过使用KeStackAttachProcess附加进程的方式得到了该进程的PEB结构信息&#xff0c;本篇文章同样需要使用进程附加功能&#xff0c;但这次我们将实现一个更加有趣的功能&#xff0c;在某些情况下应用层与内核层需要共享一片内存…

freertos源码下载和目录结构分析

1、源码下载 下载网址&#xff1a;https://www.freertos.org/zh-cn-cmn-s/&#xff1b; 2、源码目录结构 3、关键的代码文件