javaweb啟動(dòng)時(shí)啟動(dòng)socket服務(wù)端代碼實(shí)現(xiàn)
這篇文章主要介紹了javaweb啟動(dòng)時(shí)啟動(dòng)socket服務(wù)端代碼實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
說明:在javaweb項(xiàng)目啟動(dòng)的時(shí)候啟動(dòng)socket服務(wù)端,可以接受客戶端發(fā)送過來的數(shù)據(jù),客戶端可以反復(fù)斷開連接
1.新建SocketThread線程類
package com.wlw.modules.startImplement.web;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
/**
* socket 線程類
* @Author: zhouhe
* @Date: 2019/4/16 14:58
*/
public class SocketThread extends Thread {
private ServerSocket serverSocket = null;
public SocketThread(ServerSocket serverScoket){
try {
if(null == serverSocket){
this.serverSocket = new ServerSocket(8877);
System.out.println("socket start");
}
} catch (Exception e) {
System.out.println("SocketThread創(chuàng)建socket服務(wù)出錯(cuò)");
e.printStackTrace();
}
}
public void run(){
while(!this.isInterrupted()){
try {
Socket socket = serverSocket.accept();
if(null != socket && !socket.isClosed()){
//處理接受的數(shù)據(jù)
new SocketOperate(socket).start();
}
// socket.setSoTimeout(30000); //設(shè)置超時(shí)
}catch (Exception e) {
}
}
}
public void closeSocketServer(){
try {
if(null!=serverSocket && !serverSocket.isClosed())
{
serverSocket.close();
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
2.新建SocketOperate,用于接受客戶端傳來的數(shù)據(jù)
package com.wlw.modules.startImplement.web;
import com.wlw.modules.lhjh.socket.tstandard.MessageParsing;
import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.IOException;
import java.net.Socket;
/**
* 多線程處理socket接收的數(shù)據(jù)
* @Author: zhouhe
* @Date: 2019/4/16 14:59
*/
public class SocketOperate extends Thread {
private Socket socket;
public SocketOperate(Socket socket) {
this.socket=socket;
}
@Override
public void run() {
try {
//封裝輸入流(接收客戶端的流)
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
DataInputStream dis = new DataInputStream(bis);
byte[] bytes = new byte[1]; // 一次讀取一個(gè)byte
String ret = "";
while (dis.read(bytes) != -1) {
ret += MessageParsing.bytesToHexString(bytes) + "";
if (dis.available() == 0) { //一個(gè)請(qǐng)求
System.out.println("轉(zhuǎn)換為字符串后:"+MessageParsing.hexStringToString(ret));
System.out.println("轉(zhuǎn)為map后的數(shù)據(jù):"+MessageParsing.stringToMap(MessageParsing.hexStringToString(ret)));
ret = "";
}
}
} catch (Exception e) {
e.printStackTrace();
} finally {
System.out.println("client is over");
if (socket != null) {
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
3.新建InitJob,web項(xiàng)目啟動(dòng)的時(shí)候會(huì)執(zhí)行里面的方法,去啟動(dòng)socket,可以用串口調(diào)試工具測(cè)試
package com.wlw.modules.startImplement.web;
import com.wlw.common.config.Global;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
/**
* @Author: zhouhe
* @Date: 2019/4/16 11:00
*/
//創(chuàng)建的類名根據(jù)需要定義,但一定要實(shí)現(xiàn)ServletContextListener接口
public class InitJob implements ServletContextListener {
//socket server 線程
private SocketThread socketThread;
/**
* 項(xiàng)目在啟動(dòng)初始化的時(shí)候就會(huì)執(zhí)行的方法(啟動(dòng)服務(wù)時(shí)執(zhí)行)
* @param arg0
*/
@Override
public void contextInitialized(ServletContextEvent arg0) {
// TODO Auto-generated method stub
//這里可以放你要執(zhí)行的代碼或方法
if(null==socketThread && "yes".equals(Global.getConfig("socket"))){
// MessageParsing.calculation();
//新建線程類
socketThread=new SocketThread(null);
//啟動(dòng)線程
socketThread.start();
}
}
/**
*contextDestroyed是在消亡的時(shí)候執(zhí)行的方法(關(guān)閉服務(wù)時(shí)執(zhí)行)
* @param arg0
*/
@Override
public void contextDestroyed(ServletContextEvent arg0) {
// TODO Auto-generated method stub
if(null!=socketThread && !socketThread.isInterrupted()){
socketThread.closeSocketServer();
socketThread.interrupt();
}
}
}
4.這里需要一個(gè)報(bào)文解析工具類
package com.wlw.modules.lhjh.socket.tstandard;
import java.util.HashMap;
import java.util.Map;
/**
* HJ/T212 報(bào)文解析
* @Author: zhouhe
* @Date: 2019/4/12 10:11
*/
public class MessageParsing {
/**
* 字符串轉(zhuǎn)換為 map
* @param arr
* @return
*/
public static Map stringToMap(String arr){
arr=arr.replaceAll(",",";");
Map map = new HashMap();
if (null != arr) {
String[] param = arr.split(";");
for (int i = 0; i < param.length; i++) {
//這里的 index 要 >-1 才是 map格式
int index = param[i].indexOf('=');
if(index>-1)
map.put(param[i].substring(0,index), param[i].substring((index + 1)));
}
}
return map;
}
/**
* byte[]數(shù)組轉(zhuǎn)換為16進(jìn)制的字符串
*
* @param bytes 要轉(zhuǎn)換的字節(jié)數(shù)組
* @return 轉(zhuǎn)換后的結(jié)果
*/
public static String bytesToHexString(byte[] bytes) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < bytes.length; i++) {
String hex = Integer.toHexString(0xFF & bytes[i]);
if (hex.length() == 1) {
sb.append('0');
}
sb.append(hex);
}
return sb.toString();
}
/**
* 16進(jìn)制轉(zhuǎn)換成為string類型字符串
* 這個(gè)方法中文會(huì)亂碼,字母和數(shù)字都不會(huì)亂碼
*
* @Author zhouhe
* @param s
* @return
*/
public static String hexStringToString(String s) {
if (s == null || s.equals("")) {
return null;
}
s = s.replace(" ", "");
byte[] baKeyword = new byte[s.length() / 2];
for (int i = 0; i < baKeyword.length; i++) {
try {
baKeyword[i] = (byte) (0xff & Integer.parseInt(s.substring(i * 2, i * 2 + 2), 16));
} catch (Exception e) {
e.printStackTrace();
}
}
try {
s = new String(baKeyword, "UTF-8");
new String();
} catch (Exception e1) {
e1.printStackTrace();
}
return s;
}
}
這樣就大功告成了,啟動(dòng)web項(xiàng)目,就可以接受客戶端過來的數(shù)據(jù)了
以上就是本文的全部內(nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
SpringBoot項(xiàng)目中的favicon.ico圖標(biāo)無法顯示問題及解決
這篇文章主要介紹了SpringBoot項(xiàng)目中的favicon.ico圖標(biāo)無法顯示問題及解決,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-01-01
java 中用split分割字符串,最后的空格等不被拆分的方法
下面小編就為大家?guī)硪黄猨ava 中用split分割字符串,最后的空格等不被拆分的方法。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2017-02-02
java7鉆石語法知識(shí)點(diǎn)總結(jié)
在本篇文章里小編給大家整理的是關(guān)于java7鉆石語法的相關(guān)知識(shí)點(diǎn)內(nèi)容,有需要的朋友們參考下。2019-11-11
IDEA的Mybatis Log Plugin插件配置和使用詳解
這篇文章主要介紹了IDEA的Mybatis Log Plugin插件配置和使用,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-09-09

