Description
Question
fragmentIsFulfilled
returns a boolean for whether or not a response resolves a fragment. I believe this is impossible to know by the client.
Imagine the schema:
type Query { appConfiguration: AppConfiguration! }
interface AppConfiguration {
foo: String!
}
interface MobileConfiguration implements AppConfiguration {
foo: String!
}
type iPhoneAppConfiguration implements AppConfiguration & MobileAppConfiguration {
foo: String!
}
type ChromeAppConfiguration implements AppConfiguration {
foo: String!
}
And the query:
query AppConfiguration {
appConfiguration {
...Config
}
}
fragment Config on MobileAppConfiguration {
foo
}
This creates a type that looks like:
struct AppConfiguration {
...
var asMobileAppConfiguration: AsMobileAppConfiguration? { _asInlineFragment() }
}
In the response, when the concrete type is an iPhoneAppConfiguration asMobileAppConfiguration
is non-nil. If the response returned a ChromeAppConfiguration, asMobileAppConfiguration would be nil. This works as expected.
But imagine 2010 rolls around and the following type is added to the schema.
type iPadAppConfiguration implements AppConfiguration & MobileAppConfiguration {
foo: String!
}
This is a non-breaking server change, however the apps running the query from above would now see nil
for asMobileAppConfiguration
even though the server is still fulfilling the fragment on MobileAppConfiguration.
Without knowing all the implementation details. I assume Apollo stores all the possible concrete types at generation time then uses the __typename
field at runtime and checks if it's one of the possible concrete types. However, because of the way graphql schemas are allowed to evolve over time, it's impossible to know at runtime all the possible concrete types.
To me this seems like incorrect behavior, but please help me understand if I'm missing something.