Java复习之知识点整理(二十)--- QQ通信案例(三):公共类和工具类

37 篇文章 3 订阅
-----------------------------------------------------------------------------------
------------------ 四、公共部分:(test.qq.common) --------------
-----------------------------------------------------------------------------------

4.1 封装消息类Message:
---------------------------------------------------------------------------------------
public abstract class Message <T> {

	//客户端发送给服务器:刷新好友列表
	public static final int CLIENT_TO_SERVER_REFERSH_FRIENDS = 1;
	//客户端发送给服务器:文本消息--群聊
	public static final int CLIENT_TO_SERVER_CHATS = 2;
	//客户端发送给服务器:文本消息--私聊
	public static final int CLIENT_TO_SERVER_CHAT_SINGLE = 3;
	//服务器发送给客户端:好友列表
	public static final int SERVER_TO_CLIENT_FRIENDLIST = 4;
	//服务器发送给客户端:聊天消息--群聊
	public static final int SERVER_TO_CLIENT_CHAT_MESSAGE = 5;
	public static final int SERVER_TO_CLIENT_CHAT_MESSAGE_SINGLE = 6;
	//
	
	//消息内容
	private T messageContent;

	//获取消息内容
	public T getMessageContent() {
		return messageContent;
	}

	//设置消息内容
	public void setMessageContent(T messageContent) {
		this.messageContent = messageContent;
	}		
}




4.2 消息工厂类Factory:
---------------------------------------------------------------------------------------
/**
 *	消息工厂
 */
public class MessageFactory {

	/**
	 * 组装客户端发送的文本消息--群聊 
	 */
	public static byte[] popClientTextMessage(String msg)
	{
		return popMsg(Message.CLIENT_TO_SERVER_CHATS,msg.getBytes());
	}
	
	/**
	 * 组装客户端发送的文本消息--私聊 
	 */
	public static byte[] popClientTextMessageSingle(String msg,String destClientInfo)
	{
		//消息类型
		byte [] clientChatMsg = msg.getBytes();
		//
		byte[] userInfoArr = destClientInfo.getBytes();
		
		//总消息长度
		byte[] allArr = new byte[4 + 4 + userInfoArr.length + 4 + clientChatMsg.length];
		
		//消息类型
		System.arraycopy(Util.int2Bytes(Message.CLIENT_TO_SERVER_CHAT_SINGLE), 0, allArr, 0, 4);
		
		//用户信息长度
		System.arraycopy(Util.int2Bytes(userInfoArr.length), 0, allArr, 4, 4);
		
		//用户信息内容
		System.arraycopy(userInfoArr,0,allArr,8,userInfoArr.length);
		
		//聊天内容长度
		System.arraycopy(Util.int2Bytes(clientChatMsg.length) , 0 , allArr , (4 + 4 + userInfoArr.length) , 4);
		
		//聊天内容
		System.arraycopy(clientChatMsg , 0 , allArr , 4 + 4 + userInfoArr.length + 4 , clientChatMsg.length);
		
		return allArr ;
			
	}
	
	
	
	
	/**
	 * 组装客户端刷新好友列表消息
	 */
	public static byte[] popClientRefleshFriends()
	{
		return Util.int2Bytes(Message.CLIENT_TO_SERVER_REFERSH_FRIENDS);
	}
	
	/**
	 * 组装好友列表
	 */
	public static byte [] popServerFriends(ArrayList<String> msg)
	{
		//将消息内容对象通过序列化转换成字节数组
		byte [] msgArr = Util.serialize(msg);
		return popMsg(Message.SERVER_TO_CLIENT_FRIENDLIST,msgArr);	
	}
	

	/**
	 * 组装服务器发送消息 ---群聊
	 * --------------------------------------------
	 * |    |    |    |     4个字节---->消息类型
	 * --------------------------------------------
	 * |    |    |    |     4个字节---->客户端信息长度
	 * --------------------------------------------
	 * |    |    |    |     n个字节---->客户端信息
	 * --------------------------------------------
	 * |    |    |    |     4个字节---->消息长度
	 * --------------------------------------------
	 * |    |    |    |     n个字节---->消息内容
	 * --------------------------------------------
	 */
	
	public static byte[] popServerChatMessage(String userInfo,byte[] clientChatMsg){
		//用户信息数组
		byte[] userInfoArr = userInfo.getBytes();
		
		//总消息长度
		byte[] allArr = new byte[4 + 4 + userInfoArr.length + 4 + clientChatMsg.length];
		
		//消息类型
		System.arraycopy(Util.int2Bytes(Message.SERVER_TO_CLIENT_CHAT_MESSAGE), 0, allArr, 0, 4);
		
		//用户信息长度
		System.arraycopy(Util.int2Bytes(userInfoArr.length), 0, allArr, 4, 4);
		
		//用户信息内容
		System.arraycopy(userInfoArr,0,allArr,8,userInfoArr.length);
		
		//聊天内容长度
		System.arraycopy(Util.int2Bytes(clientChatMsg.length) , 0 , allArr , (4 + 4 + userInfoArr.length) , 4);
		
		//聊天内容
		System.arraycopy(clientChatMsg , 0 , allArr , 4 + 4 + userInfoArr.length + 4 , clientChatMsg.length);
		
		return allArr ;
	}
	
	/**
	 * 组装服务器发送消息 ---私聊
	 * @param userInfo
	 * @param clientChatMsg
	 * @return
	 */
	public static byte[] popServerChatMessageSingle(String senderInfo,byte[] clientChatMsg){
		//用户信息数组
		byte[] userInfoArr = senderInfo.getBytes();
		
		//总消息长度
		byte[] allArr = new byte[4 + 4 + userInfoArr.length + 4 + clientChatMsg.length];
		
		//消息类型
		System.arraycopy(Util.int2Bytes(Message.SERVER_TO_CLIENT_CHAT_MESSAGE_SINGLE), 0, allArr, 0, 4);
		
		//用户信息长度
		System.arraycopy(Util.int2Bytes(userInfoArr.length), 0, allArr, 4, 4);
		
		//用户信息内容
		System.arraycopy(userInfoArr,0,allArr,8,userInfoArr.length);
		
		//聊天内容长度
		System.arraycopy(Util.int2Bytes(clientChatMsg.length) , 0 , allArr , (4 + 4 + userInfoArr.length) , 4);
		
		//聊天内容
		System.arraycopy(clientChatMsg , 0 , allArr , 4 + 4 + userInfoArr.length + 4 , clientChatMsg.length);
		
		return allArr ;
	}
		
	
	/**
	 * 组装消息数组
	 */
	private static byte [] popMsg(int type, byte [] msgArr)
	{
		//消息内容长度数组
		byte [] msgLenArr = Util.int2Bytes(msgArr.length);
		//消息类型
		byte [] typeArr = Util.int2Bytes(type);
		
		byte [] all = new byte[msgArr.length + msgLenArr.length + typeArr.length];
		
		System.arraycopy(typeArr, 0, all, 0, typeArr.length);
		System.arraycopy(msgLenArr, 0, all, typeArr.length, msgLenArr.length);
		System.arraycopy(msgArr, 0, all, typeArr.length + msgLenArr.length, msgArr.length);		
		
		return all;
	}
	
	/**
	 * 解析消息流
	 */
	public static Message parseMessageFromInputStream(InputStream is)
	{
		try {
			//报头4字节都是消息类型
			byte [] typeArr = new byte [4];
			//
			is.read(typeArr);
			//获取消息类型
			int type = Util.bytes2Int(typeArr);
			switch (type) {
			
			//客户端请求刷新好友列表消息
			case Message.CLIENT_TO_SERVER_REFERSH_FRIENDS:
				return new ClientReflashFriendsListMessage();
				
			//客户端发送消息给服务器---群聊
			case Message.CLIENT_TO_SERVER_CHATS:
				byte [] lenArr = new byte [4];
				is.read(lenArr);
				int len = Util.bytes2Int(lenArr);
				byte [] strArr = new byte [len];
				is.read(strArr);				
				return new ClientSendChatMessage(strArr);
				
			//客户端发送消息给服务器---私聊
			case Message.CLIENT_TO_SERVER_CHAT_SINGLE:
				//解析目的地客户端信息
				byte [] desClientInfolenArr = new byte [4];
				is.read(desClientInfolenArr);
				int desClientInfolen = Util.bytes2Int(desClientInfolenArr);
				byte [] desClientInfoArr = new byte [desClientInfolen];
				is.read(desClientInfoArr);
				//destClient info
				String desClientInfoStr =  new String(desClientInfoArr);
				
				//解析发送的消息
				byte [] desClientMsglenArr = new byte [4];
				is.read(desClientMsglenArr);
				int desClientMsglen = Util.bytes2Int(desClientMsglenArr);
				byte [] desClientMsgArr = new byte [desClientMsglen];
				is.read(desClientMsgArr);						
				//组装消息				
				return new ClientSendChatMessageSingle(new ChatSingleBean(desClientInfoStr, desClientMsgArr));
			
				
				
			//服务器转发客户端消息---群聊
			case Message.SERVER_TO_CLIENT_CHAT_MESSAGE:
				
				//客户端信息长度
				byte [] clientInfolenArr = new byte [4];
				is.read(clientInfolenArr);
				int clientInfolen = Util.bytes2Int(clientInfolenArr);
				byte [] clientInfoArr = new byte [clientInfolen];
				is.read(clientInfoArr);
				String clientInfoStr =  new String(clientInfoArr);
				
				//客户端信息
				byte [] clientMsglenArr = new byte [4];
				is.read(clientMsglenArr);
				int clientMsglen = Util.bytes2Int(clientMsglenArr);
				byte [] clientMsgArr = new byte [clientMsglen];
				is.read(clientMsgArr);
				
				String clientMsgStr =  new String(clientMsgArr);
				
				return new ServerChatMessage(new String[]{clientInfoStr,clientMsgStr});
				
				
			//服务器转发客户端消息 ---私聊
			case Message.SERVER_TO_CLIENT_CHAT_MESSAGE_SINGLE:
				
				//解析发送方信息
				byte [] sendclientInfolenArr = new byte [4];
				is.read(sendclientInfolenArr);
				int sendclientInfolen = Util.bytes2Int(sendclientInfolenArr);
				byte [] sendclientInfoArr = new byte [sendclientInfolen];
				is.read(sendclientInfoArr);
				String sendclientInfoStr =  new String(sendclientInfoArr);
				
				//纯消息字节数组
				byte [] sendclientMsglenArr = new byte [4];
				is.read(sendclientMsglenArr);
				int sendclientMsglen = Util.bytes2Int(sendclientMsglenArr);
				byte [] sendclientMsgArr = new byte [sendclientMsglen];
				is.read(sendclientMsgArr);
							
				return new ServerChatMessageSingle(new ChatSingleBean(sendclientInfoStr, sendclientMsgArr));
			
				
			//服务器发送好友列表给客户端
			case Message.SERVER_TO_CLIENT_FRIENDLIST:
				
				//客户端信息长度
				byte [] friendListlenArr = new byte [4];
				is.read(friendListlenArr);
				int friendListlen = Util.bytes2Int(friendListlenArr);
				byte [] friendListArr = new byte [friendListlen];
				is.read(friendListArr);
				
				List<String> list = (List<String>)Util.deSerialize(friendListArr);				
				return new ServerFriendsListMessage(list);
							
			}
			
		} catch (Exception e) {
		}
		
		return null;
	}	
}



4.3 Message类的子类:服务器端具体消息类
---------------------------------------------------------------------------------------
  • 4.3.1 : 服务器端消息类NO1.------发送给客户端的消息--群聊
public class ServerChatMessage extends Message<String []>
{
	public ServerChatMessage(String [] info) {		
		this.setMessageContent(info);
	}	
}



  • 4.3.2: 服务器端消息类NO2.------发送给客户端的消息--私聊
    
public class ServerChatMessageSingle extends Message<ChatSingleBean>
{
	public ServerChatMessageSingle(ChatSingleBean info) {		
		this.setMessageContent(info);
	}	
}




  • 4.3.3: 服务器端消息类NO3.------发送好友列表给客户端
public class ServerFriendsListMessage extends Message<List<String>>
{
	public ServerFriendsListMessage(List<String> list)
	{
		super.setMessageContent(list);
	}	
}




4.4 Message类的子类:客户端具体消息类
---------------------------------------------------------------------------------------
  • 4.4.1 : 客户端消息类NO1.------向服务器发送消息-----群聊
public class ClientSendChatMessage extends Message<byte []>
{
	public  ClientSendChatMessage(byte[] messageContent) {
		this.setMessageContent(messageContent);
	}
}


  • 4.4.2: 客户端消息类NO2.------向服务器发送消息------私聊
public class ClientSendChatMessageSingle extends Message<ChatSingleBean>
{
	public  ClientSendChatMessageSingle(ChatSingleBean messageContent) {
		this.setMessageContent(messageContent);
	}
}



  • 4.4.3: 客户端消息类NO3.------向服务器请求刷新好友列表
public class ClientReflashFriendsListMessage extends Message
{

}



4.5 私聊消息封装类---仅用于私聊:
---------------------------------------------------------------------------------------
public class ChatSingleBean {

	
	private String cilentInfo;
	//聊天信息(纯内容)
	private byte[] chat;
	
	public String getReceiver() {
		return cilentInfo;
	}
	public void setReceiver(String cilentInfo) {
		this.cilentInfo = cilentInfo;
	}
	public byte[] getChat() {
		return chat;
	}
	public void setChat(byte[] chat) {
		this.chat = chat;
	}
	
	public ChatSingleBean(String cilentInfo, byte[] chat) {
	
		this.cilentInfo = cilentInfo;
		this.chat = chat;
	}			
}





-----------------------------------------------------------------------------------
------------------ 五、工具类部分:(test.qq.util) ------------
-----------------------------------------------------------------------------------
/**
 *	工具类 
 */
public class Util {

	/**
	 * 将int转换成字节数组
	 */
	public static byte[] int2Bytes(int i)
	{
		byte[] bs = new byte[4];
		bs[0] = (byte)(i >>> 24);
		bs[1] = (byte)(i >>> 16);
		bs[2] = (byte)(i >>> 8);
		bs[3] = (byte)(i >>> 0);
		return bs;
	}
	
	/**
	 * 将字节数组前4位,转换成int
	 */
	public static int bytes2Int(byte [] bs)
	{
		int i0 = (bs[0] & 0xff) <<24;
		int i1 = (bs[1] & 0xff) <<16;
		int i2 = (bs[2] & 0xff) <<8;
		int i3 = (bs[3] & 0xff) <<0;
		return i0 | i1 | i2 | i3;
	}
	
	/**
	 * 将字节数组off位 + 4位, 转换成int
	 */
	public static int bytes2Int(byte [] bs , int offset)
	{
		int i0 = (bs[0 + offset] & 0xff) <<24;
		int i1 = (bs[1 + offset] & 0xff) <<16;
		int i2 = (bs[2 + offset] & 0xff) <<8;
		int i3 = (bs[3 + offset] & 0xff) <<0;
		return i0 | i1 | i2 | i3;
	}
	
	
	/**
	 * 序列化内存对象到字节数组
	 */
	public static byte[] serialize(Serializable src)
	{
		try {
			
			ByteArrayOutputStream baos = new ByteArrayOutputStream();
			ObjectOutputStream oos = new ObjectOutputStream(baos);
			oos.writeObject(src);
			oos.close();
			baos.close();
			return baos.toByteArray();
			
		} catch (Exception e) {
			e.printStackTrace();
		}
		return null;
	}
	
	/**
	 * 反序列化对象字节到内存对象
	 */
	public static Object deSerialize(byte [] bArr)
	{
		try {
			
			ByteArrayInputStream bais = new ByteArrayInputStream(bArr);
			ObjectInputStream ois = new ObjectInputStream(bais);
			Serializable copy = (Serializable)ois.readObject();
			ois.close();
			bais.close();
			return copy;
			
		} catch (Exception e) {
			
			e.printStackTrace();
		}
		
		return null;
	}
	
	
	/**
	 * 提取客户端信息
	 */
	public static String getClientInfo(Socket s) {
	
		InetSocketAddress is = (InetSocketAddress)s.getRemoteSocketAddress();
		//远程ip地址
		String ip = is.getAddress().getHostAddress();
		int port = is.getPort();
		return ip +":"+ port;
	}

}





  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值