我理解promises是如何工作的,并且过去曾使用过JQuery做出承诺。我正在构建一个非常简单的应用程序,它使用YouTube API来显示视频。我碰到了一堵砖墙,因为我遇到了一种情况,我需要使用一个承诺,但不知道如何。
在我的index.js文件中,我定义了一个App类,其构造函数调用API以获取与默认搜索词“national geographic”匹配的视频列表。一旦这些结果回来(需要在这里使用一个承诺),我想调用this.setSelectedVideo来获取要播放的特定视频。
// Node Modules
import React from 'react';
import ReactDOM from 'react-dom';
import YTSearch from 'youtube-api-search';
// Components
import SearchBar from './components/search_bar';
import VideoList from './components/video_list';
import VideoDetail from './components/video_detail';
const API_KEY_YOUTUBE = <MY_YOUTUBE_API_KEY>;
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
videos: [],
selectedVideo: null
};
// initialize videos: finish this up when you learn how to do redux promises
this.videoSearch('National Geographic');
this.setSelectedVideo(this.state.videos[0]);
}
videoSearch(term) {
// Make AJAX request to YouTube for a list of videos matching term.
YTSearch({ key: API_KEY_YOUTUBE, term: term }, videos => {
this.setState({ videos: videos });
});
}
setSelectedVideo(video) {
// Make AJAX request to YouTube for the specific video being played.
console.log(video);
}
render() {
return (
<div>
<div className="row margin-bottom-md">
<div className="col-12 col-lg-8">
<SearchBar onSearchTrigger={ term => this.videoSearch(term) } />
</div>
</div>
<div className="row margin-bottom-md">
<div className="col-12 col-lg-8">
<VideoDetail video={ this.state.selectedVideo } />
</div>
<div className="col-12 col-lg-4">
<VideoList
videos={ this.state.videos }
onVideoSelect={ selectedVideo => this.setSelectedVideo({ selectedVideo }) }
selectedVideo={ this.state.selectedVideo }
/>
</div>
</div>
</div>
);
}
} // App class end
// Take this component's generated HTML and put it on the page.
ReactDOM.render(<App />, document.querySelector('#react-render'));
我一直在网上四处寻找并听过一些选择。 我可以使用香草JS承诺。 2.我可以以某种方式将JQuery合并到我的应用程序中并使用其promise函数。不幸的是,我需要从NPM中包含一个单独的包管理器来执行此操作? 我听说redux有承诺功能。
这三个选项中哪一个最好/我在这里实施简单承诺的最简单方法是什么?
答案 0 :(得分:1)
未经测试,但这应该符合您的要求:
videoSearch(term) {
// Make AJAX request to YouTube for a list of videos matching term.
YTSearch({ key: API_KEY_YOUTUBE, term: term }, videos => {
this.setState({
videos: videos,
selectedVideo: videos[0]
});
});
}
来源:https://medium.com/@charlie.spencer/making-requests-to-the-youtube-api-with-react-fbd50fa8d77e
答案 1 :(得分:1)
我建议使用redux-api-middleware。 由于您使用状态容器(redux)管理应用程序,因此使用redux类型的流样式生成http请求是一个好习惯:调度操作将依次进行实际的http调用,然后相应地调用预定义的reducer 。
所以它看起来像这样:
// actions_file.js
import { RSAA } from `redux-api-middleware`;
// the action itself
export function myYoutubeAction(someArg) {
return {
[RSAA]: {
endpoint: '<YOUTUBE_API_PATH>',
method: 'GET',
types: ['REQUEST_REDUCER', 'SUCCESS_REDUCER', 'FAILURE_REDUCER']
}
}
// reducer_file.js
// this reducers is called right after http request made
'REQUEST_REDUCER': (state, action) {
const { response } = action.payload;
...
...
// DO SOME STUFF AND UPDATE STATE..
}
// this reducers is called right after http request is back
'SUCCESS_REDUCER': (state, action) {
const { response } = action.payload;
...
...
// DO SOME STUFF WITH RESPONSE AND UPDATE STATE..
}
当然你可以使用本机(或外部)http请求库(请求 - 承诺,获取),发出内联http请求(并绕过redux流),它也可以正常工作,但我认为它会在你的情况下(使用状态容器时)这样做会更麻烦,更不干净。利用redux流量并让http请求通过redux圈:调度操作(例如,http请求) - &gt; reducer中的改变状态(在请求,成功或失败之后) - &gt; 更新用户界面
希望它有所帮助。
答案 2 :(得分:0)
我真的取决于你的情况,但由于近10% of all current users不使用支持本机Promise(IE)的浏览器,我建议使用外部库。
我已经使用Bluebird很长一段时间了,我会推荐它,但有很多替代品可供选择。
我建议不要仅仅因为它的承诺功能而包含jQuery,因为它会为你的用户带来大量不必要的带宽,而其余的库却未被使用。