使用Reactjs和ajax

时间:2016-07-17 21:02:59

标签: ajax reactjs

我是javascript的新手,正在开发一个实时搜索应用,我正在使用反应来获取搜索结果。 我使用ajax从URL获取数据,因为我不得不使用jsonp来绕过服务器约束。虽然我能够在我的searchForTerm函数中获得console.log中的结果但​​不能在render函数中获取结果,因为我无法正确地将它绑定到我的变量。所以我无法在屏幕上得到我想要的结果。

请查看我的jsfiddle

这是我的代码:

// var test = {};
// var json = {"F": {"symbol": "F", "name": "Ford Motor", "bidPrice": 13.43, "askPrice": 13.52}};
// test.data = [json];
// If i use the above variable and feed them to data during initialization,
// then it works. But when i get the same data from server i am not able to
// get the same update on my screen.


var SearchStock = React.createClass({

    getInitialState: function() {
        return {searchString: '', data: [], quantity: ''};
    },

    componentWillMount: function() {
        // Get the initial terms
        this.doSearch();
    },

    componentWillUnmount: function() {
        this.serverRequest.abort();
    },

    doSearch: function(term) {
        this.serverRequest = this.searchForTerm(term || '').then(this.handleSearchResult);
    },

    searchForTerm: function (term) {
    var url = 'http://data.benzinga.com/rest/richquoteDelayed?symbols=' + term;
    return $.ajax({
        url,
        dataType: 'jsonp',
        success: function (data) {
            console.log("in search", JSON.stringify(data));
            this.setState({data: [JSON.stringify(data)]});
            }.bind(this)
        });
    },

    handleSearchResult: function(quote) {
        this.setState(quote);
    },

    handleChange: function(e) {
        this.setState({searchString: e.target.value});

        // The server doesn't seem to respond to lowercase values
        this.doSearch(e.target.value.toUpperCase());
    },

    buy: function(e){
        if(!term.quantity){
            term.quantity = e;
        } else {
            term.quantity = term.quantity + e;
        }
        return term.quantity;
    },

    sell: function(e){
        term.quantity = term.quantity - e;
        return term.quantity;
    },

    viewStock: function(e){
        searchForTerm(e);
    },

    render: function() {
        var stocks = this.state.data;
        console.log("in render", stocks);

        var searchString = this.state.searchString.trim().toLowerCase();

        if (searchString.length > 0) {
            stocks = stocks.filter(function(l) {
                // return l.name.toLowerCase().match(searchString);
                return l[Object.keys(l)[0]]["symbol"].toLowerCase().match(searchString);
            });
        }

        return (
            <div>
                <div id='searchResult'>
                    <input type="text" value={this.state.searchString} onChange={this.handleChange} placeholder="Type here" />
                    <ul>
                        {stocks.map(function(l) {
                            return <div>
                                <h3>{l[Object.keys(l)[0]]["name"]}</h3>
                                <table class="table  table-striped table-bordered">
                                    <tr>
                                        <th>Bid</th>
                                        <th>Ask</th>
                                    </tr>
                                    <tr>
                                        <td>{l[Object.keys(l)[0]]["bidPrice"]}</td>
                                        <td>{l[Object.keys(l)[0]]["askPrice"]}</td>
                                    </tr>
                                </table>
                            </div>
                        })}
                    </ul>
                    <input type="text" value={this.state.quantity} placeholder="Quantity" />
                    <input type="button" value="Buy" onClick={this.buy} />
                    <input type="button" value="Sell" onClick={this.sell} />
                </div>
                <div id='currentPorfolio'>
                    <h5>Current Portfolio</h5>
                    <h5>$100,000 This needs a disabled text box with value comming from a variable with initial value as $100000</h5>
                    <table class="table  table-striped table-bordered">
                        <tr>
                            <th>Company</th>
                            <th>Quantity</th>
                            <th>Price Paid</th>
                            <th></th>
                        </tr>
                        {stocks.map(function(l) {
                            return <tr>
                                <td>{l[Object.keys(l)[0]]["name"]}</td>
                                <td>{l[Object.keys(l)[0]]["quantity"]}</td>
                                <td>{l[Object.keys(l)[0]]["bidPrice"]}</td>
                                <td>{<input type="button" value="View Stock"/>}</td>
                            </tr>
                        })}
                    </table>
                </div>
            </div>
        );
    }
});

ReactDOM.render( <SearchStock />, document.getElementById('container'));

我认为这应该与变量范围及其更新方式有关。但我很感激,如果有人可以帮助我,因为我可以在控制台日志中看到结果,但不能在屏幕上看到。

我必须在此之后进行debouncing,因为现在即使没有变化,这也是向服务器发送请求。有没有更好的方法使用handleChange只在文本框发生变化时调用?

道歉,如果我在这里遗漏了一些东西,因为我对javascript很新并做出反应。而且我一直对javascript处理范围的方式感到困惑。

2 个答案:

答案 0 :(得分:1)

这里有一些问题,第一个可能是this没有引用jQuery的ajax()方法中的React组件(我无法分辨,因为URL不适用于我)。

试试这个,它将从jQuery代码外部引用setState。

searchForTerm: function (term) {
    const setState = state => this.setState(state);
    var url = 'http://data.benzinga.com/rest/richquoteDelayed?symbols=' + term;
    return $.ajax({
    url,
    dataType: 'jsonp',
    success: function (data) {// your code here
        console.log("in search", JSON.stringify(data));
        setState({data: [JSON.stringify(data)]});
        }.bind(this)
    });
},

如果这没有帮助,我建议修复控制台中显示的所有错误,或删除导致它们的所有代码(例如)。如果有一个简单的例子表明你的工作没有按预期发挥作用,那么其他人就会更容易提供帮助。

您将遇到的另一个问题是变量的作用域是定义它们的函数。因此,在buy()sell()中,term未定义。

答案 1 :(得分:0)

我能够使用onBlur而不是onChange进行反应。这是我提到的一篇文章,它帮助我们理解javascripts onchange()的不同之处,并对onChange()属性做出反应,以及react中的onBlur()如何等同于javascript的onchange()。

How to "onchange" in ReactJS

我希望这可以帮助那些在两种功能之间感到困惑的人。