JavaWeb QQZone项目架构总结

JavaWeb QQZone项目架构总结

这是学习JavaWeb过程中和以往相比做的比较复杂的小项目,是通过tymeleaf进行渲染的B/S(浏览器/服务器)小项目,课程链接:尚硅谷丨2022版JavaWeb教程(全新技术栈,全程实战),尚硅谷,yyds!!!
由于不想花过多的时间在前端上,所以HTML/CSS/JavaScript页面模板大多直接使用的课程资料,就自己模仿着做了一个添加日志和注册的页面。听视频介绍这个项目的主要目的就是手撕简约版Spring MVC框架,为了后面学习框架相对轻松一点。第一次实现了数据库、后台程序、前端页面的交互,还是很有意思,所以写下来理清自己的思路,为了自己更好的理解,也欢迎大家纠错更正。

一、开发环境:

jdk8+MySQL8+tomcat8.5(课程中用的数据库是MySQL5,由于版本不同有些细节不同也耽误了不少时间,下面会提到)

二、流程图:

在这里插入图片描述

三、主要模块

监听器和IOC容器:

一旦监听到服务器启动,开始调用BeanFactory创建容器,通过读取配置文件中的标签内容,将后续的Controller类、Service类、DAO类实例化保存。并且建立依赖关系,比如说操作日志相关内容的控制器TopicController里面用到了TopicService,那么直接将刚刚实例化的TopicService赋值到TopicController中,这就是“控制反转”和“依赖注入”。以往我们写程序,一个对象里面需要另一个对象我们就让前者自己直接new出来,但是这样会导致对象依赖和耦合严重,不利于代码维护。为了实现“高内聚,低耦合”的架构,我们现在把创建对象的权利全部交给第三方,即“控制反转”,然后再通过配置文件中的信息进行“依赖注入”,达到解除耦合的目的。

DispatcherServlet:

作为核心响应调度,它的工作是拦截获取到浏览器的(A.do?opetate=B)请求,通过字符串处理,在IOC容器中查找到处理该A请求的指定Controller类,再通过反射找到B方法,进行方法参数赋值调用方法。

把MVC中的V即“view‘也放在dispatcherServlet中,控制器进行操作后需要给dispatcherServlet返回一个字符串,dispatcherServlet通过该字符串判断下一步工作,是继续调用其他控制器,还是直接返回页面给浏览器。

Controller、Service、DAO:

Controller作为控制器提供一些方法供浏览器选择,比如说浏览器端需要执行日志(Topic)添加工作,那需要调用TopicController中的addTopic()方法,再比如需要执行登录操作,当用户点击“登录”按键时浏览器就调用了UserBasicController(UserBasic是用户信息类,登录时需要查询用户信息,所以调用它的Controller)中的login方法。Service就是业务方法,比如说Controller现在整理好了浏览器发来的日志添加内容,需要保存到数据库了,它就调用相应的Service方法,Service再看看有什么需要封装整理的,然后再调用DAO方法,至于DAO就是JDBC中的内容,应该很熟悉了。

四、遇到的主要问题

1、项目关联包问题

异常:java.lang.IllegalStateException: 启动子级时出错

注意操作顺序!一定要先关联上lib下的各种驱动包、添加上tomcat、然后再打包成Artifacts进行部署。刚开始就遇到了找不到MySQL驱动器的问题,原因是将新建的项目一开始就打包成了Artifacts,然后再关联,这样的话Artifacts进行部署时里面当然没有我们关联的驱动。出现这样的问题解决很简单,不需要你删除Artifacts后再添加,只需要Project Structer下面的problems就可以解决。

2、类加载器问题

异常:java.lang.NullPointerException
at java.util.Properties$LineReader.readLine(Properties.java:434)
at java.util.Properties.load0(Properties.java:353)
at java.util.Properties.load(Properties.java:341)

这个问题我解决了好久,抛出的异常就是在获取数据库链接的时候无法读到你的properties配置文件,无法获取链接。就是这一句出了问题:InputStream stream=ClassLoader.getSystemClassLoader().getResourceAsStream(“jdbc.properties”);

于是我做了个单元测试,在idea里面明明可以获取链接,但是到tomcat服务器上就不行。然后我在评论区下发现了一个留言,需要改成:InputStream stream =JDBCUtils.class.getClassLoader().getResourceAsStream(“jdbc.properties”),我一试果然成功,为什么出现这样的情况呢,说到底是路径问题:

你可以尝试在idea下和在tomcat环境下分别执行以上两句,你会发现在idea下两个得到的路径是相同的,都是当前项目的src下:

System.out.println(JDBCUtils.class.getClassLoader().getResource(""));
System.out.println(ClassLoader.getSystemClassLoader().getResource(""));

在这里插入图片描述
但是同样的代码在tomcat调用时:
在这里插入图片描述

会发现InputStream stream =JDBCUtils.class.getClassLoader().getResourceAsStream(“jdbc.properties”) 调用的路径是artifacts打包后的“src”目录,是正确的。而InputStream stream=ClassLoader.getSystemClassLoader().getResourceAsStream(“jdbc.properties”);得到的是null。

3、LocalDateTime类转化问题

异常:java.lang.IllegalArgumentException: Can not set java.util.Date field com.guoliang.qqzone.pojo.Topic.topicDate to java.time.LocalDateTime

当调用DAO时一旦发现异常can not set A to B,就是你不能把B类型赋值给A。

视频中老师讲的时候是没有这个问题的,因为老师用的是MySQL5,这个问题应该是MySQL8驱动引入的。该项目数据库中的Date全部是DateTime,对应的Java中是LocalDateTime或者TimeStamp,而我们Java中设定的全部是Date。

解决方法:1、将pojo类中的Date全部转化为LocalDateTime

​ 2、BaseDAO中加上以下代码进行转化

//LocalDateTime需要转化
            if (propertyValue.getClass().toString().equals("class java.time.LocalDateTime")) {
                propertyValue = Timestamp.valueOf((LocalDateTime) propertyValue);
            }
4、tymeleaf渲染问题

写好的前端页面展示出来发现与我们所想不一样,这个问题老师也遇到了,再上一个项目中老师一直没有发现,但是这个项目老师成功解决了这个问题。问题根源在于既然使用了tymeleaf,你就不能直接调用网页,必须经过DispactureServlet中的视图模块进行调用渲染,否则你页面上的所有“th:”都无法识别。

六、部分结果展示:

登录
主页面
回复
添加日志

  • 3
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

LeoCache

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值