将NextJS,next-i18next,带有redux和带有redux-saga的连接:“错误:如果自定义_app.js文件中有getInitialProps方法...”

时间:2019-02-07 13:29:48

标签: javascript reactjs redux i18next

我试图将使用'with-redux-saga'和'with-redux'的功能正常的NextJS / React应用程序连接到'next-i1iN'(https://github.com/isaachinman/next-i18next)-但是当我的应用程序启动时我收到以下错误:

  

错误:如果您的自定义_app.js中有getInitialProps方法   文件,必须显式返回pageProps。了解更多信息,   参见:https://github.com/zeit/next.js#custom-app

     

TypeError:无法读取未定义的属性“ namespacesRequired”       在Function.getInitialProps(/Users/cerulean/Documents/Projects/PAW-React/node_modules/next-i18next/dist/hocs/app-with-translation.js:94:57)       在process._tickCallback(internal / process / next_tick.js:68:7)

但是我要在_app.js中返回页面道具。

// _app.js
 static async getInitialProps({ Component, ctx }) {

    const pageProps = {};
    let temp;

    if (Component.getInitialProps) {
      temp = await Component.getInitialProps({ ctx });
    }
    Object.assign(pageProps, temp);
    return { ...pageProps };
  }

也许我将各种HOC挂钩在一起有问题吗?在_app.js中,我有:

export default withRedux(createStore, { debug: false })(withReduxSaga({ async: true })(i18nInstance.appWithTranslation(MyApp)));

在我的index.js中,我有:

   // index.js
const mapStateToProps = (state) => ({ homeData: getHomePageData(state) });

export default connect(mapStateToProps)(withNamespaces('common')(Index));

任何见解都值得赞赏!

4 个答案:

答案 0 :(得分:2)

对于任何遇到此问题并想知道@cerulean在his answer中的含义的人。

1)使用require代替import

如果您使用自定义服务器(more info),则NextJS不会转换您的模块。因此,如果不哭泣,就不能在 next-i18next 配置中使用import

// NextI18NextConfig.js

const NextI18Next = require('next-i18next/dist/commonjs')

module.exports = new NextI18Next({
  defaultLanguage: "en",
  otherLanguages: ["de"]
  // ... other options
});
// server.js

const nextI18next = require("./path/to/NextI18NextConfig");

// ... the rest of your server.js code

这是 next-i18next example documentation

的混合搭配

2)保持pageProps不变

返回值getInitialProps不能玩得太多。如果您需要添加其他内容,则应注意不要替换或操作pageProps。见下文。

  static async getInitialProps({ Component, ctx }) {
    let pageProps = {}

    const extraStuff = doSomeExtraStuff()

    if (Component.getInitialProps) {
      pageProps = await Component.getInitialProps(ctx)
    }

    return { pageProps, extraStuff }
  }

有关this thread的更多信息。

答案 1 :(得分:1)

如果您正确配置了redux sagas,这种方式对我有用:

export default withRedux(configureStore)(withReduxSaga(appWithTranslation(MyApp)));

答案 2 :(得分:0)

遇到类似情况的人有两件事。

1)当他们说“ return pageProps”时,表示“ return pageProps”,而不是“ ... pageProps”

2)我在文件中使用ES6导入语句,该语句设置了“ next-i18next”单例。需要使用'require'和'module.exports'

现在可以了...

答案 3 :(得分:0)

我仍然无法使其正常运行,并且代码看起来还可以。有没有人对此有任何想法?导致错误

无法读取未定义的属性“ namespacesRequired”

// pages/_app.js

import App from 'next/app';
import React from 'react';
import { Provider } from 'react-redux';
import withRedux from 'next-redux-wrapper';
import withReduxSaga from 'next-redux-saga';
import { appWithTranslation } from '../i18n';

import createStore from '../lib/store';

class MyApp extends App {
  static async getInitialProps({ Component, ctx }) {
    let pageProps = {};

    if (Component.getInitialProps) {
      pageProps = await Component.getInitialProps({ ctx });
    }

    return { pageProps };
  }

  render() {
    const { Component, pageProps, store } = this.props;
    return (
      <Provider store={store}>
        <Component {...pageProps} />
      </Provider>
    );
  }
}

export default appWithTranslation(withRedux(createStore)(withReduxSaga(MyApp)));



// i18n.js
const NextI18Next = require('next-i18next/dist/commonjs').default;

module.exports = new NextI18Next({
  otherLanguages: ['en', 'pl'],
  strictMode: false
});



// server.js
const express = require('express');
const next = require('next');
const nextI18NextMiddleware = require('next-i18next/middleware').default;
const nextI18next = require('./i18n');

const port = parseInt(process.env.PORT, 10) || 3000;
const dev = process.env.NODE_ENV !== 'production';
const app = next({ dev });
const routes = require('./routes');

const handle = routes.getRequestHandler(app);
app.prepare().then(() => {
  const server = express();
  server.use(nextI18NextMiddleware(nextI18next));
  server.get('*', (req, res) => handle(req, res));
  server.listen(port, err => {
    if (err) throw err;
    console.log(`> Ready on http://localhost:${port}`);
  });
});