`
come_for_dream
  • 浏览: 116607 次
  • 性别: Icon_minigender_1
  • 来自: 长沙
社区版块
存档分类
最新评论

Android使用Java Web服务器作为中转实现即时通信

阅读更多

               Android使用Java Web服务器作为中转实现即时通信

 

       白白浪费掉的今天,是我们向往的明天,是我们悔恨的昨天。~~~~~~~~~~与汝共勉

 

         我相信一个人的时间按天计算和按秒计算其效果的差别是巨大的,我们应该相信上帝赋予我们足够的时间来让我们变得睿智,成熟。但是我们的时间又是不够的,因为我们要做的事好多好多。但是有时候又不知道自己该干什么,我能为别人带来什么,或者我又可以收获什么。自己或许还并不是一个程序员,但是我并不想把编程只看做Code,我在做的是Program。我希望我可以去做很伟大的事情,但是有时候又很害怕。其实那又有什么呢,尝试是一件多么令人心动的事啊。

       我感觉我不能说的太多了,要不然会滔滔不绝偏离主题的。最近一个人没事在搞一个聊天的模块,因为想要这个模块真正的变得有价值,加上我们这些学习爱好者并没有服务器的原因,云服务器并不提供我们编写Socket程序所需要的端口,于是我的这个模块就显得很长有意义了。这个模块其实很简单,只不过由于本人能力有限,还是中间出了点差错,错误调试了好久才得以实现,不过还好我这人挺豁达的。不跟程序较劲,所以后来还是慢慢的完成了这个模块成功交差。

 

 

       这个实现的思想就是:

        发送消息时:客户端发一个http请求,将用户名加上接收方的名字和发送的消息放在座位请求参数发送给服务器。这个功能实现起来较为简单。

        接受消息:这个过程实现起来相对会比较麻烦一点点,但是也没几行代码就可以解决了。

思想就是客户端每隔一段时间就去访问一下服务器,想服务器问问有没有我的消息,有的话就把消息带回去。

 

      首先贴下java web服务器端的代码:

 

public class CoreServlet extends HttpServlet {

	Map<String, String> mapMessage = new HashMap<String, String>();
	private PrintWriter out;

	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		response.setContentType("text/html");
		request.setCharacterEncoding("UTF-8");

		// 取得请求者名称
		String strReqName = request.getParameter("name");
		// 取得请求者状态
		String strState = request.getParameter("state");

		// 如果状态是登录
		if (strState.equals("load")) {
			String strRep = "load success";
			System.out.println(strReqName + "登录");
			// 向客户端回应登录成功
			out = response.getWriter();
			out.write(strRep);
		}
		// 如果状态是发送
		else if (strState.equals("sendMsg")) {
			// 取得发送至的名字
			String strSendToName = request.getParameter("toName");
			// 得到信息
			String strMsg = request.getParameter("Msg");
			// 回应请求客户端信息
			String strSendMsg = strReqName + "    send   to    "
					+ strSendToName + "     message:   \n" + strMsg;
			System.out.println(strSendMsg);
			// 将信息和发送至的名字和相对应的信息放在Map表中
			mapMessage.put(strSendToName, strSendMsg);
		}
		// 如果状态是获得信息
		else if (strState.equals("getMsg")) {
			out = response.getWriter();
			// 送map中取得信息
			String strMessage = mapMessage.get(strReqName);

			System.out.println(strReqName + "------>" + strMessage);
			// 判断信息是否存在
			if (strMessage != null && !strMessage.equals("")) {
				// 存在则将信息发给请求客户端
				out.write(strMessage);
				out.flush();
				System.out.println("移除消息");
				// 将消息从消息队列中移除,防止消息返回发送
				mapMessage.put(strReqName, "");
			}

		}

	}
}
 

 

 再看我们的客户端,也就是Android端的程序的代码:

 

  这是一个登陆界面,用来实现用户登录过程。
 

 

 

package com.example.tttt;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;

import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;

public class MainActivity extends Activity {

	private EditText editNameText;
	private EditText pwdEditText;
	private EditText sendToEditText;
	private Button loginButton;
        //服务器的ip和端口号
	protected String serverIP = "192.168.0.115:8080";

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);

		editNameText = (EditText) findViewById(R.id.edit_name);
		pwdEditText = (EditText) findViewById(R.id.edit_password);
		sendToEditText = (EditText) findViewById(R.id.edit_toname);
		loginButton = (Button) findViewById(R.id.button_login);

		loginButton.setOnClickListener(new OnClickListener() {

			@Override
			public void onClick(View v) {
				/*
				 * requestUrl---->请求地址
				 * 
				 * @name用户名为tlh
				 * 
				 * @ state状态为load
				 */
				String requestUrl = "http://" + serverIP
						+ "/AppWebConnect/CoreServlet?name=userName&state=load";

				// 得到输入框中的内容
				// 用户名
				String strName = editNameText.getText().toString();
				// 密码
				String strPassWord = pwdEditText.getText().toString();
				// 信息接收方的名称
				String strSendTo = sendToEditText.getText().toString();

				// 检查内容是否为空
				if (check(strName) && check(strPassWord) && check(strSendTo)) {
					// 将用户名替换成自己的名称---->strName
					requestUrl = requestUrl.replace("userName", strName);
					// 向服务器发送请求并得到服务器端的回应信息
					String strMessage = ConnectToServer(requestUrl);
					Toast.makeText(MainActivity.this, "--->" + strMessage,
							Toast.LENGTH_SHORT).show();
					if (check(strMessage)) {
						// 跳转聊天界面
						Intent intent = new Intent(MainActivity.this,
								ChatActivity.class);
						intent.putExtra("name", strName);
						intent.putExtra("sendTo", strSendTo);
						startActivity(intent);
					}

				} else {
					Toast.makeText(MainActivity.this, "用户名或密码不能为空", 2000)
							.show();
				}

			}
		});

	}

	public String ConnectToServer(String requestUrl) {
		String strMessage = "";
		try {
			HttpClient httpclient = new DefaultHttpClient();
			// 创建Get方法实例
			HttpGet httpgets = new HttpGet(requestUrl);
			HttpResponse response = httpclient.execute(httpgets);
			HttpEntity entity = response.getEntity();
			if (entity != null) {
				InputStream instreams = entity.getContent();
				String str = convertStreamToString(instreams);
				if (str == null || str.equals("")) {
					Log.i("tag", "无应答");
				}
				System.out.println(str);
				strMessage = str;
				// Do not need the rest
				httpgets.abort();
			}
		} catch (Exception e) {
			Log.i("tag", "" + e);
		}

		return strMessage;

	}

	public String convertStreamToString(InputStream is) {
		BufferedReader reader = new BufferedReader(new InputStreamReader(is));
		StringBuilder sb = new StringBuilder();

		String line = null;
		try {
			while ((line = reader.readLine()) != null) {
				sb.append(line + "\n");
			}
		} catch (IOException e) {
			e.printStackTrace();
		} finally {
			try {
				is.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}

		return sb.toString();
	}

	public boolean check(String strCheck) {
		if (strCheck == null || strCheck.equals("")) {
			return false;
		}
		return true;
	}
}

 

 

 

下面是一个类用来实现聊天功能:

 

 

 

 

 

 下面的这个类是实现消息的发送和接受的功能的

 

package com.example.tttt;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;

import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

public class ChatActivity extends Activity {

	private TextView textView;
	private EditText editText;
	private Button button;
	// 要发送的信息
	String strMessage;
	// 用户名
	String strUserName;
	// 接受者姓名
	String strToName;

	// 出于Android线程界面安全,用来处理接受到信息后使textView将消息呈现出来
	private Handler handler;
	// 接受到的信息
	private String strResult;
	// 服务器的地址
	protected String serverIp = "192.168.0.115:8080";

	@SuppressWarnings("static-access")
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.talk);

		// 对界面进行初始化
		initUI();
		// 对数据进行初始化
		initData();
		// 开始监听其他用户发来的消息
		startMessageReciver();

		// 设置按钮的监听器
		button.setOnClickListener(new OnClickListener() {
			String requestUrl;

			@SuppressLint("ShowToast")
			@Override
			public void onClick(View v) {
				// 获得信息
				strMessage = editText.getText().toString();
				editText.setText("");
				// 设置请求地址和参数
				requestUrl = "http://" + serverIp
						+ "/AppWebConnect/CoreServlet?name=" + strUserName
						+ "&state=sendMsg&Msg=" + strMessage + "&toName="
						+ strToName + "";

				Log.i("tag", "strMessage--->" + requestUrl);
				Log.i("tag", "URL--->" + strMessage);
				if (strMessage.equals("") || strMessage == null) {
					Toast.makeText(getApplicationContext(), "发送内容不能为空!!", 2000)
							.show();
				} else {

					textView.append("向" + strToName + "发送消息----->" + strMessage
							+ "\n");

					// 请求服务器
					String strResult = ConnectToServer(requestUrl);

					Toast.makeText(ChatActivity.this, "------->" + strResult,
							2000).show();

				}

			}
		});

	}

	/**
	 * 对数据进行初始化,并设置回调
	 */
	private void initData() {
		Intent intent = getIntent();
		strUserName = intent.getStringExtra("name");
		strToName = intent.getStringExtra("sendTo");

		handler = new Handler() {
			@Override
			public void handleMessage(Message msg) {
				super.handleMessage(msg);

				if (msg.what == 1) {
					Log.i("tag", "执行回调方法!!");
					textView.append(strResult + "\n");
				}
			}
		};
	}

	/**
	 * 对界面进行初始化
	 */
	private void initUI() {
		textView = (TextView) findViewById(R.id.tv_display);
		editText = (EditText) findViewById(R.id.edit_message);
		button = (Button) findViewById(R.id.btn_send);

	}

	/**
	 * 开始监听服务器发来的消息
	 */
	private void startMessageReciver() {
		new Thread() {
			String requestUrl = "http://" + serverIp
					+ "/AppWebConnect/CoreServlet?name=" + strUserName
					+ "&state=getMsg";
			HttpClient httpclient = new DefaultHttpClient();

			public void run() {
				// 创建Get方法实例
				HttpGet httpgets = new HttpGet(requestUrl);
				HttpResponse response = null;
				// 设置循环,使程序不停的访问服务器
				for (;;) {
					try {
						response = httpclient.execute(httpgets);

						HttpEntity entity = response.getEntity();
						if (entity != null) {
							InputStream instreams = entity.getContent();
							String str = convertStreamToString(instreams);

							// 如果接收到服务器发来的消息(即有好友发来消息)
							if (str != null && !str.equals("")) {
								System.out.println(str);
								strResult = str;
								Log.i("tag", "" + strResult);

								//回调,将好友发来的消息呈现在TextView上
								handler.sendEmptyMessage(1);

							} else {
								Log.i("tag", "无 应 答");

							}
						}

						//设置每两秒访问一次
						Thread.sleep(2000);

					} catch (Exception e) {

						e.printStackTrace();
					}

				}
			};
		}.start();
	}

	
	/**
	 * 连接服务器
	 * @param requestUrl 请求参数
	 * @return 返回服务器发来的消息
	 */
	public String ConnectToServer(String requestUrl) {
		String strMessage = "";
		HttpClient httpClient = new DefaultHttpClient();
		try {

			// 创建Get方法实例
			HttpGet httpgets = new HttpGet(requestUrl);
			HttpResponse response = httpClient.execute(httpgets);
			HttpEntity entity = response.getEntity();
			if (entity != null) {
				InputStream instreams = entity.getContent();
				String str = convertStreamToString(instreams);
				if (str == null || str.equals("")) {
					Log.i("tag", "无应答");
				} else {
					System.out.println(str);
					strMessage = str;
					Log.i("tag", "*******" + strMessage);
				}

				httpgets.abort();
			}
		} catch (Exception e) {
			Log.i("tag", "" + e);
		}

		return strMessage;

	}

	/**
	 * 将字节流转换为字符串
	 * @param is 输入流
	 * @return 转换后的字符窜
	 */
	public String convertStreamToString(InputStream is) {
		BufferedReader reader = new BufferedReader(new InputStreamReader(is));
		StringBuilder sb = new StringBuilder();

		String line = null;
		try {
			while ((line = reader.readLine()) != null) {
				sb.append(line + "\n");
			}
		} catch (IOException e) {
			e.printStackTrace();
		} finally {
			try {
				is.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
		return sb.toString();
	}
}

 

其实现在看看这个功能的实现,是非常简单的但是在我编写他们的时候由于马虎大意反了很多的错误,这里也感谢强哥和胡哥对我指导和鼓励。

 

 

  • 大小: 10.2 KB
  • 大小: 4.5 KB
分享到:
评论

相关推荐

    WebSocket.rar Android java-webSocket完整案例源码,推送,即时通信,双向通信,心跳重连

    java-webSocket是免费的,集成java-webSocket开源而成的一个比较完整的demo,实现了客户端向服务端发送消息,以及接收...适用于需要双方相互主动互发消息,推送,以及客户端与客户端通信(此时服务器只做中转)等场景。

    java实现打印机通信源码(awt)

    java实现与打印机通信具体包括内容有: 1.实现打印输入文本预览打印显示 2.实现选择文件显示 3.配置打印服务器

    使用java实现的linux和ftp服务器文件上传下载工具

    这是我使用java实现的linux和ftp服务器文件上传下载工具,需要电脑安装jdk8, 启动命令,java -jar linuxAndFtp.jar 启动成功后,浏览器访问:http://localhost:9999 服务器的账号密码通过服务器列表页面管理,添加的...

    用java写的mqttbroker,实现mqtt中转通信,与mosquitto一样的功能

    用java写的mqttbroker,实现mqtt中转通信,与mosquitto一样的功能 代码简洁明了,可以多次开发,方便部署至各种服务器 包非常小,仅仅3.24MB

    Android即时通讯 socket.zip

     要用android实现点对点通信,可以使用socket完成,使用socket需要知道对方的IP地址以及端口号,这里我省略了服务器端(编写正规的通信软件还是得需要服务器做中转,用服务器得知A的IP地址,然后让A做服务器端,B用A的Ip...

    java中转数据(服务端代码)

    运行在中转服务器上面。采用了Nutty框架,实现了数据中转,客户端发送数据给中转服务器后,数据会转发给另外一台服务器上面。只需修改ip及端口即可。

    中转服务器,SSL中转线路搭建

    中转服务器,SSL中转线路搭建

    基于Android调用OpenAI接口的ChatGPT实例

    ✓ 无需代理即可与ChatGPT对话(可以使用自己的服务器中转) ✓ 支持带记忆的连续对话,可以随时清除记忆 ✓ 可以复制ai回答文本 ✓ 使用流式传输,ai的回答是动态连续的 ✓ 使用wss保护数据传输安全 ? vits...

    游戏服务器中转代码

    游戏服务器中转代码,一个比较简单的转发数据包

    基于TCP的服务器中转简易版QQ聊天程序

    简易版QQ聊天 本程序基于VS2013开发,实现QQ客户端,QQ服务器的简易版聊天功能,是学习TCP客户端,...客户端发送的消息都经过服务器中转,然后发送到对端客户端,基于TCP模式实现,便于了解服务器,客户端的传输机制。

    基于Linux的网络中转服务器的设计与实现.pdf

    基于Linux的网络中转服务器的设计与实现.pdf

    Tracking-System 基于移动互联网的速递物流跟踪系统eciliplse+Android studioweb服务器

    web服务器tomcat数据库mysql 物流跟踪正确流程: 一、起始网点 二、转运 三、中转网点 四、目标网点 错误流程: 1. 打包时扫错误状态的码(会报错), 当拆包过程中,发现剩余快递,意味着快递丢失,点击报错,在该...

    javaweb做接口中转服务

    内网调外网接口服务,通用中转程序,并使用log4记录请求与返回值,使用springMvc框架一个简单的demo

    minerProxy / babyProxy 搭建中转教程+软件

    如果使用windows服务器, 则直接管理员运行 : babyProxy_windows.exe 注意事项: 1、在服务器 云服务商控制台 操作安全组,放行对应的端口,百度教程 2、在linux本机设置开放端口,centos、ubuntu等不同服务器开放...

    java httpclient https或http及文件中转上传工具类

    该工具类使用httpclient进行http or https请求,包括requestbody格式和form表单格式,另外含文件服务器中转上传方法,几乎支持所有常用接口调用,内含详细注释和说明文件,含jar包,及maven方式引用,拿过去直接用吧

    java web开发技术大全

    《Java Web开发技术大全:JSP+Servlet+Struts+Hibernate+Spring+Ajax+》讲解了JSP/S rvlet技术的基础知识,并提供了一个综合案例展示其具体应用,它们是Java Web服务端技术的基石,也是学习Java Web开发所要必须掌握...

    java web技术开发大全(最全最新)

    《Java Web开发技术大全:JSP+Servlet+Struts+Hibernate+Spring+Ajax+》讲解了JSP/S rvlet技术的基础知识,并提供了一个综合案例展示其具体应用,它们是Java Web服务端技术的基石,也是学习Java Web开发所要必须掌握...

    类QQ实现代码(即时通讯)

    传输大多数情况不需要经服务器中转而直接发往接收者所使用的机器,传输速度更快。 而且因服务器仅仅只是起着维护用户状态列表的功能,因此占用资源极少, 可允许同时在线的人数就越多,对系统的影响也最小。 可以...

    服务器中转聊天室.rar

    利用Python·实现中转服务器聊天,利用服务器进行中转。可以实现与多个客户端进行通讯。采用多线程技术。

    Android studio模仿qq聊天

    使用Android Studio软件构建客户端,使用VS2015的C#语言构建服务器端,客户端进行消息的发送与接收,服务器端进行信息管理以及信息中转,客户端与服务器端联合使用,最终构成了一个简单的聊天系统。

Global site tag (gtag.js) - Google Analytics