安装了React组件后,第一次不调用socket.on函数

时间:2019-01-20 22:13:20

标签: reactjs socket.io

我正在尝试创建一个简单的实时聊天应用程序以与socket-io一起练习。我正在使用React来创建UI,并且我正在将NodeJS与Express Web服务器一起使用。我有ChatPage React组件来显示消息。

当用户加入会议室时,我正在发送事件newMessage,并且我正在将欢迎消息作为数据从服务器发送到客户端。当时我正在路由到ChatPage组件,并且正在componentWillMount中订阅updateUserList事件,但是该事件并没有达到我定义的回调。经过一番试验后,我意识到这个事件很奇怪。我从另一个.js文件订阅了此事件,并且可以看到我从服务器发送的数据。

// server.js
socket.on('joinRoom', (data, callback) => {
    const { username, roomName } = data
    if (username === '' || roomName === '') {
        if (callback) {
            return callback({ error: 'Username and password required!' })
        }
        return
    }

    socket.join(roomName, (err) => {
        if (err && callback) {
            return callback({ error: 'Could not connect to room.' })
        }

        socket.emit('newMessage', generateMessage('Admin', 'Welcome to chat app'))
        if (callback) {
            callback()
        }
    })
})


// ChatPage.js
componentWillMount() {
    const socket = io('http://localhost:3400')
    socket.on('newMessage', (message) => {
        console.log('newMessage', message)
    })
}



// event is coming to here instead!
import socketIOClient from "socket.io-client";

export const getSocketIOClient = () => {
    const endpoint = "http://localhost:3400"
    const socket = socketIOClient(endpoint)
    socket.on('newMessage', (er) => {
        console.log('newMessage', message)
    })
    return socket;
}

1 个答案:

答案 0 :(得分:0)

我在项目中遇到了类似的问题。在那里,我注意到您的代码中缺少一些东西。

  1. 您还需要使用componentWillMount()方法用客户端代码回调联接空间。
  2. 您需要在socket变量中初始化state。我不完全知道为什么在const变量中初始化时它不起作用,但是当我们使用state变量时它才起作用。我验证了此代码,即使在第一次安装组件时也能正常工作。

这是示例代码:

import React from 'react'
import io from 'socket.io-client';

class SocketExample extends React.Component {

    state = {
        chatMessage: '',
        chatMessages: [],
        socket: io.connect(`http://localhost:3001`),
    }

    submitChatMessage = (e) => {
        e.preventDefault()
        if (this.state.chatMessage.length > 0) {
            this.state.socket.emit('newMessage', {
                username: this.props.currentUser.username,
                message: this.state.chatMessage,
            });
            this.setState({
                chatMessage: '',
            })
        }
    }

    componentDidMount(){
        this.state.socket.on('connect', () => {
            this.state.socket.emit('join', { uniqueValue: chatRoomName });
        });
        this.state.socket.on("newMessage", data => {
            this.setState({
                chatMessages: [...this.state.chatMessages, data],
            });
        });
    }

    render() {
        return (
            <div>{this.state.chatMessages.map(chat => {
                return <p>{chat.username + ': ' + chat.message}</p>
            })}</div>
        )    
    }  
}

export default SocketExample