将 { t }(从 i18n-react)传递给无状态组件时不能使用 props

Can't use props when passing { t } (from i18n-react) to stateless component

我的 parent 组件具有以下状态:

class RecordEdit extends PureComponent {
    state = { 
        allRecordData: {},
        changelog: [
            {hello1: '1'},
            {hello2: '2'}
        ]
    }

它尝试渲染其 child 并将 prop 传递给它:

<div className='cards-container'>
    <ChangeHistory recordEditHistory={this.state.changelog} />
</div>

并且 ChangeHistory 组件尝试映射接收到的 prop 以呈现元素列表:

const ChangeHistoryCard = ({ t }, props) => (
  <CardOuterContainer recordEditHistory={props.recordEditHistory}>
    <h1>{t('История изменений')}</h1>
    {
      props.recordEditHistory &&
      props.recordEditHistory.map(item =>
        <p>{t('Последнее изменение')}: <span>[22.11.2018]</span></p>
      )
    }
  </CardOuterContainer>
);
export default withNamespaces()(ChangeHistoryCard);

出于某种原因,组件始终认为 recordEditHistory 属性未定义。但是如果在检查器中点击它,我可以看到该值已成功传递:

我不明白这个问题。可能是因为我使用 i18n 并使用 withNamespaces 做一些道具或......?我必须考虑如何解决这个问题。

重要提示: { t } 来自 i18n-react,我用它来将界面翻译成英文并返回。我尝试完全删除它,但没有帮助。

编辑:我尝试删除 { t } 方法并从导出中删除 withNamesSpaces() HOC,现在一切正常。但是现在我不能在这个组件中使用 i18n-react :(

我认为问题出在组件参数上:

const ChangeHistoryCard = ({ t }, props) => ();

应该是:

const ChangeHistoryCard = (props) => ();

功能组件的签名只得到props

https://reactjs.org/docs/components-and-props.html

Conceptually, components are like JavaScript functions. They accept arbitrary inputs (called “props”) and return React elements describing what should appear on the screen.

改变

const ChangeHistoryCard = ({ t }, props) => ();

const ChangeHistoryCard = (props) => ();

因此,如果您阅读了第二个编辑,您就会知道如果我从组件中完全删除 i18n,一切似乎都有效。

太好了,但我真的希望 i18n 留下来,所以我找到了更好的方法:

您可以 import 'i18next' 并调用 t 作为组件的方法,而不是将 { t } 传递给组件。

所以这个:

import { withNamespaces } from 'react-i18next';

const ChangeHistoryCard = ({ t }, props) => (
  <CardOuterContainer recordEditHistory={props.recordEditHistory}>
    <h1>{t('История изменений')}</h1>
    {
      props.recordEditHistory &&
      props.recordEditHistory.map(item =>
        <p>{t('Последнее изменение')}: <span>[22.11.2018]</span></p>
      )
    }
  </CardOuterContainer>
);
export default withNamespaces()(ChangeHistoryCard);

变成这样:

import { withNamespaces } from 'react-i18next';
import i18next from 'i18next';

const ChangeHistoryCard = (props) => (
  <CardOuterContainer recordEditHistory={props.recordEditHistory}>
    <h1>{i18next.t('История изменений')}</h1>
    {
      props.recordEditHistory &&
      props.recordEditHistory.map(item =>
        <p>{i18next.t('Последнее изменение')}: <span>[22.11.2018]</span></p>
      )
    }
  </CardOuterContainer>
);


export default withNamespaces()(ChangeHistoryCard);

Thay 方式 i18n 留在原地,而道具保持不变和可用。