(手贱点了更新发布时间,发布时间变成6-9。。。)

  2017-5-20,在这个奇特的日子,我不再满足于在本地测试javaweb,于是在上腾讯云买了第一个云服务器,由于是学生认证,所以一个月只要10块钱,还是要抢的,每天早上9点开抢(腾讯云的学生优惠活动好像取消了,所以我又选择了阿里云)打开后,发现其实是一个云主机,就是远程主机,只不过他可以给你一个公网ID,就是在浏览器输入公网ID的话,全国所有人都可以访问你的项目

  关于怎么把自己的javaweb项目放到云主机,有一个教程http://www.cnblogs.com/diyunfei/p/6826557.html,前提是得先在云主机下载配置jkd,tomcat

  安装eclipse后先安装servers,在help中的安装软件,输入http://download.eclipse.org/releases/kepler,选择Web,XML, java EE and OSGi Enterprise Development

  配置jdk

    新建 JAVA_HOME 变量 。

    变量值填写jdk的安装目录

 

    寻找 Path 变量

    在变量值最后输入 %JAVA_HOME%\bin;%JAVA_HOME%\jre\bin;

    (注意原来Path的变量值末尾有没有;号,如果没有,先输入;号再输入上面的代码)

    新建 CLASSPATH 变量

     .;%JAVA_HOME%\lib;%JAVA_HOME%\lib\tools.jar(注意最前面有一点)

    检验是否配置成功 运行cmd 输入 java -version (java 和 -version 之间有空格)

    若如图所示 显示版本信息 则说明安装和配置成功。

  配置tomcat

    新建CATALINA_HOME,变量值是tomcat的安装路径

    找到PATH,在最后增加tomcat的bin文件的绝对路径(我的就是F:\eclipse\apache-tomcat-7.0.77\bin)

    配置后可以在浏览器输入localhost:8080,试试看可以可以访问tomcat的主页,如果可以即为配置成功

  

  云主机全部准备好了之后,可以把在本机的eclipse中的maven项目导出成一个war包,复制这个war包到云主机,放到tomcat的webapp的目录下,打开tomcat/bin里的start.bat,然后就可以在别的电脑通过“公网ID:端口号/项目名/”的方式访问该项目

----------------------------------------------------------------------------------------------------------------------------------

 下面开始说我这个项目,是跟我室友合作的,前端页面是他做的,这个是一个多人即时聊天室,在此之前没有接触过怎么实现即时聊天,走了很多弯路,不过幸好可以说是摸出点门道。

一、实现效果如下:

1、先进入登录界面,输入呢称和选择头像后进入

2、进入后的界面是这样的:

3、然后就可以输入聊天内容了

二、主要逻辑代码

因为我现在只会后端,就不把前端的代码贴出来了,主要逻辑是建立在servlet和ajax通信之上

1、我使用maven来构建这个项目,不过我这里并没有用maven来导入包,因为就几个包,我就手动导入项目结构如下

2、Control类用来接收用户名,头像id,聊天内容,然后生成一个系统当前时间,把这4个当成参数传给Model,这里先说一下为什么要生成一个系统当前时间,这就说到我遇到的另一个问题了,本来我们是商量说让前台把用户名,头像id,聊天内容,用户当前时间也传过来,但是发现效果并不好,因为如果涉及到多人同时聊天,各个客户端的当前时间不一定会一样,会造成一些请求得不到正确的响应,然后就想了个办法,客户端在发送聊天记录这条请求时,只发送用户名,头像id,聊天内容,然后由服务器生成时间作为响应返回,然后把4个属性传给Model

 1 public class Control extends HttpServlet {
2
3 @Override
4 protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
5
6 doGet(req, resp);
7 }
8
9 @Override
10 protected void doGet(HttpServletRequest req, HttpServletResponse resp)
11 throws ServletException, IOException {
12
13 // 接受聊天记录不发送东西:1
14 req.setCharacterEncoding("utf-8");
15
16 String username = req.getParameter("username");// 用户名
17 String content = req.getParameter("content");// 内容
18 String pic = req.getParameter("picture");
19 SimpleDateFormat df = new SimpleDateFormat("HH:mm:ss");// 设置日期格式
20
21 String time = df.format(new Date());
22
23 String callbackName = req.getParameter("jsoncallback");// 时间
24 // -------------------------------------------------------------------------
25
26 try {
27 new Model();
28 Model.write(username, content, time, pic);
29 } catch (ClassNotFoundException e) {
30 e.printStackTrace();
31 }
32 String success = "success";
33 String result = "{\"success\":\"" + success + "\",\"time\":\"" + time + "\"}";
34
35 String renderStr = callbackName + "(" + result + ")";
36 resp.setContentType("text/plain;charset=UTF-8");
37 resp.getWriter().write(renderStr);
38 }
39
40 }

这里的success只是为了给前台做判断。。里面的time也是前台用来给聊天内容打时间标签用的,json数据是动态拼接的,然后以callbackname作为函数名,直接返回一个字符串

2、Model类是做数据处理的,就是把4个属性存到keyvaluepair对象中,然后在把对象存到Arraylist中,Model里有3个方法:

(1)fileinit()方法是初始化一个流,打开txt文件的开口,(其实这里我本来是想用mybatis,但是时间仓促我就说先存在txt里凑合吧,以后找时间改一下)

(2)write()是把4个属性追加到文件尾,这里遇到的问题是,写到文件里的中文变成了乱码,所以我就把他处理了一下URLDecoder.decode(username, "UTF-8");

(3)getContent()方法是用来提取数据用的,用的key就是时间

  1 public class Model {
2 public static BasicDataSource ds = null;
3
4 public final static String JDBC_DRIVER = "com.mysql.jdbc.Driver";
5 public final static String USER_NAME = "root";
6 public final static String PASSWORD = "123456";
7 public final static String DB_URL = "jdbc:mysql://localhost/shen_db?useUnicode=true&characterEncoding=utf-8&useSSL=false";
8
9 public static FileWriter writer = null;
10 public static OutputStreamWriter osw = null;
11 public static FileOutputStream fos = null;
12 static List<KeyValuePair> list = new ArrayList<KeyValuePair>();// 创建一个arraylist,把键值对象保存在其中
13
14 public Model() {
15 fileInit();
16 }
17
18 // public static void dbcpInit() {
19 // ds = new BasicDataSource();
20 // ds.setUrl(DB_URL);
21 // ds.setDriverClassName(JDBC_DRIVER);
22 // ds.setUsername(USER_NAME);
23 // ds.setPassword(PASSWORD);
24 //
25 // }
26 public static void fileInit() {
27 String fileName = "C:\\a.txt";
28 try {
29 fos = new FileOutputStream(fileName, true);
30 } catch (FileNotFoundException e1) {
31 e1.printStackTrace();
32 }
33 try {
34 osw = new OutputStreamWriter(fos, "UTF-8");
35 } catch (UnsupportedEncodingException e1) {
36 e1.printStackTrace();
37 }
38 }
39
40 public static void write(String username, String content, String time, String pic)
41 throws ClassNotFoundException {
42 // Connection connection = null;
43 // PreparedStatement preparedStatement = null;
44 String x = null;
45 String y = null;
46 try {
47 x = URLDecoder.decode(username, "UTF-8");
48 y = URLDecoder.decode(content, "UTF-8");
49 } catch (UnsupportedEncodingException e1) {
50 e1.printStackTrace();
51 }
52 String z = time;
53 String p = pic;
54 System.out.println("发送东西来的内容:" + y); 57
58 list.add(new KeyValuePair(z, x, y, p));
59 try {
60 osw.write(KeyValuePair.getKey());
61 osw.write("---");
62 osw.write(KeyValuePair.getPic(z));
63 osw.write("---");
64 osw.write(KeyValuePair.getName(z));
65 osw.write("---");
66 osw.write(KeyValuePair.getContent(z));
67 osw.write("\r\n");
68 } catch (IOException e) {
69 e.printStackTrace();
70 } finally {
71 try {
72 if (osw != null) {
73 osw.close();
74 }
75 } catch (IOException e) {
76 e.printStackTrace();
77 }
78 }
79
80 // try {
81 // connection = ds.getConnection();
82 // preparedStatement = connection.prepareStatement("insert into Chatlog
83 // (time,logs) values (?,?)");
84 // preparedStatement.setString(1, currentTime);
85 // preparedStatement.setString(2, x);
86 // } catch (SQLException e) {
87 //
88 // e.printStackTrace();
89 // }
90
91 }
92
93 public static KeyValuePair getContent(String time) {
94
95 String time1 = time;
96 KeyValuePair kvp = null;
97 if (list.isEmpty()) {
98 } else {
99 for (KeyValuePair ss : list) {
100 if (time1.equals(ss.getKey())) {
101 kvp = ss;
102 } else {
103 kvp = null;
104 }
105 }
106 }
107 return kvp;
108 }
109
110 public static void main(String[] args) {
111
112 new Model();
113 }
114
115 }

3、GetCurrentTime这个类就是用来返回当前时间的

public class GetCurrentTime extends HttpServlet {

    @Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doPost(req, resp);
} @Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String callbackName = req.getParameter("jsoncallback");
System.out.println("get current time");
String time = null;
SimpleDateFormat df = new SimpleDateFormat("HH:mm:ss");
time=df.format(new Date());
String result=null;
result="{\"time\":\""+time+"\"}";
String renderStr = callbackName + "(" + result + ")";
resp.setContentType("text/plain;charset=UTF-8");
resp.getWriter().write(renderStr); } }

4、SendServlet这个类是用来提取聊天数据的,前台在GetCurrentTime那个servlet中接收到我的系统时间后,把这个系统时间当成一个参数然后发送一个请求到SendServlet,然后我就去调用Model的getcontent(),返回一个keyvaluepair对象,

利用这个对象调出所有数据,可以看到json数据都是动态拼接的方法做成的,甚是拙劣

 1 public class SendServlet extends HttpServlet {
2
3 @Override
4 protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
5 doPost(req, resp);
6 }
7
8 @Override
9 protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
10
11
12 String time = req.getParameter("time");
13 System.out.println("时间"+time);
14 KeyValuePair kvp = null;
15 String result = "{\"content\":\"" + null + "\",\"time\":\"" + null + "\",\"name\":\"" + null
16 + "\",\"picture\":\"" + null + "\"}";
17 String callbackName4 = req.getParameter("jsoncallback");
18
19 try {
20 kvp = Model.getContent(time);
21 System.out.println(kvp);
22 if (kvp != null) {
23 result = "{\"content\":\"" + kvp.getContent(time) + "\",\"time\":\"" + kvp.getKey() + "\",\"name\":\""
24 + kvp.getName(time) + "\",\"picture\":\""+kvp.getPic(time) +"\"}";
25 }
26 kvp = null;
27 String renderStr = callbackName4 + "(" + result + ")";
28 resp.setContentType("text/plain;charset=UTF-8");
29 resp.getWriter().write(renderStr);
30
31 } catch (IOException e) {
32 e.printStackTrace();
33 }
34 }
35
36 }

5、keyvaluepair对象时用来保存那4个属性的bean,就一个构造函数和4个get方法

public class KeyValuePair {

    public static String Key;
public static String Name;
public static String Content;
public static String Pic; public KeyValuePair(String k, String n,String c,String p) {
Key = k;
Name = n;
Content =c;
Pic=p;
} public static String getName(String k){
return Name;
}
public static String getPic(String k){
return Pic;
}
public static String getKey(){
return Key;
}
public static String getContent(String k){
return Content;
} public static void main(String[] args) { }
}

三、还存在的问题

1、当用户输入很快的时候有时候会丢失聊天数据

2、里面没有把聊天数据保存到数据库,而是单纯保存在Arraylist中和txt中,一旦宕机重启,后果很严重。。。关于mysql数据库,以前用的都是解压版,在windowserver2012好像不能用,反正我试了好多次都不行,到最后迫不得已下载了安装版,才把mysql搞定。(虽然我里面没用到数据库。。。==)安装版数据库教程

3、servlet怎么跟ajax异域通讯,那时候还没有学spring,所以纠结了很久,查了资料到最后发现是通过一个很不“优雅”的方式进行通信的,就是强行拼接一个json数据类型,不知道还有没有更好的方法

4、不能查看聊天记录

5、在学习sockets中。。

基于servlet和ajax的聊天室的更多相关文章

  1. Ajax实现聊天室

    Ajax实现聊天室 运行效果如下: 代码显示: var net=new Object();//编写构造函数net.AjaxRequest=function(url,onload,onerror,met ...

  2. 基于Server-Sent Event的简单聊天室 Web 2.0时代,即时通信已经成为必不可少的网站功能,那实现Web即时通信的机制有哪些呢?在这门项目课中我们将一一介绍。最后我们将会实现一个基于Server-Sent Event和Flask简单的在线聊天室。

    基于Server-Sent Event的简单聊天室 Web 2.0时代,即时通信已经成为必不可少的网站功能,那实现Web即时通信的机制有哪些呢?在这门项目课中我们将一一介绍.最后我们将会实现一个基于S ...

  3. 基于LINUX的多功能聊天室

    原文:基于LINUX的多功能聊天室 基于LINUX的多功能聊天室 其实这个项目在我电脑已经躺了多时,最初写完项目规划后,我就认认真真地去实现了它,后来拿着这个项目区参加了面试,同样面试官也拿这个项目来 ...

  4. 基于 OpenResty 实现一个 WS 聊天室

    基于 OpenResty 实现一个 WS 聊天室 WebSocket WebSocket 协议分析 WebSocket 协议解决了浏览器和服务器之间的全双工通信问题.在WebSocket出现之前,浏览 ...

  5. 基于EPOLL模型的局域网聊天室和Echo服务器

    一.EPOLL的优点 在Linux中,select/poll/epoll是I/O多路复用的三种方式,epoll是Linux系统上独有的高效率I/O多路复用方式,区别于select/poll.先说sel ...

  6. 基于Linux的TCP网络聊天室

    1.实验项目名称:基于Linux的TCP网络聊天室 2.实验目的:通过TCP完成多用户群聊和私聊功能. 3.实验过程: 通过socket建立用户连接并传送用户输入的信息,分别来写客户端和服务器端,利用 ...

  7. 《基于Node.js实现简易聊天室系列之详细设计》

    一个完整的项目基本分为三个部分:前端.后台和数据库.依照软件工程的理论知识,应该依次按照以下几个步骤:需求分析.概要设计.详细设计.编码.测试等.由于缺乏相关知识的储备,导致这个Demo系列的文章层次 ...

  8. JAVA基础知识之网络编程——-基于TCP通信的简单聊天室

    下面将基于TCP协议用JAVA写一个非常简单的聊天室程序, 聊天室具有以下功能, 在服务器端,可以接受客户端注册(用户名),可以显示注册成功的账户 在客户端,可以注册一个账号,并用这个账号发送信息 发 ...

  9. 通信——基于Xmpp协议实现的聊天室

    前段时间写了个自定义通信协议的聊天室(即用\r\n标记字符串,作为一句话),总感觉自己弄的那个协议实现虽然简单,但是拓展性就太差了,只适合于发送聊天的内容,难以包含更多的信息.基于上述几点,于是就开始 ...

随机推荐

  1. 消息队列NetMQ 原理分析3-命令产生/处理和回收线程

    消息队列NetMQ 原理分析3-命令产生/处理和回收线程 前言 介绍 目的 命令 命令结构 命令产生 命令处理 创建Socket(SocketBase) 创建连接 创建绑定 回收线程 释放Socket ...

  2. Java中四种遍历List的方法

    package com.ietree.basic.collection.loop; import java.util.ArrayList; import java.util.Iterator; imp ...

  3. git学习笔记之一

    Git是比较优秀的分布式版本管理工具,这次学习了git的基本命令,现在作一些归纳总结,已备复习之用. Git 认识 Git 直接用hash值记录提交的修改文件的快照,本地操作无需联网 Git 有三种状 ...

  4. 并发容器之CopyOnWriteArrayList(转载)

    Copy-On-Write简称COW,是一种用于程序设计中的优化策略.其基本思路是,从一开始大家都在共享同一个内容,当某个人想要修改这 个内容的时候,才会真正把内容Copy出去形成一个新的内容然后再改 ...

  5. 深入Java集合学习系列:Hashtable的实现原理

    第1部分 Hashtable介绍 和HashMap一样,Hashtable也是一个散列表,它存储的内容是键值对(key-value)映射.Hashtable继承于Dictionary,实现了Map.C ...

  6. iOS 关于UITableView的黑科技

      UITableView是我们最常用的控件了,今天我就来介绍一些关于UITableView的黑科技和一些注意的地方. 1.修改左滑删除按钮的高度   左滑删除这是iOS最先发明的,之后安卓开始模仿. ...

  7. centos修改无法用用户名和密码登录

    vi /etc/ssh/sshd_configPermitRootLogin这行改为PermitRootLogin yesPasswordAuthentication no上面的no改为yesUseP ...

  8. 如何用C#寻找100到999的所有水仙花数?

    首先解释一下何为水仙花数:水仙花数只是自幂数的一种,严格来说是三位数的个位.十位.百位的3次幂数相加等于原来的数字,称为水仙花数.(例如:1^3 + 5^3+ 3^3 = 153) 那么如何通过C#语 ...

  9. Go - Struct

    定义 go 语言中的struct与c的很相似,此外,go没有Class,也没有继承. stuct的格式为:type <name> struct{} package main import ...

  10. XCode 出现 is missing from working copy文件一直红色情况解决方法

    解决方案:1.打开终端2.cd 到警告所提示的文件夹下3.执行命令svn rm 丢失文件的名称4.回车