schema.graphql not pushing to aws cloud due to migration keywords of @key and @connection

Viewed 442

I am constructing a React Native app with AWS Amplify, AppSync, Cognito, Dynamodb and GraphQL.

I designed the schema.graphql file and want to push that to the cloud (amplify push). Initially, it had no problem pushing to the cloud.

But as soon as I introduced @key and @connection , I get an error when pushing to cloud.

amplify push

The error is:

 An error occurred during the push operation: Your GraphQL Schema is using
"@connection", "@key" directives from an older version of the GraphQL Transformer. 
Visit https://docs.amplify.aws/cli/migration/transformer-migration/ to 
learn how to migrate your GraphQL schema.

I read the article and followed their instruction to the best of my ability.

Then I get this error when pushing:

 An error occurred during the push operation: Schema validation failed.

Unknown argument "keyName" on directive "@hasMany". Did you mean "indexName"?

GraphQL request:13:44
12 |
13 |   portfolioCoins: [PortfolioCoin] @hasMany(keyName: "byUser", fields: ["id"])
   |                                            ^
14 | }

Directive "primaryKey" may not be used on OBJECT.

GraphQL request:16:27
15 |
16 | type PortfolioCoin @model @primaryKey(name: "byUser", fields: ["userId"]) {
   |                           ^
17 |   id: ID!

Unknown argument "name" on directive "@primaryKey".

GraphQL request:16:39
15 |
16 | type PortfolioCoin @model @primaryKey(name: "byUser", fields: ["userId"]) {
   |                                       ^
17 |   id: ID!

Unknown argument "fields" on directive "@primaryKey".

GraphQL request:16:55
15 |
16 | type PortfolioCoin @model @primaryKey(name: "byUser", fields: ["userId"]) {
   |                                                       ^
17 |   id: ID!

Unknown argument "fields" on directive "@manyToMany".

GraphQL request:21:26
20 |   userId: ID!
21 |   user: User @manyToMany(fields: ["userId"])
   |                          ^
22 |

Directive "@manyToMany" argument "relationName" of type "String!" is required, but it was not provided.

GraphQL request:21:14
20 |   userId: ID!
21 |   user: User @manyToMany(fields: ["userId"])
   |              ^
22 |

Unknown argument "fields" on directive "@manyToMany".

GraphQL request:24:26
23 |   coinId: ID!
24 |   coin: Coin @manyToMany(fields: ["coinId"])
   |                          ^
25 | }

Directive "@manyToMany" argument "relationName" of type "String!" is required, but it was not provided.

GraphQL request:24:14
23 |   coinId: ID!
24 |   coin: Coin @manyToMany(fields: ["coinId"])
   |              ^
25 | }

This is my schema.graphql file:

# This "input" configures a global authorization rule to enable public access to
# all models in this schema. Learn more about authorization rules here: https://docs.amplify.aws/cli/graphql/authorization-rules
# input AMPLIFY {
#   globalAuthRule: AuthRule = { allow: public }
# } # FOR TESTING ONLY!
type User @model @auth(rules: [{ allow: public }]) {
  id: ID!
  email: String!
  name: String
  image: String
  networth: Float!

  portfolioCoins: [PortfolioCoin] @connection(keyName: "byUser", fields: ["id"])
}

type PortfolioCoin @model @key(name: "byUser", fields: ["userId"]) {
  id: ID!
  amount: Float!

  userId: ID!
  user: User @connection(fields: ["userId"])

  coinId: ID!
  coin: Coin @connection(fields: ["coinId"])
}

type Coin @model {
  id: ID!
  cgId: String!
  name: String!
  symbol: String!
  image: String
  currentPrice: Float!
  valueChange24H: Float!
  valueChange1D: Float!
  valueChange7D: Float!
  priceHistoryString: String
}

And here is an image of the table relationships for your reference:

tables

Please tell me how I can replace the @key and @connection properly so that I can amplify push successfully. Your help will be extremely appreciated.

2 Answers

I encountered this a while back when GraphQL Transformer version 2 came out and my schema stopped working.

I found this article helpful to understand how the new keywords worked. https://aws.amazon.com/blogs/mobile/aws-amplify-announces-the-new-graphql-transformer-v2-more-feature-rich-flexible-and-extensible/

This link is also very helpful for modeling in the current version: https://docs.amplify.aws/cli/graphql/data-modeling

I think your schema should probably work as follows in the current version:

type User @model @auth(rules: [{ allow: public }]) {
  id: ID!
  email: String!
  name: String
  image: String
  networth: Float!

  portfolioCoins: [PortfolioCoin] @hasMany
}

type PortfolioCoin @model @key(name: "byUser", fields: ["userId"]) {
  id: ID!
  amount: Float!
  user: User @belongsTo

  coin: Coin @hasOne
}

type Coin @model {
  id: ID!
  cgId: String!
  name: String!
  symbol: String!
  image: String
  currentPrice: Float!
  valueChange24H: Float!
  valueChange1D: Float!
  valueChange7D: Float!
  priceHistoryString: String
}

With the GraphQL Transformer v2, Amplify introduces as a range of new features to help customers create app backends even faster and easier. The @key directive is being replaced by two new directives. @primaryKey and @index

@connection is being replaced with several new directives.
@hasOne
@hasMany
@belongsTo
@manyToMany

for your case is @hasOne read https://docs.amplify.aws/cli/migration/transformer-migration/#changes-that-amplify-cli-will-auto-migrate-for-you for more info on this.

Here's your code let me know if bugs arise. type User @model @auth(rules: [{ allow: public }]) { id: ID! email: String! name: String image: String networth: Float!

  portfolioCoins: PortfolioCoin @hasOne(keyName: fields: ["id"])
}

type PortfolioCoin @model  {
  id: ID!
  amount: Float!

  userId: ID!@primaryKey @index(name:"byUser")
  user: User @hasOne(fields: ["userId"])

  coinId: ID!
  coin: Coin @hasOne(fields: ["coinId"])
}

type Coin @model {
  id: ID!
  cgId: String!
  name: String!
  symbol: String!
  image: String
  currentPrice: Float!
  valueChange24H: Float!
  valueChange1D: Float!
  valueChange7D: Float!
  priceHistoryString: String
}
Related