新手求教Nodejs相关问题,好心人帮助一下。

新手求教Nodejs相关问题,好心人帮助一下。

小弟是一新手,刚接触node不久,现在遇到一个问题搞了半天无法解决,哪位大神能指点一下,小弟将不胜感激。 我用nodejs做服务器,用socket.io接收客户端的连接,客户端是java程序写的: 客户端如下: import java.io.; import java.net.; public class TalkClient { public static void main(String args[]) throws Exception { String host = “127.0.0.1”; int port = 3000; Socket client = new Socket(host, port); Writer writer = new OutputStreamWriter(client.getOutputStream()); writer.write(“Hello Server.”); writer.flush(); Reader reader = new InputStreamReader(client.getInputStream()); char chars[] = new char[64]; int len; StringBuffer sb = new StringBuffer(); while ((len=reader.read(chars)) != -1) { sb.append(new String(chars, 0, len)); } System.out.println("from server: " + sb); writer.close(); reader.close(); client.close(); } } 服务器端app.js如下: //引入程序包 var express = require(‘express’) , path = require(‘path’) , app = express() , server = require(‘http’).createServer(app) , io = require(‘socket.io’).listen(server);

io.sockets.on(‘connection’, function(socket){ console.log(“有连接来了”); }); //express基本配置 app.configure(function(){ app.set(‘port’, process.env.PORT || 3000); app.set(‘views’, __dirname + ‘/views’); app.use(express.favicon()); app.use(express.logger(‘dev’)); app.use(express.bodyParser()); app.use(express.methodOverride()); app.use(app.router); app.use(express.static(path.join(__dirname, ‘public’))); }); app.configure(‘development’, function(){ app.use(express.errorHandler()); });

server.listen(app.get(‘port’), function(){ console.log("Express server listening on port " + app.get(‘port’)); });

当我运行客户端java程序的时候,服务器端不是应该打印一行“有链接来了”么? 可是怎么实验也没有啊,问题出在哪里啊?求教,急!


3 回复

根据你的描述,你正在使用 socket.io 来处理客户端与服务器之间的通信。然而,从你的代码来看,客户端是通过普通的 TCP 连接发送数据,而不是通过 socket.io 客户端。

问题分析

  1. 客户端使用普通TCP连接:你当前的客户端代码只是通过普通的 TCP 连接向服务器发送消息,而没有使用 socket.io 的客户端库。socket.io 需要特定的握手协议和心跳机制来保持连接,因此普通 TCP 连接不会触发 socket.ioconnection 事件。

  2. 服务器端配置:你的服务器端配置正确地监听了连接事件,但是由于客户端没有正确地发起 socket.io 连接,所以不会触发 connection 事件。

解决方案

你需要在客户端使用 socket.io 的客户端库,这样才能正确地触发服务器端的 connection 事件。

修改客户端代码

首先,确保客户端使用 socket.io 客户端库。你可以通过 Maven 或 Gradle 添加依赖项,或者直接下载 socket.io 客户端库并将其包含在项目中。

import io.socket.client.IO;
import io.socket.client.Socket;
import java.net.URI;

public class TalkClient {
    public static void main(String[] args) throws Exception {
        URI uri = new URI("http://localhost:3000");
        IO.Options opts = new IO.Options();
        opts.forceNew = true;
        opts.reconnection = false;

        Socket socket = IO.socket(uri, opts);

        socket.on(Socket.EVENT_CONNECT, args1 -> {
            System.out.println("Connected to server!");
            socket.emit("message", "Hello Server.");
        });

        socket.on("message", args1 -> {
            System.out.println("from server: " + args1[0]);
        });

        socket.connect();
    }
}

修改服务器端代码

确保你的服务器端代码正确地处理了 socket.io 的连接事件。

// 引入程序包
var express = require('express');
var path = require('path');
var app = express();
var server = require('http').createServer(app);
var io = require('socket.io')(server);

io.sockets.on('connection', function(socket){
    console.log("有连接来了");
    socket.on('message', function(data) {
        console.log('Received message:', data);
        io.emit('message', 'Hello Client!');
    });
});

// express基本配置
app.configure(function(){
    app.set('port', process.env.PORT || 3000);
    app.set('views', __dirname + '/views');
    app.use(express.favicon());
    app.use(express.logger('dev'));
    app.use(express.bodyParser());
    app.use(express.methodOverride());
    app.use(app.router);
    app.use(express.static(path.join(__dirname, 'public')));
});

app.configure('development', function(){
    app.use(express.errorHandler());
});

server.listen(app.get('port'), function(){
    console.log("Express server listening on port " + app.get('port'));
});

总结

通过以上修改,客户端将能够正确地与服务器建立 socket.io 连接,并且服务器端会触发 connection 事件。这样,你就可以在服务器端看到“有连接来了”的输出。


socket.io 用的协议不是普通 tcp 借口,是 websocket 需要找一个支持 websocket 协议的客户端。

根据你的描述,你希望当客户端连接到服务器时,服务器端能够输出“有连接来了”。从你提供的代码来看,问题可能出在几个地方。首先确认几个关键点:

  1. 端口是否正确:确保客户端连接的端口号(在这个例子中是3000)与服务器监听的端口号一致。

  2. 协议一致性:客户端使用的是标准TCP套接字进行通信,而socket.io通常需要一个支持WebSocket协议的连接。尽管直接使用net.Socket对象也可以工作,但默认情况下socket.io客户端库期望使用WebSocket。

  3. 安装依赖:确保你已经安装了expresshttpsocket.io模块。可以通过npm命令安装:

    npm install express http socket.io
    

示例代码调整

客户端(Java程序)

由于你提到客户端是Java程序,并且它没有使用socket.io客户端库,而是直接使用了标准TCP套接字。为了匹配socket.io服务器的预期,你需要发送一个特殊的握手消息,或者简单地使用WebSocket客户端库来替代。

服务器端(Node.js)

// 引入必要的模块
const express = require('express');
const http = require('http');
const io = require('socket.io');

// 创建应用实例
const app = express();
const server = http.createServer(app);

// 启动socket.io服务
const socketIO = io.listen(server);

// 监听连接事件
socketIO.on('connection', (socket) => {
    console.log("有连接来了");
});

// 配置express
app.set('port', process.env.PORT || 3000);
app.set('views', __dirname + '/views');
app.use(express.favicon());
app.use(express.logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(express.methodOverride());
app.use(app.router);
app.use(express.static(path.join(__dirname, 'public')));

// 开发环境错误处理中间件
if (process.env.NODE_ENV === 'development') {
    app.use(express.errorHandler());
}

// 启动服务器
server.listen(app.get('port'), () => {
    console.log(`Express server listening on port ${app.get('port')}`);
});

解释

  • socket.io 默认监听所有类型的连接,包括WebSocket。如果你的客户端发送的是标准TCP数据,你可能需要自定义处理逻辑。
  • 确保客户端发送的数据格式符合socket.io的握手协议,否则连接可能不会被识别为有效连接。

如果客户端使用的是标准TCP套接字,而不是WebSocket,你可能需要修改服务器端的代码来适配这种情况,或者使用一个支持WebSocket的Java客户端库。

回到顶部