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

Nondeterministic output when query and subscription return (non)nullable list elements #896

Closed
zannen opened this issue Oct 11, 2019 · 5 comments

Comments

@zannen
Copy link
Contributor

zannen commented Oct 11, 2019

With the schema below, output is nondeterministic.

This behaviour occurs when a query returns a list of nullable things and a subscription returns a list of non-nullable things (or vice versa), the generated code for the subscription (it seems to always be the subscription) flips between using the normal function (marshalOThing2ᚖgqlgentestᚐThing) and the function with the null check (marshalNThing2ᚖgqlgentestᚐThing).

This behaviour does not occur:

  • with two queries, one returning [Thing] and one returning [Thing!]
  • with two subscriptions, one returning [Thing] and one returning [Thing!]
  • with one query and one subscription, if Thing is replaced by String

What did you expect?

Deterministic output.

Minimal graphql.schema to reproduce

schema {
  query: Query
  subscription: Subscription
}

type Thing {id: Int}

type Query {
  things1: [Thing] # Note the "!" or lack thereof.
}

type Subscription {
  things2: [Thing!] # Note the "!" or lack thereof.
}

gqlgen.yml

---
schema: graphql.schema
exec:
  filename: generated.go
model:
  filename: models.go

Here's the script I've been using to test. Run it and wait for a while to see if files with different checksums get created.

rm -f *generated.go
while test "$(find -name '*-generated.go' | wc -l)" -lt 2 ; do
  date
  gqlgen -c gqlgen.yml
  cp -a generated.go "$(md5sum generated.go | awk '{print $1}')-generated.go"
  sleep 1
done

versions

  • gqlgen version v0.10.1
  • go version go1.11.13 linux/amd64
  • dep or go modules? go modules: go.mod
    module gqlgentest
    
    require (
    	github.com/99designs/gqlgen v0.10.1
    	github.com/vektah/gqlparser v1.1.2
    )
    
@alexsn
Copy link
Contributor

alexsn commented Oct 12, 2019

I have the exact some issue.

@zannen
Copy link
Contributor Author

zannen commented Oct 13, 2019

The template creating the code line that flips is codegen/type.gotpl L93.

Then we head to MarshalFunc then to UniquenessKey:

func (t *TypeReference) UniquenessKey() string {
	var nullability = "O"
	if t.GQL.NonNull {
		nullability = "N"
	}

	return nullability + t.Definition.Name + "2" + templates.TypeIdentifier(t.GO)
}

Let's see what's happening with t.GQL.NonNull.

@zannen
Copy link
Contributor Author

zannen commented Oct 14, 2019

PR #900 should fix this.

@colinschoen
Copy link

Pretty sure I am running into this too. Thanks for the PR @zannen.

vektah added a commit that referenced this issue Nov 11, 2019
Update UniquenessKey for when Element is/isn't nullable (#896)
@zannen
Copy link
Contributor Author

zannen commented Nov 11, 2019

Thanks @vektah.

@zannen zannen closed this as completed Nov 11, 2019
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
With a schema:
type Query {
  things1: [Thing] # Note the lack of "!"
}

type Subscription {
  things2: [Thing!] # Note the "!"
}

the UniquenessKey for the two lists is the same, which causes non-deterministic output.
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
cgxxv pushed a commit to cgxxv/gqlgen that referenced this issue Mar 25, 2022
Update UniquenessKey for when Element is/isn't nullable (99designs#896)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants