Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Different error behavior for Amplify mock vs real API: "Cannot return null for non-nullable field" #6450

Closed
Nxtra opened this issue Jan 21, 2021 · 14 comments
Assignees
Labels
bug Something isn't working mock Issues tied to the mock functionality pending-release Code has been merged but pending release

Comments

@Nxtra
Copy link

Nxtra commented Jan 21, 2021

Describe the bug
Mock API throws error on non-nullable field of nested object when connection does not exist, real API works fine.

Amplify CLI Version
4.41.2

To Reproduce

  • I use the following schema.graphql:
type Writer @model @auth(rules: [{ allow: owner }]) {
  id: ID!
  name: String!
  addressLine: String
  blogs: [Blog] @connection(keyName: "byWriter", fields: ["id"])
}

type Blog
  @model
  @auth(rules: [{ allow: owner }])
  @key(name: "byWriter", fields: ["blogWriterId"]) {
  id: ID!
  name: String
  posts: [Post] @connection(keyName: "byBlog", fields: ["id"])
  blogWriterId: ID
  writer: Writer @connection
}

type Post
  @model
  @auth(rules: [{ allow: owner }])
  @key(name: "byBlog", fields: ["blogID"]) {
  id: ID!
  title: String!
  blogID: ID!
  blog: Blog @connection(fields: ["blogID"])
}
  • I run amplify push --y to deploy the API
  • I start a local mock of the API: amplify mock
  • Try to execute the following query locally:
mutation createBlog {
  createBlog(input: {name: "Nick's blog"}) {
    id
    name
    posts {
      items {
        blogID
        id
        title
        owner
      }
    }
    writer {
      addressLine
      name
      owner
      id
    }
    owner
  }
}

This results in an error:

{
  "data": {
    "createBlog": {
      "id": "e8dba61a-1049-4212-9396-ac4d4c5e4123",
      "name": "Nick's blog",
      "posts": {
        "items": []
      },
      "writer": null,
      "owner": "Nxtra"
    }
  },
  "errors": [
    {
      "message": "Cannot return null for non-nullable field Writer.name.",
      "locations": [
        {
          "line": 30,
          "column": 7
        }
      ],
      "path": [
        "createBlog",
        "writer",
        "name"
      ]
    }
  ]
}
  • Execute the same query in the AppSync console (cloud).
    This gives me the following result (no error):
{
  "data": {
    "createBlog": {
      "id": "0fa3cb68-949b-499b-b308-7f54235fc469",
      "name": "Nick's blog",
      "posts": {
        "items": []
      },
      "writer": null,
      "owner": "nxtra"
    }
  }
}

Expected behavior
I expect the mock API to behave without errors as well.

Screenshots
On the left the response in the AppSync console, on the left the local Amplify mock API.
image

Desktop:

  • OS: Mac
  • Node Version: v12.20.1

Log output
Include any relevant log output under ~/.amplify/logs/amplify-cli-<issue-date>.log
I don't see anything relevant here:

2021-01-21T10:38:14.639Z|info : amplify version core  {"version":true,"yes":false}
2021-01-21T10:38:19.986Z|info : amplify mock mock
2021-01-21T10:39:49.026Z|info : amplify mock mock

Related issue
This seems to be related but no solution was provided yet: #2248

@Nxtra Nxtra changed the title Different error behavior for Amplify mock vs real API: Different error behavior for Amplify mock vs real API: "Cannot return null for non-nullable field" Jan 21, 2021
@Nxtra
Copy link
Author

Nxtra commented Jan 21, 2021

I have not found the source of the problem but it is connected to the way you configure auth.

If the schema would use @auth(rules: [{ allow: private }]) then it would have worked.

type Writer @model @auth(rules: [{ allow: private }]) {
  id: ID!
  name: String!
  addressLine: String
  blogs: [Blog] @connection(keyName: "byWriter", fields: ["id"])
}

type Blog
  @model
  @auth(rules: [{ allow: private }])
  @key(name: "byWriter", fields: ["blogWriterId"]) {
  id: ID!
  name: String
  posts: [Post] @connection(keyName: "byBlog", fields: ["id"])
  blogWriterId: ID
  writer: Writer @connection
}

type Post
  @model
  @auth(rules: [{ allow: private }])
  @key(name: "byBlog", fields: ["blogID"]) {
  id: ID!
  title: String!
  blogID: ID!
  blog: Blog @connection(fields: ["blogID"])
}

But I'm trying to make it work with @auth(rules: [{ allow: owner }])

@nikhname nikhname added mock Issues tied to the mock functionality pending-triage Issue is pending triage labels Jan 22, 2021
@ammarkarachi
Copy link
Contributor

@Nxtra I believe there is a second PR that addresses this issue, it's been merged should be available within the next release
#5153

@alexkates
Copy link

It appears that https://github.com/aws-amplify/amplify-cli/releases/tag/v4.42.0 contains this, however I am still seeing this issue.

@lostcodingsomewhere
Copy link

i am having this same issue on 4.43.0, any advise?

@lostcodingsomewhere
Copy link

For anyone running into this issue (on v4.43.0), here's a workaround (pretty hackey but will suffice for now):

replace all of your API.graphql with the following helper:

const graphqlAPI = async (
   options,
   additionalHeaders?: {
      [key: string]: string;
   }
): Promise<any> => {
   try {
      return await API.graphql(options, additionalHeaders);
   } catch (err) {
      const realErrors = err.errors.filter(
         (e) => !e.message.startsWith('Cannot return null for non-nullable')
      );
      if (realErrors.length > 0) {
         console.log(`THROWING GRAPHQL ERROR`);
         throw err;
      } else {
         const realDataResult = { data: err.data };
         return realDataResult;
      }
   }
};

@cwinters8
Copy link

I am having the opposite problem compared to the the OP's original issue - my local mocked API works fine, but subscriptions are failing on the deployed API due to the error "Cannot return null for non-nullable type: 'String' within parent 'Form' (/onCreateForm/name)". The 'Form' item is created successfully and can be subsequently queried - it is only the subscription throwing the error. Here is the full output from the subscription:

{
  "data": {
    "onCreateForm": null
  },
  "errors": [
    {
      "message": "Cannot return null for non-nullable type: 'String' within parent 'Form' (/onCreateForm/name)",
      "path": [
        "onCreateForm",
        "name"
      ]
    }
  ]
}

Please let me know if there is any other information that might be helpful in debugging this issue. It seems to be fairly new - I wasn't having this issue with my deployed API as early as about a week ago.

@cwinters8
Copy link

This comment fixed me: #5542 (comment)

Adding the field in the return value from the mutation allows the subscription access to the field. I'm still not sure why it works fine in the locally mocked API and not the deployed one. But I'll take it!

@alexkates
Copy link

I think this needs to be looked into. Amplify mock hasn't worked for us for weeks.

@patrickcze
Copy link

Also having this same issue on incoming subscriptions:

DataStore - Skipping incoming subscription. Messages: Cannot return null for non-nullable type: 'AWSTimestamp' within parent 'LocationV1' (/onCreateLocationV1/_lastChangedAt)

The comment mentioned by @cwinters8 does not seem to resolve anything in my case as my subscriptions and mutations already have identical values.

@dmost714
Copy link

I'm running v4.44.1 and this issue is still alive and kicking.

The easiest way to reproduce it is to simply query a record that doesn't exist with a non-nullable in the expected results.

@alexkates
Copy link

Yup same here. I upgrade the CLI every release and this is the first thing I check.

Haven't been able to mock in weeks. Really frustrating.

@edwardfoyle edwardfoyle added bug Something isn't working pending-release Code has been merged but pending release and removed pending-triage Issue is pending triage labels Feb 27, 2021
@kaustavghosh06
Copy link
Contributor

Fix for this issue was merged and released in the latest version of the CLI.
@alexkates Could you please confirm?

@alexkates
Copy link

Confirmed ty!

@cjihrig cjihrig self-assigned this Mar 21, 2021
@github-actions
Copy link

This issue has been automatically locked since there hasn't been any recent activity after it was closed. Please open a new issue for related bugs.

Looking for a help forum? We recommend joining the Amplify Community Discord server *-help channels for those types of questions.

@github-actions github-actions bot locked as resolved and limited conversation to collaborators May 24, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
bug Something isn't working mock Issues tied to the mock functionality pending-release Code has been merged but pending release
Projects
None yet
Development

No branches or pull requests