2016-05-08 5 views
2

Ich bekomme einen Fehler, wenn Sie versuchen, den Zustand einer Komponente zu ändern.SetState von einer API-Antwort mit Superagent und React

Uncaught TypeError: Cannot read property 'setState' of undefined

constructor(props){ 
    super(props); 

    this.state={ 
     r:'', 
     message:'' 
    }; 
    this.setStateMessage = this.setStateMessage.bind(this); 
} 
setStateMessage (e){ 
    e.preventDefault(); 
    var test = this.state.message; 

    request 
     .post('http://127.0.0.1:5000/api/db') 
     .send({message: this.state.message}) 
     .accept('application/json') 
     .withCredentials() 
     .end(function(err, res){ 
     if(err) 
      throw err; 
     this.setState({ r: res.body.message }); 
     }); 
} 

render() { 
    return (
     <div> 
      <div className='response'> 
       {this.state.r} 
      </div> 
      //form with input 
     </div> 
    )} 

Antwort

6

Dies liegt daran, Sie this.setState innerhalb einer Funktion so this ist eigentlich ein Verweis auf die Funktion, die Sie in sind anrufen. Sie müssen entweder speichern Sie einen Verweis auf die richtige this oder einen Pfeil benutzen, die hat keinen eigenen Kontext und erbt vom übergeordneten Kontext. Also:

setStateMessage (e){ 
    e.preventDefault(); 
    var test = this.state.message; 
    var self = this; 

    request 
    .post('http://127.0.0.1:5000/api/db') 
    .send({message: this.state.message}) 
    .accept('application/json') 
    .withCredentials() 
    .end(function(err, res){ 
     if(err) throw err; 
     self.setState({ r: res.body.message }); 
    }); 
} 

Oder:

setStateMessage (e){ 
    e.preventDefault(); 
    var test = this.state.message; 

    request 
    .post('http://127.0.0.1:5000/api/db') 
    .send({message: this.state.message}) 
    .accept('application/json') 
    .withCredentials() 
    .end((err, res) => { 
     if(err) throw err; 
     this.setState({ r: res.body.message }); 
    }); 
} 
+0

Ich wachte heute auf und hatte die Idee, dass "das" sich tatsächlich auf die Callback-Funktion bezieht, so dass die Schuld ist rit des Problems. Meine beste Vermutung war, etwas wie 'var res = request.post ('......);' zu schreiben und dann vielleicht 'res' in einem setState außerhalb der Callback-Funktion zu verwenden? Wäre das eine dritte Option? – Ando

+0

Und eine letzte Frage ... Wenn ich Redux verwendet hätte, könnte ich von "Versand" verwendet werden und das würde von richtig funktioniert? Liegt das daran, dass die Funktionen von Redux global definiert sind? – Ando

+0

'Versand' ist nicht global definiert. Wenn Sie redux verwenden, sollten Sie die API innerhalb einer asynchronen Aktion mit 'redux-thunk' aufrufen. Es ist ein wenig schwierig, Ihre Frage mit einem Beispiel zu beantworten. Aber da Sie 'this.setState' nicht innerhalb dieses Callbacks aufrufen würden, hätten Sie dieses Problem nicht. Das heißt, dass Sie in JS etwas über 'this' lesen sollten. Sonst wirst du woanders verwirrt sein. – aray12

2

Hinzufügen zu @ aray12 Antwort, können Sie den Rückruf binden.

setStateMessage (e){ 
    e.preventDefault(); 
    var test = this.state.message; 

    request 
    .post('http://127.0.0.1:5000/api/db') 
    .send({message: this.state.message}) 
    .accept('application/json') 
    .withCredentials() 
    .end((function(err, res) { 
     if(err) throw err; 
     this.setState({ r: res.body.message }); 
    }).bind(this)); 
} 
0

Nach zu viel Zeit auf dieser meine letzte Code ist hier

class Data extends React.Component{ 

    constructor(){ 
     super() 
     this.state={ 
      name:'' 
     } 
    } 

    componentDidMount(){ 
     console.log('componentDidMount'); 

     var url = "http:\//localhost:3000/order/test"; 
     Request 
     .get(url) 
     .query(null) 
     .set('Accept', 'application/json') 
     .end ((error, response)=>{ 
      const title=response.text 
      console.log(JSON.stringify(title)); 

      this.setState({ 
       name:title 
      }); 
     }); 

    } 

    render(){ 
     return <div>World {this.state.name}</div>; 
    } 

} 

Hinweis: Wenn Antwort ist ein Text, den Sie haben response.text zu verwenden, wie ich in meinem Fall verwenden

Wenn Sie mehr Details wünschen click here

Verwandte Themen