我该如何解决这个问题我可以发送和接收消息,但它不是一对一的消息传递套接字 io react [英] How can i solve this i am able to send msg and receive but it is not one to one messaging socket io react

查看:53
本文介绍了我该如何解决这个问题我可以发送和接收消息,但它不是一对一的消息传递套接字 io react的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我尝试阅读文章,这就是我从中得到的结果我如何严格地进行一对一消息传递以及如何在我在私人消息中切换用户时也单独进行群组消息我想获得空的 showmessagespace 但它正在显示来自前一个用户的消息,当第三个用户发送消息时,两个用户都可以看到消息.

我如何制作一对一的消息并在单击特定用户消息按钮时更改用户(消息按钮工作正常,它正在切换用户).我的首要目标是私信.

服务器代码:

const io = require(socket.io")(server, {核心:{起源: '*',}});//为每个请求分配套接字对象app.use(function (req, res, next) {req.io = io;下一个();});io.on('connection', (socket) => {console.log('连接建立',socket.id);//io.emit('新连接')socket.on('send', (data)=>{console.log("从单个用户名接收数据",data)socket.join(`${data.username}`)io.emit('发送',数据)socket.to(`${data.username}`).emit(`${data.username}`,data)});socket.on('断开',()=>{io.emit('message','用户离开')})});

反应代码:当我点击其他用户的消息按钮时,我发送的消息会同时发送到上一个和我点击的消息按钮,并且所有消息都在他们之间共享

import React, { Component } from 'react';从'react-router-dom'导入{链接,重定向};从../services/userservice"导入 UserService;从../services/messageservice"导入{getUsersFriend};从socket.io-client"导入io;const SOCKET_IO_URL = "http://localhost:4000/";导出默认类消息扩展组件{构造函数(道具){超级(道具)this.socket = io(SOCKET_IO_URL)this.state = {当前用户:UserService.getCurrentUser(),正在加载:假,用户详细信息:[],显示:假,用户名:'',信息:'',套接字连接:假,消息:[]};this.onTextboxChangeMes​​sage = this.onTextboxChangeMes​​sage.bind(this)}componentDidMount(){this.fetchUser()this.socket.on('connect',()=>{this.setState({ socketConnected : true}) })this.socket.on('send',(data)=>{console.log('组件确实挂载了',data)this.setState({messages:[...this.state.messages,data]})})}异步 fetchUser(){尝试{const {currentUser} = this.state控制台日志(当前用户)const data = { userid : currentUser.user._id }控制台日志(数据)让用户 = 等待 getUsersFriend(data)this.setState({ userdetails: user });//控制台日志(用户)}抓住(错误){控制台日志(错误)}}showMessageSpace(elementusername){//用这个我点击另一个用户和那个特定用户的用户名const {currentUser} =this.statethis.setState({显示:真实,用户名:元素用户名});}onTextboxChangeMes​​sage(e){this.setState({消息:e.target.value})}发送消息(用户名,消息,发件人用户名){const {messages} =this.state如果(this.state.socketConnected){console.log('if condition test',username,message,senderusername)this.socket.emit('send',{username,message,senderusername});console.log('条件用户名',`${用户名}`, )this.socket.on(`${username}`, (d)=>{this.setState({messages:[...messages,d]})})}this.setState( { 消息:'' })}使成为(){const { currentUser ,isLoading,userdetails,message,messages} = this.state;控制台日志(消息)如果(正在加载){返回(<div><p>加载中...</p></div>);}如果(!当前用户){返回(<div><重定向到='/登录'/>

)}别的{返回(<div><h1>消息</h1><div><p>用户</p>{' '}<ul className="集合">{userdetails.map((元素) => {返回(<div key={element._id}><li><Link to={`/dashboard/profile/:${element._id}`}>{element.username}</Link>{' '}

);})}{' '}

{' '}<Link to="/dashboard">Dashboard</Link>{' '}<div>{this.state.show &&(

<h2>用户名:{' '}{this.state.username}</h2>{' '}<div><h3>身体</h3><div><ul>{messages.map((msg,key) =>{return(<li key={key}><span>{msg?.message}</span></li>);})}

{' '}<div>{' '}<输入类型=文本"名称=消息"值={消息}onChange={this.onTextboxChangeMes​​sage}></输入><button className='btn btn-info' onClick={this.SendMessage.bind(this,this.state.username,this.state.message,currentUser.user.username)}>发送</button>

{' '}</div>)}

)}}}

解决方案

我有 socketio 的基础知识.我想我设法在我的测试项目中发送了私人消息.

此示例仅用于私信

这是我用来发送私人消息的解决方案.

在客户端,当您连接到 socketio 时,您需要传递唯一的用户 ID,它可能是 firebase 客户端 Uid 或 jwt id,如下所示:

 await socketIO.io('http://localhost:3000', {询问: {用户 ID:val,}});

现在在后端你需要有一个数组对象,以这个 userId 作为键和相应的 socketId(当用户连接时你会得到 socketId)像这样:

socket.on(connect", () => {//编写逻辑以添加 userId 和 socketId//通过调用 socket.id 和传递的 userId 获取 socketId socket.handshake.query.userIdsocket.on(断开连接",(原因)=> {//使用 socketId 从数组对象中删除用户});});

现在你有在线用户(连接到套接字),你的 userId 和当前的 socketId 发出这个用户数组对象

 io.emit('users', users);

现在你可以发送像(socketid你将从用户数组对象中获得)这样的私人消息:

 io.to(socketid).emit(new_message",{to:to, from: from, msg:msg,date:date});//用于发送私人消息,

如果你想看看,我有一个半完成的项目:前端(Angular) , 后端(nodejs)

I tried reading articles and this is what i get out of it how can i strictly make one to one messaging and how can i make group messaging separately too also when i switch user in private msg i want to get empty showmessagespace but it is showing messages from previous user and when third user sends a msg both users are able to see the msg.

How can i make it one to one msg and change user on clicking particular user message button (message button is working properly it is toggling user). My first aim is for private messaging.

Server code:

const io = require("socket.io")(server, {
  cors: {
    origin: '*',
  }
});

// Assign socket object to every request
app.use(function (req, res, next) {
  req.io = io;
  next();
});

io.on('connection', (socket) => { 
  console.log('connection established',socket.id);
  // io.emit('New Connection')
  socket.on('send', (data)=>{
    console.log("Receive data from single username",data)
    socket.join(`${data.username}`)
    io.emit('send',data)
    socket.to(`${data.username}`).emit(`${data.username}`,data)
  });
  
  socket.on('disconnect',()=>{
    io.emit('message','user left')
  })
});

React code : When i click on message button of other user the msg i send goes to both the previous and to whose message button i clicked and all msg are shared between them

import React, { Component } from 'react';
import { Link,Redirect } from 'react-router-dom';
import UserService from "../services/userservice";
import {getUsersFriend} from "../services/messageservice";
import io from "socket.io-client";
const SOCKET_IO_URL = "http://localhost:4000/";

export default class Messages extends Component {
    constructor(props){
        super(props)
        this.socket = io(SOCKET_IO_URL)
        this.state = {
            currentUser: UserService.getCurrentUser(),
            isLoading:false,
            userdetails:[],
            show:false,
            username:'',
            message:'',
            socketConnected:false,
            messages:[]
        };
        this.onTextboxChangeMessage = this.onTextboxChangeMessage.bind(this)
    }

    componentDidMount(){
        this.fetchUser()
        this.socket.on('connect',()=> {
            this.setState({ socketConnected : true})        })
        this.socket.on('send',(data)=>{
            console.log('component did mount',data)
                this.setState({messages:[...this.state.messages,data]})            
        })
    }

    async fetchUser(){
        try{
            const {currentUser} = this.state
            console.log(currentUser)
            const data = { userid : currentUser.user._id }
            console.log(data)
            let user = await getUsersFriend(data)
            this.setState({ userdetails: user });
            // console.log(user)
        }catch(err){
            console.log(err)
        }
    }

    showMessageSpace(elementusername){  //with this i click on another user and username of that particular user comes
        const {currentUser} =this.state
        this.setState({
            show: true,
            username:elementusername
          });
    }

    onTextboxChangeMessage(e){
        this.setState({ message:e.target.value})
    }

    SendMessage(username,message,senderusername){
        const {messages} =this.state
        if(this.state.socketConnected){            
            console.log('if condition test',username,message,senderusername )
            this.socket.emit('send',{username,message,senderusername});
            console.log('condition username',`${username}`,  )
            this.socket.on(`${username}`, (d)=>{
                    this.setState({messages:[...messages,d]})
               
            })
        }
        this.setState( { message:'' })
    }

    

    render(){
        const { currentUser ,isLoading,userdetails,message,messages} = this.state;
        console.log(messages)
        if (isLoading) {
            return (<div><p>Loading...</p></div>);
        }

        if(!currentUser){
            return(
                <div>
                    <Redirect  to='/login' />
                </div>
            )
        }
        else{
        return(
            <div>
                <h1>Messages</h1>
                <div>
                    <p>Users</p>
                    {' '}
                    <ul className="collection">
                        {userdetails.map((element) => {
                            return(
                                <div key={element._id}>
                                    <li><Link to={`/dashboard/profile/:${element._id}`}>{element.username}</Link>{' '}<input 
                                    type="button" 
                                    id={element._id}
                                    value="Message"
                                    onClick={this.showMessageSpace.bind(this,element.username)} ></input></li>
                                </div>
                            );
                        })
                        }
                    </ul>
                    {' '}
                </div>
                {' '}
                    <Link to="/dashboard">Dashboard</Link>
                {' '}
                <div>
                {
                    this.state.show &&
                    (<div>
                        <h2>Username : {' '}{this.state.username}</h2>
                        {' '}
                        <div>
                            <h3>Body</h3>
                            <div>
                                <ul>
                                {messages.map((msg,key) =>{
                                    return(<li key={key}><span>{msg?.message}</span></li>);
                                })
                                }
                                </ul>
                            </div>
                        </div>
                        {' '}
                        <div>
                            {' '}
                            <input 
                            type="text"
                            name="message"
                            value={message}
                            onChange={this.onTextboxChangeMessage}
                            ></input>
                            <button className='btn btn-info' onClick={this.SendMessage.bind(this,this.state.username,this.state.message,currentUser.user.username )}>Send</button>
                        </div>
                        {' '}
                    </div>)
                    }
                </div>
            </div>
        )
        }
    }
}

解决方案

I have basic knowledge in socketio. I think i managed to send private messages in my test project.

this example is for private message only

Here is the solution i followed to send private messages.

in client side when you connect to socketio you need to pass unique user id it maybe firebase client Uid or jwt id like this:

    await socketIO.io('http://localhost:3000', {
          query: {
            userId: val,
          }
        });

now in backend you need to have an array object with this userId as key and corresponding socketId(You will get socketId when user connects) like this:

socket.on("connect", () => {
  // write your logic to add userId and socketId
 //  get socketId by calling socket.id and for passed userId socket.handshake.query.userId
 socket.on("disconnect", (reason) => {
    // remove the user from array object using socketId
  });
});

now at this point you have online users (who are connected to socket) with your userId and current socketId emit this user array object

 io.emit('users', users);

now you can send private message like(socketid you will get from user array object) :

   io.to(socketid).emit("new_message",{to:to, from: from, msg:msg,date:date}); //for sending private message, 

I have a semi completed project if you want have a look: frontend (Angular) , backend(nodejs)

这篇关于我该如何解决这个问题我可以发送和接收消息,但它不是一对一的消息传递套接字 io react的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
其他开发最新文章
热门教程
热门工具
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆