The stack - React native, socket.io, Node.js
Im developing a chat app. At this point I have a flow like that :
User clicks "send message" -> the message is emitted by socket.io to the server -> the socket connection on the server gets the message.
Now, from that point what I want is the message to be sent from the server to the redux reducer and then the reducer will return a new state that the frontend component will render.
How do I make the connection between the server side socket and the reducer?
The current server :
const express = require("express");
const app = express();
const port = 3000;
const server = require("http").createServer(app);
let io = require("socket.io")(server);
app.get("/", (req, res) => res.send("Hello World!"));
io.on("connection", socket => {
console.log("a user connected");
socket.on("join", (name, message) => {
console.log("chat room connected")
});
});
server.listen(port, () => console.log(`listening on port ${port}!`));
The current reducer :
const initialState = {
chats: [
]
};
const chatsReducer = (state = initialState, action) => {
let sender = action.sender;
let message = action.message;
switch (action.type) {
case SEND_MESSAGE:
let newMessage = {
sender: sender,
message: message
};
let newState = { ...state, chats: state.chats.push(newMessage) };
return state;
default:
state;
}
return state;
};
export default chatsReducer;
You can emit the new message from the node server like.
let msg = {message: 'Actual Message', sender: 'Name of sender'}
io.on('connection', socket => {
socket.on('chat message', msg => {
io.emit('chat message', msg);
});
});
Then in you chat component listen the chat message event.
componentDidMount() {
this.socket = io("http://server.address:port");
this.socket.on("chat message", msg => {
this.props.onMessageReceivedAction (msg); // import action and will execute on message received event
});
});
Then add the action :
export const onMessageReceivedAction = (params) => {
return {type: MESSAGE_RECEIVED, payload:msg};
};
Add message received reducer case to your reducer
case MESSAGE_RECEIVED:
let newMessage = {
sender: payload.sender,
message: payload.message
};
return { ...state, chats: state.chats.push(newMessage) };
This will return the new state and the component props mapped to the above state will get re-rendered.
Hope this will answer your question.
Exactly what I meant. Thank u
Glad to hear that.