commit
bc223da3d0
@ -16,6 +16,7 @@
|
||||
"react": "^15.3.2",
|
||||
"react-bootstrap": "^0.30.6",
|
||||
"react-dom": "^15.3.2",
|
||||
"react-loading": "^0.0.9",
|
||||
"react-redux": "^4.4.6",
|
||||
"react-redux-form": "^1.2.4",
|
||||
"react-router": "^3.0.0",
|
||||
|
@ -2,11 +2,14 @@ package extmedias
|
||||
|
||||
import (
|
||||
"database/sql"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net/http"
|
||||
|
||||
"gitlab.quimbo.fr/odwrtw/canape-sql/src/internal/auth"
|
||||
"gitlab.quimbo.fr/odwrtw/canape-sql/src/internal/movies"
|
||||
"gitlab.quimbo.fr/odwrtw/canape-sql/src/internal/shows"
|
||||
"gitlab.quimbo.fr/odwrtw/canape-sql/src/internal/users"
|
||||
|
||||
"gitlab.quimbo.fr/odwrtw/canape-sql/src/internal/web"
|
||||
|
||||
@ -89,12 +92,19 @@ func GetMediaIDs(env *web.Env, mediaType string, source string, category string,
|
||||
}
|
||||
|
||||
// GetMovies get some movies
|
||||
func GetMovies(env *web.Env, source string, category string, force bool) ([]*movies.Movie, error) {
|
||||
func GetMovies(env *web.Env, user *users.User, source string, category string, force bool) ([]*movies.Movie, error) {
|
||||
movieIds, err := GetMediaIDs(env, "movie", source, category, force)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Get the URLs from polochon, we don't really care if it fails for now
|
||||
var urls map[string]string
|
||||
urls, err = movies.GetPolochonMoviesURLs(user)
|
||||
if err != nil {
|
||||
env.Log.Errorf("error while getting polochon movies url: %s", err)
|
||||
}
|
||||
|
||||
movieList := []*movies.Movie{}
|
||||
for _, id := range movieIds {
|
||||
movie := movies.New(id)
|
||||
@ -108,6 +118,13 @@ func GetMovies(env *web.Env, source string, category string, force bool) ([]*mov
|
||||
env.Log.Errorf("error while getting movie torrents : %s", err)
|
||||
continue
|
||||
}
|
||||
|
||||
if urls != nil {
|
||||
if url, ok := urls[id]; ok {
|
||||
movie.PolochonURL = url
|
||||
}
|
||||
}
|
||||
|
||||
movieList = append(movieList, movie)
|
||||
}
|
||||
return movieList, nil
|
||||
@ -157,10 +174,16 @@ func Explore(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
category = "popular"
|
||||
}
|
||||
|
||||
v := auth.GetCurrentUser(r, env.Log)
|
||||
user, ok := v.(*users.User)
|
||||
if !ok {
|
||||
return env.RenderError(w, errors.New("invalid user"))
|
||||
}
|
||||
|
||||
// Get the medias without trying to refresh them
|
||||
movies, err := GetMovies(env, source, category, false)
|
||||
movies, err := GetMovies(env, user, source, category, false)
|
||||
if err != nil {
|
||||
return err
|
||||
return env.RenderError(w, err)
|
||||
}
|
||||
|
||||
return env.RenderJSON(w, movies)
|
||||
@ -188,7 +211,7 @@ func ExploreShows(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
// Get the medias without trying to refresh them
|
||||
shows, err := GetShows(env, source, category, false)
|
||||
if err != nil {
|
||||
return err
|
||||
return env.RenderError(w, err)
|
||||
}
|
||||
|
||||
return env.RenderJSON(w, shows)
|
||||
@ -218,13 +241,19 @@ func Refresh(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
category = "popular"
|
||||
}
|
||||
|
||||
v := auth.GetCurrentUser(r, env.Log)
|
||||
user, ok := v.(*users.User)
|
||||
if !ok {
|
||||
return fmt.Errorf("invalid user type")
|
||||
}
|
||||
|
||||
// We'll refresh the medias for each sources
|
||||
for _, source := range MediaSources {
|
||||
env.Log.Debugf("refreshing %s", source)
|
||||
// GetMedias and refresh them
|
||||
_, err := GetMovies(env, source, category, true)
|
||||
_, err := GetMovies(env, user, source, category, true)
|
||||
if err != nil {
|
||||
return err
|
||||
return env.RenderError(w, err)
|
||||
}
|
||||
}
|
||||
|
||||
@ -250,7 +279,7 @@ func RefreshShows(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
// GetMedias and refresh them
|
||||
_, err := GetShows(env, source, category, true)
|
||||
if err != nil {
|
||||
return err
|
||||
return env.RenderError(w, err)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
package movies
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net"
|
||||
@ -63,6 +64,21 @@ func getPolochonMovies(user *users.User) ([]*Movie, error) {
|
||||
return movies, nil
|
||||
}
|
||||
|
||||
// GetPolochonMoviesURLs returns the polochon urls associated with an imdb id
|
||||
func GetPolochonMoviesURLs(user *users.User) (map[string]string, error) {
|
||||
movies, err := getPolochonMovies(user)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
urls := make(map[string]string, len(movies))
|
||||
for _, movie := range movies {
|
||||
urls[movie.ImdbID] = movie.PolochonURL
|
||||
}
|
||||
|
||||
return urls, nil
|
||||
}
|
||||
|
||||
// FromPolochon will returns movies from Polochon
|
||||
func FromPolochon(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
v := auth.GetCurrentUser(r, env.Log)
|
||||
@ -113,15 +129,28 @@ func GetDetailsHandler(env *web.Env, w http.ResponseWriter, r *http.Request) err
|
||||
|
||||
// SearchMovie will search movie
|
||||
func SearchMovie(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
key := r.FormValue("key")
|
||||
if key == "" {
|
||||
var data struct {
|
||||
Key string `json:"key"`
|
||||
}
|
||||
err := json.NewDecoder(r.Body).Decode(&data)
|
||||
if err != nil {
|
||||
return env.RenderError(w, errors.New("failed to get the search key"))
|
||||
}
|
||||
|
||||
if data.Key == "" {
|
||||
return env.RenderError(w, errors.New("no given key"))
|
||||
}
|
||||
|
||||
v := auth.GetCurrentUser(r, env.Log)
|
||||
user, ok := v.(*users.User)
|
||||
if !ok {
|
||||
return env.RenderError(w, errors.New("invalid user"))
|
||||
}
|
||||
|
||||
var movies []*polochon.Movie
|
||||
searchers := env.Config.MovieSearchers
|
||||
for _, searcher := range searchers {
|
||||
result, err := searcher.SearchMovie(key, env.Log)
|
||||
result, err := searcher.SearchMovie(data.Key, env.Log)
|
||||
if err != nil {
|
||||
env.Log.Errorf("error while searching movie : %s", err)
|
||||
continue
|
||||
@ -129,7 +158,14 @@ func SearchMovie(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
movies = append(movies, result...)
|
||||
}
|
||||
|
||||
env.Log.Debugf("got %d movies doing search %q", len(movies), key)
|
||||
// Get the URLs from polochon, we don't really care if it fails for now
|
||||
var urls map[string]string
|
||||
urls, err = GetPolochonMoviesURLs(user)
|
||||
if err != nil {
|
||||
env.Log.Errorf("error while getting polochon movies url: %s", err)
|
||||
}
|
||||
|
||||
env.Log.Debugf("got %d movies doing search %q", len(movies), data.Key)
|
||||
movieList := []*Movie{}
|
||||
for _, m := range movies {
|
||||
movie := New(m.ImdbID)
|
||||
@ -143,6 +179,13 @@ func SearchMovie(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
env.Log.Errorf("error while getting movie torrents : %s", err)
|
||||
continue
|
||||
}
|
||||
|
||||
if urls != nil {
|
||||
if url, ok := urls[m.ImdbID]; ok {
|
||||
movie.PolochonURL = url
|
||||
}
|
||||
}
|
||||
|
||||
movieList = append(movieList, movie)
|
||||
}
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
package shows
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"net/http"
|
||||
|
||||
@ -27,15 +28,21 @@ func GetDetailsHandler(env *web.Env, w http.ResponseWriter, r *http.Request) err
|
||||
|
||||
// SearchShow will search a show
|
||||
func SearchShow(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
key := r.FormValue("key")
|
||||
if key == "" {
|
||||
var data struct {
|
||||
Key string `json:"key"`
|
||||
}
|
||||
if err := json.NewDecoder(r.Body).Decode(&data); err != nil {
|
||||
return env.RenderError(w, errors.New("failed to get the search key"))
|
||||
}
|
||||
|
||||
if data.Key == "" {
|
||||
return env.RenderError(w, errors.New("no given key"))
|
||||
}
|
||||
|
||||
var shows []*polochon.Show
|
||||
searchers := env.Config.ShowSearchers
|
||||
for _, searcher := range searchers {
|
||||
result, err := searcher.SearchShow(key, env.Log)
|
||||
result, err := searcher.SearchShow(data.Key, env.Log)
|
||||
if err != nil {
|
||||
env.Log.Errorf("error while searching show : %s", err)
|
||||
continue
|
||||
@ -43,7 +50,7 @@ func SearchShow(env *web.Env, w http.ResponseWriter, r *http.Request) error {
|
||||
shows = append(shows, result...)
|
||||
}
|
||||
|
||||
env.Log.Debugf("got %d shows doing search %q", len(shows), key)
|
||||
env.Log.Debugf("got %d shows doing search %q", len(shows), data.Key)
|
||||
showList := []*Show{}
|
||||
for _, s := range shows {
|
||||
show := New(s.ImdbID)
|
||||
|
24
src/main.go
24
src/main.go
@ -71,22 +71,24 @@ func main() {
|
||||
|
||||
authMiddleware := auth.NewMiddleware(env.Auth, log)
|
||||
|
||||
// TODO: refresh sould be handled by admins only
|
||||
|
||||
env.Handle("/users/login", users.LoginPOSTHandler).Methods("POST")
|
||||
env.Handle("/users/signup", users.SignupPOSTHandler).Methods("POST")
|
||||
env.Handle("/users/details", users.DetailsHandler).WithRole(users.UserRole)
|
||||
env.Handle("/users/edit", users.EditHandler).WithRole(users.UserRole)
|
||||
env.Handle("/users/details", users.DetailsHandler).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/users/edit", users.EditHandler).WithRole(users.UserRole).Methods("POST")
|
||||
|
||||
env.Handle("/movies/polochon", movies.FromPolochon).WithRole(users.UserRole)
|
||||
env.Handle("/movies/{id:tt[0-9]+}/get_details", movies.GetDetailsHandler).WithRole(users.UserRole)
|
||||
env.Handle("/movies/explore", extmedias.Explore)
|
||||
env.Handle("/movies/refresh", extmedias.Refresh)
|
||||
env.Handle("/movies/search", movies.SearchMovie)
|
||||
env.Handle("/movies/polochon", movies.FromPolochon).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/movies/{id:tt[0-9]+}/get_details", movies.GetDetailsHandler).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/movies/explore", extmedias.Explore).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/movies/refresh", extmedias.Refresh).WithRole(users.UserRole).Methods("POST")
|
||||
env.Handle("/movies/search", movies.SearchMovie).WithRole(users.UserRole).Methods("POST")
|
||||
|
||||
// env.Handle("/shows/polochon", shows.FromPolochon).WithRole(users.UserRole)
|
||||
env.Handle("/shows/{id:tt[0-9]+}", shows.GetDetailsHandler)
|
||||
env.Handle("/shows/refresh", extmedias.RefreshShows)
|
||||
env.Handle("/shows/explore", extmedias.ExploreShows)
|
||||
env.Handle("/shows/search", shows.SearchShow)
|
||||
env.Handle("/shows/{id:tt[0-9]+}", shows.GetDetailsHandler).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/shows/refresh", extmedias.RefreshShows).WithRole(users.UserRole).Methods("POST")
|
||||
env.Handle("/shows/explore", extmedias.ExploreShows).WithRole(users.UserRole).Methods("GET")
|
||||
env.Handle("/shows/search", shows.SearchShow).WithRole(users.UserRole).Methods("POST")
|
||||
|
||||
n := negroni.Classic()
|
||||
n.Use(authMiddleware)
|
||||
|
@ -80,6 +80,13 @@ export function selectMovie(imdbId) {
|
||||
}
|
||||
}
|
||||
|
||||
export function searchMovies(search) {
|
||||
return request(
|
||||
'SEARCH_MOVIES',
|
||||
configureAxios().post('/movies/search', search)
|
||||
)
|
||||
}
|
||||
|
||||
export function getMovieDetails(imdbId) {
|
||||
return request(
|
||||
'MOVIE_GET_DETAILS',
|
||||
@ -105,6 +112,13 @@ export function fetchShows(url) {
|
||||
)
|
||||
}
|
||||
|
||||
export function searchShows(search) {
|
||||
return request(
|
||||
'SEARCH_SHOWS',
|
||||
configureAxios().post('/shows/search', search)
|
||||
)
|
||||
}
|
||||
|
||||
export function fetchShowDetails(imdbId) {
|
||||
return request(
|
||||
'SHOW_FETCH_DETAILS',
|
||||
|
@ -83,14 +83,19 @@ const MovieListPopular = (props) => (
|
||||
const MovieListPolochon = (props) => (
|
||||
<MovieList {...props} moviesUrl='/movies/polochon'/>
|
||||
)
|
||||
const MovieListSearch = (props) => (
|
||||
<MovieList {...props} />
|
||||
)
|
||||
|
||||
const ShowListPopular = (props) => (
|
||||
<ShowList {...props} showsUrl='/shows/explore'/>
|
||||
)
|
||||
|
||||
const ShowDetailsView = (props) => (
|
||||
<ShowDetails {...props} />
|
||||
)
|
||||
const ShowListSearch = (props) => (
|
||||
<ShowList {...props} />
|
||||
)
|
||||
|
||||
ReactDOM.render((
|
||||
<Provider store={store}>
|
||||
@ -100,8 +105,10 @@ ReactDOM.render((
|
||||
<Route path="/users/login" component={UserLoginForm} />
|
||||
<Route path="/users/signup" component={UserSignUp} />
|
||||
<Route path="/users/edit" component={UserIsAuthenticated(UserEdit)} />
|
||||
<Route path="/movies/search/:search" component={UserIsAuthenticated(MovieListSearch)} />
|
||||
<Route path="/movies/popular" component={UserIsAuthenticated(MovieListPopular)} />
|
||||
<Route path="/movies/polochon(/:page)" component={UserIsAuthenticated(MovieListPolochon)} />
|
||||
<Route path="/shows/search/:search" component={UserIsAuthenticated(ShowListSearch)} />
|
||||
<Route path="/shows/popular" component={UserIsAuthenticated(ShowListPopular)} />
|
||||
<Route path="/shows/details/:imdbId" component={UserIsAuthenticated(ShowDetailsView)} />
|
||||
</Route>
|
||||
|
@ -1,6 +1,10 @@
|
||||
import React from 'react'
|
||||
|
||||
export default function ListDetails(props) {
|
||||
let genres;
|
||||
if (props.data.genres) {
|
||||
genres = props.data.genres.join(', ');
|
||||
}
|
||||
return (
|
||||
<div className="col-xs-7 col-md-4">
|
||||
<div className="show-detail affix">
|
||||
@ -12,6 +16,12 @@ export default function ListDetails(props) {
|
||||
{props.data.runtime} min
|
||||
</p>
|
||||
}
|
||||
{props.data.genres &&
|
||||
<p>
|
||||
<i className="fa fa-tags"></i>
|
||||
{genres}
|
||||
</p>
|
||||
}
|
||||
<p>
|
||||
<i className="fa fa-star-o"></i>
|
||||
{props.data.rating} <small>({props.data.votes} counts)</small>
|
||||
|
17
src/public/js/components/loader/loader.js
Normal file
17
src/public/js/components/loader/loader.js
Normal file
@ -0,0 +1,17 @@
|
||||
import React from 'react'
|
||||
import Loading from 'react-loading'
|
||||
|
||||
export default function Loader() {
|
||||
return (
|
||||
<div className="row" id="container">
|
||||
<div className="col-md-6 col-md-offset-3">
|
||||
<Loading
|
||||
type="bars"
|
||||
height="100%"
|
||||
width="100%"
|
||||
color="#EBEBEB"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
@ -2,6 +2,7 @@ import React from 'react'
|
||||
|
||||
import ListPosters from '../list/posters'
|
||||
import ListDetails from '../list/details'
|
||||
import Loader from '../loader/loader'
|
||||
|
||||
class MovieButtons extends React.Component {
|
||||
constructor(props) {
|
||||
@ -53,7 +54,24 @@ class MovieButtons extends React.Component {
|
||||
|
||||
export default class MovieList extends React.Component {
|
||||
componentWillMount() {
|
||||
this.props.fetchMovies(this.props.moviesUrl);
|
||||
if (this.props.moviesUrl) {
|
||||
this.props.fetchMovies(this.props.moviesUrl);
|
||||
} else if (this.props.params && this.props.params.search != "") {
|
||||
this.props.searchMovies({
|
||||
key: this.props.params.search
|
||||
});
|
||||
}
|
||||
}
|
||||
componentWillUpdate(nextProps, nextState) {
|
||||
if (!nextProps.params || nextProps.params.search === "") {
|
||||
return
|
||||
}
|
||||
if (this.props.params.search === nextProps.params.search) {
|
||||
return
|
||||
}
|
||||
this.props.searchMovies({
|
||||
key: nextProps.params.search
|
||||
});
|
||||
}
|
||||
render() {
|
||||
const movies = this.props.movieStore.movies;
|
||||
@ -63,6 +81,12 @@ export default class MovieList extends React.Component {
|
||||
index = 0;
|
||||
}
|
||||
const selectedMovie = movies[index];
|
||||
|
||||
// Loading
|
||||
if (this.props.movieStore.loading) {
|
||||
return (<Loader />);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="row" id="container">
|
||||
<ListPosters
|
||||
|
@ -1,15 +1,37 @@
|
||||
import React from 'react'
|
||||
import { Link } from 'react-router'
|
||||
import { store } from '../store'
|
||||
import { isUserLoggedIn } from '../actions/actionCreators'
|
||||
|
||||
import { Nav, Navbar, NavItem, NavDropdown, MenuItem } from 'react-bootstrap'
|
||||
import { LinkContainer } from 'react-router-bootstrap'
|
||||
import { Control, Form } from 'react-redux-form';
|
||||
|
||||
export default class NavBar extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.handleMovieSearch = this.handleMovieSearch.bind(this);
|
||||
this.handleShowSearch = this.handleShowSearch.bind(this);
|
||||
}
|
||||
handleMovieSearch() {
|
||||
this.props.router.push(`/movies/search/${encodeURI(this.props.movieStore.search)}`)
|
||||
}
|
||||
handleShowSearch() {
|
||||
this.props.router.push(`/shows/search/${encodeURI(this.props.showStore.search)}`)
|
||||
}
|
||||
render() {
|
||||
const username = this.props.userStore.username;
|
||||
const isLoggedIn = username !== "" ? true : false;
|
||||
const location = this.props.router.getCurrentLocation().pathname;
|
||||
let displayMovieSearch = false;
|
||||
let displayShowSearch = false;
|
||||
if (isLoggedIn && location.indexOf("movies") > -1)
|
||||
{
|
||||
displayMovieSearch = true;
|
||||
}
|
||||
if (isLoggedIn && location.indexOf("shows") > -1)
|
||||
{
|
||||
displayShowSearch = true;
|
||||
}
|
||||
return (
|
||||
<div>
|
||||
<Navbar fluid fixedTop collapseOnSelect>
|
||||
@ -53,6 +75,30 @@ export default class NavBar extends React.Component {
|
||||
</NavDropdown>
|
||||
}
|
||||
</Nav>
|
||||
{displayMovieSearch &&
|
||||
<Navbar.Form pullRight>
|
||||
<Form model="movieStore" className="input-group" onSubmit={() => this.handleMovieSearch()}>
|
||||
<Control.text
|
||||
model="movieStore.search"
|
||||
className="form-control"
|
||||
placeholder="Search movies"
|
||||
updateOn="change"
|
||||
/>
|
||||
</Form>
|
||||
</Navbar.Form>
|
||||
}
|
||||
{displayShowSearch &&
|
||||
<Navbar.Form pullRight>
|
||||
<Form model="showStore" className="input-group" onSubmit={() => this.handleShowSearch()}>
|
||||
<Control.text
|
||||
model="showStore.search"
|
||||
className="form-control"
|
||||
placeholder="Search shows"
|
||||
updateOn="change"
|
||||
/>
|
||||
</Form>
|
||||
</Navbar.Form>
|
||||
}
|
||||
</Navbar.Collapse>
|
||||
</Navbar>
|
||||
</div>
|
||||
|
@ -1,10 +1,15 @@
|
||||
import React from 'react'
|
||||
import Loader from '../loader/loader'
|
||||
|
||||
export default class ShowDetails extends React.Component {
|
||||
componentWillMount() {
|
||||
this.props.fetchShowDetails(this.props.params.imdbId);
|
||||
}
|
||||
render() {
|
||||
// Loading
|
||||
if (this.props.showStore.loading) {
|
||||
return (<Loader />);
|
||||
}
|
||||
return (
|
||||
<div className="row" id="container">
|
||||
<Header data={this.props.showStore.show} />
|
||||
|
@ -3,6 +3,7 @@ import { Link } from 'react-router'
|
||||
|
||||
import ListDetails from '../list/details'
|
||||
import ListPosters from '../list/posters'
|
||||
import Loader from '../loader/loader'
|
||||
|
||||
function ShowButtons(props) {
|
||||
const imdbLink = `http://www.imdb.com/title/${props.show.imdb_id}`;
|
||||
@ -20,7 +21,24 @@ function ShowButtons(props) {
|
||||
|
||||
export default class ShowList extends React.Component {
|
||||
componentWillMount() {
|
||||
this.props.fetchShows(this.props.showsUrl);
|
||||
if (this.props.showsUrl) {
|
||||
this.props.fetchShows(this.props.showsUrl);
|
||||
} else if (this.props.params && this.props.params.search != "") {
|
||||
this.props.searchShows({
|
||||
key: this.props.params.search
|
||||
});
|
||||
}
|
||||
}
|
||||
componentWillUpdate(nextProps, nextState) {
|
||||
if (!nextProps.params || nextProps.params.search === "") {
|
||||
return
|
||||
}
|
||||
if (this.props.params.search === nextProps.params.search) {
|
||||
return
|
||||
}
|
||||
this.props.searchShows({
|
||||
key: nextProps.params.search
|
||||
});
|
||||
}
|
||||
render() {
|
||||
const shows = this.props.showStore.shows;
|
||||
@ -30,6 +48,12 @@ export default class ShowList extends React.Component {
|
||||
index = 0;
|
||||
}
|
||||
const selectedShow = shows[index];
|
||||
|
||||
// Loading
|
||||
if (this.props.showStore.loading) {
|
||||
return (<Loader />);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="row" id="container">
|
||||
<ListPosters
|
||||
|
@ -1,13 +1,19 @@
|
||||
const defaultState = {
|
||||
loading: false,
|
||||
movies: [],
|
||||
filter: "",
|
||||
perPage: 30,
|
||||
selectedImdbId: "",
|
||||
fetchingDetails: false,
|
||||
search: "",
|
||||
};
|
||||
|
||||
export default function movieStore(state = defaultState, action) {
|
||||
switch (action.type) {
|
||||
case 'MOVIE_LIST_FETCH_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
loading: true,
|
||||
})
|
||||
case 'MOVIE_LIST_FETCH_FULFILLED':
|
||||
let selectedImdbId = "";
|
||||
// Select the first movie
|
||||
@ -17,6 +23,16 @@ export default function movieStore(state = defaultState, action) {
|
||||
return Object.assign({}, state, {
|
||||
movies: action.payload.data,
|
||||
selectedImdbId: selectedImdbId,
|
||||
loading: false,
|
||||
})
|
||||
case 'SEARCH_MOVIES_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
loading: true,
|
||||
})
|
||||
case 'SEARCH_MOVIES_FULFILLED':
|
||||
return Object.assign({}, state, {
|
||||
movies: action.payload.data,
|
||||
loading: false,
|
||||
})
|
||||
case 'MOVIE_GET_DETAILS_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
|
@ -1,4 +1,5 @@
|
||||
const defaultState = {
|
||||
loading: false,
|
||||
shows: [],
|
||||
filter: "",
|
||||
perPage: 30,
|
||||
@ -6,10 +7,15 @@ const defaultState = {
|
||||
show: {
|
||||
seasons: [],
|
||||
},
|
||||
search: "",
|
||||
};
|
||||
|
||||
export default function showStore(state = defaultState, action) {
|
||||
switch (action.type) {
|
||||
case 'SHOW_LIST_FETCH_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
loading: true,
|
||||
})
|
||||
case 'SHOW_LIST_FETCH_FULFILLED':
|
||||
let selectedImdbId = "";
|
||||
// Select the first show
|
||||
@ -19,12 +25,26 @@ export default function showStore(state = defaultState, action) {
|
||||
return Object.assign({}, state, {
|
||||
shows: action.payload.data,
|
||||
selectedImdbId: selectedImdbId,
|
||||
loading: false,
|
||||
})
|
||||
case 'SHOW_FETCH_DETAILS_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
loading: true,
|
||||
})
|
||||
case 'SHOW_FETCH_DETAILS_FULFILLED':
|
||||
return Object.assign({}, state, {
|
||||
show: sortEpisodes(action.payload.data),
|
||||
loading: false,
|
||||
})
|
||||
case 'SEARCH_SHOWS_PENDING':
|
||||
return Object.assign({}, state, {
|
||||
loading: true,
|
||||
})
|
||||
case 'SEARCH_SHOWS_FULFILLED':
|
||||
return Object.assign({}, state, {
|
||||
shows: action.payload.data,
|
||||
loading: false,
|
||||
})
|
||||
return state;
|
||||
case 'SELECT_SHOW':
|
||||
// Don't select the show if we're fetching another show's details
|
||||
if (state.fetchingDetails) {
|
||||
|
@ -3081,6 +3081,10 @@ react-dom@^15.3.2:
|
||||
version "15.3.2"
|
||||
resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-15.3.2.tgz#c46b0aa5380d7b838e7a59c4a7beff2ed315531f"
|
||||
|
||||
react-loading:
|
||||
version "0.0.9"
|
||||
resolved "https://registry.yarnpkg.com/react-loading/-/react-loading-0.0.9.tgz#e9fba6948915ba7742a508193828b6c73eb04956"
|
||||
|
||||
react-overlays@^0.6.10:
|
||||
version "0.6.10"
|
||||
resolved "https://registry.yarnpkg.com/react-overlays/-/react-overlays-0.6.10.tgz#e7e52dad47f00a0fc784eb044428c3a9e874bfa3"
|
||||
|
Loading…
x
Reference in New Issue
Block a user