简体   繁体   English

React-Redux不会渲染,如何解决正在发生的事情?

[英]React-Redux will not render, how do I troubleshoot what is going on?

I am in the middle of developing an application in React with Redux and it's frustrating when nothing renders and no errors appear. 我正在用Redux用React开发一个应用程序,当什么都没有呈现并且没有错误出现时,它令人沮丧。 Can anybody provide some troubleshooting practices in such a situation? 在这种情况下,有人可以提供一些故障排除方法吗?

I saw a similar post: React/Redux Component will not render 我看到了一个类似的帖子: React / Redux Component将不会渲染

and I tried to implement the suggestions there, but it did nothing for me, I just continued to get a blank stare from the browser. 我尝试在那儿实施建议,但对我却无济于事,我只是继续从浏览器中呆呆地凝视着。

This is my reducers/reducer_books.js: 这是我的reducers / reducer_books.js:

// Step 1. Developing Our Reducer.
// Step 2. In index.js we will wire it in so that it will work
// this is a reducer, just a function and a return with a piece of our application state, a list of books
// to be able to make use of this reducer function anywhere else in our application, we need to export it.
// with export default any other file in our application can import this one and it will just automatically
// receive the books reducer.
export default function() {
  return [ // return array
    {title: 'Coding with Javascript for Dummies'}, // these will be a couple of different books
    {title: 'Meaningful Work'},
    {title: 'Head First Javascript'},
    {title: 'How To Do Everything With Javascript'},
  ]
}

This is my reducers/index.js: 这是我的reducers / index.js:

// Step 2. In index.js we will wire it in so that it will work
// importing Javascript objects that contain methods we need to use
// in order to use React. They are the react library.
import {combineReducers} from 'redux';
import BooksReducer from './reducer_books';

// we need to ensure that this code is generating usable state for our
// application by creating a booklist component within react
const rootReducer = combineReducers({
    // this gives us the same mapping of state
    // key is books and value is BooksReducer
    // passing this into the function combineReducers is essentially telling
    // reduce how to create our application state
    // the single piece of state is books
    books: BooksReducer
});

export default rootReducer;

This is the component I promoted to a container in container/book-list.js: 这是我在container / book-list.js中提升为容器的组件:

// purpose of this component is to render a list of books
// we are going to use the react-redux library by making use of one of our components
// as a container instead.
// A container is a react component that has a direct connection to the state
// managed by redux.
// React and Redux are two separate libraries, this file is the melding of both
// libraries, thereby making this component aware of the state contained in Redux.
import React, {Component} from 'react';
// pulling off a single property called connect
// this is the glue between React and Redux, only through this library do we
// merge them. React-Redux in turn makes this connect function available.
import {connect} from 'react-redux';

class BookList extends Component {
  // new function
  renderList() {
    // plugin our application state as this.props.books
    return this.props.books.map((book) => { // mapping the array
        return (
          // for each book in the array, we create a list with title
          <li key={book.title} className="list-group-item">{book.title}</li> // because it is a list we have to add a key
        );
    });
  }
  render() {
    return (
      <ul className="list-group col-sm-4">
        // when calling a separate function inside of JSX, we write curly braces
        // this calls a new function of renderList
        // helper function, which is a function that helps another function
        {this.renderList()}
      </ul>
    )
  }
}
// This function is the glue between React and Redux.
// purpose of this function is to take our application state as an argument
// our state contains the array of books and the active book
// The argument is a state that returns an object.
function mapStateToProps(state) {
  // Whatever is returned will show up as props
  // inside of BookList
  return {
    // the object returned with a key of books and a value of state.books
    // because our books reducer is returning the books property, the array of
    // objects.
    books: state.books
  };
}

// the connect function says take this component, take this map.state to props
// and returns a container. The container is aware of the state in Redux.
// In a container file we do not want to export the BookList, we want to export
// the container
export default connect(mapStateToProps)(BookList);

This is the book-list/index.html: 这是book-list / index.html:

<!DOCTYPE html>
<html>
  <head>
    <link rel="stylesheet" href="/style/style.css">
    <link rel="stylesheet" href="https://cdn.rawgit.com/twbs/bootstrap/48938155eb24b4ccdde09426066869504c6dab3c/dist/css/bootstrap.min.css">
    <script src="https://maps.googleapis.com/maps/api/js"></script>
  </head>
  <body>
    <div class="container"></div>
  </body>
  <script src="/bundle.js"></script>
</html>

This is the components/app.js: 这是components / app.js:

import React from 'react';
import {Component} from 'react';

import BookList from '../containers/book-list';

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

Adding webpack.config.js file: 添加webpack.config.js文件:

module.exports = {
  entry: [
    './src/index.js'
  ],
  output: {
    path: __dirname,
    publicPath: '/',
    filename: 'bundle.js'
  },
  module: {
    loaders: [{
      exclude: /node_modules/,
      loader: 'babel',
      query: {
        presets: ['react', 'es2015', 'stage-1']
      }
    }]
  },
  resolve: {
    extensions: ['', '.js', '.jsx']
  },
  devServer: {
    historyApiFallback: true,
    contentBase: './'
  }
};

Throw a debugger in your code. 在代码中放入调试器。 Then open Chrome Dev Tools panel. 然后打开Chrome开发工具面板。 Navigate to the console tab. 导航到控制台选项卡。

The debugger looks like this (you can put it anywhere not in a return statement): 调试器如下所示(您可以将其放在return语句中以外的任何位置):

class BookList extends Component {
  // new function
  renderList() {

    debugger

    // plugin our application state as this.props.books
    return this.props.books.map((book) => { // mapping the array
        return (
          // for each book in the array, we create a list with title
          <li key={book.title} className="list-group-item">{book.title}</li> // because it is a list we have to add a key
        );
    });
  }
  //...

If your code runs past your debugger it will stop in the console and allow you to interact with your current scope. 如果您的代码运行通过调试器,它将在控制台中停止并允许您与当前作用域进行交互。

So you'd be able to type this.props.books in the console and see if its giving you what you'd expect. 因此,您可以在控制台中键入this.props.books ,看看它是否能满足您的期望。

It is also handy for checking which code is running. 这对于检查正在运行的代码也很方便。

Does anything load when you access the page? 访问页面时,是否加载任何内容? When you inspect the html see if your index.html content is loaded. 当您检查html时,请查看是否已加载index.html内容。 It'd be invisible on the page, as it has no actual content, but can be viewed in the Chrome Dev Tools. 它没有实际内容,因此在页面上不可见,但是可以在Chrome开发工具中查看。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM