我有一个带套接字的服务器和客户端,它们之间的连接正在进行,但我的React组件没有刷新。
我的组件是一个由一系列元素打印的出版物,我将所有这些信息和API(Express)连接到MySQL数据库。
这是我的React文件:
import React, { Component } from 'react';
import './component.css';
import io from 'socket.io-client';
import Msg from './components/Msg';
import ItemMsg from './components/ItemMsg';
import Sidebar from './components/Sidebar';
let socket = io('http://localhost:8082');
class App extends Component {
constructor(props){
super(props);
this.state = {
ids: []
};
}
componentDidMount() {
socket.on('update:component', (data) => {
// Debug line
console.log('recived message:', data);
// Update state
this.setState(prevState => {
// Get previous state
const { ids } = prevState;
// Add new item to array
ids.push(data);
// Debug line
console.log('new state:', ids);
// Return new state
return { ids };
});
});
fetch('/todos/ids')
.then((response) => response.json())
.then((responseJson) => {
this.setState({ids: responseJson.data})
console.log(responseJson.data);
})
}
render() {
return (
<div>
<Sidebar/>
<Msg/>
<ul>
{
this.state.ids.map((i, k) =>
<li key={k}><ItemMsg idfromparent={i.ID_Publicacion}/></li>
)
}
</ul>
</div>
);
}
}
export default App;
这是我的服务器文件:
var express = require('express');
var http = require('http');
var app = express();
var server = http.createServer(app);
var io = require('socket.io').listen(server);
var messages = [{
id: 1,
text: "I'm a message",
author: "I'm the author"
}];
app.use(express.static('public'));
app.use(function (req, res, next) {
res.header('Access-Control-Allow-Origin', '*');
res.header('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept-Type');
res.header('Access-Control-Allow-Credentials', 'true');
next();
})
app.get('/hello', function(req, res) {
res.status(200).send("Hello World!");
});
io.on('connection', function(socket) {
console.log('Alguien se ha conectado con Sockets');
socket.on('update:component', function(data) {
socket.emit('Thanks', data);
console.log(data);
});
});
server.listen(8082, function() {
console.log("Server corriendo en http://localhost:8082");
});
插入组件:
import React, { Component } from 'react';
import avatar from '../avatar.jpg'
import '../component.css'
import io from 'socket.io-client';
let socket = io('http://localhost:8082');
class Msg extends Component {
constructor(props) {
super(props);
this.handleSubmit = this.handleSubmit.bind(this);
this.state = {value: ''};
this.handleChange = this.handleChange.bind(this);
}
handleSubmit(e){
e.preventDefault();
var self = this;
// On submit of the form, send a POST request with the data to the server.
fetch('/todo/meterla',{
method: 'POST',
body:JSON.stringify({
publicacion: self.refs.task.value
}),
headers: {"Content-Type": "application/json"}
})
.then(function(response){
return response.json()
}).then(function(data){
console.log('json:', data);
socket.emit('update:component', data );
});
}
componentDidMount(){
socket.on('update:component', (data) => {
// Update state
this.setState(prevState => {
// Get previous state
const { ids } = prevState;
// Add new item to array
ids.push(data);
// Return new state
return { ids };
});
});
}
handleChange(event) {
this.setState({value: event.target.value});
}
render(data) {
return (
<div>
<form className="post" action="index.html" method="post" onSubmit={this.handleSubmit.bind(this)}>
<img className="avatar" src={avatar} alt="" />
<input type="text" placeholder="Escribe algo" ref="task" value={this.state.value} onChange={this.handleChange}/>
<input type="submit" value="Publicar" />
</form>
</div>
);
}
}
export default Msg;
答案 0 :(得分:1)
我想在数据库中插入数据时自动刷新组件,这就是为什么我实现了websockets。 fetch为我提供了数据库中的选择
我猜您的意思是每次通过post
发送handleSubmit()
请求时,对吗?
使用express
处理您的帖子请求:
每次发送post
请求时,您都需要发出自定义事件:
将事件发送到由字符串名称标识的套接字。可以包括任何其他参数。
app.post("/foo", function(req, res, next) {
io.sockets.emit("foo", req.body);
res.send({});
});
请参阅:docs
在HTML中,
<input>
,<textarea>
和<select>
等表单元素通常会维护自己的状态,并根据用户输入进行更新。在React中,可变状态通常保存在组件的state属性中,并且仅使用setState()更新。
// Set state
this.state = {value: ''};
...
handleChange(event) {
this.setState({value: event.target.value});
}
...
// Render
<input type="text" value={this.state.value} onChange={this.handleChange} />
此绑定对于使
this
在回调中起作用是必要的
this.handleSubmit = this.handleSubmit.bind(this);
this.handleChange = this.handleChange.bind(this);
请参阅:docs
const io = require('socket.io-client');
...
class MyComponent extends React.Component {
ComponentWillMount(){
this.socket = io();
}
}
请参阅:Set up React component to listen to socket.io
为给定事件注册新的处理程序。 请参阅:docs
updating
只有fetch()
个状态,在听众中触发updateState
:
ComponentDidMount(){
// Listen for custom event and add handler
this.socket.on('update:component', (data) => {
...
因为this.props和this.state可以异步更新,所以不应该依赖它们的值来计算下一个状态。
不要直接修改State
,唯一可以指定this.state
的地方是构造函数:
this.setState(prevState => {
// Get previous state
const { ids } = prevState;
// Add new item to array
ids.push(data);
// Return new state
return { ids };
});
}
JSX允许在花括号中嵌入任何表达式,因此我们可以内联map()结果
{
this.state.ids.map((i, k) =>
<li key={k}><ItemMsg idfromparent={i.ID_Publicacion}/></li>
);
}