socketio.emit virker ikke netty socketio
Jeg arbejder med socketio og netty med java, og jeg er ny i dem begge.
min klientsidekode ser sådan ud.
<!DOCTYPE html> <html lang="en" xmlns="http://www.w3.org/1999/xhtml" xmlns:th="http://www.thymeleaf.org"> <head> <title >webSocket test</title> <script src="http://code.jquery.com/jquery-1.12.4.min.js"></script> <script src="https://cdn.socket.io/3.1.3/socket.io.min.js" integrity="sha384-cPwlPLvBTa3sKAgddT6krw0cJat7egBga3DJepJyrLl4Q9/5WLra3rrnMcyTyOnh" crossorigin="anonymous"></script> < !-- New Bootstrap core CSS file--> <!-- Optional Bootstrap theme file (generally not necessary to import) --> <!- -jQuery file. Be sure to introduce before bootstrap.min.js --> <!-- The latest Bootstrap core JavaScript file--> <script type=" text/javascript"> $(function(){ /** * The socket.emit("event name", "parameter data") method of the front-end js is used when triggering the back-end custom message event, * front-end js The socket.on("event name", anonymous function (data sent by the server to the client)) for monitoring server-side events **/ //io({path: 'ws://localhost:9099/', transports: ['websocket'] ,upgrade: false}); var socket = io.connect("ws://localhost:9099",{transports: ['websocket'] ,upgrade: false}); var firstconnect = true; if(firstconnect) { console.log("First connection initialization"); //Monitor server connection event socket.on('connect',function(){ socket.emit('messageEvent', 'Hello server'); console.log("First connection success"); $("#tou").html("Connect to the server successfully!"); }); //Monitor server shutdown service event socket.on('disconnect', function(){ $("#tou").html("Disconnected from the server!"); }); //Monitor server Send message event socket.on('responseEvent', function(data) { console.log('data'); $("#msg").html($("#msg").html() + "<br/>" + data); } ); firstconnect = false; } else { console.log("why?"); socket.socket.reconnect(); } $('#send').bind('click', function() { send(); }); function send(){ if (socket != null) { var message = document.getElementById('message').value; var title = "message"; var obj = {message:message,title:title}; var str = JSON.stringify(obj); socket.emit("messageEvent",str); console.log("message event" , str); } else { alert('Send'); } } }); </script> </head> <body> <div class="page-header" id="tou"> webSocket Demo </div> <div class="well" id="msg"> </div> <div class="col-lg"> <div class="input-group"> <input type="text" class="form-control" placeholder="send Message..." id="message"> <span class="input-group-btn"> <button class="btn btn-default" type="button" id="send" >send</button> </span> </div><!-- /input-group --> </div><!-- /.col-lg-6 --> </div><!-- /.row --><br><br> </body> </html>
Hændelseshåndteringen er som vist nedenfor.
@Component public class MessageEventHandler { private static final Logger logger = LoggerFactory.getLogger(MessageEventHandler.class); public static ConcurrentMap<String, SocketIOClient> socketIOClientMap = new ConcurrentHashMap<>(); @Autowired private RedissonClient redisson; @Resource private SocketIOServer socketIOServer; @OnConnect public void onConnect(SocketIOClient client){ Map<String,Object> clientMap = new HashMap<>(16); client.sendEvent("responseEvent", client.getSessionId().toString()+": "+ "hello"); if(client!=null){ String room = client.getHandshakeData().getSingleUrlParam("room"); String nameSpace = client.getNamespace().getName(); logger.info("namespace {} ",nameSpace); String sessionId = client.getSessionId().toString(); logger.info("namespace, room={}, sessionId={},namespace={}",room,sessionId,nameSpace); if(StringUtils.isEmpty(room)){ //client.joinRoom(room); clientMap.put("rooms",room); } clientMap.put("createTime", LocalDateTime.now().toString()); redisson.getBucket("room"+sessionId).trySet(clientMap); } return; } /** * Triggered when the client closes the connection * * @param client */ @OnDisconnect public void onDisconnect(SocketIOClient client) { logger.info("client:" + client.getSessionId() + "disconnected"); } /** * Client events * * @param client * @param request * @param msg */ @OnEvent(value = "messageEvent") public void onMessageEvent(SocketIOClient client, AckRequest request, String msg) { System.out.println("haha"); logger.info("message :" + msg); //Post the message back JSONObject jsonObject = JSON.parseObject(msg); String message = jsonObject.getString("message"); Collection<SocketIOClient> clients = socketIOServer.getBroadcastOperations().getClients(); for (SocketIOClient clientByRoom : clients) { clientByRoom.sendEvent("responseEvent", client.getSessionId().toString()+": "+message); } } }
Serverens startkode er vist nedenfor.
@Component @Order(1) public class SocketServerRunner implements CommandLineRunner { private static Logger logger = LoggerFactory.getLogger(SocketServerRunner.class); @Resource private SocketIOServer socketIOServer; @Resource private PubSubStore pubSubStore; @Autowired private RedissonClient redisson; @Override public void run(String... args) throws Exception { logger.info("socketIOServer "); socketIOServer.start(); pubSubStore.subscribe(PubSubType.DISPATCH, data -> { Collection<SocketIOClient> clients = null; String room = data.getRoom(); String namespace = data.getNamespace(); Packet packet = data.getPacket(); String jsonData = packet.getData(); if(!StringUtils.isEmpty(namespace)){ SocketIONamespace socketIONamespace = socketIOServer.getNamespace(namespace); if(StringUtils.isEmpty(room)){ clients = socketIONamespace.getRoomOperations(room).getClients(); } }else{ clients = socketIOServer.getBroadcastOperations().getClients(); } if(!CollectionUtils.isEmpty(clients)){ for (SocketIOClient client : clients) { client.sendEvent("messageEvent",jsonData); } } }, DispatchMessage.class); // addNameSpace(socketIOServer); }
Jeg får en forbindelsesregistrering på OnConnect
annoteret metode, men metoden ser ud til at køre to gange, fordi jeg får loggen to gange, mens stikket tilsluttes. Jeg ved ikke, hvorfor det sker.
Men endnu værre er, at emit-metoden ikke virker, som er skrevet i klientsidens javascript. Der er ingen fejl. Loggen under udsendelsen udføres. Men OnEvent
annoteret metode i Java EventHandler ser ikke ud til at opdage det.
Kan nogen hjælpe mig med at forstå dette?
Svar
Tilsyneladende ser det ud til, at problemet er med bibliotekerne. Der er et eller andet kompatibilitetsproblem med nyere versioner af socketio-klientbiblioteket med netty-afhængigheder til java, og det forårsager de mærkelige problemer.
Min afhængighed af netty socketio er vist nedenfor, hvilket tydeligvis er det seneste ved at besvare dette spørgsmål.
<dependency> <groupId>com.corundumstudio.socketio</groupId> <artifactId>netty-socketio</artifactId> <version>1.7.19</version> </dependency>
Og for at klientbiblioteket skulle fungere problemfrit var jeg nødt til at nedgradere biblioteket fra 3.X.X til 2.X.X.
I mit tilfælde fra
<script src="https://cdn.socket.io/3.1.3/socket.io.min.js" integrity="sha384-cPwlPLvBTa3sKAgddT6krw0cJat7egBga3DJepJyrLl4Q9/5WLra3rrnMcyTyOnh" crossorigin="anonymous"></script>
til
<script src="https://cdn.bootcss.com/socket.io/2.1.1/socket.io.js"></script>