javaWeb实现聊天室(私聊+群聊)

article/2025/10/23 5:26:38

写在前面

近几天,迎来了第一个小项目,不做不知道,一做吓一跳。好多知识都掌握的不够扎实,看似会了,但其实似懂非懂,不能真正掌握原理,导致使用起来错误百出。而且深深体会到,知识只有到用时方恨少,一个简单的功能,各种受限做不出来。唉,还是好好学习吧,学习使我快乐!

知识储备

本次的目标是用javaWeb做一个聊天室,能实现简单的群聊+私聊以及查看在线人数、历史聊天等功能。
1、在做一切之前,我们首先了解一下四个范围。
按照范围的大小来排序的话:页面范围(PageContext)<请求范围(HttpServletRequest)<会话范围(HttpSession)<应用程序范围(ServletContext)。
a.页面范围:只在jsp当前页面范围内有效
b.请求范围:只要一次请求不断开即可
c.会话范围:其生命周期可理解为从浏览器打开到关闭(其实本质是会话到期了才会真正结束)
d.应用程序范围:其生命周期为从服务器打开到关闭
至于什么时候使用以上范围?
可以遵循以下原则:会话范围是私有范围,只有自己可以看到,当一个功能需要存储到一个范围,而又不想让所有人都看到(比如登录信息);而应用程序范围是公共的,所有人都可以通过key获取,当一个功能需要存储到一个范围,所有人必须都能看到这个范围内的内容的时候可以用它(比如群聊聊天记录)。
2、如何从PowerDesigner中导出表结构?
Database—>generateDatebase(选一个要导出的路径其他不变)—>点击确定。此时你已经获得了建表的sql语句,那么接下来只需要将sql语句复制下来放到Oracle新建的命令窗口中执行即可,到现在表已经建成。
如何去掉sql语句中的双引号?
Datebase—>EditCurrentDBMS—>Script—>Sql—>Format—>Case SensitivityUsingQuote—>将Yes改为No即可。

成果展示

1.首先看一下群聊:
群聊
2.再来看一下私聊(这里需要聊天双方互点对方名称的超链接):
私聊

项目总结

本次项目学到了很多知识点,下面我将一个个整理下来,希望对大家有所帮助。

知识点一:如何用触发器和序列实现主键自动生成?

create sequence 序列名 create or replace trigger 触发器名 before insert on表名 for each row 
begin:new.列名:=序列名.nextval;
end;

知识点二:如何获取多选框中选中的值?


//将注册表单中的爱好这一项存储到数据库中
Users u = new Users();
String hobby[]=request.getParameterValues("hobby");//注意这里获取到的是一个数组
System.out.println("");
String loves="";
PrintWriter out = response.getWriter();
for(int i=0;i<hobby.length;i++){loves=loves+hobby[i]+",";//各项之间用逗号隔开,以便后期使用撕裂方法
}
loves=loves.substring(0,loves.length()-1);//取除去最后一个逗号的字符串
u.setLoves(loves);
//从数据库中取出并展示某用户爱好
String loves="1,3";
String arr[] = loves.split(",");//以逗号为分割进行撕裂
for(int j=0;j<arr.length;j++){if(arr[j].equals("1")){out.println("运动");}else if(arr[j].equals("2")){out.println("聊天");}else if(arr[j].equals("3")){out.println("玩游戏");}
}

知识点三:如何存储群聊聊天记录内容?

        HttpSession session = request.getSession();ServletContext application = session.getServletContext();String message1 = request.getParameter("message");int userid = new Integer(session.getAttribute("userid").toString());List<String> list = (List<String>)application.getAttribute("list");//解决第一次问题if(list==null){list = new ArrayList<String>();}Date d = new Date();SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");String date = sdf.format(d);String username = session.getAttribute("username").toString();String message = username+":"+message1+"&nbsp"+date;Messages m= new Messages();m.setUserid(userid);m.setMcontent(message1);m.setMdate(date);MessagesDAO md = new MessagesDAO();int i= md.add(m);if(i==0){System.out.println("Messages表插入失败");}list.add(message);application.setAttribute("list", list);//因为群聊的消息记录所有人都有权查看所以用application范围response.sendRedirect("send.jsp");//方便第二次发送

知识点四:如何处理私聊的聊天记录展示?

//私聊存储到数据库的过程,以下发生在Servlet中
System.out.println("进入私聊");HttpSession session = request.getSession();ServletContext application = session.getServletContext();List<String> list2 = (List<String>)application.getAttribute("list2");if(list2==null){list2 = new ArrayList<String>();}String message1 = request.getParameter("message1");Date d = new Date();SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");String date = sdf.format(d);String username = session.getAttribute("username").toString();int senderid = new Integer(session.getAttribute("userid").toString());int accepterid = new Integer(session.getAttribute("userid1").toString());UserDAO ud = new UserDAO();String sendername = ud.findById(senderid).getUsername();//发送者姓名String acceptername = ud.findById(accepterid).getUsername();//接受者姓名session.setAttribute("sendername", sendername);session.setAttribute("acceptername", acceptername);String pmessage = sendername+"#对#"+acceptername+"#说:"+message1+" "+date;//#是私聊关键,用于撕裂list2.add(pmessage);application.setAttribute("list2", list2);PrivateMessage pm = new PrivateMessage();pm.setAccepterid(accepterid);pm.setSenderid(senderid);pm.setPmcontent(message1);pm.setPmdate(date);PrivateMessageDAO pmd = new PrivateMessageDAO();int i= pmd.add(pm);if(i==0){System.out.println("私聊插入失败");}response.sendRedirect("privatesend.jsp");
//从数据库中取出并展示出来的过程,以下发生在jsp中<%List<String> list2 = (List<String>)application.getAttribute("list2"); if(list2==null){return;}String sendername = session.getAttribute("username").toString();//获取发送者名称int accepterid = new Integer(session.getAttribute("userid1").toString());UserDAO ud = new UserDAO();String acceptername = ud.findById(accepterid).getUsername();//获取接收者名称for(int i=0;i<list2.size();i++){String[] s = list2.get(i).split("#");//按#进行撕裂//分两类进行讨论并展示。通过名称比对,从而来限制要展示的聊天内容,实现私聊。这是实现私聊的关键    if((s[0].equals(sendername)&&s[2].equals(acceptername))||(s[0].equals(acceptername)&&s[2].equals(sendername))){out.println(s[0]+s[1]+s[2]+s[3]+"<br />");}} %>

知识点五:如何限制用户不能重复登录?

public void doPost(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {int userid = new Integer(request.getParameter("userid"));String userpass = request.getParameter("password");HttpSession session = request.getSession();UserDAO ud = new UserDAO();Users u = ud.findById(userid); if(u!=null){if(u.getUserpass().equals(userpass)){ServletContext application = session.getServletContext();boolean iden = false;List<Users> list1 = (List<Users>)application.getAttribute("list1");//第一次问题  if(list1==null){list1 = new ArrayList<Users>();}for(int i =0;i<list1.size();i++){if(userid==list1.get(i).getUserid()){//判断是否重复登录iden = true;break;}}if(iden){response.sendRedirect("login.jsp");//如果已在线,则登录不上}else{list1.add(u);application.setAttribute("list1", list1);response.sendRedirect("main.jsp");//登陆成功以后进入聊天的主界面}}else{System.out.println("密码错误");response.sendRedirect("login.jsp");}}}

知识点六:如何解决下线在线人数减少以及名称消失的问题?

//在线人数展示问题
public class MyUtil {public static int count = 0;
}public class MyListener implements HttpSessionListener{//HttpSessionListener这是一个接口务必用implemenetspublic void sessionCreated(HttpSessionEvent arg0) {MyUtil.count = MyUtil.count+1;//创建对话就增加一个在线人数}public void sessionDestroyed(HttpSessionEvent arg0) {MyUtil.count = MyUtil.count-1;//销毁对话就减少一个在线人数}
}
//以下发生在online.jsp<%if(MyUtil.count>=0){ %>在线用户:<%=MyUtil.count%><br /><%}else{%>在线用户:0<br /><%}%><%List<Users> list1 = (List<Users>)application.getAttribute("list1");int myuserid1 = new Integer(session.getAttribute("userid").toString()); if(list1==null){return;}for(int i=0;i<list1.size();i++){if(myuserid1==list1.get(i).getUserid()){%><%=list1.get(i).getUsername() %><input type = "button" onclick="doClick()" value="下线"/> 上线了!<br /><%}else{%><a href = "doPrivateChat?userid=<%=list1.get(i).getUserid() %>" target = "_blank"><%=list1.get(i).getUsername() %></a> 上线了!<br /><%}}%>
//下线人数减少问题
public void doPost(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {HttpSession session = request.getSession();PrintWriter out = response.getWriter();ServletContext application = session.getServletContext();List<Users> list1 = (List<Users>)application.getAttribute("list1");String myname = session.getAttribute("username").toString();for(int i=0;i<list1.size();i++){if(list1.get(i).getUsername().equals(myname)){list1.remove(i);//将下线的人从列表中删除MyUtil.count= MyUtil.count-1;//在线人数数量减一break;}}response.sendRedirect("online.jsp");}

尾声

好了,这次就先总结到这,不得不说此次真是收获颇丰,也希望对各位崇尚编程的小伙伴们有所帮助,祝大家生活愉快,在这条道路上越走越远!

May God bless you!

点击下载源码


http://chatgpt.dhexx.cn/article/Mtkg8EKw.shtml

相关文章

java实现聊天室(GUI界面+私聊+群聊)

登录界面的用户名和端口号不能重复&#xff01; 登录界面的用户名和端口号不能重复&#xff01; 登录界面的用户名和端口号不能重复&#xff01; java的socket编写的聊天室&#xff0c;GUI的界面&#xff0c;可以私聊和群聊&#xff0c; 聊天信息保存为txt 有需要的可以自行下…

用Java代码实现一个简单的聊天室功能

一.客户端的创建 1.我们可以用Socket来创建客户端 /***类名 Client*描述 TODO 客户端 1*版本 1.0*创建人 XuKang*创建时间 2020/9/24 16:18**/ public class Client {public static void main(String[] args) throws UnknownHostException, IOException {System.out.println(…

Java在线聊天室(客户端+服务器)

Java在线聊天室&#xff08;客户端服务器&#xff09;基于webSocket实现模拟在线聊天系统 运行环境&#xff1a; JDK1.8version 开发环境&#xff1a;Eclipse 一、结构 以下是系统主要结构&#xff1a; 1.用户&#xff08;均实现部分可能会有bug&#xff09; &#xff08;…

apiDay09整理笔记(笔记优化)

目录 1.聊天室&#xff08;续&#xff09; &#xff08;1&#xff09;实现服务端发送消息给客户端 &#xff08;2&#xff09;服务端转发消息给所有客户端 &#xff08;3&#xff09;客户端解决收发消息的冲突问题 &#xff08;4&#xff09;服务端完成处理客户端断开连接…

JAVA简单聊天室的实现

目录 界面效果图 一、聊天室功能介绍&#xff1f; 二、功能代码 1.服务端 2.客户端 界面效果图 提示&#xff1a;以下是本篇文章正文内容&#xff0c;下面案例可供参考 一、聊天室功能介绍&#xff1f; 1. 、对于聊天室就是处理多个客户端发送的请求与信息&#xff0c;从…

Java网络聊天室---个人博客

Java网络聊天室 ———个人博客 一、项目简介 功能描述&#xff1a; 使用图形用户界面和socket通信&#xff0c;能实现一个聊天室中多人聊天&#xff0c;可以两人私聊&#xff0c;可以发送文件。 实现类似QQ用户注册、登录、聊天等功能。 参考git地址或博客地址&#xff1a…

Java实现ChatRoom

基于连接通信Socket、多线程的Java聊天室 1、开发环境&#xff1a; IDEA2018.1JDK1.8 2、实现功能&#xff1a; 实现了模拟登录注册、群聊、私聊、显示当前在线人数列表&#xff1b; 在发送信息时&#xff0c;会向对方发送者及显示发送时间&#xff1b; 显示在线人数列表…

Java聊天室

项目介绍&#xff1a; Java聊天室是期末设计&#xff0c; 阿里巴巴druidmysql多线程GUImvn项目java Socket 服务端模块&#xff1a;踢出聊天室&#xff1a;管理员可以踢出发言不当的用户。只有当开启服务端的时候&#xff0c;客户端才能起到作用。 客户端模块&#xff1a; 注册…

用Java实现简易聊天室

说明&#xff1a;如果一个 类&#xff0c;需要有界面的显示&#xff0c;那么该类就需要继承自JFrame&#xff0c;此时&#xff0c;该类就可以被称为一个“窗体类"。 服务端代码&#xff1a; package cn.qy.chat;import javax.swing.*; import java.awt.*; import java.aw…

微信小程序购物车功能实现(干货满满)

微信小程序定制好看的购物车页面&#xff0c;实现购物车功能&#xff0c;希望对您有所帮助&#xff01; 1. 应用场景 2. 思路分析 3. 代码分析 4. 具体实现代码 效果截图&#xff1a; 1.应用场景 适用于商城、秒杀、商品购买等类型的小程序&#xff0c;负责将顾客浏览的商…

微信小程序微商城(八):缓存实现商品购物车功能

IT实战联盟博客&#xff1a;http://blog.100boot.cn 上一篇&#xff1a;微信小程序微商城&#xff08;七&#xff09;&#xff1a;动态API实现商品分类 看效果 购物车.gif 开发计划 1、商品详情页将商品信息放入缓存 2、购物车页面读取缓存获取商品信息 3、购物车商品计算…

微信小程序开发一个小型商城(六、购物车页面)

上一篇文章&#xff1a;微信小程序开发一个小型商城&#xff08;五、商品详情&#xff09; 当我们在商品详情界面中点击添加购物后&#xff0c;会跳转到购物车界面&#xff0c;购物车界面是一个tabbar&#xff0c;在跳转的时候需要加上ope-type。看下购物车的静态页面把&#x…

微信小程序实现一个购物车页面的简易列表效果

本文只是简单的模仿天猫APP的购物车列表的样式效果&#xff0c;并实现了部分事件功能&#xff0c;功能并不完善&#xff0c;请降低期待观看。 天猫APP的购物车效果&#xff1a; 小程序模仿的实现效果&#xff1a; wxml部分的代码&#xff1a; <view wx:if"{{!isCartEmp…

【Python之pymysql库学习】一、分析fetchone()、fetchmany()、fetchall()(保姆级图文+实现代码)

目录 实现效果实现思路实现代码总结 欢迎关注 『Python之pymysql库学习』 系列&#xff0c;持续更新中 欢迎关注 『Python之pymysql库学习』 系列&#xff0c;持续更新中 实现效果 实现思路 其实有半数代码是创建数据库和创建数据表并插入数据这些环境配置部分我都写好了&…

fetchone、fetchall

fetchone(): 该方法获取下一个查询结果集。结果集是一个对象,读取一行结果&#xff0c;读取完指向下一行&#xff0c;到空为止 fetchall():接收全部的返回结果行&#xff0c;到空为止 fetchone() &#xff1a; 返回单个的元组&#xff0c;也就是一条记录(row)&#xff0c;如果没…

python fetchall方法_Python连接MySQL并使用fetchall()方法过滤特殊字符

python3.3从mysql里取出的数据莫名其妙有括号和逗号每天跟自己喜欢的人一起&#xff0c;通电话&#xff0c;旅行&#xff0c;重复一个承诺和梦想&#xff0c;听他第二十八次提起童年往事&#xff0c;每年的同一天和他庆祝生日&#xff0c;每年的情人节圣诞节除夕&#xff0c;也…

pdo fetchAll

作用 fetchAll()方法是获取结果集中的所有行.其返回值是一个包含结果集中所有数据的二维数组。 PDOStatement::fetchAll ([ int $fetch_style [, mixed $fetch_argument[, array$ctor_args array() ]]] ) fetch_style:控制结果的返回方式 PDO::FETCH_ASSOC 关联数组形式 PD…

记录一个常用函数fetchall()的使用过程

fetchall() 作用是返回多个元组&#xff0c;即对应数据库里的多条数据概念&#xff1b; 常见用法是 cursor.execute(‘select * from table’) value cursor.fetchall() 此时&#xff0c;print(value)则会输出以下二维元组&#xff0c;如下图 拓展&#xff1a; 同类函数fet…

Python从Oracle数据库中获取数据——fetchall(),fetchone(),fetchmany()函数功能分析

Python从Oracle数据库中获取数据——fetchall(),fetchone(),fetchmany()函数功能分析 一、fetchall()&#xff0c;fetchone()&#xff0c;fetchmany()简单介绍 1、fetchall()函数,它的返回值是多个元组,即返回多个行记录,如果没有结果,返回的是() 2、fetchone()函数,它的返回…

KITTI数据集可视化(一):点云多种视图的可视化实现

如有错误&#xff0c;恳请指出。 在本地上&#xff0c;可以安装一些软件&#xff0c;比如&#xff1a;Meshlab&#xff0c;CloudCompare等3D查看工具来对点云进行可视化。而这篇博客是将介绍一些代码工具将KITTI数据集进行可视化操作&#xff0c;包括点云鸟瞰图&#xff0c;FOV…