Amplify-ios: Incorrect codegen error - DataStore does not support 1 to 1 connection with both sides of connection as optional field

Created on 1 Jun 2020  路  16Comments  路  Source: aws-amplify/amplify-ios

Describe the bug
Codegen produces the following error even though both sides of the connection are actually non-optional:
"DataStore does not support 1 to 1 connection with both sides of connection as optional field"

To Reproduce

  1. Create the schema below
  2. Add api, push, then run amplify codegen models
  3. See error

Expected behavior
Generates the code

Environment:

  • Amplify Framework Version: 4.21.0
  • Dependency Manager: Cocoapods
  • Swift Version : 5.0

Device Information:

  • Device: Simulator
  • iOS Version: iOS 13.5

Additional context
Schema:

type PhoneCall @model {
  id: ID!
  caller: Person! @connection(name: "PhoneCallCaller")
  callee: Person! @connection(name: "PhoneCallCallee")
  transcript: Transcript! @connection(name: "PhoneCallTranscript")
}

type Person @model {
  id: ID!
  name: String!
  callerOf: [PhoneCall!] @connection(name: "PhoneCallCaller")
  calleeOf: [PhoneCall!] @connection(name: "PhoneCallCallee")
}

type Transcript @model {
  id: ID!
  text: String!
  language: String
  phoneCall: PhoneCall! @connection(name: "PhoneCallTranscript")
}
bug datastore pending triage

Most helpful comment

Thanks guys. I've been told it's being looked into, has to do with which side of the relationship should be the "owner". I've made a feature request that possibly addresses this and other issues RFC - Simplified @connection directive

All 16 comments

I'm having the same issue on amplify-android library.
Maybe this is related to amplify-cli...

+1

type TestModel @model {
  id: ID!
  name: String
}

type TestModel2 @model {
  id: ID!
  test1: TestModel! @connection
}

this works well, but

type TestModel @model {
  id: ID!
  name: String
}

type TestModel2 @model {
  id: ID!
  test1Id: ID!
  test1: TestModel! @connection(fields: ["test1Id"])
}

this causes error: DataStore does not support 1 to 1 connection with both sides of connection as optional field

But,

type TestModel @model {
  id: ID!
  name: String
}

type TestModel2 @model {
  id: ID!
  test1Id: ID!
  test1: TestModel @connection(fields: ["test1Id"]) # `!` removed
}

This works!!! 馃檭 @anthonymoretti @watanabethais

Thanks guys. I've been told it's being looked into, has to do with which side of the relationship should be the "owner". I've made a feature request that possibly addresses this and other issues RFC - Simplified @connection directive

I just ran into this, and can confirm paradoxically removing the ! from the connected model (TestModel in the example above) avoids the error as well for me.

The downside is now the generated TypeScript binding has the field as a nullable field when I want it non-nullable, especially as the key (test1Id in the example above) is defined as non-nullable, so it doesn't make sense that the connected field is nullable.

I wonder if there's any update to this bug?

Isn't the bug here?: https://github.com/aws-amplify/amplify-cli/blob/master/packages/amplify-codegen-appsync-model-plugin/src/utils/process-connections.ts#L201

There are only 3 branches in the if statement checking if both sides of the connection are null or not:

  • if (!field.isNullable && otherSideField.isNullable)
  • else if (field.isNullable && !otherSideField.isNullable)
  • else

But there are 4 separate possibilities, and 2 of them are being swallowed up by the last else clause. It looks like there should be a separate clause checking that both are not null and not throwing an error in that case.

I confirmed by monkey patch that if there was this 4th branch added (!field.isNullable && !otherSideField.isNullable), then it would fall into it and not error out for the schema @wooklym provided above.

@drochetti is the above known, and any idea if this will be fixed any time soon if so?

This issue is stale because it has been open 14 days with no activity. Please, provide an update or this will be automatically closed in 7 days.

This is still a relevant issue and needs to be triaged and prioritized.

I'm using a translation tool, so it may be confusing
I added a child element connection to the parent element and verified that it works
In @wooklym, amplify codegen models does not output an error, but DataStore.query cannot get it as Connection.

type TestModel @model {
  id: ID!
  name: String
  children: [TestModel2] @connection(fields: ["id"])
}

type TestModel2 @model {
  id: ID!
  test1Id: ID!
  test1: TestModel! @connection(fields: ["test1Id"])
}

@danrivett did any downstream issues come up from your monkey patch?

@kldeb we removed the connection for now instead of money-patching; we monkey-patched just to prove out the theory that the if-block is missing a clause and it would fall into that missing clause if added instead of erroring.

@drochetti I guess everyone is busy, but been 6 months since this ticket was opened and the issue looks relatively simple to triage if someone is available to.

If this is an easy fix maybe i'll try my luck with a PR

@danrivett how did you apply the monkey patch?

For the record this isn't just a iOS issue. Hit it today trying to get the new Admin UI working on an existing schema, this requires DataStore to be configurated which throws this error when I push :(

@kldeb we removed the connection for now instead of money-patching; we monkey-patched just to prove out the theory that the if-block is missing a clause and it would fall into that missing clause if added instead of erroring.

@drochetti I guess everyone is busy, but been 6 months since this ticket was opened and the issue looks relatively simple to triage if someone is available to.

I mentioned it earlier in https://github.com/aws-amplify/amplify-ios/issues/505#issuecomment-639804984 - I was told it's being looked into and has to do with determining which side of the relationship should be the "owner". If the missing else clause is added I think you still have the problem of determining the "owner" and thus have a problem setting deletion rules. I've made a feature request that might solve this and other problems: RFC - Simplified @connection directive

Any updates?

Was this page helpful?
0 / 5 - 0 ratings