0

我的目标是将相同arrays的多个嵌套同级组合到一个调用中。edgesRelay fragmentrender

后端数据通过Relay容器传递(也使用react-router-relay)。

我有一个组件层次结构,它显示Tags来自几个不同的多个Users. 顶级查询如下所示:

getUserGroup(id: 'abc') {
  users {
    edges { // array of arrays objects with nested arrays
      node {
        Tags {
          edges { // array of objects with target items
            node {
              tagName // target item
              id
            }
          }
        }
      }
    }
  }
}

结果是这样的(完全扁平化的形式):

  results = [['tagname1', 'tagname2'], [tagname3, tagname4]]

目前我渲染一个层次结构,每个层次都有node Type自己的Component,即Tagmenu-> UserTagGroup-> TagItems(代码在这篇文章的底部)。

这将所有标签按 分组User,最终呈现如下列表:

User 1:
  - Tag 1
  - Tag 2
User 2:
  - Tag 3
  - Tag 4

我想要实现的是render所有Users' 标签在第二层混合在一起,即像TagMenu->这样的层次结构TagItems,以呈现:

User Tags
  - Tag 1
  ...
  - Tag 4

到目前为止,我可以管理的唯一方法是手动从顶级Relay容器结果中提取和组合所有数组,如下所示(伪代码):

for each array in users.edges:
  for each array in node.Tags.edges:
    return node.tagName

这似乎不正确,原因有两个:

  1. 打包成一个render()函数有点多,
  2. 目前尚不清楚是否可以在 Relay中防止nullrefsdefault props

...但这显然是可行的。

我的问题是:Relay这样做的方法是什么?考虑到库如何自然地导致组件组合,我无法想象在更高级别拉深嵌套结果并手动改组它们是最佳的。这是我的组件:

// TagsMenu component, top level
class TagsMenu extends Component {
  render() {
    return (
      <div>
        {
          this.props.userGroup.users.edges.map(u => {
            return <UserTagGroup user={u.node} />
          })
        }
      </div>
    )
  }
}

fragment on UserGroup {
  users(first: 1000) {
    edges {
      node {
        ${UserTagGroup.getFragment('user')}
      }
    }
  }
}


// UserTagGroup, second component
class UserTagGroup extends Component {
  render() {
    return (
      <div>
        <h4>User:  {this.props.user.id}</h4>
        {
          this.props.user.Tags.edges.map(t => {
            return <TagMenuItem tag={t.node} />
          })
        }
      </div>
    )
  }
}
fragment on User {
  id
  listingTags(first: 1000) {
    edges {
      node {
        ${TagMenuItem.getFragment('tag')}
      }
    }
  }
}


// TagMenuItem, bottom level component. Renders 1 Tag.
class TagMenuItem extends Component {
  render() {
    return (
      <div>
        {this.props.tag.tagName}
      </div>
    )
  }
}
fragment on Tag {
  tagName
  id
}
4

1 回答 1

0

不过,您一直在描述的内容-“从顶级 Relay 容器中手动提取和组合所有数组”-似乎确实是要走的路。

如果问题出在render()方法中有这个功能,我建议你结合使用 state 和 method componentWillReceiveProps()。目标是仅在this.props.users真正改变时重新计算扁平化列表。

沿着这些线的东西:

class MyRootContainer extends Component {

  constructor(props) {
    super(props);

    this.state = {
      flattenedList: this.computeFlattenedListFromProps(this.props),
    };
  }

  componentWillReceiveProps(props) {
    if (this.props.users !== props.users) {
      this.setState({
        flattenedList: this.computeFlattenedListFromProps(props),
      });
    }
  }

  computeFlattenedListFromProps(props) {
    // Compute and return flattened list
  }

  render() {
    ...
  }
}
于 2017-01-12T22:46:52.740 回答