Skip to content

Accessing an unset deprecated field in input causes a crash #3506

@pixelmatrix

Description

@pixelmatrix

Summary

We recently deprecated a field in an input object.

As a result, codegen created a new default initializer that that excludes that field.

public init(newField: GraphQLNullable<MyType>) {
  __data = InputDict(["newField": newField])
}

@available(*, deprecated, message: "Argument 'oldField' is deprecated")
public init(oldField: GraphQLNullable<MyType>) {
  __data = InputDict(["oldField": oldField])
}

Now, when accessing the deprecated field through the input object, it crashes because that field is not actually present in the underlying InputDict.

Generated code for the property looks like:

@available(*, deprecated, message: "Use newField instead")
public var oldField: GraphQLNullable<MyType> {
  get { __data["oldField"] }
  set { __data["oldField"] = newValue }
}

…which calls:

public subscript<T: GraphQLOperationVariableValue>(key: String) -> T {
  get { data[key] as! T }
  set { data[key] = newValue }
}

Version

1.15.3

Steps to reproduce the behavior

  1. Deprecate a field of an input object in your schema
  2. Run codegen to pick up the field
  3. Create an instance of the input object using the new default initializer
let input = MyInput()
  1. Try accessing the deprecated field on the object
if input.oldField == .none { // crash!
  print("worked")
}

Logs

Could not cast value of type 'Swift.Optional<ApolloAPI.GraphQLOperationVariableValue>' (0x1f05300a0) to 'ApolloAPI.GraphQLNullable<Swift.String>' (0x1f052f388).

Anything else?

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugGenerally incorrect behavior

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions