首页 > 解决方案 > 我们如何在 CordApp 的 Contract-States 库中访问 NetworkMapCache

问题描述

我正在尝试在 CordApp 的 Contract-States 库中实现一个 Validator 类,该类具有几个验证方法,这些验证方法由 Model 类在其 init() 乐趣中继承,因此每次调用/初始化 Model 类时,验证都会发生在点。

现在我被困在一个点上,我需要验证传入的成员名称(通过模型类)是否与节点的组织名称匹配,我需要为此访问 NetworkMap。我怎样才能做到这一点?

在 Work-Flow 库中,每个流都扩展了实现 ServiceHub 接口的 FlowLogic 类,通过它我们可以访问 NetworkMap,但是在 Contract-States 库中如何做到这一点?

PS - 我试图避免任何循环依赖(合同状态库不应依赖工作流库)

标签: corda

解决方案


简短的回答,你不能。

长答案:

  • 流验证和合同验证之间的区别在于后者(合同)对于相同的输入必须具有确定性意义,无论是现在还是 100 年后,在当前节点或任何其他节点中,它们必须始终给出相同的输出。
  • 这样做的原因是因为任何时候(甚至在未来)当节点接收到交易时,它都必须验证该交易,其中包括验证输入,这反过来需要验证创建这些输入的交易等等,直到您获得完全导致用作输入的输出的所有输入的验证图,依此类推。
  • 这就是为什么合约应该在任何时候返回相同的结果,这就是为什么它应该是确定性的,这就是为什么合约(不像流)不能访问外部资源(比如 HTTP 调用,甚至是节点的数据库)。
  • 想象一下,如果合约依赖于节点的数据库来获取某些验证规则,如您所知,状态是在需要知道的基础上分布的(即仅对participants状态);因此一个节点可能具有您用作验证源的状态,而另一个节点不会,因此合约的输出(交易有效/无效)在节点之间会有所不同,这打破了确定性概念。
  • 合约只能访问交易组件:输入、输出、附件、签名、时间窗口、参考状态。

好消息,还有其他方法可以实现您的要求:

  • 使用具有允许成为事务一部分的节点列表的附件,如果黑名单不经常更新,则应使用此方法,您可以在此处查看示例。
  • 使用参考状态,您可以在其中创建具有允许方的状态并要求在您的交易中存在该参考状态;当黑名单更新较频繁时,应使用此方法。您可以在此处阅读有关参考状态的信息。
  • 使用 Oracles,如果有一个世界组织(或例如某个国家的贸易部)提供一个返回黑名单方列表的 Oracle,则使用此选项;并且您在交易中使用该 Oracle。您可以在此处阅读有关 Oracle的信息。

推荐阅读