课程Project总结 - 移动web大作业(不看微博)

news/2024/12/17 10:48:45/文章来源:https://www.cnblogs.com/smiecj/p/18611856

移动web最后的大作业我们组做的是实现类似新浪微博的功能。基本功能包括修改个人信息、发微博、看微博和回复数据库设计微博。我认为整个工程可以分为数据库设计、前台HTML、JSP和CSS开发、后台JavaScript设计。下面就依次看这几个部分

数据库设计

用户类:登录不看微博的用户,个人属性包括用户id、用户姓名、登录密码、个性签名和头像。其中,用户姓名是不能重复的,登录密码和个性签名可以修改,头像上传功能没有实现(这个是我最遗憾的地方)

其他类我就不一一讲了,回复和评论有什么区别呢?评论是针对博客的,而回复是针对评论的(这种设计是根据QQ空间、新浪博客等平台的功能:你发了一个说说,好友可以对它发表评论,然后你又可以针对这个评论回复看法),但是在设计的时候不知道出了什么问题,回复竟然也是和博客有关的。当时应该是贪方便,没有设计得更完善。

所以啊,一开始数据库的设计很重要,不要以为看起来它很简单,就不认真设计,因为不合理的设计会导致后面网页开发的时候出现很大的困难。

JSP设计

数据库

数据库准备工作

写好了数据库代码之后,肯定要先在本地创建好数据库。在这里我用wampServer提供的mysql,然后用下面的指令导入:(要先创建Blog database)

mysql -u root -p blog < blog.sql

用Navicat查看数据库是否成功创建:

接着把mysql-connector-java-5.1.36-bin.jar文件拷贝到tomcat目录的lib子目录下,这样JSP才能引入连接数据库的库。

数据库数据类型引入

数据库里的实体集有用户、博客、评论和回复,为了之后方便存储数据,在JSP中也创建这几个类,然后定义相同的属性和方法。比如用户,有uid、name和signature等

// Test.jsp - User类
class User{public String nickname;public String password;public String signature;public String head;public User(String n, String p, String s, String h) {nickname = n;password = p;signature = s;head = h;}public User() {nickname = password = signature = head = "";}
}

注意:虽然这个JSP文件的User类没有定义uid,但是在展示博客的JSP页面的User类有uid。有没有uid其实是看页面的要求,可以灵活变通。

连接数据库

代码如下:

String connectString = "jdbc:mysql://localhost:3306/blog"+ "?autoReconnect=true&useUnicode=true&characterEncoding=UTF-8";
try {Class.forName("com.mysql.jdbc.Driver");conn = DriverManager.getConnection(connectString, "root", "");
} catch (Exception e) {try {out.print(e.getStackTrace());	}catch (Exception ee) {}
}

数据库操作(选择、插入、修改、删除)

四种操作中,最复杂的就是选择,因为后三种操作返回的就是一个整数,表示受影响的行数。而选择操作返回的是一个ResultSet,相当于一个Iterator,可以用遍历的方式获取里面的数据。
首先看看插入操作:

boolean insertUser(User user){try {String sql = String.format("insert into User(nickname, password, signature, head)"+ "values('%s', '%s', '%s', '%s');", user.nickname, user.password, user.signature, user.head);state = conn.createStatement();resultInt = state.executeUpdate(sql);}catch (Exception e) {return false;}return resultInt >= 1;
}

修改和删除操作不同之处就是指令。再看看选择操作,这里选择了最复杂的部分,获取所有的博客:

Blog[] getAllBlog() {List<Blog> list = new ArrayList<Blog>();try {String sql = "select * from Blog";state = conn.createStatement();resultSet = state.executeQuery(sql);while (resultSet.next()) {String bid = resultSet.getString("bid");String content = resultSet.getString("content");String btime = resultSet.getString("btime");list.add(new Blog(bid, content, btime));}}catch (Exception e) {}return (Blog[]) list.toArray(new Blog[list.size()]);
} 

关键在于通过resultSet获取每一行的数据的方法(getString(columnName))以及把 list 转化为数组的方法。

获取当前时间

博客、评论、回复都需要存储创建的时间。JSP(Java)用下面的方式获取:

String getCurrentTime() {SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//return df.format(new Date());String date = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(Calendar.getInstance().getTime());return date;
}

但是要注意:这种方法获取的时间在页面刷新之后才会更新,所以在获取发微博的时间的时候不能用这种方法,因为页面不用刷新。而应该用JavaScript代码获取时间。

其他部分

由于其他部分的代码比较多,我们就按照的博客的点开顺序来讲一下每一个JSP的关键点。但是在这之前再讲一个每一个JSP都要添加的一个东西:设置编码方式:

request.setCharacterEncoding("utf-8"); 
response.setContentType("text/html;charset=utf-8");

如果没有这两行的设置,浏览器在打开JSP的时候,不会打开一个网页,而会显示要下载JSP文件。

登录(login.jsp)

登录界面最重要的功能就是登录,首先输入账号和密码,然后按登录按钮,检查账号和密码是否正确,如果正确就跳转到另一个界面,否则依然回到登录界面。还有一些到修改密码界面、注册新用户的功能。

判断登录账号和密码是否正确

这里用到了POST方法来传输数据,依然发送到login.jsp,所以页面首先会刷新一下,再进行判断。判断的方法很简单:检查数据库里是否有相同的账号和密码。

<%// 如果登录失败,显示提示信息String name = request.getParameter("userId");String password = request.getParameter("passWord");NAME = name;boolean loginSuccess = false;if (name == null || password == null) {}else if (connect() && login(name, password)) {loginSuccess = true;}else {
%><br/><br/><font id="LoginFail" style=" font-size:20px; color:red; margin-left: 255px;">登录失败!</font>
<%}
%>
boolean login(String nickname, String password) {try {String sql = String.format("select * from User where nickname = '%s';", nickname);state = conn.createStatement();resultSet = state.executeQuery(sql);if (resultSet != null && resultSet.next()) {// 说明找到了用户if (password.equals(resultSet.getString("password"))) return true;else return false;}else return false;}catch (Exception e) {return false;}
}

补充:后来我觉得,登录失败的文字不应该直接在网站上显示,用显示对话框的形式可能会更好:

if (name == null || password == null) {}
else if (connect() && login(name, password)) {loginSuccess = true;
}
else {out.print("<script>alert('登录失败!');</script>");
}

可见通过JSP代码显示JavaScript很简单,用out.print("<script>alert('string')</script>");这种形式就可以了。

登录成功后的跳转

一开始我用上面的函数跳转网页:

public void jump3(HttpServletRequest request, HttpServletResponse response, String username) throws Exception{
response.setCharacterEncoding("utf-8");
response.setHeader("iso-8859-1","utf-8");
request.setCharacterEncoding("utf-8");String name = request.getParameter("name");String psd  = request.getParameter("psd");response.setHeader("Refresh","1;url=MyWB.jsp?user="+username);
}

但是这种方法比较麻烦,还有一种方法,就是用到上面通过out.print()展示JavaScript代码的方式。代码如下:

if (loginSuccess) {String urlUser = getUrlString(NAME);out.print("<script>window.location.href='MyWB.jsp?user="+urlUser+"'</script>");
}

不过这种方法要先对参数处理一下。如果参数中有空格,直接作为url传输是不行的,必须把空格替换成%20:

//获取用于URL传输的字符串
String getUrlString(String str) {String urlStr = "";for (int i = 0; i < str.length(); i++) {if (str.charAt(i) == ' '){urlStr += "%20";}else urlStr += String.valueOf(str.charAt(i));}return urlStr;
}

注册账号(register.jsp)

首先看看注册界面是怎样的:

所以注册界面主要的功能就是输入用户的信息(包括用户名、个性签名、密码和确认密码、确认条款)。不过这些信息的输入是有要求的:用户名不能和当前已有的重复、密码和确认密码必须一样、以及必须确认条款。所以,注册成功是一种情况,注册失败分几种情况,下面是判断注册情况的代码:

int registerSuccess = ALLNULL;
String name = request.getParameter("userID");
String signature = request.getParameter("userName");
String password = request.getParameter("userPass");
String rPassword = request.getParameter("userRpass");
String[] checkbox = request.getParameterValues("checkbox");
if (name == null || password == null || rPassword == null) {registerSuccess = ALLNULL;
}
else if (name == "" || password == "" || rPassword == "") {registerSuccess = SOMENULL;
}
else if (checkbox == null) {// 当这个为空的时候,说明没有同意协议registerSuccess = NOTAGREE;
}
else if (!password.equals(rPassword)) registerSuccess = PASSWORDDIFF;
else if (connect() && insertUser(new User(name, password, signature, ""))) {registerSuccess = SUCCESS;
}
else registerSuccess = FAIL;

为什么要有ALLNULL这种情况分析呢?因为注册界面是通过login.jsp跳转过来的,所以第一次跳转到注册界面的时候,通过string.getParameter()获取的变量都是null,所以ALLNULL代表的意思就是第一次进入注册界面。特别判断这种情况的目的是区分其他注册失败的情况,避免ALLNULL的时候也输出登录失败的结果。
SOMENULL的意思就是注册信息不完整,无法注册。
通过这两种情况的区分,我们可以知道通过POST传递的数据,如果是通过本网页跳转,而且没有输入,那么返回的结果就是空字符串(checkbox除外,接下来会讲)。如果是通过其他网页跳转过来的,url中没有这个参数,那么得到的就是null。
NOTAGREE就是没有确认条款的情况。注意:checkbox用POST方法传送的是一个字符串数组。如果没有勾选相同name的任何checkbox,返回的自字符串数组就为null,否则字符串里面的值就是checkbox的value属性值(不指明则为on)。
下面通过TestCheckbox.jsp测试:

<body>
<%
String[] checkbox = request.getParameterValues("checkbox");
if (checkbox != null) {out.print("<p>" + checkbox.length + "</p>");for (String str : checkbox) {out.print(str);}
}
else out.print("checkbox为空!");
%>
<form action="TestCheckbox.jsp">
<input name="checkbox" type="checkbox" id="checkbox1" value="呵呵呵"/> 这是checkbox1 <br />
<input name="checkbox" type="checkbox" id="checkbox2" value="哈哈哈"/> 这是checkbox2 <br />
<input value="点击提交" id="button" type="submit" />
</form>
</body>

最后是数据库的操作了,先判断当前的用户名是否在数据库中已经存在,如果没有,就插入User,否则返回false。

boolean insertUser(User user){try {// 首先要检查用户名是否已经被其他人注册过,如果是的话,不能注册String sql = String.format("select * from User where nickname = '%s';", user.nickname);state = conn.createStatement();resultSet = state.executeQuery(sql);if (resultSet.next()) {// 说明这个用户名注册过,返回falseisExist = true;return false;}isExist = false;sql = String.format("insert into User(nickname, password, signature, head) "+ "values('%s', '%s', '%s', '%s');", user.nickname, user.password, user.signature, user.head);//state = conn.createStatement();resultInt = state.executeUpdate(sql);}catch (Exception e) {return false;}return resultInt >= 1;
}

修改密码(findpassword.jsp -> 这个名字有点问题)

修改密码的逻辑比较简单,首先输入的当前密码要正确,其次,新密码和重复新密码要一致。不过解释了。

ref_username = request.getParameter("username");
if (ref_username != null) {// 第一次到这个jsp,到达ref_username获取passworduser = getUser(ref_username);// 如果user为空,说明用户不存在,则会跳回到login//out.print("<script>alert('呵呵呵');</script>");if (user == null) {out.print("<script>alert('用户不存在!');window.location.href='login.jsp';</script>");}else oldPass = user.password;
}
else {// 通过提交按钮到达,此时需要检查两个地方:一个是新密码和重复新密码是否相同,另一个是旧密码是否匹配String pass1 = request.getParameter("textfield1");String pass2 = request.getParameter("textfield2");String pass3 = request.getParameter("textfield3");if (pass1 == "") {out.print("<script>alert('请输入当前密码!')</script>");}else if (pass2 == "") {out.print("<script>alert('请输入新密码!')</script>");			}else if (!pass2.equals(pass3)) {out.print("<script>alert('新密码和重复新密码不一致!')</script>");}else if (!pass1.equals(oldPass)) {out.print("<script>alert('当前密码错误!')</script>");}else {// 现在可以更新了updatePass(user.nickname, pass2);out.print("<script>alert('修改密码成功!')</script>");}
}

查看自己的所有博客(MyWB.jsp)

主要就是for循环和<% %>之间的嵌套:

修改个人信息(account.jsp)

JavaScript

由于我对JavaScript的掌握还不够,所以设计基本是沿用模板,只是添加了返回时间(因为通过Java获取时间的话必须刷新网页,而发博客、发评论是不用刷新网页的)的代码,以及其他方面的处理。我就展示一下报告中的知识吧。

最后再说说innerHTML和outerHTML、innerText、value之间的区别:
innerHTML:对象从起始到终止位置的全部内容,包括HTML标签,不包括对象本身
outerHTML:innerHTML的内容加上对象本身
innerText:innerText去除HTML标签
value:表单元素一般没有innerHTML(除了select),用value取出值。另外textarea还可以用innerText

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

C# static关键字—— 对象引用对于非静态字段、方法或属性是必需的

原文链接:https://blog.csdn.net/Jeffxu_lib/article/details/96425138 在 C# 中,当主函数调用另一个非静态函数时总是提示: “ 对象引用对于非静态的字段、方法或属性是必需的 ” 一、错误分析 1、因为 f02() 是非静态函数;而主函数 Main 前有关键字 static ,其为静态函数…

管道传输

提交运行 ls | sort -r的结果,总结管道的功能 管道的功能总结: 数据流传输: 管道允许将一个命令的输出直接传输到另一个命令的输入,无需中间文件。 命令组合: 可以组合多个命令,实现复杂的数据处理流程。 效率提升: 由于数据在内存中直接传输,避免了磁盘 I/O,提高了处…

网站颜色在哪里修改图片,网站颜色和图片修改指南

修改网站的颜色和图片可以提升网站的视觉效果和用户体验。以下是详细的步骤:备份文件:使用FTP工具(如FileZilla)下载网站的所有文件。 确保备份文件的安全。编辑CSS文件:使用代码编辑器(如VS Code、Sublime Text)打开style.css文件。 根据需求修改颜色。例如,修改背景颜…

寻找教育团队协作神器!J 人备考有何优质软件可选?

在教育领域,无论是教育教培团队的日常运营,还是个人备考者的学习提升,高效的协作与管理工具都至关重要。对于注重计划和秩序的 J 人来说,可视化团队协作办公软件更是能契合其工作和学习风格,助力他们更好地达成目标。本文将为您盘点 6 款此类软件,包括国内的板栗看板以及…

Z-BlogPHP 中“主题模板的编译文件不存在”错误的原因是什么?

“主题模板的编译文件不存在”错误通常出现在 Z-BlogPHP 中,表示系统未能正确编译主题模板文件,导致无法正常显示网站内容。以下是常见的原因和解决方法:缓存文件未生成:缓存文件未生成或已损坏,导致系统无法找到编译后的模板文件。 解决方法:登录 Z-BlogPHP 后台管理界面…

如何在 Z-BlogPHP 中临时禁用所有插件以排除插件冲突?

在 Z-BlogPHP 中,如果遇到网站无法正常运行的问题,可能是由于某个插件引起的冲突。为了排除插件冲突,您可以临时禁用所有插件,然后逐步启用插件以确定问题所在。以下是具体的操作步骤:确定问题原因:首先,确认问题是否与插件有关。常见的插件冲突症状包括网站无法加载、后…

如何使用 Lambda 自动添加CloudWatch所有实例磁盘告警及 SNS 通知

利用Lambda轻松实现EC2实例监控 最近新增了一些服务器,因为每个服务器的基础监控都是要做的。我就想,如何能够快速便捷的方式把这些基础指标都监控上呢?本文将详细介绍如何通过Lambda自动为所有EC2实例添加CloudWatch磁盘告警,并在磁盘利用率超过阈值时,通过SNS主题发送通知…

实现hive的bitmap同步到doris

背景: 官方提供的方案不可行 doris提供的hive-udf中:https://doris.apache.org/zh-CN/docs/3.0/ecosystem/hive-bitmap-udf 官网方式如下: 需要使用doris外接hive的元数据地址:hive.metastore.uris 这里有个问题是,很多公司都会有数据安全和权限控制,这个接口一般不会外露…

一款可以完整保留排版的PDF翻译,GitHub增长第一

最近看论文较多,顺手给大家推荐一个用下来觉得不错的开源PDF翻译工具:PDFMathTranslate 目前这款开源项目在GitHub上已经收获了7.6K Star,而且由于一直处于增长趋势榜第一的位置,预计未来还会持续增长许多。 PDFMathTranslate 简介开源项目地址:https://github.com/Byaidu…

在 IIS 中发布网站,使用 PUT、DELETE 等请求方法时,提示错误:HTTP 错误 405.0 - Method Not Allowed

搜了一圈,发现是因为安装了 IIS 的 WebDAV 功能,就会导致站点出现此类问题 一种方法是移除 WebDAV 功能,但比较费时费力 另一种就是在站点的 Web.config 中显式移除 WebDAV 模块 配置文件: <configuration><system.webServer><modules><!-- 移除模块 …

如何用python批量转换.doc文件为.docx文件

需要用到的库: pywin32、os实现效果: 把文件夹下的文件1.doc、2.doc、3.doc 转化成1.docx、2.docx、3.docx,保存到output文件夹下。 代码运行前: 代码运行后: 实现代码:# 批量把".doc"文件另存在".docx"文件import osfrom win32com import clientde…