简体   繁体   English

React JS Firebase:调用 function 刷新数据时的奇怪行为

[英]React JS Firebase :Strange behavior when calling function to refresh data

I have some strange behavior when calling a function in my React JS message app.在我的 React JS 消息应用程序中调用 function 时,我有一些奇怪的行为。 I delete the last message added to the database then call a function to re-query the db and setState with the new data (message list minus the deleted message).我删除添加到数据库中的最后一条消息,然后调用 function 以使用新数据重新查询 db 和 setState(消息列表减去已删除的消息)。

However, it only seems to work on reloading of the page, or typing a new message, then the 'deleted' message would disappear and be replaced with the new one - but this should happen automatically via the function!但是,它似乎只适用于重新加载页面或输入新消息,然后“已删除”消息将消失并替换为新消息 - 但这应该通过该功能自动发生!

The refresh() is called after deleting the data from db - this seems correct.从 db 删除数据后调用 refresh() - 这似乎是正确的。 At this point, the real-time db in firebase shows the message has been deleted.此时firebase中的实时db显示消息已被删除。

Then in the refresh() function I have a console log - it is definately being called, but appears to be called several times in the console.log.然后在 refresh() function 我有一个控制台日志 - 它肯定被调用,但似乎在 console.log 中被调用了几次。 Also, the messages listed in the log still contain the 'deleted' message until page is refreshed.此外,在刷新页面之前,日志中列出的消息仍包含“已删除”消息。

I have moved the setState function (see belox the two positions I have tried) and now it does delete the message, yet when I submit a new message, both the old and new message are shown!我已经移动了 setState function (请参阅我尝试过的两个位置),现在它确实删除了消息,但是当我提交新消息时,旧消息和新消息都会显示!

Code:代码:

import React, { Component } from 'react';
import firebase from 'firebase';
import { firebaseConfig } from './connection';

// Initialize Firebase
firebase.initializeApp(firebaseConfig);
let messageRef = firebase.database().ref('messages');
let listRef = firebase.database().ref('users');

class LandingPage extends Component {

  constructor(props) {
    super(props);

    this.state = {
      name: '',
      message: '',
      list: [],
      names: [],
      font: "black",
    }

  }

  // LOAD PREVIOUS NAME AND MESSAGES ON PAGE LOAD 
  componentDidMount() {
    const previousMessages = this.state.list;

    messageRef.limitToLast(10).on('child_added', snapshot => {
      previousMessages.push({
        id: snapshot.key,
        message: snapshot.val().text,
        name: snapshot.val().name
      })

      this.setState({
        list: previousMessages
      })
    })
  }

  // PUSH MESSAGE TO DB THEN RESET THIS.STATE
  submitHandler = e => {
    e.preventDefault()
    let name = this.state.name;
    let text = this.state.message;
    function saveMessage(name, text) {
      let newMessageRef = messageRef.push();
      newMessageRef.set({
        name,
        text,
      })
    }
    saveMessage(name, text);

    this.setState({ message: '' });
  }

  // DELETE LAST USER COMMENT 
  onDelete = () => {
    let userName = this.state.name;
    // console.log(userName);
    messageRef.orderByChild('name').equalTo(userName).limitToLast(1).once('child_added', function (snapshot) {
      snapshot.ref.remove();
    })
    this.refresh();

    console.log('call refresh function');
  }
  // REFRESH MESSAGE LIST AFTER DELETING LAST MESSAGE
  refresh = () => {
    const previousMessages = [];
    messageRef.on('child_added', snapshot => {
      previousMessages.push({
        id: snapshot.key,
        message: snapshot.val().text,
        name: snapshot.val().name
      })
      // this.setState({
      //   list: previousMessages
      // })
      console.log(previousMessages);
    })
    this.setState({
      list: previousMessages
    })
  }

  // RENDER THE HTML
  render() {
    return <div className='container'>

      {/* messages will be listed here */}
      < div className='messagesDiv' id='messagesDivId' >
        <ul>
          {/* List array is mapped through*/}
          {this.state.list.map(item => {
            return (
              <li className={(item.name === this.state.name ? 'right' : 'left')}
                style={{ color: this.state.font }}
                key={item.id}
                id={item.id}>
                {item.name}: {item.message}
              </li>
            )
          })}
        </ul>
      </div >

      {/* message text area and send button here  */}
      < div className='inputDiv' id='inputDivId' >
        <form onSubmit={this.submitHandler}>
          <input name="message"
            className='inputBox'
            id='messageInputBox'
            placeholder="Send message..."
            value={this.state.message}
            onChange={this.changeHandler}
            required />
          <button className='submit' type="submit">Send Message</button>
        </form>
      </div >

      {/*think, delete options*/}
      < div id='options' >
        <button id='delete' className='button delete' onClick={this.onDelete}>Delete last message</button>
      </div >

    </div >
  }
}

export default LandingPage;

If I comment-out the refresh function, the db updates ()deletes last message) and the all messages stay on the screen, as expected.如果我注释掉刷新 function,数据库更新()删除最后一条消息)并且所有消息都按预期保留在屏幕上。 This makes me think that the problem is within the refresh() function itself, if that helps.这让我认为问题出在 refresh() function 本身,如果有帮助的话。

Found the problem.发现了问题。

It is the .limitToLast(10) in componentDidMount()它是 componentDidMount() 中的.limitToLast(10) componentDidMount()

This interfered somehow with refresh() further down in the script.这在某种程度上干扰了脚本中的refresh() I realise this isn't a worthy explanation.我意识到这不是一个值得的解释。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM