# Object Type Definition Object Type is the most frequently used primitive in a typical GraphQL application. Conceptually Object Type is a collection of Fields. Each field, in turn, has its own type which allows building complex hierarchies. ## Writing Object Types In **graphql-php** object type is an instance of `GraphQL\Type\Definition\ObjectType` (or one of its subclasses) which accepts a configuration array in its constructor: ```php use GraphQL\Type\Definition\ObjectType; use GraphQL\Type\Definition\Type; use GraphQL\Examples\Blog\Data\DataSource; use GraphQL\Examples\Blog\Data\Story; $userType = new ObjectType([ 'name' => 'User', 'description' => 'Our blog visitor', 'fields' => [ 'firstName' => [ 'type' => Type::string(), 'description' => 'User first name' ], 'email' => Type::string() ] ]); $blogStory = new ObjectType([ 'name' => 'Story', 'fields' => [ 'body' => Type::string(), 'author' => [ 'type' => $userType, 'description' => 'Story author', 'resolve' => fn (Story $blogStory): ?User => DataSource::findUser($blogStory->authorId), ], 'likes' => [ 'type' => Type::listOf($userType), 'description' => 'List of users who liked the story', 'args' => [ 'limit' => [ 'type' => Type::int(), 'description' => 'Limit the number of recent likes returned', 'defaultValue' => 10 ] ], 'resolve' => fn (Story $blogStory, array $args): array => DataSource::findLikes($blogStory->id, $args['limit']), ] ] ]); ``` This example uses **inline** style for Object Type definitions, but you can also use [inheritance or schema definition language](index.md#definition-styles). ## Configuration options | Option | Type | Notes | | ------------ | --------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | name | `string` | **Required.** Unique name of this object type within Schema | | fields | `array` or `callable` | **Required**. An array describing object fields or callable returning such an array. See [field configuration options](#field-configuration-options) section below for expected structure of each array entry. See also the section on [Circular types](#recurring-and-circular-types) for an explanation of when to use callable for this option. | | description | `string` | Plain-text description of this type for clients (e.g. used by [GraphiQL](https://github.com/graphql/graphiql) for auto-generated documentation) | | interfaces | `array` or `callable` | List of interfaces implemented by this type or callable returning such a list. See [Interface Types](interfaces.md) for details. See also the section on [Circular types](#recurring-and-circular-types) for an explanation of when to use callable for this option. | | isTypeOf | `callable` | **function ($value, $context, [ResolveInfo](../class-reference.md#graphqltypedefinitionresolveinfo) $info): bool**
Expected to return **true** if **$value** qualifies for this type (see section about [Abstract Type Resolution](interfaces.md#interface-role-in-data-fetching) for explanation). | | resolveField | `callable` | **function ($value, array $args, $context, [ResolveInfo](../class-reference.md#graphqltypedefinitionresolveinfo) $info): mixed**
Given the **$value** of this type, it is expected to return value for a field defined in **$info->fieldName**. A good place to define a type-specific strategy for field resolution. See section on [Data Fetching](../data-fetching.md) for details. | | visible | `bool` or `callable` | Defaults to `true`. The given callable receives no arguments and is expected to return a `bool`, it is called once when the field may be accessed. The field is treated as if it were not defined at all when this is `false`. | ### Field configuration options | Option | Type | Notes | | ----------------- | ---------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | name | `string` | **Required.** Name of the field. When not set - inferred from **fields** array key (read about [shorthand field definition](#shorthand-field-definitions) below) | | type | `Type` | **Required.** An instance of internal or custom type. Note: type must be represented by a single instance within one schema (see also [lazy loading of types](../schema-definition.md#lazy-loading-of-types)) | | args | `array` | An array describing any number of possible field arguments, each element being an array. See [field argument configuration options](#field-argument-configuration-options). | | resolve | `callable` | **function ($objectValue, array $args, $context, [ResolveInfo](../class-reference.md#graphqltypedefinitionresolveinfo) $info): mixed**
Given the **$objectValue** of this type, it is expected to return actual value of the current field. See section on [Data Fetching](../data-fetching.md) for details | | complexity | `callable` | **function (int $childrenComplexity, array $args): int**
Used to restrict query complexity. The feature is disabled by default, read about [Security](../security.md#query-complexity-analysis) to use it. | | description | `string` | Plain-text description of this field for clients (e.g. used by [GraphiQL](https://github.com/graphql/graphiql) for auto-generated documentation) | | deprecationReason | `string` | Text describing why this field is deprecated. When not empty - field will not be returned by introspection queries (unless forced) | ### Field argument configuration options | Option | Type | Notes | | ------------ | -------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | name | `string` | **Required.** Name of the argument. When not set - inferred from **args** array key | | type | `Type` | **Required.** Instance of one of [Input Types](inputs.md) (**scalar**, **enum**, **InputObjectType** + any combination of those with **nonNull** and **listOf** modifiers) | | description | `string` | Plain-text description of this argument for clients (e.g. used by [GraphiQL](https://github.com/graphql/graphiql) for auto-generated documentation) | | defaultValue | `scalar` | Default value for this argument. Use the internal value if specifying a default for an **enum** type | ## Shorthand field definitions Fields can be also defined in **shorthand** notation (with only **name** and **type** options): ```php 'fields' => [ 'id' => Type::id(), 'fieldName' => $fieldType ] ``` which is equivalent of: ```php 'fields' => [ 'id' => ['type' => Type::id()], 'fieldName' => ['type' => $fieldName] ] ``` which is in turn equivalent of the full form: ```php 'fields' => [ ['name' => 'id', 'type' => Type::id()], ['name' => 'fieldName', 'type' => $fieldName] ] ``` Same shorthand notation applies to field arguments as well. ## Recurring and circular types Almost all real-world applications contain recurring or circular types. Think user friends or nested comments for example. **graphql-php** allows such types, but you have to use `callable` in option **fields** (and/or **interfaces**). For example: ```php use GraphQL\Type\Definition\Type; use GraphQL\Type\Definition\ObjectType; $userType = new ObjectType([ 'name' => 'User', 'fields' => function () use (&$userType): array { return [ 'email' => [ 'type' => Type::string() ], 'friends' => [ 'type' => Type::listOf($userType) ] ]; }, ]); ``` Same example for [inheritance style of type definitions](index.md#definition-styles) using a type registry (see [lazy loading of types](../schema-definition.md#lazy-loading-of-types)): ```php use GraphQL\Type\Definition\ListOfType; use GraphQL\Type\Definition\ScalarType; use GraphQL\Type\Definition\Type; use GraphQL\Type\Definition\ObjectType; class UserType extends ObjectType { public function __construct() { parent::__construct([ 'fields' => [ 'email' => fn (): ScalarType => MyTypes::string(), 'friends' => fn (): ListOfType => MyTypes::listOf(MyTypes::user()) ], ]); } } class MyTypes { private static UserType $user; public static function user(): UserType { return self::$user ??= new UserType(); } public static function string(): ScalarType { return Type::string(); } public static function listOf($type): ListOfType { return Type::listOf($type); } } ``` ## Field Resolution Field resolution is the primary mechanism in **graphql-php** for returning actual data for your fields. It is implemented using **resolveField** callable in type definition or **resolve** callable in field definition (which has precedence). Read the section on [Data Fetching](../data-fetching.md) for a complete description of this process. ## Custom Metadata All types in **graphql-php** accept configuration array. In some cases, you may be interested in passing your own metadata for type or field definition. **graphql-php** preserves original configuration array in every type or field instance in public property **$config**. Use it to implement app-level mappings and definitions.