2016-06-08 2 views
0

Пройдя через удэми учебник и застрял и по какой-то причине не может понять, что произошло. Я просмотрел весь свой код, и он выглядит правильно, насколько я могу судить по сравнению с учебником. Код:реагировать и сокращать: нечистая ошибка: ожидается, что редуктор будет функцией

index.js

import React from 'react'; 
import ReactDOM from 'react-dom'; 
import { Provider } from 'react-redux'; 
import { createStore, applyMiddleware } from 'redux'; 

import ReduxPromise from 'redux-promise'; 

import App from './components/app'; 
import reducers from './reducers'; 

const createStoreWithMiddleware = applyMiddleware(ReduxPromise)(createStore); 

ReactDOM.render(
    <Provider store={createStoreWithMiddleware(reducers)}> 
    <App /> 
    </Provider> 
    , document.querySelector('.container')); 

searchbar.js:

import React, {Component} from 'react'; 
import {connect} from 'react-redux'; 
import {bindActionCreators} from 'redux'; 
import {fetchWeather} from '../actions/index'; 
export default class SearchBar extends Component{ 
    constructor(props){ 
     super(props); 
     this.state = {term: ''} 
     this.onInputChange = this.onInputChange.bind(this) 
    } 
    onInputChange(e){ 
     console.log(e.target.value) 
     this.setState({ 
      term: e.target.value 
     }) 
    } 
    onFormSubmit(e){ 
     e.preventDefault() 
    } 
    render(){ 

     return (

      <form onSubmit ={this.onFormSubmit} className = "input-group"> 
       < input 
       placeholder =" Get a forecast" 
       className = "form-control" 
       value = {this.state.term} 
       onChange = {this.onInputChange} 
       /> 
       <span className = "input-group-btn"> 
        <button type="submit" className = "btn btn-secondary">Submit </button> 
       </span> 
      </form> 
     ); 
    } 
} 
function mapDispatchToProps(dispatch){ 
    return bindActionCreators({fetchWeather}, dispatch); 
} 
export default connect (null, mapDispatchToProps)(SearchBar); 

редукторы/index.js

import axios from 'axios'; 

const API_KEY = 'c4c2ff174cb65bad330f7367cc2a36fa' 
const ROOT_URL = `http://api.openweathermap.org/data/2.5/forecast?q=appid=${API_KEY}`; 

export const FETCH_WEATHER = 'FETCH_WEATHER'; 

export function fetchWeather(city){ 
    let url = `${ROOT_URL}&q=${city},us`; 
    let request = axios.get(url); 

    return { 
     type: FETCH_WEATHER, 
     payload: request 
    }; 

} 

app.js

import React, { Component } from 'react'; 
import SearchBar from '../containers/search_bar'; 

export default class App extends Component { 
    render() { 
    return (
     <div> 
     <SearchBar /> 
     </div> 
    ); 
    } 
} 
+4

Вы не нашел код в файле/переходники индекса? Там нет редуктора, и вы не экспортируете по умолчанию, поэтому «редукторы» будут не определены в вашем основном файле индекса .... – azium

+2

Функция 'fetchWeather' в' reducers/index.js' больше похожа на действие, а не на редуктор , Вы уверены, что не ошибаетесь в предоставленном коде? –

+0

@azium - это код, который был в учебнике, я должен просто отключить видео, и он соответствует, насколько я могу судить, это учебник: https://www.udemy.com/react-redux/ learn/v4/t/lecture/4284600 – codemonkey

ответ

0

Чтобы ответить,

Ваш код получил немного перепутали, блок, который вы имеете в reducers/index.js ваше действие и должны быть расположены в actions/index.js вместо. Как уже упоминалось вы импортируете его оттуда в вашем searchbar компонента:

import {fetchWeather} from '../actions/index';

Редуктор здесь следует сделать использование FETCH_WEATHER типа, который вы настраиваете в своем действии, чтобы обновить состояние Redux магазин, так что-то вдоль линий:

switch(action.type) { 
    case FETCH_WEATHER: 
     return [action.payload.data].concat(state); 
} 

return state; 

Тогда либо экспорт, которые непосредственно или использовать combineReducers от Redux вернуть одну функцию редуктора, если у вас есть больше чем один.

Ссылка на всегда удивительный: DOCS

Смежные вопросы