看来,graphql突变中的嵌套对象继承了父对象的动词语义。这导致了对什么的疑问 CRUD语义应该是嵌套突变。
例如,如果我希望在更新现有对象时创建对象并将其连接到现有关联对象,则创建父对象语义,并且嵌套对象语义是更新。但是,GraphQL没有在单个原子突变(AFAICT)中明确允许混合动词。
这是一个真值表,显示嵌套对象何时在数据库中或在变异中,或两者都有的一些问题:
O1<----hasa---->O2
O1 {
id: "1234",
descr: "Object1",
someAttr: "foo"
}
O2 {
id: "5678",
descr: "Object2",
someOtherAttr: "bar"
}
hasa {
id1: "1234",
id2: "5678",
type: "hasa"
edgeAttr: "someRelationAttr"
}
请注意,“更新操作”需要突变中的ID,否则会根据业务规则变成创建或错误。
如果包含ID,则处理嵌套对象的一种方法是将它们视为更新。当发生编码错误时,这将导致意外创建嵌套对象。它也是丑陋的语义。
第二种方法是将父对象的动词视为嵌套对象的相同动词,除非在创建时嵌套对象具有ID,嵌套对象被视为更新。
第三种方法是要求使用返回的ID为下一个突变处理嵌套对象的多个突变。这是3次往返时间,它破坏了单个突变的自然原子性, 这将导致巨大的一致性问题。
用于创建和更新的嵌套对象的最佳动词语义是什么?
以下是一个明确的例子。答案将显示上表中情况的变异是不明确的。
mutation { O1Create(
descr: "Object1",
someAttr: "foo",
hasa {
edgeAttr: "someRelationAttr",
O2 {
descr: "Object2",
someOtherAttr: "bar"
}
}
)}
以上的示例创建变异:
dataType: 'jsonp',
我想知道当O2已经在数据库中时O1Create变异有什么好的选择。我还想知道当O2不在数据库中时O1Update有什么好的选择。