springboot中如何开启两个长连接线程的端口呢?
以前搞一个端口是没问题的,代码片断如下:
`
package com.smart.env.service.impl;
import com.smart.env.utils.ParseDust;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.Socket;
@Component
public class DustDeviceServerSocket {
@Value("${socket.dustPort}")
private Integer port;
@Autowired
private MsgProducer msgProducer;
public static void main(String[] args) {
new DustDeviceServerSocket().startAction();
}
public void startAction(){
java.net.ServerSocket serverSocket=null;
try {
serverSocket=new java.net.ServerSocket(port); //端口号
System.out.println("环境监测Socket服务已启动,占用端口: " + serverSocket.getLocalPort() );
//通过死循环开启长连接,开启线程去处理消息
while(true){
Socket socket=serverSocket.accept();
new Thread(new MyRuns(socket)).start();
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (serverSocket!=null) {
serverSocket.close();
}
} catch (Exception e2) {
e2.printStackTrace();
}
}
}
class MyRuns implements Runnable{
Socket socket;
BufferedReader reader;
BufferedWriter writer;
public MyRuns(Socket socket) {
super();
this.socket = socket;
}
@Override
public void run() {
try {
reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));//读取客户端消息
writer=new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));//向客户端写消息
String lineString="";
String str="";
while((lineString=reader.readLine())!=null){
System.out.println("接收数据:"+lineString);
str = ParseDust.Shift(lineString);
writer.write("server response:"+str+"\n");
if(str!=null&&!"".equals(str)){
System.out.println(str);
msgProducer.sendMsg(str);
}
writer.flush();
}
System.out.println(str);
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (reader!=null) {
reader.close();
}
if (writer!=null) {
writer.close();
}
if (socket!=null) {
socket.close();
}
} catch (Exception e2) {
e2.printStackTrace();
}
}
}
}
}
主入口里的代码:
ApplicationContext applicationContext = SpringApplication.run(EnvApplication.class, args);
applicationContext.getBean(DustDeviceServerSocket.class).startAction();
SpringApplication.run(EnvApplication.class, args);
现在又加一个端口,我把上面的文件复制一份出来改为新端口,发现第一个可以跑,第二个却跑不起来了。
主入口代码:
ApplicationContext applicationContext = SpringApplication.run(EnvApplication.class, args);
applicationContext.getBean(DustDeviceServerSocket.class).startAction();
applicationContext.getBean(CraneDeviceServerSocket.class).startAction();
SpringApplication.run(EnvApplication.class, args);
在网上找资料
找到以下代码片断:
package com.smart.env.service.impl;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.stereotype.Component;
@Component
public class ApplicationContextProvider implements ApplicationContextAware {
private static ApplicationContext context;
private ApplicationContextProvider(){}
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
context = applicationContext;
}
public static <T> T getBean(String name,Class<T> aClass){
return context.getBean(name,aClass);
}
}
moniotr代码:
package com.smart.env.service.impl;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;
import javax.management.monitor.Monitor;
@Component("mTask")
@Scope("prototype")
public class MoniotrTask extends Thread {
final static Logger logger= LoggerFactory.getLogger(MoniotrTask.class);
//参数封装
private Monitor monitor;
@Autowired
private DustDeviceServerSocket dustDeviceServerSocket;
public void setMonitor(Monitor monitor) {
this.monitor = monitor;
}
public void startAction1(){
dustDeviceServerSocket.startAction();
}
public void startAction2(){
System.out.println("222222");
}
@Override
public void run() {
logger.info("线程:"+Thread.currentThread().getName()+"运行中.....");
}
}
主入口代码:
MoniotrTask m1= ApplicationContextProvider.getBean("mTask",MoniotrTask .class);
m1.startAction1();
System.out.println("123");
MoniotrTask m2= ApplicationContextProvider.getBean("mTask",MoniotrTask .class);
m2.startAction2();
第二个端口还是跑不起来
我分析了原因:主要在于
while(true){
Socket socket=serverSocket.accept();
new Thread(new MyRuns(socket)).start();
}
这几段代码,进入死循环后面的都不跑了,但是翻了网上资料,如果搞长链接,必须要死循环。
请各位路过的大神,指点下,应该如何解决这个问题,谢谢了!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
每次初始化一个服务端socket就新开一个线程,要不当线程初始化第一个时候socket服务端已经阻塞到那里,不会往下面执行初始化第二个服务端了。
兄弟,我和你遇到了同样的问题,你这边有解决办法了嘛?能提供下解决办法嘛,不胜感谢!