2016-06-20 7 views
2

Ich habe die folgende Route: -Wie wird eine Komponente neu geladen, reagiert auf URL-Parameteränderung?

ReactDOM.render((
    <Router history={browserHistory}> 
     <Route path="/" component={app}> 
     <IndexRoute component={home}/> 
     <Route path="/articles" component={articles} /> 
     <Route path="/articles/topics/:featureName" component={filteredArticles} /> 
     </Route> 
    </Router> 
), document.getElementById('app')); 

Jetzt, als ich für/articles/Themen/topic1 anfordern, die ersten 5 Inhalte abgerufen werden API-Aufruf. Wenn der Benutzer den unteren Rand der Seite erneut erreicht, wird ein API-Aufruf durchgeführt, bei dem die nächsten 5 Inhalte abgerufen werden. Dies funktioniert gut (Beachten Sie, dass die Grindscroll-Funktion für die Seite unten überprüft, die einige kleinere Probleme so kommentiert hat.)

Jetzt sagen, ich wähle das nächste Thema aus der Liste, so ändert sich die URL, also meine URL Änderungen an/articles/topics/topic2, jetzt brauche ich das gleiche wie oben erwähnt und apis für dieses Thema aufrufen.

Folgende ist mein aktueller Komponentencode: -

import React from 'react'; 
import axios from 'axios'; 
import ArticleList from './ArticleList'; 
import Banner from './Banner'; 
import LeftNavBar from './LeftNavBar'; 
import RightNavbar from './RightNavbar'; 
import {url} from './Constants'; 


/*MERGE INTO ARTICLES ONCE SCROLL LOGIC IS FIXED*/ 
class FilteredArticles extends React.Component{ 

    constructor(){ 
    super(); 
    {/* Adding global event listener,binding it to scroll event and adding it to handleScroll function */} 
    /*window.addEventListener("scroll", this._handleScroll.bind(this));*/ 
    this.state ={ 
     articles : [], 
     loadingFlag:false, 
     limit : 5, 
     offset :0, 
     subFeatureName:[], 
     flag: false 
    } 
    } 


    _getContent(){ 
    let self=this; 
    axios.get(url+'/articles/filter/?filter=popular&category='+this.props.params.featureName+'&limit='+this.state.limit+'&offset='+this.state.offset) 
    .then(function(response){ 
     /*Checking if limit has exceeded meta count, if it has stopped we dont call the APIS*/ 
     if(self.state.limit >= response.data.meta.total_count){ 
      self.setState({articles : self.state.articles.concat(response.data.results), 
       offset : self.state.limit, 
       limit: self.state.limit+self.state.offset, 
       subFeatureName: self.props.params.featureName, 
       loadingFlag: false} 
     ) 
     } 
     else{ 
      self.setState({articles : self.state.articles.concat(response.data.results), 
       offset : self.state.limit, 
       limit: self.state.limit+self.state.offset, 
       subFeatureName: self.props.params.featureName, 
       loadingFlag: true} 
      ) 
     } 
    }) 
    .catch(function(error){ 
     console.log(error); 
    }); 
    } 



    _handleScroll(){ 
    /*Calling 5 more articles when someone scrolls down and reaches the page end 
    const windowHeight = window.innerHeight; 
    const scrollT = $(window).scrollTop(); 
    if(windowHeight- scrollT < 200){ 
     if(!this.state.loadingFlag){ 
     this.setState({loadingFlag : true}); 
     this._getContent(); 
     } 
    }*/ 
} 

    componentDidMount(){ 
    /*calling _getContent function to get first five articles on page load*/ 
    console.log("got content"); 
    this._getContent(); 
    } 

    render(){ 
    console.log("inside render"); 
    return(
     <div> 
     <Banner title="Article Page"/> 
     <div className="content-container"> 
      <LeftNavBar/> 
      <div className ="feeds"> 
      <div className="card"> 
       {/* Sending hideSeeAll as prop to remove see all button on main article page*/} 
       <ArticleList articles={this.state.articles} hideSeeAll='true' keyword="Top Articles"/> 
      </div> 
      </div> 
      <RightNavbar/> 
     </div> 
     </div> 
    ) 
} 
} 

export default FilteredArticles; 

Also im Grunde ich zu verstehen versuche, dass, wenn ich eine Route habe wie /articles/Themen /: Feature und nenne ich eine Seite wie/Artikel/topics/topic1 oder/articles/topics/topic2, kann die Komponente realoaded werden (Ich muss andere API aufrufen, holen Inhalt noch einmal).

Das heißt, für/articles/Themen/topic1 der API genannt ist

/api/v0/articles/Filter /? Filter = beliebte & Kategorie = topic1 & Grenze = 5 & offset = 0

und/articles/Themen/Thema2 der API genannt

/api/v0/articles/Filter /? filter = beliebte & Kategorie = Thema2 & Grenze = 5 & Offset = 0

Gibt es eine Möglichkeit, dies zu erreichen?

Antwort

3

Sie sollten nicht wirklich die API abfragen/den Zustand der Komponenten auf diese Weise aktualisieren, aber hey, das ist eine ganz andere Frage. Vielleicht in Betracht ziehen, einen Flux Ansatz zu verwenden.

Wie auch immer, können Sie die componentWillReceiveProps (nextProps) Lebenszyklus-Methode verwenden, um die Router nextProps params zu empfangen und Ihre API abfragen wieder:

componentWillReceiveProps(nextProps) { 
    this._getContent(nextProps.params.featureName); 
} 

_getContent(featureName) { 
...query your API 
} 
+0

ich das versucht: - componentWillReceiveProps (nextProps) { console.log ("hier"); console.log ("Requisiten" + nextProps.params.featureName); this.setState ({ Artikel: [], loadingFlag: false, Grenze: 5, Offset: 0, subFeatureName [], Flag: false }); console.log ("nach dem Empfang" + JSON.stringify (this.state)); this._getContent (nextProps.params.FeatureName); } aber der Status wird nicht aktualisiert, wenn ich nach dem Aufrufen von SetState –

+0

drucken versuchte SetState() nicht sofort mutieren this.state aber erstellt einen ausstehenden Statusübergang. Der Zugriff auf this.state nach dem Aufruf dieser Methode kann möglicherweise den vorhandenen Wert zurückgeben. – Mark

+0

dann wie soll ich das verwenden? es verwendet alte Daten, um die API aufzurufen –

1

Auch wenn Sie Redux verwenden, stellen Sie einen Scheck wie dies eine Endlosschleife zu vermeiden:

componentWillReceiveProps(newProps) { 
    if (this.props.someValue === newProps.someValue) { 
     this.props.fetchSomething(newProps.params.somethingName); 
    } 
} 
+2

sollte vielleicht 'this.props.someValue! == newProps.someValue' sein, mit der! ...? – Winter

Verwandte Themen