From c57fe1eaad114dcd02fb13f62d16f00201d60a4d Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Sun, 25 Oct 2026 16:51:13 +0100 Subject: [PATCH 01/24] Format directive descriptions with one sentence per line MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 81 ++++++------------- .../digging-deeper/client-directives.md | 3 +- .../eloquent/complex-where-conditions.md | 8 +- src/Async/AsyncDirective.php | 6 +- src/Auth/BaseCanDirective.php | 3 +- src/Auth/CanDirective.php | 12 +-- src/Auth/CanQueryDirective.php | 3 +- src/Auth/GuardDirective.php | 3 +- src/Cache/CacheDirective.php | 3 +- src/Defer/DeferrableDirective.php | 3 +- .../Directives/ComposeDirectiveDirective.php | 4 +- .../Directives/ExtendsDirective.php | 4 +- .../Directives/ExternalDirective.php | 6 +- .../Directives/InaccessibleDirective.php | 9 +-- .../Directives/InterfaceObjectDirective.php | 3 +- src/Federation/Directives/KeyDirective.php | 3 +- .../Directives/OverrideDirective.php | 9 ++- .../Directives/ProvidesDirective.php | 10 +-- .../Directives/RequiresDirective.php | 9 +-- .../Directives/ShareableDirective.php | 9 +-- src/Federation/Directives/TagDirective.php | 4 +- src/GlobalId/GlobalIdDirective.php | 3 +- src/GlobalId/NodeDirective.php | 3 +- src/Schema/Directives/BelongsToDirective.php | 3 +- .../Directives/BelongsToManyDirective.php | 6 +- src/Schema/Directives/CreateDirective.php | 3 +- src/Schema/Directives/CreateManyDirective.php | 3 +- src/Schema/Directives/DeleteDirective.php | 3 +- src/Schema/Directives/EnumDirective.php | 3 +- src/Schema/Directives/HasManyDirective.php | 6 +- .../Directives/HasManyThroughDirective.php | 6 +- src/Schema/Directives/HasOneDirective.php | 3 +- .../Directives/HasOneThroughDirective.php | 3 +- src/Schema/Directives/InjectDirective.php | 9 +-- src/Schema/Directives/LazyLoadDirective.php | 3 +- src/Schema/Directives/LikeDirective.php | 3 +- src/Schema/Directives/LimitDirective.php | 13 ++- src/Schema/Directives/MethodDirective.php | 3 +- src/Schema/Directives/MorphManyDirective.php | 6 +- src/Schema/Directives/MorphOneDirective.php | 3 +- src/Schema/Directives/MorphToDirective.php | 3 +- .../Directives/MorphToManyDirective.php | 6 +- src/Schema/Directives/NestDirective.php | 3 +- src/Schema/Directives/SpreadDirective.php | 3 +- src/Schema/Directives/ThrottleDirective.php | 3 +- src/Schema/Directives/UpdateDirective.php | 3 +- src/Schema/Directives/UpdateManyDirective.php | 3 +- src/Schema/Directives/UploadDirective.php | 3 +- src/Schema/Directives/UpsertDirective.php | 3 +- src/Schema/Directives/UpsertManyDirective.php | 3 +- .../Directives/WhereBetweenDirective.php | 3 +- .../Directives/WhereNotBetweenDirective.php | 3 +- src/Schema/Directives/WithCountDirective.php | 5 +- src/Schema/Directives/WithDirective.php | 3 +- src/SoftDeletes/SoftDeletesDirective.php | 3 +- .../Directives/BroadcastDirective.php | 3 +- src/Tracing/TracingDirective.php | 3 +- src/Validation/RulesDirective.php | 3 +- src/Validation/RulesForArrayDirective.php | 3 +- src/Validation/ValidatorDirective.php | 5 +- .../WhereHasConditionsDirective.php | 8 +- 61 files changed, 125 insertions(+), 230 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 1fad092db3..5ed3fd552b 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -156,11 +156,9 @@ type Query { Defer the execution of mutations to [queued jobs](https://laravel.com/docs/queues). This directive must only be used on fields of the root mutation type. -When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched -and the value `true` is returned - thus the fields return type must be `Boolean!`. +When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned - thus the fields return type must be `Boolean!`. -Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, -it will actually execute the underlying field resolver. +Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. The handlers in the `config/lighthouse.php` option `error_handlers` are not called. """ @@ -221,8 +219,7 @@ Resolves a field through the Eloquent `BelongsTo` relationship. """ directive @belongsTo( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -273,8 +270,7 @@ Resolves a field through the Eloquent `BelongsToMany` relationship. """ directive @belongsToMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -303,8 +299,7 @@ directive @belongsToMany( maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -729,8 +724,7 @@ directive @cache( """ Limit access to cached data to the currently authenticated user. - When the field is accessible by guest users, this will not have - any effect, they will access a shared cache. + When the field is accessible by guest users, this will not have any effect, they will access a shared cache. """ private: Boolean = false ) on FIELD_DEFINITION @@ -818,8 +812,7 @@ injectArgs: Boolean! = false """ Statically defined arguments that are passed to `Gate::check`. -You may pass arbitrary GraphQL literals, -e.g.: [1, 2, 3] or { foo: "bar" } +You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } """ args: CanArgs @@ -1029,8 +1022,7 @@ A custom complexity function may look like the following, refer to the [complexi ```php namespace App\GraphQL\Security; -final class ComplexityAnalyzer -{ +final class ComplexityAnalyzer { public function userPosts(int $childrenComplexity, array $args): int { $postComplexity = ($args['includeFullText'] ?? false) @@ -1656,8 +1648,7 @@ type Mutation { The event class must accept an `Order` in the constructor: ```php -final class PlacedOrder -{ +final class PlacedOrder { public function __construct(Order $order) { ... } } ``` @@ -2146,13 +2137,9 @@ You can get the appropriate Object Type from Lighthouse's type registry. ```php namespace App\GraphQL\Interfaces; -use GraphQL\Type\Definition\Type; -use Nuwave\Lighthouse\Execution\ResolveInfo; -use Nuwave\Lighthouse\Schema\TypeRegistry; -use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use GraphQL\Type\Definition\Type; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Schema\TypeRegistry; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Commentable -{ +final class Commentable { public function __construct( private TypeRegistry $typeRegistry ) {} @@ -2778,8 +2765,7 @@ The `resolver` argument must specify a function. It receives the decoded `id` and resolves to a result. ```php -public function byId($id): array -{ +public function byId($id): array { return [ 'DE' => ['name' => 'Germany'], 'MY' => ['name' => 'Malaysia'], @@ -3016,8 +3002,7 @@ type Query { ): PostPaginator } -"A paginated list of Post items." -type PostPaginator { +"A paginated list of Post items." type PostPaginator { "A list of Post items." data: [Post!]! @@ -3025,8 +3010,7 @@ type PostPaginator { paginatorInfo: PaginatorInfo! } -"Information about pagination using a fully featured paginator." -type PaginatorInfo { +"Information about pagination using a fully featured paginator." type PaginatorInfo { "Number of items in the current page." count: Int! @@ -3097,8 +3081,7 @@ type Query { ): PostConnection } -"A paginated list of Post edges." -type PostConnection { +"A paginated list of Post edges." type PostConnection { "Pagination information about the list of edges." pageInfo: PageInfo! @@ -3106,8 +3089,7 @@ type PostConnection { edges: [PostEdge] } -"An edge that contains a node of type Post and a cursor." -type PostEdge { +"An edge that contains a node of type Post and a cursor." type PostEdge { "The Post node." node: Post @@ -3148,8 +3130,7 @@ type Query { ): PostSimplePaginator } -"A paginated list of Post items." -type PostSimplePaginator { +"A paginated list of Post items." type PostSimplePaginator { "A list of Post items." data: [Post!]! @@ -3157,8 +3138,7 @@ type PostSimplePaginator { paginatorInfo: SimplePaginatorInfo! } -"Information about pagination using a simple paginator." -type SimplePaginatorInfo { +"Information about pagination using a simple paginator." type SimplePaginatorInfo { "Number of items in the current page." count: Int! @@ -3259,13 +3239,9 @@ It must return an instance of `Illuminate\Database\Query\Builder`. ```php namespace App\Models; -use Illuminate\Support\Facades\DB; -use Illuminate\Database\Query\Builder; -use Nuwave\Lighthouse\Execution\ResolveInfo; -use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use Illuminate\Support\Facades\DB; use Illuminate\Database\Query\Builder; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Blog -{ +final class Blog { public function statistics(mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolveInfo): Builder { return DB::table('posts') @@ -3295,8 +3271,7 @@ namespace App\GraphQL\Queries; use Illuminate\Pagination\LengthAwarePaginator; -final class Posts -{ +final class Posts { /** * @param null $root Always null, since this field has no parent. * @param array{} $args The field arguments passed by the client. @@ -3553,11 +3528,9 @@ type Query { The scope will be passed the value of the client-given argument: ```php -use Illuminate\Database\Eloquent\Builder; -use Illuminate\Database\Eloquent\Model; +use Illuminate\Database\Eloquent\Builder; use Illuminate\Database\Eloquent\Model; -final class Post extends Model -{ +final class Post extends Model { public function scopeTrending(Builder $query, bool $trending): Builder { ... } } ``` @@ -3877,13 +3850,9 @@ It must resolve an Object Type from Lighthouse `TypeRegistry`. ```php namespace App\GraphQL\Unions; -use GraphQL\Type\Definition\Type; -use Nuwave\Lighthouse\Execution\ResolveInfo; -use Nuwave\Lighthouse\Schema\TypeRegistry; -use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use GraphQL\Type\Definition\Type; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Schema\TypeRegistry; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Person -{ +final class Person { public function __construct( private TypeRegistry $typeRegistry ) {} diff --git a/docs/master/digging-deeper/client-directives.md b/docs/master/digging-deeper/client-directives.md index 3bf598a75f..40bd4207cd 100644 --- a/docs/master/digging-deeper/client-directives.md +++ b/docs/master/digging-deeper/client-directives.md @@ -18,8 +18,7 @@ Allows for conditional exclusion during execution as described by the `if` argum ```graphql directive @skip( """ - If the value passed into the if field is true the field this - is decorating will not be included in the query response. + If the value passed into the if field is true the field this is decorating will not be included in the query response. """ if: Boolean! ) on FIELD | FRAGMENT_SPREAD | INLINE_FRAGMENT diff --git a/docs/master/eloquent/complex-where-conditions.md b/docs/master/eloquent/complex-where-conditions.md index 29856b5851..50c57ef2e2 100644 --- a/docs/master/eloquent/complex-where-conditions.md +++ b/docs/master/eloquent/complex-where-conditions.md @@ -237,16 +237,14 @@ Qualify such columns with the table name, e.g. `@whereConditions(columns: ["role ```graphql """ -Allows clients to filter a query based on the existence of a related model, using -a dynamically controlled `WHERE` condition that applies to the relationship. +Allows clients to filter a query based on the existence of a related model, using a dynamically controlled `WHERE` condition that applies to the relationship. """ directive @whereHasConditions( """ The Eloquent relationship that the conditions will be applied to. - This argument can be omitted if the argument name follows the naming - convention `has{$RELATION}`. For example, if the Eloquent relationship - is named `posts`, the argument name must be `hasPosts`. + This argument can be omitted if the argument name follows the naming convention `has{$RELATION}`. + For example, if the Eloquent relationship is named `posts`, the argument name must be `hasPosts`. """ relation: String diff --git a/src/Async/AsyncDirective.php b/src/Async/AsyncDirective.php index 0be52a0dfb..f3547ab444 100644 --- a/src/Async/AsyncDirective.php +++ b/src/Async/AsyncDirective.php @@ -26,11 +26,9 @@ public static function definition(): string Defer the execution of mutations to [queued jobs](https://laravel.com/docs/queues). This directive must only be used on fields of the root mutation type. -When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched -and the value `true` is returned - thus the fields return type must be `Boolean!`. +When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned - thus the fields return type must be `Boolean!`. -Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, -it will actually execute the underlying field resolver. +Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. The handlers in the `config/lighthouse.php` option `error_handlers` are not called. """ diff --git a/src/Auth/BaseCanDirective.php b/src/Auth/BaseCanDirective.php index 3401ec37c6..355a216514 100644 --- a/src/Auth/BaseCanDirective.php +++ b/src/Auth/BaseCanDirective.php @@ -34,8 +34,7 @@ protected static function commonArguments(): string """ Statically defined arguments that are passed to `Gate::check`. - You may pass arbitrary GraphQL literals, - e.g.: [1, 2, 3] or { foo: "bar" } + You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } """ args: CanArgs diff --git a/src/Auth/CanDirective.php b/src/Auth/CanDirective.php index 21eb99249d..2bea898f0c 100644 --- a/src/Auth/CanDirective.php +++ b/src/Auth/CanDirective.php @@ -44,8 +44,7 @@ public static function definition(): string """ Check a Laravel Policy to ensure the current user is authorized to access a field. -When `injectArgs` and `args` are used together, the client given -arguments will be passed before the static args. +When `injectArgs` and `args` are used together, the client given arguments will be passed before the static args. """ directive @can( """ @@ -75,16 +74,14 @@ public static function definition(): string """ Statically defined arguments that are passed to `Gate::check`. - You may pass arbitrary GraphQL literals, - e.g.: [1, 2, 3] or { foo: "bar" } + You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } CanArgs pseudo-scalar is defined in BaseCanDirective. """ args: CanArgs """ - Query for specific model instances to check the policy against, using arguments - with directives that add constraints to the query builder, such as `@eq`. + Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. Mutually exclusive with `resolved`, `find`, and `root`. """ @@ -96,8 +93,7 @@ public static function definition(): string scopes: [String!] """ - If your policy checks against specific model instances, specify - the name of the field argument that contains its primary key(s). + If your policy checks against specific model instances, specify the name of the field argument that contains its primary key(s). You may pass the string in dot notation to use nested inputs. diff --git a/src/Auth/CanQueryDirective.php b/src/Auth/CanQueryDirective.php index 8b7c417a73..f430336293 100644 --- a/src/Auth/CanQueryDirective.php +++ b/src/Auth/CanQueryDirective.php @@ -15,8 +15,7 @@ public static function definition(): string """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using arguments -with directives that add constraints to the query builder, such as `@eq`. +Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. """ directive @canQuery( {$commonArguments} diff --git a/src/Auth/GuardDirective.php b/src/Auth/GuardDirective.php index e2b1a1ed10..6c3b2c1fb9 100644 --- a/src/Auth/GuardDirective.php +++ b/src/Auth/GuardDirective.php @@ -32,8 +32,7 @@ public static function definition(): string """ Run authentication through one or more guards from `config/auth.php`. -This is run per field and may allow unauthenticated -users to still receive partial results. +This is run per field and may allow unauthenticated users to still receive partial results. Used upon an object, it applies to all fields within. """ diff --git a/src/Cache/CacheDirective.php b/src/Cache/CacheDirective.php index ff43a1c812..2b03631951 100644 --- a/src/Cache/CacheDirective.php +++ b/src/Cache/CacheDirective.php @@ -36,8 +36,7 @@ public static function definition(): string """ Limit access to cached data to the currently authenticated user. - When the field is accessible by guest users, this will not have - any effect, they will access a shared cache. + When the field is accessible by guest users, this will not have any effect, they will access a shared cache. """ private: Boolean = false ) on FIELD_DEFINITION diff --git a/src/Defer/DeferrableDirective.php b/src/Defer/DeferrableDirective.php index ff420fde2a..f09307e248 100644 --- a/src/Defer/DeferrableDirective.php +++ b/src/Defer/DeferrableDirective.php @@ -26,8 +26,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Do not use this directive directly, it is automatically added to the schema -when using the defer extension. +Do not use this directive directly, it is automatically added to the schema when using the defer extension. """ directive @deferrable on FIELD_DEFINITION GRAPHQL; diff --git a/src/Federation/Directives/ComposeDirectiveDirective.php b/src/Federation/Directives/ComposeDirectiveDirective.php index 6ad144fec0..4142609abd 100644 --- a/src/Federation/Directives/ComposeDirectiveDirective.php +++ b/src/Federation/Directives/ComposeDirectiveDirective.php @@ -12,9 +12,7 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Indicates to composition that all uses of a particular custom type system directive -in the subgraph schema should be preserved in the supergraph schema -(by default, composition omits most directives from the supergraph schema). +Indicates to composition that all uses of a particular custom type system directive in the subgraph schema should be preserved in the supergraph schema (by default, composition omits most directives from the supergraph schema). ```graphql extend schema diff --git a/src/Federation/Directives/ExtendsDirective.php b/src/Federation/Directives/ExtendsDirective.php index 11fada6851..2a874d0550 100644 --- a/src/Federation/Directives/ExtendsDirective.php +++ b/src/Federation/Directives/ExtendsDirective.php @@ -13,8 +13,8 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Some libraries such as graphql-java don't have native support for type extensions in their printer. Apollo Federation -supports using an @extends directive in place of extend type to annotate type references: +Some libraries such as graphql-java don't have native support for type extensions in their printer. +Apollo Federation supports using an @extends directive in place of extend type to annotate type references: type User @key(fields: "id") @extends { diff --git a/src/Federation/Directives/ExternalDirective.php b/src/Federation/Directives/ExternalDirective.php index cb272ade40..e42df21267 100644 --- a/src/Federation/Directives/ExternalDirective.php +++ b/src/Federation/Directives/ExternalDirective.php @@ -17,9 +17,9 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Individual federated services should be runnable without having the entire graph present. Fields marked with @external -are declarations of fields that are defined in another service. All fields referred to in @key, @requires, and @provides -directives need to have corresponding @external fields in the same service. +Individual federated services should be runnable without having the entire graph present. +Fields marked with @external are declarations of fields that are defined in another service. +All fields referred to in @key, @requires, and @provides directives need to have corresponding @external fields in the same service. https://www.apollographql.com/docs/apollo-server/federation/federation-spec/#schema-modifications-glossary """ diff --git a/src/Federation/Directives/InaccessibleDirective.php b/src/Federation/Directives/InaccessibleDirective.php index 500226d4ef..dd3dda0c25 100644 --- a/src/Federation/Directives/InaccessibleDirective.php +++ b/src/Federation/Directives/InaccessibleDirective.php @@ -12,8 +12,7 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Indicates that a definition in the subgraph schema should be omitted from the router's API schema, -even if that definition is also present in other subgraphs. +Indicates that a definition in the subgraph schema should be omitted from the router's API schema, even if that definition is also present in other subgraphs. This means that the field is not exposed to clients at all. ```graphql @@ -24,10 +23,8 @@ public static function definition(): string } ``` -An @inaccessible field or type is not omitted from the supergraph schema, so the router -still knows it exists (but clients can't include it in operations). -This is what enables the router to use an @inaccessible field as part of an entity's @key -when combining entity fields from multiple subgraphs. +An @inaccessible field or type is not omitted from the supergraph schema, so the router still knows it exists (but clients can't include it in operations). +This is what enables the router to use an @inaccessible field as part of an entity's @key when combining entity fields from multiple subgraphs. If a type is marked @inaccessible, all fields that return that type must also be marked @inaccessible. Otherwise, a composition error occurs. diff --git a/src/Federation/Directives/InterfaceObjectDirective.php b/src/Federation/Directives/InterfaceObjectDirective.php index 20646200a3..d82cc1a508 100644 --- a/src/Federation/Directives/InterfaceObjectDirective.php +++ b/src/Federation/Directives/InterfaceObjectDirective.php @@ -15,8 +15,7 @@ public static function definition(): string Indicates that an object definition serves as an abstraction of another subgraph's entity interface. This abstraction enables a subgraph to automatically contribute fields to all entities that implement a particular entity interface. -During composition, the fields of every @interfaceObject are added both to their corresponding interface definition -and to all entity types that implement that interface. +During composition, the fields of every @interfaceObject are added both to their corresponding interface definition and to all entity types that implement that interface. https://www.apollographql.com/docs/federation/federated-types/federated-directives#interfaceobject """ diff --git a/src/Federation/Directives/KeyDirective.php b/src/Federation/Directives/KeyDirective.php index 9d92c24336..ef5148b3cc 100644 --- a/src/Federation/Directives/KeyDirective.php +++ b/src/Federation/Directives/KeyDirective.php @@ -16,8 +16,7 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -The @key directive is used to indicate a combination of fields that -can be used to uniquely identify and fetch an object or interface. +The @key directive is used to indicate a combination of fields that can be used to uniquely identify and fetch an object or interface. """ directive @key( """ diff --git a/src/Federation/Directives/OverrideDirective.php b/src/Federation/Directives/OverrideDirective.php index a29cda79b9..de45e2e578 100644 --- a/src/Federation/Directives/OverrideDirective.php +++ b/src/Federation/Directives/OverrideDirective.php @@ -12,8 +12,8 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Indicates that an object field is now resolved by this subgraph instead of another subgraph -where it's also defined. This enables you to migrate a field from one subgraph to another. +Indicates that an object field is now resolved by this subgraph instead of another subgraph where it's also defined. +This enables you to migrate a field from one subgraph to another. You can apply @override to entity fields and fields of the root operation types (such as Query and Mutation). @@ -24,8 +24,9 @@ public static function definition(): string } ``` -You can apply @override to a @shareable field. If you do, only the subgraph you provide -in the from argument no longer resolves that field. Other subgraphs can still resolve the field. +You can apply @override to a @shareable field. +If you do, only the subgraph you provide in the from argument no longer resolves that field. +Other subgraphs can still resolve the field. Only one subgraph can @override any given field. If multiple subgraphs attempt to @override the same field, a composition error occurs. diff --git a/src/Federation/Directives/ProvidesDirective.php b/src/Federation/Directives/ProvidesDirective.php index edc6151bb9..0177570e10 100644 --- a/src/Federation/Directives/ProvidesDirective.php +++ b/src/Federation/Directives/ProvidesDirective.php @@ -12,8 +12,8 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -The `@provides` directive is used to annotate the expected returned fieldset from a field -on a base type that is guaranteed to be selectable by the gateway. Given the following example: +The `@provides` directive is used to annotate the expected returned fieldset from a field on a base type that is guaranteed to be selectable by the gateway. +Given the following example: ```graphql type Review @key(fields: "id") { @@ -26,10 +26,8 @@ public static function definition(): string } ``` -When fetching `Review.product` from the Reviews service, it is possible to request the `name` -with the expectation that the Reviews service can provide it when going from review to product. -`Product.name` is an external field on an external type which is why the local type extension -of `Product` and annotation of `name` is required. +When fetching `Review.product` from the Reviews service, it is possible to request the `name` with the expectation that the Reviews service can provide it when going from review to product. +`Product.name` is an external field on an external type which is why the local type extension of `Product` and annotation of `name` is required. https://www.apollographql.com/docs/federation/federation-spec/#provides """ diff --git a/src/Federation/Directives/RequiresDirective.php b/src/Federation/Directives/RequiresDirective.php index 140272ba48..fe478ac107 100644 --- a/src/Federation/Directives/RequiresDirective.php +++ b/src/Federation/Directives/RequiresDirective.php @@ -13,9 +13,9 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -The @requires directive is used to annotate the required input fieldset from a base type for a resolver. It is used to -develop a query plan where the required fields may not be needed by the client, but the service may need additional -information from other services. For example: +The @requires directive is used to annotate the required input fieldset from a base type for a resolver. +It is used to develop a query plan where the required fields may not be needed by the client, but the service may need additional information from other services. +For example: extend type User @key(fields: "id") { id: ID! @external @@ -25,8 +25,7 @@ public static function definition(): string """ directive @requires( """ - It is used to develop a query plan where the required fields may not be needed by the client, but the service may - need additional information from other services. + It is used to develop a query plan where the required fields may not be needed by the client, but the service may need additional information from other services. """ fields: _FieldSet! ) on FIELD_DEFINITION diff --git a/src/Federation/Directives/ShareableDirective.php b/src/Federation/Directives/ShareableDirective.php index 718ba1d8f7..bced58bb45 100644 --- a/src/Federation/Directives/ShareableDirective.php +++ b/src/Federation/Directives/ShareableDirective.php @@ -12,8 +12,7 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Indicates that an object type's field is allowed to be resolved by multiple subgraphs -(by default in Federation 2, object fields can be resolved by only one subgraph). +Indicates that an object type's field is allowed to be resolved by multiple subgraphs (by default in Federation 2, object fields can be resolved by only one subgraph). If applied to an object type definition, all of that type's fields are considered @shareable. ```graphql @@ -28,11 +27,9 @@ public static function definition(): string } ``` -If a field is marked @shareable in any subgraph, it must be marked as either -@shareable or @external in every Federation 2 subgraph that defines it. +If a field is marked @shareable in any subgraph, it must be marked as either @shareable or @external in every Federation 2 subgraph that defines it. -If a field is included in an entity's @key directive, that field is automatically -considered @shareable and the directive is not required in the corresponding subgraph(s). +If a field is included in an entity's @key directive, that field is automatically considered @shareable and the directive is not required in the corresponding subgraph(s). https://www.apollographql.com/docs/federation/federated-types/federated-directives#shareable """ diff --git a/src/Federation/Directives/TagDirective.php b/src/Federation/Directives/TagDirective.php index c3ba87fe8a..e29d8b1a0e 100644 --- a/src/Federation/Directives/TagDirective.php +++ b/src/Federation/Directives/TagDirective.php @@ -12,8 +12,8 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Applies arbitrary string metadata to a schema location. Custom tooling can use this metadata -during any step of the schema delivery flow, including composition, static analysis, and documentation. +Applies arbitrary string metadata to a schema location. +Custom tooling can use this metadata during any step of the schema delivery flow, including composition, static analysis, and documentation. ```graphql extend schema diff --git a/src/GlobalId/GlobalIdDirective.php b/src/GlobalId/GlobalIdDirective.php index 7037ca5362..ab2e2298c9 100644 --- a/src/GlobalId/GlobalIdDirective.php +++ b/src/GlobalId/GlobalIdDirective.php @@ -23,8 +23,7 @@ public static function definition(): string """ Converts between IDs/types and global IDs. -When used upon a field, it encodes; -when used upon an argument, it decodes. +When used upon a field, it encodes; when used upon an argument, it decodes. """ directive @globalId( """ diff --git a/src/GlobalId/NodeDirective.php b/src/GlobalId/NodeDirective.php index c0c7fba5e9..6466c12a6f 100644 --- a/src/GlobalId/NodeDirective.php +++ b/src/GlobalId/NodeDirective.php @@ -32,8 +32,7 @@ public static function definition(): string """ Register a type for Relay's global object identification. -When used without any arguments, Lighthouse will attempt -to resolve the type through a model with the same name. +When used without any arguments, Lighthouse will attempt to resolve the type through a model with the same name. """ directive @node( """ diff --git a/src/Schema/Directives/BelongsToDirective.php b/src/Schema/Directives/BelongsToDirective.php index 0b0a61ca3b..04f9a364f1 100644 --- a/src/Schema/Directives/BelongsToDirective.php +++ b/src/Schema/Directives/BelongsToDirective.php @@ -12,8 +12,7 @@ public static function definition(): string """ directive @belongsTo( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/BelongsToManyDirective.php b/src/Schema/Directives/BelongsToManyDirective.php index c6d03c4477..3d5f70d4f8 100644 --- a/src/Schema/Directives/BelongsToManyDirective.php +++ b/src/Schema/Directives/BelongsToManyDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ directive @belongsToMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -44,8 +43,7 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/CreateDirective.php b/src/Schema/Directives/CreateDirective.php index e1ddee304b..f901650269 100644 --- a/src/Schema/Directives/CreateDirective.php +++ b/src/Schema/Directives/CreateDirective.php @@ -22,8 +22,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/CreateManyDirective.php b/src/Schema/Directives/CreateManyDirective.php index 8aed0ff428..dc802dbcec 100644 --- a/src/Schema/Directives/CreateManyDirective.php +++ b/src/Schema/Directives/CreateManyDirective.php @@ -22,8 +22,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/DeleteDirective.php b/src/Schema/Directives/DeleteDirective.php index 9765ad464d..74956fccb4 100644 --- a/src/Schema/Directives/DeleteDirective.php +++ b/src/Schema/Directives/DeleteDirective.php @@ -34,8 +34,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String diff --git a/src/Schema/Directives/EnumDirective.php b/src/Schema/Directives/EnumDirective.php index 2638b98976..8428b62492 100644 --- a/src/Schema/Directives/EnumDirective.php +++ b/src/Schema/Directives/EnumDirective.php @@ -9,8 +9,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Assign an internal value to an enum key. -When dealing with the Enum type in your code, -you will receive the defined value instead of the string key. +When dealing with the Enum type in your code, you will receive the defined value instead of the string key. """ directive @enum( """ diff --git a/src/Schema/Directives/HasManyDirective.php b/src/Schema/Directives/HasManyDirective.php index 4742dd2100..ed090b392c 100644 --- a/src/Schema/Directives/HasManyDirective.php +++ b/src/Schema/Directives/HasManyDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ directive @hasMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -44,8 +43,7 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/HasManyThroughDirective.php b/src/Schema/Directives/HasManyThroughDirective.php index 093296aaed..81317634e1 100644 --- a/src/Schema/Directives/HasManyThroughDirective.php +++ b/src/Schema/Directives/HasManyThroughDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ directive @hasManyThrough( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -42,8 +41,7 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/HasOneDirective.php b/src/Schema/Directives/HasOneDirective.php index 2daede7831..f2997e5fdf 100644 --- a/src/Schema/Directives/HasOneDirective.php +++ b/src/Schema/Directives/HasOneDirective.php @@ -12,8 +12,7 @@ public static function definition(): string """ directive @hasOne( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/HasOneThroughDirective.php b/src/Schema/Directives/HasOneThroughDirective.php index 0b2a875917..8b30cd1ebf 100644 --- a/src/Schema/Directives/HasOneThroughDirective.php +++ b/src/Schema/Directives/HasOneThroughDirective.php @@ -12,8 +12,7 @@ public static function definition(): string """ directive @hasOneThrough( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/InjectDirective.php b/src/Schema/Directives/InjectDirective.php index 2a6b013fed..37e266c60c 100644 --- a/src/Schema/Directives/InjectDirective.php +++ b/src/Schema/Directives/InjectDirective.php @@ -19,17 +19,14 @@ public static function definition(): string directive @inject( """ A path to the property of the context that will be injected. - If the value is nested within the context, you may use dot notation - to get it, e.g. "user.id". + If the value is nested within the context, you may use dot notation to get it, e.g. "user.id". """ context: String! """ The target name of the argument into which the value is injected. - You can use dot notation to set the value at arbitrary depth - within the incoming argument. - Use an asterisk `*` as a path segment to inject the value into every - element of a list found at that position. + You can use dot notation to set the value at arbitrary depth within the incoming argument. + Use an asterisk `*` as a path segment to inject the value into every element of a list found at that position. """ name: String! ) repeatable on FIELD_DEFINITION diff --git a/src/Schema/Directives/LazyLoadDirective.php b/src/Schema/Directives/LazyLoadDirective.php index 862c6f6707..c1e58fcbce 100644 --- a/src/Schema/Directives/LazyLoadDirective.php +++ b/src/Schema/Directives/LazyLoadDirective.php @@ -19,8 +19,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Perform a [lazy eager load](https://laravel.com/docs/eloquent-relationships#lazy-eager-loading) -on the relations of a list of models. +Perform a [lazy eager load](https://laravel.com/docs/eloquent-relationships#lazy-eager-loading) on the relations of a list of models. """ directive @lazyLoad( """ diff --git a/src/Schema/Directives/LikeDirective.php b/src/Schema/Directives/LikeDirective.php index b7748fa5ba..25a8c46fdd 100644 --- a/src/Schema/Directives/LikeDirective.php +++ b/src/Schema/Directives/LikeDirective.php @@ -36,8 +36,7 @@ public static function definition(): string key: String """ - Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the - placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. + Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. If specified, wildcard characters in the client-given input are escaped. If not specified, the client can pass wildcards unescaped. """ diff --git a/src/Schema/Directives/LimitDirective.php b/src/Schema/Directives/LimitDirective.php index 41a2aa86bf..7e677d2304 100644 --- a/src/Schema/Directives/LimitDirective.php +++ b/src/Schema/Directives/LimitDirective.php @@ -28,18 +28,15 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Allow clients to specify the maximum number of results to return when used on an argument, -or statically limit them when used on a field. +Allow clients to specify the maximum number of results to return when used on an argument, or statically limit them when used on a field. -By default, this directive does not influence the number of results the resolver queries internally, -but limits how much of it is returned to clients. Use the `builder` argument to change this. +By default, this directive does not influence the number of results the resolver queries internally, but limits how much of it is returned to clients. +Use the `builder` argument to change this. """ directive @limit( """ - You may set this to `true` if the field uses a query builder, - then this directive will apply a LIMIT clause to it. - Typically, this option should only be used for root fields, - as it may cause wrong results with batched relation queries. + You may set this to `true` if the field uses a query builder, then this directive will apply a LIMIT clause to it. + Typically, this option should only be used for root fields, as it may cause wrong results with batched relation queries. """ builder: Boolean! = false ) on ARGUMENT_DEFINITION | FIELD_DEFINITION diff --git a/src/Schema/Directives/MethodDirective.php b/src/Schema/Directives/MethodDirective.php index 0eee147767..ff2a18c570 100644 --- a/src/Schema/Directives/MethodDirective.php +++ b/src/Schema/Directives/MethodDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ Resolve a field by calling a method on the parent object. -Use this if the data is not accessible through simple property access or if you -want to pass argument to the method. +Use this if the data is not accessible through simple property access or if you want to pass argument to the method. """ directive @method( """ diff --git a/src/Schema/Directives/MorphManyDirective.php b/src/Schema/Directives/MorphManyDirective.php index 0e6d91a657..21ac5e912f 100644 --- a/src/Schema/Directives/MorphManyDirective.php +++ b/src/Schema/Directives/MorphManyDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ directive @morphMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -44,8 +43,7 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/MorphOneDirective.php b/src/Schema/Directives/MorphOneDirective.php index 8b259de66b..952518197a 100644 --- a/src/Schema/Directives/MorphOneDirective.php +++ b/src/Schema/Directives/MorphOneDirective.php @@ -12,8 +12,7 @@ public static function definition(): string """ directive @morphOne( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphToDirective.php b/src/Schema/Directives/MorphToDirective.php index 7a4fd2307a..45e3754021 100644 --- a/src/Schema/Directives/MorphToDirective.php +++ b/src/Schema/Directives/MorphToDirective.php @@ -12,8 +12,7 @@ public static function definition(): string """ directive @morphTo( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphToManyDirective.php b/src/Schema/Directives/MorphToManyDirective.php index 5d0bedd445..682e8d44e3 100644 --- a/src/Schema/Directives/MorphToManyDirective.php +++ b/src/Schema/Directives/MorphToManyDirective.php @@ -14,8 +14,7 @@ public static function definition(): string """ directive @morphToMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -44,8 +43,7 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/NestDirective.php b/src/Schema/Directives/NestDirective.php index 892e23f329..a7e69d784d 100644 --- a/src/Schema/Directives/NestDirective.php +++ b/src/Schema/Directives/NestDirective.php @@ -26,8 +26,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -A no-op nested arg resolver that delegates all calls -to the ArgResolver directives attached to the children. +A no-op nested arg resolver that delegates all calls to the ArgResolver directives attached to the children. """ directive @nest on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/SpreadDirective.php b/src/Schema/Directives/SpreadDirective.php index 88150f7635..d5948deef1 100644 --- a/src/Schema/Directives/SpreadDirective.php +++ b/src/Schema/Directives/SpreadDirective.php @@ -22,8 +22,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Merge the fields of a nested input object into the arguments of its parent -when processing the field arguments given by a client. +Merge the fields of a nested input object into the arguments of its parent when processing the field arguments given by a client. """ directive @spread on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/ThrottleDirective.php b/src/Schema/Directives/ThrottleDirective.php index 7991d038ce..3066f16e39 100644 --- a/src/Schema/Directives/ThrottleDirective.php +++ b/src/Schema/Directives/ThrottleDirective.php @@ -28,7 +28,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Sets rate limit to access the field. Does the same as ThrottleRequests Laravel Middleware. +Sets rate limit to access the field. +Does the same as ThrottleRequests Laravel Middleware. """ directive @throttle( """ diff --git a/src/Schema/Directives/UpdateDirective.php b/src/Schema/Directives/UpdateDirective.php index 2f30f6af84..c84476eeff 100644 --- a/src/Schema/Directives/UpdateDirective.php +++ b/src/Schema/Directives/UpdateDirective.php @@ -23,8 +23,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UpdateManyDirective.php b/src/Schema/Directives/UpdateManyDirective.php index 3af93be4bc..91c935e253 100644 --- a/src/Schema/Directives/UpdateManyDirective.php +++ b/src/Schema/Directives/UpdateManyDirective.php @@ -23,8 +23,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UploadDirective.php b/src/Schema/Directives/UploadDirective.php index e2c8a9dd14..82e9181ff1 100644 --- a/src/Schema/Directives/UploadDirective.php +++ b/src/Schema/Directives/UploadDirective.php @@ -13,8 +13,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Uploads given file to storage, removes the argument and sets -the returned path to the attribute key provided. +Uploads given file to storage, removes the argument and sets the returned path to the attribute key provided. This does not change the schema from a client perspective. """ diff --git a/src/Schema/Directives/UpsertDirective.php b/src/Schema/Directives/UpsertDirective.php index 526ee860bc..a8757f8149 100644 --- a/src/Schema/Directives/UpsertDirective.php +++ b/src/Schema/Directives/UpsertDirective.php @@ -39,8 +39,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UpsertManyDirective.php b/src/Schema/Directives/UpsertManyDirective.php index bc013293ce..384444e7bf 100644 --- a/src/Schema/Directives/UpsertManyDirective.php +++ b/src/Schema/Directives/UpsertManyDirective.php @@ -39,8 +39,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/WhereBetweenDirective.php b/src/Schema/Directives/WhereBetweenDirective.php index 29294e1481..1cd81682f1 100644 --- a/src/Schema/Directives/WhereBetweenDirective.php +++ b/src/Schema/Directives/WhereBetweenDirective.php @@ -15,8 +15,7 @@ public static function definition(): string """ Verify that a column's value is between two values. -The type of the input value this is defined upon should be -an `input` object with two fields. +The type of the input value this is defined upon should be an `input` object with two fields. """ directive @whereBetween( """ diff --git a/src/Schema/Directives/WhereNotBetweenDirective.php b/src/Schema/Directives/WhereNotBetweenDirective.php index efd0edbd3b..60cfcbc5fb 100644 --- a/src/Schema/Directives/WhereNotBetweenDirective.php +++ b/src/Schema/Directives/WhereNotBetweenDirective.php @@ -15,8 +15,7 @@ public static function definition(): string """ Verify that a column's value lies outside two values. -The type of the input value this is defined upon should be -an `input` object with two fields. +The type of the input value this is defined upon should be an `input` object with two fields. """ directive @whereNotBetween( """ diff --git a/src/Schema/Directives/WithCountDirective.php b/src/Schema/Directives/WithCountDirective.php index d3a95cdc5c..7a3c81cc21 100644 --- a/src/Schema/Directives/WithCountDirective.php +++ b/src/Schema/Directives/WithCountDirective.php @@ -22,9 +22,8 @@ public static function definition(): string """ Eager-load the count of an Eloquent relation if the field is queried. -Note that this does not return a value for the field, the count is simply -prefetched, assuming it is used to compute the field value. Use `@count` -if the field should simply return the relation count. +Note that this does not return a value for the field, the count is simply prefetched, assuming it is used to compute the field value. +Use `@count` if the field should simply return the relation count. """ directive @withCount( """ diff --git a/src/Schema/Directives/WithDirective.php b/src/Schema/Directives/WithDirective.php index 6eb3072eb1..b6ff4ddbf2 100644 --- a/src/Schema/Directives/WithDirective.php +++ b/src/Schema/Directives/WithDirective.php @@ -24,8 +24,7 @@ public static function definition(): string """ directive @with( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String diff --git a/src/SoftDeletes/SoftDeletesDirective.php b/src/SoftDeletes/SoftDeletesDirective.php index 5edb7d86b4..8ab5aab559 100644 --- a/src/SoftDeletes/SoftDeletesDirective.php +++ b/src/SoftDeletes/SoftDeletesDirective.php @@ -17,8 +17,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Allows to filter if trashed elements should be fetched. -This manipulates the schema by adding the argument -`trashed: Trashed @trashed` to the field. +This manipulates the schema by adding the argument `trashed: Trashed @trashed` to the field. """ directive @softDeletes on FIELD_DEFINITION GRAPHQL; diff --git a/src/Subscriptions/Directives/BroadcastDirective.php b/src/Subscriptions/Directives/BroadcastDirective.php index 0d31ed0793..63395595fe 100644 --- a/src/Subscriptions/Directives/BroadcastDirective.php +++ b/src/Subscriptions/Directives/BroadcastDirective.php @@ -15,8 +15,7 @@ public static function definition(): string """ Broadcast the results of a mutation to subscribed clients. -Ensure you place this after other field middleware directives that may transform the -result to broadcast the final value. +Ensure you place this after other field middleware directives that may transform the result to broadcast the final value. """ directive @broadcast( """ diff --git a/src/Tracing/TracingDirective.php b/src/Tracing/TracingDirective.php index efbab6e070..bc32bc1045 100644 --- a/src/Tracing/TracingDirective.php +++ b/src/Tracing/TracingDirective.php @@ -19,8 +19,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Do not use this directive directly, it is automatically added to the schema -when using the tracing extension. +Do not use this directive directly, it is automatically added to the schema when using the tracing extension. """ directive @tracing on FIELD_DEFINITION GRAPHQL; diff --git a/src/Validation/RulesDirective.php b/src/Validation/RulesDirective.php index d13301a60d..0f90103dd7 100644 --- a/src/Validation/RulesDirective.php +++ b/src/Validation/RulesDirective.php @@ -15,8 +15,7 @@ public static function definition(): string directive @rules( """ Specify the validation rules to apply to the field. - This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), - or the fully qualified class name of a custom validation rule. + This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input value are _not_ supported: - `exclude_if` diff --git a/src/Validation/RulesForArrayDirective.php b/src/Validation/RulesForArrayDirective.php index 5ba317ee21..87e43166f7 100644 --- a/src/Validation/RulesForArrayDirective.php +++ b/src/Validation/RulesForArrayDirective.php @@ -16,8 +16,7 @@ public static function definition(): string directive @rulesForArray( """ Specify the validation rules to apply to the field. - This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, - or the fully qualified class name of a custom validation rule. + This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` diff --git a/src/Validation/ValidatorDirective.php b/src/Validation/ValidatorDirective.php index a09990a1d3..4819d237d2 100644 --- a/src/Validation/ValidatorDirective.php +++ b/src/Validation/ValidatorDirective.php @@ -37,9 +37,8 @@ public static function definition(): string """ The name of the class to use. - If defined on an input, this defaults to a class called `{$inputName}Validator` in the - default validator namespace. For fields, it uses the namespace of the parent type - and the field name: `{$parent}\{$field}Validator`. + If defined on an input, this defaults to a class called `{$inputName}Validator` in the default validator namespace. + For fields, it uses the namespace of the parent type and the field name: `{$parent}\{$field}Validator`. """ class: String ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | INPUT_OBJECT diff --git a/src/WhereConditions/WhereHasConditionsDirective.php b/src/WhereConditions/WhereHasConditionsDirective.php index 8b2d4ea94b..5764b9d18b 100644 --- a/src/WhereConditions/WhereHasConditionsDirective.php +++ b/src/WhereConditions/WhereHasConditionsDirective.php @@ -13,16 +13,14 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Allows clients to filter a query based on the existence of a related model, using -a dynamically controlled `WHERE` condition that applies to the relationship. +Allows clients to filter a query based on the existence of a related model, using a dynamically controlled `WHERE` condition that applies to the relationship. """ directive @whereHasConditions( """ The Eloquent relationship that the conditions will be applied to. - This argument can be omitted if the argument name follows the naming - convention `has{$RELATION}`. For example, if the Eloquent relationship - is named `posts`, the argument name must be `hasPosts`. + This argument can be omitted if the argument name follows the naming convention `has{$RELATION}`. + For example, if the Eloquent relationship is named `posts`, the argument name must be `hasPosts`. """ relation: String From b3aeaea6e9bb1d40a055e515d77ea76379494712 Mon Sep 17 00:00:00 2001 From: spawnia <12158000+spawnia@users.noreply.github.com> Date: Sun, 25 Oct 2026 15:52:18 +0000 Subject: [PATCH 02/24] Prettify docs --- docs/master/api-reference/directives.md | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 5ed3fd552b..5b5fa3e31f 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -3002,7 +3002,8 @@ type Query { ): PostPaginator } -"A paginated list of Post items." type PostPaginator { +"A paginated list of Post items." +type PostPaginator { "A list of Post items." data: [Post!]! @@ -3010,7 +3011,8 @@ type Query { paginatorInfo: PaginatorInfo! } -"Information about pagination using a fully featured paginator." type PaginatorInfo { +"Information about pagination using a fully featured paginator." +type PaginatorInfo { "Number of items in the current page." count: Int! @@ -3081,7 +3083,8 @@ type Query { ): PostConnection } -"A paginated list of Post edges." type PostConnection { +"A paginated list of Post edges." +type PostConnection { "Pagination information about the list of edges." pageInfo: PageInfo! @@ -3089,7 +3092,8 @@ type Query { edges: [PostEdge] } -"An edge that contains a node of type Post and a cursor." type PostEdge { +"An edge that contains a node of type Post and a cursor." +type PostEdge { "The Post node." node: Post @@ -3130,7 +3134,8 @@ type Query { ): PostSimplePaginator } -"A paginated list of Post items." type PostSimplePaginator { +"A paginated list of Post items." +type PostSimplePaginator { "A list of Post items." data: [Post!]! @@ -3138,7 +3143,8 @@ type Query { paginatorInfo: SimplePaginatorInfo! } -"Information about pagination using a simple paginator." type SimplePaginatorInfo { +"Information about pagination using a simple paginator." +type SimplePaginatorInfo { "Number of items in the current page." count: Int! From 3be2241e80e3bdfa974fa9d1dbf0eddef2154371 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Sun, 25 Oct 2026 17:33:34 +0100 Subject: [PATCH 03/24] Restore code blocks in directives docs and format missed descriptions MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The formatter paired `"""` across markdown fences, which reflowed PHP examples and skipped the descriptions in between. 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 185 ++++++++++-------------- 1 file changed, 80 insertions(+), 105 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 5b5fa3e31f..77e2b44f90 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -912,8 +912,7 @@ directive @canModel( """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using arguments -with directives that add constraints to the query builder, such as `@eq`. +Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. """ directive @canQuery( """ @@ -1022,7 +1021,8 @@ A custom complexity function may look like the following, refer to the [complexi ```php namespace App\GraphQL\Security; -final class ComplexityAnalyzer { +final class ComplexityAnalyzer +{ public function userPosts(int $childrenComplexity, array $args): int { $postComplexity = ($args['includeFullText'] ?? false) @@ -1151,8 +1151,7 @@ directive @create( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -1204,8 +1203,7 @@ directive @createMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -1238,8 +1236,7 @@ directive @delete( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String @@ -1540,8 +1537,7 @@ Works very similar to the [@delete](#delete) directive. ```graphql """ Assign an internal value to an enum key. -When dealing with the Enum type in your code, -you will receive the defined value instead of the string key. +When dealing with the Enum type in your code, you will receive the defined value instead of the string key. """ directive @enum( """ @@ -1648,7 +1644,8 @@ type Mutation { The event class must accept an `Order` in the constructor: ```php -final class PlacedOrder { +final class PlacedOrder +{ public function __construct(Order $order) { ... } } ``` @@ -1659,8 +1656,7 @@ final class PlacedOrder { """ Converts between IDs/types and global IDs. -When used upon a field, it encodes; -when used upon an argument, it decodes. +When used upon a field, it encodes; when used upon an argument, it decodes. """ directive @globalId( """ @@ -1716,8 +1712,7 @@ You may rebind the `Nuwave\Lighthouse\Support\Contracts\GlobalId` interface to a """ Run authentication through one or more guards from `config/auth.php`. -This is run per field and may allow unauthenticated -users to still receive partial results. +This is run per field and may allow unauthenticated users to still receive partial results. Used upon an object, it applies to all fields within. """ @@ -1788,8 +1783,7 @@ Corresponds to [the Eloquent relationship HasMany](https://laravel.com/docs/eloq """ directive @hasMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -1818,8 +1812,7 @@ directive @hasMany( maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -1879,8 +1872,7 @@ Corresponds to [the Eloquent relationship HasManyThrough](https://laravel.com/do """ directive @hasManyThrough( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -1909,8 +1901,7 @@ directive @hasManyThrough( maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -1948,8 +1939,7 @@ Corresponds to [the Eloquent relationship HasOne](https://laravel.com/docs/eloqu """ directive @hasOne( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -1982,8 +1972,7 @@ Corresponds to [the Eloquent relationship HasOneThrough](https://laravel.com/doc """ directive @hasOneThrough( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -2042,17 +2031,14 @@ Inject a value from the context object into the arguments. directive @inject( """ A path to the property of the context that will be injected. - If the value is nested within the context, you may use dot notation - to get it, e.g. "user.id". + If the value is nested within the context, you may use dot notation to get it, e.g. "user.id". """ context: String! """ The target name of the argument into which the value is injected. - You can use dot notation to set the value at arbitrary depth - within the incoming argument. - Use an asterisk `*` as a path segment to inject the value into every - element of a list found at that position. + You can use dot notation to set the value at arbitrary depth within the incoming argument. + Use an asterisk `*` as a path segment to inject the value into every element of a list found at that position. """ name: String! ) repeatable on FIELD_DEFINITION @@ -2137,9 +2123,13 @@ You can get the appropriate Object Type from Lighthouse's type registry. ```php namespace App\GraphQL\Interfaces; -use GraphQL\Type\Definition\Type; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Schema\TypeRegistry; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use GraphQL\Type\Definition\Type; +use Nuwave\Lighthouse\Execution\ResolveInfo; +use Nuwave\Lighthouse\Schema\TypeRegistry; +use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Commentable { +final class Commentable +{ public function __construct( private TypeRegistry $typeRegistry ) {} @@ -2177,8 +2167,7 @@ See [feature toggles](../digging-deeper/feature-toggles.md). ```graphql """ -Perform a [lazy eager load](https://laravel.com/docs/eloquent-relationships#lazy-eager-loading) -on the relations of a list of models. +Perform a [lazy eager load](https://laravel.com/docs/eloquent-relationships#lazy-eager-loading) on the relations of a list of models. """ directive @lazyLoad( """ @@ -2212,8 +2201,7 @@ directive @like( key: String """ - Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the - placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. + Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. If specified, wildcard characters in the client-given input are escaped. If not specified, the client can pass wildcards unescaped. """ @@ -2235,18 +2223,15 @@ directive @like( ```graphql """ -Allow clients to specify the maximum number of results to return when used on an argument, -or statically limit them when used on a field. +Allow clients to specify the maximum number of results to return when used on an argument, or statically limit them when used on a field. -By default, this directive does not influence the number of results the resolver queries internally, -but limits how much of it is returned to clients. Use the `builder` argument to change this. +By default, this directive does not influence the number of results the resolver queries internally, but limits how much of it is returned to clients. +Use the `builder` argument to change this. """ directive @limit( """ - You may set this to `true` if the field uses a query builder, - then this directive will apply a LIMIT clause to it. - Typically, this option should only be used for root fields, - as it may cause wrong results with batched relation queries. + You may set this to `true` if the field uses a query builder, then this directive will apply a LIMIT clause to it. + Typically, this option should only be used for root fields, as it may cause wrong results with batched relation queries. """ builder: Boolean! = false ) on ARGUMENT_DEFINITION | FIELD_DEFINITION @@ -2297,8 +2282,7 @@ type Query { """ Resolve a field by calling a method on the parent object. -Use this if the data is not accessible through simple property access or if you -want to pass argument to the method. +Use this if the data is not accessible through simple property access or if you want to pass argument to the method. """ directive @method( """ @@ -2380,8 +2364,7 @@ Corresponds to [Eloquent's MorphMany-Relationship](https://laravel.com/docs/eloq """ directive @morphMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -2410,8 +2393,7 @@ directive @morphMany( maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -2459,8 +2441,7 @@ Corresponds to [Eloquent's MorphOne-Relationship](https://laravel.com/docs/eloqu """ directive @morphOne( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -2491,8 +2472,7 @@ Corresponds to [Eloquent's MorphTo-Relationship](https://laravel.com/docs/eloque """ directive @morphTo( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -2519,8 +2499,7 @@ Corresponds to [Eloquent's ManyToMany-Polymorphic-Relationship](https://laravel. """ directive @morphToMany( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -2549,8 +2528,7 @@ directive @morphToMany( maxCount: Int """ - Specify a custom type that implements the Edge interface - to extend edge object. + Specify a custom type that implements the Edge interface to extend edge object. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -2671,8 +2649,7 @@ type User { ```graphql """ -A no-op nested arg resolver that delegates all calls -to the ArgResolver directives attached to the children. +A no-op nested arg resolver that delegates all calls to the ArgResolver directives attached to the children. """ directive @nest on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` @@ -2709,8 +2686,7 @@ type User { """ Register a type for Relay's global object identification. -When used without any arguments, Lighthouse will attempt -to resolve the type through a model with the same name. +When used without any arguments, Lighthouse will attempt to resolve the type through a model with the same name. """ directive @node( """ @@ -2765,7 +2741,8 @@ The `resolver` argument must specify a function. It receives the decoded `id` and resolves to a result. ```php -public function byId($id): array { +public function byId($id): array +{ return [ 'DE' => ['name' => 'Germany'], 'MY' => ['name' => 'Malaysia'], @@ -3245,9 +3222,13 @@ It must return an instance of `Illuminate\Database\Query\Builder`. ```php namespace App\Models; -use Illuminate\Support\Facades\DB; use Illuminate\Database\Query\Builder; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use Illuminate\Support\Facades\DB; +use Illuminate\Database\Query\Builder; +use Nuwave\Lighthouse\Execution\ResolveInfo; +use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Blog { +final class Blog +{ public function statistics(mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolveInfo): Builder { return DB::table('posts') @@ -3277,7 +3258,8 @@ namespace App\GraphQL\Queries; use Illuminate\Pagination\LengthAwarePaginator; -final class Posts { +final class Posts +{ /** * @param null $root Always null, since this field has no parent. * @param array{} $args The field arguments passed by the client. @@ -3368,8 +3350,7 @@ Validate an argument using [Laravel validation](https://laravel.com/docs/validat directive @rules( """ Specify the validation rules to apply to the field. - This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), - or the fully qualified class name of a custom validation rule. + This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` @@ -3424,8 +3405,7 @@ Run validation on an array itself, using [Laravel built-in validation](https://l directive @rulesForArray( """ Specify the validation rules to apply to the field. - This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, - or the fully qualified class name of a custom validation rule. + This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` @@ -3534,9 +3514,11 @@ type Query { The scope will be passed the value of the client-given argument: ```php -use Illuminate\Database\Eloquent\Builder; use Illuminate\Database\Eloquent\Model; +use Illuminate\Database\Eloquent\Builder; +use Illuminate\Database\Eloquent\Model; -final class Post extends Model { +final class Post extends Model +{ public function scopeTrending(Builder $query, bool $trending): Builder { ... } } ``` @@ -3616,8 +3598,7 @@ See [feature toggles](../digging-deeper/feature-toggles.md). ```graphql """ Allows to filter if trashed elements should be fetched. -This manipulates the schema by adding the argument -`trashed: Trashed @trashed` to the field. +This manipulates the schema by adding the argument `trashed: Trashed @trashed` to the field. """ directive @softDeletes on FIELD_DEFINITION ``` @@ -3644,8 +3625,7 @@ Find out how the added filter works: [@trashed](#trashed) ```graphql """ -Merge the fields of a nested input object into the arguments of its parent -when processing the field arguments given by a client. +Merge the fields of a nested input object into the arguments of its parent when processing the field arguments given by a client. """ directive @spread on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` @@ -3724,7 +3704,8 @@ type Subscription { ```graphql """ -Sets rate limit to access the field. Does the same as ThrottleRequests Laravel Middleware. +Sets rate limit to access the field. +Does the same as ThrottleRequests Laravel Middleware. """ directive @throttle( """ @@ -3856,9 +3837,13 @@ It must resolve an Object Type from Lighthouse `TypeRegistry`. ```php namespace App\GraphQL\Unions; -use GraphQL\Type\Definition\Type; use Nuwave\Lighthouse\Execution\ResolveInfo; use Nuwave\Lighthouse\Schema\TypeRegistry; use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; +use GraphQL\Type\Definition\Type; +use Nuwave\Lighthouse\Execution\ResolveInfo; +use Nuwave\Lighthouse\Schema\TypeRegistry; +use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; -final class Person { +final class Person +{ public function __construct( private TypeRegistry $typeRegistry ) {} @@ -3890,8 +3875,7 @@ directive @update( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -3941,8 +3925,7 @@ directive @updateMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -3965,8 +3948,7 @@ input UpdatePostInput { ```graphql """ -Uploads given file to storage, removes the argument and sets -the returned path to the attribute key provided. +Uploads given file to storage, removes the argument and sets the returned path to the attribute key provided. This does not change the schema from a client perspective. """ @@ -4024,8 +4006,7 @@ directive @upsert( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -4074,8 +4055,7 @@ directive @upsertMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg - resolver and if the name of the relation is not the arg name. + This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -4120,9 +4100,8 @@ directive @validator( """ The name of the class to use. - If defined on an input, this defaults to a class called `{$inputName}Validator` in the - default validator namespace. For fields, it uses the namespace of the parent type - and the field name: `{$parent}\{$field}Validator`. + If defined on an input, this defaults to a class called `{$inputName}Validator` in the default validator namespace. + For fields, it uses the namespace of the parent type and the field name: `{$parent}\{$field}Validator`. """ class: String ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | INPUT_OBJECT @@ -4263,8 +4242,7 @@ type Query { """ Verify that a column's value is between two values. -The type of the input value this is defined upon should be -an `input` object with two fields. +The type of the input value this is defined upon should be an `input` object with two fields. """ directive @whereBetween( """ @@ -4375,8 +4353,7 @@ type Mutation { """ Verify that a column's value lies outside two values. -The type of the input value this is defined upon should be -an `input` object with two fields. +The type of the input value this is defined upon should be an `input` object with two fields. """ directive @whereNotBetween( """ @@ -4474,8 +4451,7 @@ Eager-load an Eloquent relation. """ directive @with( """ - Specify the relationship method name in the model class, - if it is named different from the field in the schema. + Specify the relationship method name in the model class, if it is named different from the field in the schema. """ relation: String @@ -4503,9 +4479,8 @@ If you just want to return the relation as-is, see [handling Eloquent relationsh """ Eager-load the count of an Eloquent relation if the field is queried. -Note that this does not return a value for the field, the count is simply -prefetched, assuming it is used to compute the field value. Use `@count` -if the field should simply return the relation count. +Note that this does not return a value for the field, the count is simply prefetched, assuming it is used to compute the field value. +Use `@count` if the field should simply return the relation count. """ directive @withCount( """ From 02f06e4d499f5a180a508dfa9996f54325b2af9f Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:44:02 +0100 Subject: [PATCH 04/24] Split @async return type sentence MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 3 ++- src/Async/AsyncDirective.php | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 77e2b44f90..4d1b4aad8f 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -156,7 +156,8 @@ type Query { Defer the execution of mutations to [queued jobs](https://laravel.com/docs/queues). This directive must only be used on fields of the root mutation type. -When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned - thus the fields return type must be `Boolean!`. +When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned. +Thus, the field's return type must be `Boolean!`. Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. diff --git a/src/Async/AsyncDirective.php b/src/Async/AsyncDirective.php index f3547ab444..545e751e4e 100644 --- a/src/Async/AsyncDirective.php +++ b/src/Async/AsyncDirective.php @@ -26,7 +26,8 @@ public static function definition(): string Defer the execution of mutations to [queued jobs](https://laravel.com/docs/queues). This directive must only be used on fields of the root mutation type. -When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned - thus the fields return type must be `Boolean!`. +When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned. +Thus, the field's return type must be `Boolean!`. Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. From 238c006134b0cb5059fe8b04497187e0ee7aeaaf Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:44:14 +0100 Subject: [PATCH 05/24] Clarify when to specify the relation argument MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 33 ++++++++++++------- src/Schema/Directives/BelongsToDirective.php | 3 +- .../Directives/BelongsToManyDirective.php | 3 +- src/Schema/Directives/HasManyDirective.php | 3 +- .../Directives/HasManyThroughDirective.php | 3 +- src/Schema/Directives/HasOneDirective.php | 3 +- .../Directives/HasOneThroughDirective.php | 3 +- src/Schema/Directives/MorphManyDirective.php | 3 +- src/Schema/Directives/MorphOneDirective.php | 3 +- src/Schema/Directives/MorphToDirective.php | 3 +- .../Directives/MorphToManyDirective.php | 3 +- src/Schema/Directives/WithDirective.php | 3 +- 12 files changed, 44 insertions(+), 22 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 4d1b4aad8f..a41f5d0961 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -220,7 +220,8 @@ Resolves a field through the Eloquent `BelongsTo` relationship. """ directive @belongsTo( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -271,7 +272,8 @@ Resolves a field through the Eloquent `BelongsToMany` relationship. """ directive @belongsToMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -1784,7 +1786,8 @@ Corresponds to [the Eloquent relationship HasMany](https://laravel.com/docs/eloq """ directive @hasMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -1873,7 +1876,8 @@ Corresponds to [the Eloquent relationship HasManyThrough](https://laravel.com/do """ directive @hasManyThrough( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -1940,7 +1944,8 @@ Corresponds to [the Eloquent relationship HasOne](https://laravel.com/docs/eloqu """ directive @hasOne( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -1973,7 +1978,8 @@ Corresponds to [the Eloquent relationship HasOneThrough](https://laravel.com/doc """ directive @hasOneThrough( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -2365,7 +2371,8 @@ Corresponds to [Eloquent's MorphMany-Relationship](https://laravel.com/docs/eloq """ directive @morphMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -2442,7 +2449,8 @@ Corresponds to [Eloquent's MorphOne-Relationship](https://laravel.com/docs/eloqu """ directive @morphOne( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -2473,7 +2481,8 @@ Corresponds to [Eloquent's MorphTo-Relationship](https://laravel.com/docs/eloque """ directive @morphTo( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -2500,7 +2509,8 @@ Corresponds to [Eloquent's ManyToMany-Polymorphic-Relationship](https://laravel. """ directive @morphToMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String @@ -4452,7 +4462,8 @@ Eager-load an Eloquent relation. """ directive @with( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/BelongsToDirective.php b/src/Schema/Directives/BelongsToDirective.php index 04f9a364f1..7a88b1a54e 100644 --- a/src/Schema/Directives/BelongsToDirective.php +++ b/src/Schema/Directives/BelongsToDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @belongsTo( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/BelongsToManyDirective.php b/src/Schema/Directives/BelongsToManyDirective.php index 3d5f70d4f8..a2383fa283 100644 --- a/src/Schema/Directives/BelongsToManyDirective.php +++ b/src/Schema/Directives/BelongsToManyDirective.php @@ -14,7 +14,8 @@ public static function definition(): string """ directive @belongsToMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/HasManyDirective.php b/src/Schema/Directives/HasManyDirective.php index ed090b392c..53ff86cc3c 100644 --- a/src/Schema/Directives/HasManyDirective.php +++ b/src/Schema/Directives/HasManyDirective.php @@ -14,7 +14,8 @@ public static function definition(): string """ directive @hasMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/HasManyThroughDirective.php b/src/Schema/Directives/HasManyThroughDirective.php index 81317634e1..088a7538b8 100644 --- a/src/Schema/Directives/HasManyThroughDirective.php +++ b/src/Schema/Directives/HasManyThroughDirective.php @@ -14,7 +14,8 @@ public static function definition(): string """ directive @hasManyThrough( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/HasOneDirective.php b/src/Schema/Directives/HasOneDirective.php index f2997e5fdf..bba6c66cfc 100644 --- a/src/Schema/Directives/HasOneDirective.php +++ b/src/Schema/Directives/HasOneDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @hasOne( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/HasOneThroughDirective.php b/src/Schema/Directives/HasOneThroughDirective.php index 8b30cd1ebf..20047faa6a 100644 --- a/src/Schema/Directives/HasOneThroughDirective.php +++ b/src/Schema/Directives/HasOneThroughDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @hasOneThrough( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphManyDirective.php b/src/Schema/Directives/MorphManyDirective.php index 21ac5e912f..be3fbab65c 100644 --- a/src/Schema/Directives/MorphManyDirective.php +++ b/src/Schema/Directives/MorphManyDirective.php @@ -14,7 +14,8 @@ public static function definition(): string """ directive @morphMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphOneDirective.php b/src/Schema/Directives/MorphOneDirective.php index 952518197a..4461c6bdbb 100644 --- a/src/Schema/Directives/MorphOneDirective.php +++ b/src/Schema/Directives/MorphOneDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @morphOne( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphToDirective.php b/src/Schema/Directives/MorphToDirective.php index 45e3754021..ea88a1dac3 100644 --- a/src/Schema/Directives/MorphToDirective.php +++ b/src/Schema/Directives/MorphToDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @morphTo( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/MorphToManyDirective.php b/src/Schema/Directives/MorphToManyDirective.php index 682e8d44e3..b7dd6bdd7c 100644 --- a/src/Schema/Directives/MorphToManyDirective.php +++ b/src/Schema/Directives/MorphToManyDirective.php @@ -14,7 +14,8 @@ public static function definition(): string """ directive @morphToMany( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String diff --git a/src/Schema/Directives/WithDirective.php b/src/Schema/Directives/WithDirective.php index b6ff4ddbf2..5fadef9453 100644 --- a/src/Schema/Directives/WithDirective.php +++ b/src/Schema/Directives/WithDirective.php @@ -24,7 +24,8 @@ public static function definition(): string """ directive @with( """ - Specify the relationship method name in the model class, if it is named different from the field in the schema. + Specify the relationship method name in the model class. + Only necessary if it is named differently from the field in the schema. """ relation: String From 22a214a50f61b6033b3e8f4dd200cb084f6ebbee Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:44:40 +0100 Subject: [PATCH 06/24] Clarify what the edgeType argument does MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 15 ++++++++++----- src/Schema/Directives/BelongsToManyDirective.php | 3 ++- src/Schema/Directives/HasManyDirective.php | 3 ++- src/Schema/Directives/HasManyThroughDirective.php | 3 ++- src/Schema/Directives/MorphManyDirective.php | 3 ++- src/Schema/Directives/MorphToManyDirective.php | 3 ++- 6 files changed, 20 insertions(+), 10 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index a41f5d0961..a8657be1d5 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -302,7 +302,8 @@ directive @belongsToMany( maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -1816,7 +1817,8 @@ directive @hasMany( maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -1906,7 +1908,8 @@ directive @hasManyThrough( maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -2401,7 +2404,8 @@ directive @morphMany( maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String @@ -2539,7 +2543,8 @@ directive @morphToMany( maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/BelongsToManyDirective.php b/src/Schema/Directives/BelongsToManyDirective.php index a2383fa283..c80b19ce27 100644 --- a/src/Schema/Directives/BelongsToManyDirective.php +++ b/src/Schema/Directives/BelongsToManyDirective.php @@ -44,7 +44,8 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/HasManyDirective.php b/src/Schema/Directives/HasManyDirective.php index 53ff86cc3c..388de2a309 100644 --- a/src/Schema/Directives/HasManyDirective.php +++ b/src/Schema/Directives/HasManyDirective.php @@ -44,7 +44,8 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/HasManyThroughDirective.php b/src/Schema/Directives/HasManyThroughDirective.php index 088a7538b8..a645f396f1 100644 --- a/src/Schema/Directives/HasManyThroughDirective.php +++ b/src/Schema/Directives/HasManyThroughDirective.php @@ -42,7 +42,8 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/MorphManyDirective.php b/src/Schema/Directives/MorphManyDirective.php index be3fbab65c..32bd6f5f8a 100644 --- a/src/Schema/Directives/MorphManyDirective.php +++ b/src/Schema/Directives/MorphManyDirective.php @@ -44,7 +44,8 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String diff --git a/src/Schema/Directives/MorphToManyDirective.php b/src/Schema/Directives/MorphToManyDirective.php index b7dd6bdd7c..9f43abce2d 100644 --- a/src/Schema/Directives/MorphToManyDirective.php +++ b/src/Schema/Directives/MorphToManyDirective.php @@ -44,7 +44,8 @@ public static function definition(): string maxCount: Int """ - Specify a custom type that implements the Edge interface to extend edge object. + Name a custom object type to use for the edges instead of the generated one. + It needs the fields `node` and `cursor` and may add more fields. Only applies when using Relay style "connection" pagination. """ edgeType: String From 94f9955c327331eb90a177b7ee8a0e5dea784a24 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:44:44 +0100 Subject: [PATCH 07/24] Split @cache isPrivate description MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 3 ++- src/Cache/CacheDirective.php | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index a8657be1d5..9b069cc69d 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -728,7 +728,8 @@ directive @cache( """ Limit access to cached data to the currently authenticated user. - When the field is accessible by guest users, this will not have any effect, they will access a shared cache. + This has no effect when guest users can access the field. + Guest users access a shared cache. """ private: Boolean = false ) on FIELD_DEFINITION diff --git a/src/Cache/CacheDirective.php b/src/Cache/CacheDirective.php index 2b03631951..ee4ec22ee1 100644 --- a/src/Cache/CacheDirective.php +++ b/src/Cache/CacheDirective.php @@ -36,7 +36,8 @@ public static function definition(): string """ Limit access to cached data to the currently authenticated user. - When the field is accessible by guest users, this will not have any effect, they will access a shared cache. + This has no effect when guest users can access the field. + Guest users access a shared cache. """ private: Boolean = false ) on FIELD_DEFINITION From 4041b4e56658241485d21341d5b184b3c27851b6 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:45:47 +0100 Subject: [PATCH 08/24] Improve wording of directive descriptions MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 76 ++++++++++--------- .../eloquent/complex-where-conditions.md | 3 +- src/Async/AsyncDirective.php | 2 +- src/Auth/BaseCanDirective.php | 2 +- src/Auth/CanDirective.php | 9 ++- src/Auth/CanFindDirective.php | 4 +- src/Auth/CanQueryDirective.php | 3 +- src/Auth/GuardDirective.php | 2 +- src/Defer/DeferrableDirective.php | 3 +- src/GlobalId/GlobalIdDirective.php | 3 +- src/GlobalId/NodeDirective.php | 2 +- src/Schema/Directives/CreateDirective.php | 2 +- src/Schema/Directives/CreateManyDirective.php | 2 +- src/Schema/Directives/DeleteDirective.php | 2 +- src/Schema/Directives/EnumDirective.php | 2 +- src/Schema/Directives/InjectDirective.php | 4 +- src/Schema/Directives/LikeDirective.php | 2 +- src/Schema/Directives/LimitDirective.php | 10 ++- src/Schema/Directives/MethodDirective.php | 2 +- src/Schema/Directives/NestDirective.php | 2 +- src/Schema/Directives/ThrottleDirective.php | 4 +- src/Schema/Directives/UpdateDirective.php | 2 +- src/Schema/Directives/UpdateManyDirective.php | 2 +- src/Schema/Directives/UploadDirective.php | 3 +- src/Schema/Directives/UpsertDirective.php | 2 +- src/Schema/Directives/UpsertManyDirective.php | 2 +- .../Directives/WhereBetweenDirective.php | 2 +- .../Directives/WhereNotBetweenDirective.php | 2 +- src/Schema/Directives/WithCountDirective.php | 5 +- src/SoftDeletes/SoftDeletesDirective.php | 2 +- .../Directives/BroadcastDirective.php | 2 +- src/Tracing/TracingDirective.php | 3 +- src/Validation/RulesDirective.php | 2 +- src/Validation/RulesForArrayDirective.php | 2 +- .../WhereHasConditionsDirective.php | 3 +- 35 files changed, 96 insertions(+), 79 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 9b069cc69d..28693eeb62 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -159,7 +159,7 @@ This directive must only be used on fields of the root mutation type. When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned. Thus, the field's return type must be `Boolean!`. -Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. +Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it executes the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. The handlers in the `config/lighthouse.php` option `error_handlers` are not called. """ @@ -817,7 +817,7 @@ injectArgs: Boolean! = false """ Statically defined arguments that are passed to `Gate::check`. -You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } +You may pass any GraphQL literal, e.g. `[1, 2, 3]` or `{ foo: "bar" }`. """ args: CanArgs @@ -867,11 +867,11 @@ You can find usage examples of these directives in [the authorization docs](../s """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using primary key(s) from specified argument. +Query for specific model instances to check the policy against, using the primary key(s) from the specified argument. """ directive @canFind( """ - Specify the name of the field argument that contains its primary key(s). + Specify the name of the field argument that contains the primary key(s). You may pass the string in dot notation to use nested inputs. """ @@ -917,7 +917,8 @@ directive @canModel( """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. +Query for specific model instances to check the policy against. +Use arguments with directives that add constraints to the query builder, such as `@eq`. """ directive @canQuery( """ @@ -1156,7 +1157,7 @@ directive @create( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -1208,7 +1209,7 @@ directive @createMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -1241,7 +1242,7 @@ directive @delete( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String @@ -1542,7 +1543,7 @@ Works very similar to the [@delete](#delete) directive. ```graphql """ Assign an internal value to an enum key. -When dealing with the Enum type in your code, you will receive the defined value instead of the string key. +Your code receives the internal value instead of the string key. """ directive @enum( """ @@ -1661,7 +1662,8 @@ final class PlacedOrder """ Converts between IDs/types and global IDs. -When used upon a field, it encodes; when used upon an argument, it decodes. +On a field, it encodes the value. +On an argument, it decodes the value. """ directive @globalId( """ @@ -1717,7 +1719,7 @@ You may rebind the `Nuwave\Lighthouse\Support\Contracts\GlobalId` interface to a """ Run authentication through one or more guards from `config/auth.php`. -This is run per field and may allow unauthenticated users to still receive partial results. +This runs per field, so unauthenticated users may still receive partial results. Used upon an object, it applies to all fields within. """ @@ -2042,13 +2044,13 @@ Inject a value from the context object into the arguments. directive @inject( """ A path to the property of the context that will be injected. - If the value is nested within the context, you may use dot notation to get it, e.g. "user.id". + Use dot notation to get a nested value from the context, e.g. `user.id`. """ context: String! """ The target name of the argument into which the value is injected. - You can use dot notation to set the value at arbitrary depth within the incoming argument. + Use dot notation to set the value at any depth within the incoming arguments. Use an asterisk `*` as a path segment to inject the value into every element of a list found at that position. """ name: String! @@ -2212,7 +2214,7 @@ directive @like( key: String """ - Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. + Fix the positions of wildcards (`%`, `_`) around the placeholder `{}` in the LIKE comparison, e.g. `%{}`, `__{}` or `%{}%`. If specified, wildcard characters in the client-given input are escaped. If not specified, the client can pass wildcards unescaped. """ @@ -2234,15 +2236,17 @@ directive @like( ```graphql """ -Allow clients to specify the maximum number of results to return when used on an argument, or statically limit them when used on a field. +On an argument, allow clients to specify the maximum number of results to return. +On a field, limit the number of results statically. -By default, this directive does not influence the number of results the resolver queries internally, but limits how much of it is returned to clients. +By default, this directive does not change how many results the resolver queries internally. +It only limits how many of them are returned to clients. Use the `builder` argument to change this. """ directive @limit( """ - You may set this to `true` if the field uses a query builder, then this directive will apply a LIMIT clause to it. - Typically, this option should only be used for root fields, as it may cause wrong results with batched relation queries. + Set this to `true` to apply a LIMIT clause to the query builder of the field. + Only use this on root fields, as it may cause wrong results with batched relation queries. """ builder: Boolean! = false ) on ARGUMENT_DEFINITION | FIELD_DEFINITION @@ -2293,7 +2297,7 @@ type Query { """ Resolve a field by calling a method on the parent object. -Use this if the data is not accessible through simple property access or if you want to pass argument to the method. +Use this if the data is not accessible through simple property access, or to pass arguments to the method. """ directive @method( """ @@ -2666,7 +2670,7 @@ type User { ```graphql """ -A no-op nested arg resolver that delegates all calls to the ArgResolver directives attached to the children. +A no-op nested arg resolver that delegates all calls to the ArgResolver directives of its children. """ directive @nest on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` @@ -2703,7 +2707,7 @@ type User { """ Register a type for Relay's global object identification. -When used without any arguments, Lighthouse will attempt to resolve the type through a model with the same name. +Without arguments, Lighthouse tries to resolve the type through the model with the same name. """ directive @node( """ @@ -3367,7 +3371,7 @@ Validate an argument using [Laravel validation](https://laravel.com/docs/validat directive @rules( """ Specify the validation rules to apply to the field. - This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), or the fully qualified class name of a custom validation rule. + Reference either one of [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules) or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` @@ -3422,7 +3426,7 @@ Run validation on an array itself, using [Laravel built-in validation](https://l directive @rulesForArray( """ Specify the validation rules to apply to the field. - This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, or the fully qualified class name of a custom validation rule. + Reference either one of [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules) or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` @@ -3615,7 +3619,7 @@ See [feature toggles](../digging-deeper/feature-toggles.md). ```graphql """ Allows to filter if trashed elements should be fetched. -This manipulates the schema by adding the argument `trashed: Trashed @trashed` to the field. +This adds the argument `trashed: Trashed @trashed` to the field. """ directive @softDeletes on FIELD_DEFINITION ``` @@ -3721,8 +3725,8 @@ type Subscription { ```graphql """ -Sets rate limit to access the field. -Does the same as ThrottleRequests Laravel Middleware. +Limit the rate of access to the field. +Works like the Laravel middleware `ThrottleRequests`. """ directive @throttle( """ @@ -3892,7 +3896,7 @@ directive @update( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -3942,7 +3946,7 @@ directive @updateMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -3965,7 +3969,8 @@ input UpdatePostInput { ```graphql """ -Uploads given file to storage, removes the argument and sets the returned path to the attribute key provided. +Upload the given file to storage and remove the argument. +The returned path is set to the given attribute key. This does not change the schema from a client perspective. """ @@ -4023,7 +4028,7 @@ directive @upsert( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -4072,7 +4077,7 @@ directive @upsertMany( """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION @@ -4259,7 +4264,7 @@ type Query { """ Verify that a column's value is between two values. -The type of the input value this is defined upon should be an `input` object with two fields. +The type of the argument or input field should be an `input` object with two fields. """ directive @whereBetween( """ @@ -4370,7 +4375,7 @@ type Mutation { """ Verify that a column's value lies outside two values. -The type of the input value this is defined upon should be an `input` object with two fields. +The type of the argument or input field should be an `input` object with two fields. """ directive @whereNotBetween( """ @@ -4497,8 +4502,9 @@ If you just want to return the relation as-is, see [handling Eloquent relationsh """ Eager-load the count of an Eloquent relation if the field is queried. -Note that this does not return a value for the field, the count is simply prefetched, assuming it is used to compute the field value. -Use `@count` if the field should simply return the relation count. +This does not return a value for the field. +It only prefetches the count, assuming the field value is computed from it. +Use `@count` to return the relation count as the field value. """ directive @withCount( """ diff --git a/docs/master/eloquent/complex-where-conditions.md b/docs/master/eloquent/complex-where-conditions.md index 50c57ef2e2..9cd5ac3e88 100644 --- a/docs/master/eloquent/complex-where-conditions.md +++ b/docs/master/eloquent/complex-where-conditions.md @@ -237,7 +237,8 @@ Qualify such columns with the table name, e.g. `@whereConditions(columns: ["role ```graphql """ -Allows clients to filter a query based on the existence of a related model, using a dynamically controlled `WHERE` condition that applies to the relationship. +Allow clients to filter a query by the existence of a related model. +A dynamically controlled `WHERE` condition applies to the relationship. """ directive @whereHasConditions( """ diff --git a/src/Async/AsyncDirective.php b/src/Async/AsyncDirective.php index 545e751e4e..837fb8f6ab 100644 --- a/src/Async/AsyncDirective.php +++ b/src/Async/AsyncDirective.php @@ -29,7 +29,7 @@ public static function definition(): string When the field is executed, a `Nuwave\Lighthouse\Async\AsyncMutation` job is dispatched and the value `true` is returned. Thus, the field's return type must be `Boolean!`. -Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it will actually execute the underlying field resolver. +Once a [queue worker](https://laravel.com/docs/queues#running-the-queue-worker) picks up the job, it executes the underlying field resolver. Errors that occur during execution are reported through the Laravel exception handler. The handlers in the `config/lighthouse.php` option `error_handlers` are not called. """ diff --git a/src/Auth/BaseCanDirective.php b/src/Auth/BaseCanDirective.php index 355a216514..ffdc675482 100644 --- a/src/Auth/BaseCanDirective.php +++ b/src/Auth/BaseCanDirective.php @@ -34,7 +34,7 @@ protected static function commonArguments(): string """ Statically defined arguments that are passed to `Gate::check`. - You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } + You may pass any GraphQL literal, e.g. `[1, 2, 3]` or `{ foo: "bar" }`. """ args: CanArgs diff --git a/src/Auth/CanDirective.php b/src/Auth/CanDirective.php index 2bea898f0c..d73cb50fbf 100644 --- a/src/Auth/CanDirective.php +++ b/src/Auth/CanDirective.php @@ -44,7 +44,7 @@ public static function definition(): string """ Check a Laravel Policy to ensure the current user is authorized to access a field. -When `injectArgs` and `args` are used together, the client given arguments will be passed before the static args. +When `injectArgs` and `args` are used together, the client-given arguments are passed before the static args. """ directive @can( """ @@ -74,14 +74,15 @@ public static function definition(): string """ Statically defined arguments that are passed to `Gate::check`. - You may pass arbitrary GraphQL literals, e.g.: [1, 2, 3] or { foo: "bar" } + You may pass any GraphQL literal, e.g. `[1, 2, 3]` or `{ foo: "bar" }`. CanArgs pseudo-scalar is defined in BaseCanDirective. """ args: CanArgs """ - Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. + Query for specific model instances to check the policy against. + Use arguments with directives that add constraints to the query builder, such as `@eq`. Mutually exclusive with `resolved`, `find`, and `root`. """ @@ -93,7 +94,7 @@ public static function definition(): string scopes: [String!] """ - If your policy checks against specific model instances, specify the name of the field argument that contains its primary key(s). + If your policy checks against specific model instances, specify the name of the field argument that contains their primary key(s). You may pass the string in dot notation to use nested inputs. diff --git a/src/Auth/CanFindDirective.php b/src/Auth/CanFindDirective.php index 3f8cc8682a..3213390488 100644 --- a/src/Auth/CanFindDirective.php +++ b/src/Auth/CanFindDirective.php @@ -28,13 +28,13 @@ public static function definition(): string """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using primary key(s) from specified argument. +Query for specific model instances to check the policy against, using the primary key(s) from the specified argument. """ directive @canFind( {$commonArguments} """ - Specify the name of the field argument that contains its primary key(s). + Specify the name of the field argument that contains the primary key(s). You may pass the string in dot notation to use nested inputs. """ diff --git a/src/Auth/CanQueryDirective.php b/src/Auth/CanQueryDirective.php index f430336293..4edee6ac4f 100644 --- a/src/Auth/CanQueryDirective.php +++ b/src/Auth/CanQueryDirective.php @@ -15,7 +15,8 @@ public static function definition(): string """ Check a Laravel Policy to ensure the current user is authorized to access a field. -Query for specific model instances to check the policy against, using arguments with directives that add constraints to the query builder, such as `@eq`. +Query for specific model instances to check the policy against. +Use arguments with directives that add constraints to the query builder, such as `@eq`. """ directive @canQuery( {$commonArguments} diff --git a/src/Auth/GuardDirective.php b/src/Auth/GuardDirective.php index 6c3b2c1fb9..a9e608a613 100644 --- a/src/Auth/GuardDirective.php +++ b/src/Auth/GuardDirective.php @@ -32,7 +32,7 @@ public static function definition(): string """ Run authentication through one or more guards from `config/auth.php`. -This is run per field and may allow unauthenticated users to still receive partial results. +This runs per field, so unauthenticated users may still receive partial results. Used upon an object, it applies to all fields within. """ diff --git a/src/Defer/DeferrableDirective.php b/src/Defer/DeferrableDirective.php index f09307e248..50e48026a4 100644 --- a/src/Defer/DeferrableDirective.php +++ b/src/Defer/DeferrableDirective.php @@ -26,7 +26,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Do not use this directive directly, it is automatically added to the schema when using the defer extension. +Do not use this directive directly. +Lighthouse adds it to the schema when you use the defer extension. """ directive @deferrable on FIELD_DEFINITION GRAPHQL; diff --git a/src/GlobalId/GlobalIdDirective.php b/src/GlobalId/GlobalIdDirective.php index ab2e2298c9..2e489eeba6 100644 --- a/src/GlobalId/GlobalIdDirective.php +++ b/src/GlobalId/GlobalIdDirective.php @@ -23,7 +23,8 @@ public static function definition(): string """ Converts between IDs/types and global IDs. -When used upon a field, it encodes; when used upon an argument, it decodes. +On a field, it encodes the value. +On an argument, it decodes the value. """ directive @globalId( """ diff --git a/src/GlobalId/NodeDirective.php b/src/GlobalId/NodeDirective.php index 6466c12a6f..1546a72f15 100644 --- a/src/GlobalId/NodeDirective.php +++ b/src/GlobalId/NodeDirective.php @@ -32,7 +32,7 @@ public static function definition(): string """ Register a type for Relay's global object identification. -When used without any arguments, Lighthouse will attempt to resolve the type through a model with the same name. +Without arguments, Lighthouse tries to resolve the type through the model with the same name. """ directive @node( """ diff --git a/src/Schema/Directives/CreateDirective.php b/src/Schema/Directives/CreateDirective.php index f901650269..3a3e822673 100644 --- a/src/Schema/Directives/CreateDirective.php +++ b/src/Schema/Directives/CreateDirective.php @@ -22,7 +22,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/CreateManyDirective.php b/src/Schema/Directives/CreateManyDirective.php index dc802dbcec..03e912c2a4 100644 --- a/src/Schema/Directives/CreateManyDirective.php +++ b/src/Schema/Directives/CreateManyDirective.php @@ -22,7 +22,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/DeleteDirective.php b/src/Schema/Directives/DeleteDirective.php index 74956fccb4..a9edfaaf90 100644 --- a/src/Schema/Directives/DeleteDirective.php +++ b/src/Schema/Directives/DeleteDirective.php @@ -34,7 +34,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String diff --git a/src/Schema/Directives/EnumDirective.php b/src/Schema/Directives/EnumDirective.php index 8428b62492..27a13d0f2e 100644 --- a/src/Schema/Directives/EnumDirective.php +++ b/src/Schema/Directives/EnumDirective.php @@ -9,7 +9,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Assign an internal value to an enum key. -When dealing with the Enum type in your code, you will receive the defined value instead of the string key. +Your code receives the internal value instead of the string key. """ directive @enum( """ diff --git a/src/Schema/Directives/InjectDirective.php b/src/Schema/Directives/InjectDirective.php index 37e266c60c..35cc993c28 100644 --- a/src/Schema/Directives/InjectDirective.php +++ b/src/Schema/Directives/InjectDirective.php @@ -19,13 +19,13 @@ public static function definition(): string directive @inject( """ A path to the property of the context that will be injected. - If the value is nested within the context, you may use dot notation to get it, e.g. "user.id". + Use dot notation to get a nested value from the context, e.g. `user.id`. """ context: String! """ The target name of the argument into which the value is injected. - You can use dot notation to set the value at arbitrary depth within the incoming argument. + Use dot notation to set the value at any depth within the incoming arguments. Use an asterisk `*` as a path segment to inject the value into every element of a list found at that position. """ name: String! diff --git a/src/Schema/Directives/LikeDirective.php b/src/Schema/Directives/LikeDirective.php index 25a8c46fdd..00b55d54c4 100644 --- a/src/Schema/Directives/LikeDirective.php +++ b/src/Schema/Directives/LikeDirective.php @@ -36,7 +36,7 @@ public static function definition(): string key: String """ - Fixate the positions of wildcards (`%`, `_`) in the LIKE comparison around the placeholder `{}`, e.g. `%{}`, `__{}` or `%{}%`. + Fix the positions of wildcards (`%`, `_`) around the placeholder `{}` in the LIKE comparison, e.g. `%{}`, `__{}` or `%{}%`. If specified, wildcard characters in the client-given input are escaped. If not specified, the client can pass wildcards unescaped. """ diff --git a/src/Schema/Directives/LimitDirective.php b/src/Schema/Directives/LimitDirective.php index 7e677d2304..bdce03be4e 100644 --- a/src/Schema/Directives/LimitDirective.php +++ b/src/Schema/Directives/LimitDirective.php @@ -28,15 +28,17 @@ public static function definition(): string { return /* @lang GraphQL */ <<<'GRAPHQL' """ -Allow clients to specify the maximum number of results to return when used on an argument, or statically limit them when used on a field. +On an argument, allow clients to specify the maximum number of results to return. +On a field, limit the number of results statically. -By default, this directive does not influence the number of results the resolver queries internally, but limits how much of it is returned to clients. +By default, this directive does not change how many results the resolver queries internally. +It only limits how many of them are returned to clients. Use the `builder` argument to change this. """ directive @limit( """ - You may set this to `true` if the field uses a query builder, then this directive will apply a LIMIT clause to it. - Typically, this option should only be used for root fields, as it may cause wrong results with batched relation queries. + Set this to `true` to apply a LIMIT clause to the query builder of the field. + Only use this on root fields, as it may cause wrong results with batched relation queries. """ builder: Boolean! = false ) on ARGUMENT_DEFINITION | FIELD_DEFINITION diff --git a/src/Schema/Directives/MethodDirective.php b/src/Schema/Directives/MethodDirective.php index ff2a18c570..b072c23c04 100644 --- a/src/Schema/Directives/MethodDirective.php +++ b/src/Schema/Directives/MethodDirective.php @@ -14,7 +14,7 @@ public static function definition(): string """ Resolve a field by calling a method on the parent object. -Use this if the data is not accessible through simple property access or if you want to pass argument to the method. +Use this if the data is not accessible through simple property access, or to pass arguments to the method. """ directive @method( """ diff --git a/src/Schema/Directives/NestDirective.php b/src/Schema/Directives/NestDirective.php index a7e69d784d..f507217965 100644 --- a/src/Schema/Directives/NestDirective.php +++ b/src/Schema/Directives/NestDirective.php @@ -26,7 +26,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -A no-op nested arg resolver that delegates all calls to the ArgResolver directives attached to the children. +A no-op nested arg resolver that delegates all calls to the ArgResolver directives of its children. """ directive @nest on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/ThrottleDirective.php b/src/Schema/Directives/ThrottleDirective.php index 3066f16e39..098d23ffd1 100644 --- a/src/Schema/Directives/ThrottleDirective.php +++ b/src/Schema/Directives/ThrottleDirective.php @@ -28,8 +28,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Sets rate limit to access the field. -Does the same as ThrottleRequests Laravel Middleware. +Limit the rate of access to the field. +Works like the Laravel middleware `ThrottleRequests`. """ directive @throttle( """ diff --git a/src/Schema/Directives/UpdateDirective.php b/src/Schema/Directives/UpdateDirective.php index c84476eeff..43327de959 100644 --- a/src/Schema/Directives/UpdateDirective.php +++ b/src/Schema/Directives/UpdateDirective.php @@ -23,7 +23,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UpdateManyDirective.php b/src/Schema/Directives/UpdateManyDirective.php index 91c935e253..7a26630b63 100644 --- a/src/Schema/Directives/UpdateManyDirective.php +++ b/src/Schema/Directives/UpdateManyDirective.php @@ -23,7 +23,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UploadDirective.php b/src/Schema/Directives/UploadDirective.php index 82e9181ff1..84f7991cad 100644 --- a/src/Schema/Directives/UploadDirective.php +++ b/src/Schema/Directives/UploadDirective.php @@ -13,7 +13,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Uploads given file to storage, removes the argument and sets the returned path to the attribute key provided. +Upload the given file to storage and remove the argument. +The returned path is set to the given attribute key. This does not change the schema from a client perspective. """ diff --git a/src/Schema/Directives/UpsertDirective.php b/src/Schema/Directives/UpsertDirective.php index a8757f8149..901b4ded45 100644 --- a/src/Schema/Directives/UpsertDirective.php +++ b/src/Schema/Directives/UpsertDirective.php @@ -39,7 +39,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/UpsertManyDirective.php b/src/Schema/Directives/UpsertManyDirective.php index 384444e7bf..cc98af6392 100644 --- a/src/Schema/Directives/UpsertManyDirective.php +++ b/src/Schema/Directives/UpsertManyDirective.php @@ -39,7 +39,7 @@ public static function definition(): string """ Specify the name of the relation on the parent model. - This is only needed when using this directive as a nested arg resolver and if the name of the relation is not the arg name. + Only necessary when this directive is used as a nested arg resolver and the relation is named differently from the argument. """ relation: String ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION diff --git a/src/Schema/Directives/WhereBetweenDirective.php b/src/Schema/Directives/WhereBetweenDirective.php index 1cd81682f1..fcf9071803 100644 --- a/src/Schema/Directives/WhereBetweenDirective.php +++ b/src/Schema/Directives/WhereBetweenDirective.php @@ -15,7 +15,7 @@ public static function definition(): string """ Verify that a column's value is between two values. -The type of the input value this is defined upon should be an `input` object with two fields. +The type of the argument or input field should be an `input` object with two fields. """ directive @whereBetween( """ diff --git a/src/Schema/Directives/WhereNotBetweenDirective.php b/src/Schema/Directives/WhereNotBetweenDirective.php index 60cfcbc5fb..429f2285b4 100644 --- a/src/Schema/Directives/WhereNotBetweenDirective.php +++ b/src/Schema/Directives/WhereNotBetweenDirective.php @@ -15,7 +15,7 @@ public static function definition(): string """ Verify that a column's value lies outside two values. -The type of the input value this is defined upon should be an `input` object with two fields. +The type of the argument or input field should be an `input` object with two fields. """ directive @whereNotBetween( """ diff --git a/src/Schema/Directives/WithCountDirective.php b/src/Schema/Directives/WithCountDirective.php index 7a3c81cc21..7f91f84904 100644 --- a/src/Schema/Directives/WithCountDirective.php +++ b/src/Schema/Directives/WithCountDirective.php @@ -22,8 +22,9 @@ public static function definition(): string """ Eager-load the count of an Eloquent relation if the field is queried. -Note that this does not return a value for the field, the count is simply prefetched, assuming it is used to compute the field value. -Use `@count` if the field should simply return the relation count. +This does not return a value for the field. +It only prefetches the count, assuming the field value is computed from it. +Use `@count` to return the relation count as the field value. """ directive @withCount( """ diff --git a/src/SoftDeletes/SoftDeletesDirective.php b/src/SoftDeletes/SoftDeletesDirective.php index 8ab5aab559..15f66dda7c 100644 --- a/src/SoftDeletes/SoftDeletesDirective.php +++ b/src/SoftDeletes/SoftDeletesDirective.php @@ -17,7 +17,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Allows to filter if trashed elements should be fetched. -This manipulates the schema by adding the argument `trashed: Trashed @trashed` to the field. +This adds the argument `trashed: Trashed @trashed` to the field. """ directive @softDeletes on FIELD_DEFINITION GRAPHQL; diff --git a/src/Subscriptions/Directives/BroadcastDirective.php b/src/Subscriptions/Directives/BroadcastDirective.php index 63395595fe..c8d4bca2a4 100644 --- a/src/Subscriptions/Directives/BroadcastDirective.php +++ b/src/Subscriptions/Directives/BroadcastDirective.php @@ -15,7 +15,7 @@ public static function definition(): string """ Broadcast the results of a mutation to subscribed clients. -Ensure you place this after other field middleware directives that may transform the result to broadcast the final value. +Place this after other field middleware directives that may transform the result, so it broadcasts the final value. """ directive @broadcast( """ diff --git a/src/Tracing/TracingDirective.php b/src/Tracing/TracingDirective.php index bc32bc1045..6a71c9c4bc 100644 --- a/src/Tracing/TracingDirective.php +++ b/src/Tracing/TracingDirective.php @@ -19,7 +19,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Do not use this directive directly, it is automatically added to the schema when using the tracing extension. +Do not use this directive directly. +Lighthouse adds it to the schema when you use the tracing extension. """ directive @tracing on FIELD_DEFINITION GRAPHQL; diff --git a/src/Validation/RulesDirective.php b/src/Validation/RulesDirective.php index 0f90103dd7..5a398f4069 100644 --- a/src/Validation/RulesDirective.php +++ b/src/Validation/RulesDirective.php @@ -15,7 +15,7 @@ public static function definition(): string directive @rules( """ Specify the validation rules to apply to the field. - This can either be a reference to [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules), or the fully qualified class name of a custom validation rule. + Reference either one of [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules) or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input value are _not_ supported: - `exclude_if` diff --git a/src/Validation/RulesForArrayDirective.php b/src/Validation/RulesForArrayDirective.php index 87e43166f7..4d6712fb73 100644 --- a/src/Validation/RulesForArrayDirective.php +++ b/src/Validation/RulesForArrayDirective.php @@ -16,7 +16,7 @@ public static function definition(): string directive @rulesForArray( """ Specify the validation rules to apply to the field. - This can either be a reference to any of Laravel's built-in validation rules: https://laravel.com/docs/validation#available-validation-rules, or the fully qualified class name of a custom validation rule. + Reference either one of [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules) or the fully qualified class name of a custom validation rule. Validation rules that mutate the given input values are _not_ supported: - `exclude_if` diff --git a/src/WhereConditions/WhereHasConditionsDirective.php b/src/WhereConditions/WhereHasConditionsDirective.php index 5764b9d18b..6053ad9388 100644 --- a/src/WhereConditions/WhereHasConditionsDirective.php +++ b/src/WhereConditions/WhereHasConditionsDirective.php @@ -13,7 +13,8 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Allows clients to filter a query based on the existence of a related model, using a dynamically controlled `WHERE` condition that applies to the relationship. +Allow clients to filter a query by the existence of a related model. +A dynamically controlled `WHERE` condition applies to the relationship. """ directive @whereHasConditions( """ From a38be1b13e4bdf46601b5cee394fb8d9392db2e1 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 08:48:03 +0100 Subject: [PATCH 09/24] Sync directive definitions between docs and code MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 28 +++++++++++++------ src/Pagination/PaginateDirective.php | 3 +- .../Directives/BelongsToManyDirective.php | 3 +- src/Schema/Directives/HasManyDirective.php | 3 +- .../Directives/HasManyThroughDirective.php | 5 +++- src/Schema/Directives/HideDirective.php | 3 +- src/Schema/Directives/MorphManyDirective.php | 3 +- .../Directives/MorphToManyDirective.php | 3 +- src/Schema/Directives/ShowDirective.php | 3 +- 9 files changed, 37 insertions(+), 17 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 28693eeb62..854b965055 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -612,6 +612,8 @@ final class AddUsersToCompany ```graphql """ Broadcast the results of a mutation to subscribed clients. + +Place this after other field middleware directives that may transform the result, so it broadcasts the final value. """ directive @broadcast( """ @@ -718,6 +720,8 @@ final class MyClass ```graphql """ Cache the result of a resolver. + +Place this after other field middleware to ensure it caches the correct transformed value. """ directive @cache( """ @@ -829,18 +833,24 @@ action: CanAction! = EXCEPTION_PASS """ Value to return if the user is not authorized and `action` is `RETURN_VALUE`. """ -returnValue: CanArgs -""" +returnValue: CanReturnValue ``` Types are specified as: ```graphql """ -Any constant literal value: https://graphql.github.io/graphql-spec/draft/#sec-Input-Values +Any constant literal value. +See https://graphql.github.io/graphql-spec/draft/#sec-Input-Values. """ scalar CanArgs +""" +Any constant literal value. +See https://graphql.github.io/graphql-spec/draft/#sec-Input-Values. +""" +scalar CanReturnValue + enum CanAction { """ Pass exception to the client. @@ -853,7 +863,7 @@ enum CanAction { EXCEPTION_NOT_AUTHORIZED """ - Return the value specified in `returnValue` argument to conceal the real error. + Return the value specified in the `returnValue` directive argument to conceal the real error. """ RETURN_VALUE } @@ -1368,7 +1378,7 @@ directive @feature( Specify what the state of the feature should be for the field to be included. """ when: FeatureState! = ACTIVE -) on FIELD_DEFINITION | OBJECT +) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | OBJECT """ Options for the `when` argument of `@feature`. @@ -2171,7 +2181,7 @@ directive @hide( Compared against the value returned from `app()->environment()`. """ env: [String!]! -) repeatable on FIELD_DEFINITION +) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | OBJECT ``` See [feature toggles](../digging-deeper/feature-toggles.md). @@ -3373,7 +3383,7 @@ directive @rules( Specify the validation rules to apply to the field. Reference either one of [Laravel's built-in validation rules](https://laravel.com/docs/validation#available-validation-rules) or the fully qualified class name of a custom validation rule. - Validation rules that mutate the given input values are _not_ supported: + Validation rules that mutate the given input value are _not_ supported: - `exclude_if` - `exclude_unless` Use ArgTransformerDirectives or FieldMiddlewareDirectives instead. @@ -3605,11 +3615,11 @@ Includes the annotated element from the schema conditionally. """ directive @show( """ - Specify which environments include this element, e.g. ["testing"]. + Specify which environments include this element, e.g. `["testing"]`. Compared against the value returned from `app()->environment()`. """ env: [String!]! -) repeatable on FIELD_DEFINITION +) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | OBJECT ``` See [feature toggles](../digging-deeper/feature-toggles.md). diff --git a/src/Pagination/PaginateDirective.php b/src/Pagination/PaginateDirective.php index 9521ccb7f6..9c1ad1e178 100644 --- a/src/Pagination/PaginateDirective.php +++ b/src/Pagination/PaginateDirective.php @@ -95,7 +95,8 @@ enum PaginateType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/BelongsToManyDirective.php b/src/Schema/Directives/BelongsToManyDirective.php index c80b19ce27..c5916f10b3 100644 --- a/src/Schema/Directives/BelongsToManyDirective.php +++ b/src/Schema/Directives/BelongsToManyDirective.php @@ -61,7 +61,8 @@ enum BelongsToManyType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/HasManyDirective.php b/src/Schema/Directives/HasManyDirective.php index 388de2a309..207a7247d5 100644 --- a/src/Schema/Directives/HasManyDirective.php +++ b/src/Schema/Directives/HasManyDirective.php @@ -61,7 +61,8 @@ enum HasManyType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/HasManyThroughDirective.php b/src/Schema/Directives/HasManyThroughDirective.php index a645f396f1..34c8f1eb01 100644 --- a/src/Schema/Directives/HasManyThroughDirective.php +++ b/src/Schema/Directives/HasManyThroughDirective.php @@ -32,12 +32,14 @@ public static function definition(): string """ Allow clients to query paginated lists without specifying the amount of items. Overrules the `pagination.default_count` setting from `lighthouse.php`. + Setting this to `null` means clients have to explicitly ask for the count. """ defaultCount: Int """ Limit the maximum amount of items that clients can request from paginated lists. Overrules the `pagination.max_count` setting from `lighthouse.php`. + Setting this to `null` means the count is unrestricted. """ maxCount: Int @@ -59,7 +61,8 @@ enum HasManyThroughType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/HideDirective.php b/src/Schema/Directives/HideDirective.php index 43b48a1cc1..fc1cdf894b 100644 --- a/src/Schema/Directives/HideDirective.php +++ b/src/Schema/Directives/HideDirective.php @@ -39,7 +39,8 @@ public static function definition(): string """ directive @hide( """ - Specify which environments must not use this field, e.g. ["production"]. + Specify which environments exclude this element, e.g. `["production"]`. + Compared against the value returned from `app()->environment()`. """ env: [String!]! ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | OBJECT diff --git a/src/Schema/Directives/MorphManyDirective.php b/src/Schema/Directives/MorphManyDirective.php index 32bd6f5f8a..35df57f2a7 100644 --- a/src/Schema/Directives/MorphManyDirective.php +++ b/src/Schema/Directives/MorphManyDirective.php @@ -61,7 +61,8 @@ enum MorphManyType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/MorphToManyDirective.php b/src/Schema/Directives/MorphToManyDirective.php index 9f43abce2d..0e2f8d3dd7 100644 --- a/src/Schema/Directives/MorphToManyDirective.php +++ b/src/Schema/Directives/MorphToManyDirective.php @@ -61,7 +61,8 @@ enum MorphToManyType { PAGINATOR """ - Offset-based pagination like the Laravel "Simple Pagination", which does not count the total number of records. + Offset-based pagination like Laravel "Simple Pagination". + It does not count the total number of records. """ SIMPLE diff --git a/src/Schema/Directives/ShowDirective.php b/src/Schema/Directives/ShowDirective.php index 63123e860f..f86054f555 100644 --- a/src/Schema/Directives/ShowDirective.php +++ b/src/Schema/Directives/ShowDirective.php @@ -12,7 +12,8 @@ public static function definition(): string """ directive @show( """ - Specify which environments may use this field, e.g. ["testing"]. + Specify which environments include this element, e.g. `["testing"]`. + Compared against the value returned from `app()->environment()`. """ env: [String!]! ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION | OBJECT From dcafa492b9380c598ab8f34f3e251a6b0f2da395 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:10:35 +0100 Subject: [PATCH 10/24] Describe and document @mock MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/testing/extensions.md | 15 ++++++++++++++- src/Testing/MockDirective.php | 2 +- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/docs/master/testing/extensions.md b/docs/master/testing/extensions.md index 326d257487..f8debad0ef 100644 --- a/docs/master/testing/extensions.md +++ b/docs/master/testing/extensions.md @@ -40,8 +40,21 @@ final class MyCustomDirectiveTest extends TestCase When testing custom functionality through a dummy schema, you still need to have a way to resolve fields. Lighthouse provides a simple way to mock resolvers in a dummy schema. +Mark the fields to mock with the `@mock` directive: -Add the `MocksResolvers` trait to your test class: +```graphql +""" +Resolve the field with a mock resolver registered in the test, see `MocksResolvers`. +""" +directive @mock( + """ + Specify a unique key for the mock resolver. + """ + key: String = "default" +) on FIELD_DEFINITION +``` + +Then add the `MocksResolvers` trait to your test class: ```php namespace Tests; diff --git a/src/Testing/MockDirective.php b/src/Testing/MockDirective.php index 658f9b3e94..45d7e67a6e 100644 --- a/src/Testing/MockDirective.php +++ b/src/Testing/MockDirective.php @@ -17,7 +17,7 @@ public static function definition(): string { return /** @lang GraphQL */ <<<'GRAPHQL' """ -Allows you to easily hook up a resolver for an endpoint. +Resolve the field with a mock resolver registered in the test, see `MocksResolvers`. """ directive @mock( """ From 1c56b91468a0e104ac896c0cd16a616ea767a2ff Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:10:41 +0100 Subject: [PATCH 11/24] Mention that global field middleware directives apply to every field MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- src/Schema/Directives/DropArgsDirective.php | 1 + src/Schema/Directives/RenameArgsDirective.php | 1 + src/Schema/Directives/SanitizeDirective.php | 1 + src/Schema/Directives/TransformArgsDirective.php | 1 + src/Validation/ValidateDirective.php | 1 + 5 files changed, 5 insertions(+) diff --git a/src/Schema/Directives/DropArgsDirective.php b/src/Schema/Directives/DropArgsDirective.php index 42a1adebb7..ac5697fe15 100644 --- a/src/Schema/Directives/DropArgsDirective.php +++ b/src/Schema/Directives/DropArgsDirective.php @@ -15,6 +15,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Apply the @drop directives on the incoming arguments. +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @dropArgs on FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/RenameArgsDirective.php b/src/Schema/Directives/RenameArgsDirective.php index 8c4c0f825e..c600f8909a 100644 --- a/src/Schema/Directives/RenameArgsDirective.php +++ b/src/Schema/Directives/RenameArgsDirective.php @@ -15,6 +15,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Apply the @rename directives on the incoming arguments. +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @renameArgs on FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/SanitizeDirective.php b/src/Schema/Directives/SanitizeDirective.php index 317ce08ee8..3753f5db76 100644 --- a/src/Schema/Directives/SanitizeDirective.php +++ b/src/Schema/Directives/SanitizeDirective.php @@ -12,6 +12,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Apply sanitization to the arguments of a field. +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @sanitize on FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/TransformArgsDirective.php b/src/Schema/Directives/TransformArgsDirective.php index 3f08b5bffa..c17fd673d3 100644 --- a/src/Schema/Directives/TransformArgsDirective.php +++ b/src/Schema/Directives/TransformArgsDirective.php @@ -12,6 +12,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Transform the arguments of a field. +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @transformArgs on FIELD_DEFINITION GRAPHQL; diff --git a/src/Validation/ValidateDirective.php b/src/Validation/ValidateDirective.php index 6e0c38e1fd..dcfa3f2e72 100644 --- a/src/Validation/ValidateDirective.php +++ b/src/Validation/ValidateDirective.php @@ -18,6 +18,7 @@ public static function definition(): string return /** @lang GraphQL */ <<<'GRAPHQL' """ Run validation on a field. +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @validate on FIELD_DEFINITION GRAPHQL; From 721ee68ab044082e53e3be3f72796fc9819f0677 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:13:07 +0100 Subject: [PATCH 12/24] Remove filler words from prose MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- CONTRIBUTING.md | 2 +- UPGRADE.md | 17 +++++------ docs/master/api-reference/commands.md | 2 +- docs/master/api-reference/directives.md | 28 +++++++++---------- docs/master/api-reference/events.md | 4 +-- docs/master/api-reference/scalars.md | 2 +- docs/master/concepts/arg-resolvers.md | 8 +++--- .../custom-directives/field-directives.md | 2 +- .../custom-directives/getting-started.md | 6 ++-- .../input-value-directives.md | 2 +- .../adding-types-programmatically.md | 2 +- docs/master/digging-deeper/error-handling.md | 2 +- .../digging-deeper/extending-lighthouse.md | 2 +- docs/master/digging-deeper/ordering.md | 2 +- .../eloquent/complex-where-conditions.md | 15 +++++----- docs/master/eloquent/getting-started.md | 7 ++--- docs/master/eloquent/nested-mutations.md | 10 +++---- .../eloquent/polymorphic-relationships.md | 8 +++--- docs/master/eloquent/relationships.md | 8 +++--- docs/master/eloquent/soft-deleting.md | 4 +-- docs/master/federation/getting-started.md | 2 +- .../migrating-to-lighthouse.md | 2 +- docs/master/performance/caching.md | 2 +- docs/master/performance/n-plus-one.md | 4 +-- .../performance/server-configuration.md | 2 +- docs/master/security/authentication.md | 8 +++--- docs/master/security/authorization.md | 6 ++-- docs/master/security/resource-exhaustion.md | 4 +-- docs/master/security/sanitization.md | 2 +- docs/master/security/validation.md | 5 ++-- docs/master/testing/extensions.md | 6 ++-- docs/master/testing/phpunit.md | 10 +++---- docs/master/the-basics/best-practices.md | 2 +- docs/master/the-basics/directives.md | 4 +-- docs/master/the-basics/fields.md | 4 +-- docs/master/the-basics/types.md | 6 ++-- src/Cache/CacheDirective.php | 2 +- src/Events/ManipulateResult.php | 2 +- src/Execution/Arguments/ArgumentSet.php | 4 +-- src/Execution/Arguments/NestedManyToMany.php | 2 +- .../ModelsLoader/SimpleModelsLoader.php | 2 +- src/Execution/Utils/FieldPath.php | 2 +- .../Directives/ExternalDirective.php | 2 +- src/Federation/Types/Any.php | 2 +- src/GlobalId/Base64GlobalId.php | 2 +- src/GlobalId/GlobalId.php | 4 +-- src/GlobalId/GlobalIdDirective.php | 4 +-- src/GlobalId/NodeRegistry.php | 2 +- src/Http/Middleware/AcceptJson.php | 2 +- src/Http/routes.php | 2 +- src/Pagination/Cursor.php | 2 +- src/Schema/AST/ASTBuilder.php | 2 +- src/Schema/AST/ASTHelper.php | 2 +- src/Schema/Directives/ScopeDirective.php | 2 +- src/Schema/Directives/ThrottleDirective.php | 2 +- src/Schema/Validator.php | 2 +- .../Storage/RedisStorageManager.php | 2 +- src/Support/AppVersion.php | 2 +- src/Support/DriverManager.php | 2 +- src/Support/Utils.php | 2 +- src/Testing/MakesGraphQLRequests.php | 2 +- src/Testing/MakesGraphQLRequestsLumen.php | 2 +- src/WhereConditions/SQLOperator.php | 2 +- src/lighthouse.php | 4 +-- 64 files changed, 134 insertions(+), 132 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 4f552a5bf0..3773eec710 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,7 +1,7 @@ # Lighthouse Contribution Guide Thank you for contributing to Lighthouse. -Here are some tips and guidelines to make this easy for you. +Here are some tips and guidelines to help you. ## Open a Pull Request diff --git a/UPGRADE.md b/UPGRADE.md index 931a0fdd78..d939a8227d 100644 --- a/UPGRADE.md +++ b/UPGRADE.md @@ -240,7 +240,7 @@ final class MyDirective extends BaseDirective implements FieldResolver ### Simplify wrapping resolvers in `FieldMiddleware` directives -Wrapping resolvers is very common in `FieldMiddleware` directives and is now simplified. +Wrapping resolvers is common in `FieldMiddleware` directives and is now simplified. ```diff use Nuwave\Lighthouse\Execution\ResolveInfo; @@ -432,13 +432,13 @@ type Query { } ``` -Note that [@guard](docs/master/api-reference/directives.md#guard) does not log in users. +[@guard](docs/master/api-reference/directives.md#guard) does not log in users. To ensure the user is logged in, add the `AttemptAuthenticate` middleware to your `lighthouse.php` middleware config, see the [default config](src/lighthouse.php) for an example. If you used `@middleware` for authorization, replace it with [@can](docs/master/api-reference/directives.md#can). Other functionality can be replaced by a custom [`FieldMiddleware`](docs/master/custom-directives/field-directives.md#fieldmiddleware) directive. -Just like Laravel Middleware, it can wrap around individual field resolvers. +Like Laravel Middleware, it can wrap around individual field resolvers. ### Directives must have an SDL definition @@ -452,7 +452,7 @@ If you previously implemented `DefinedDirective`, remove it from your directives +class TrimDirective extends BaseDirective implements ArgTransformerDirective ``` -Instead of just providing the name of the directive, all directives must now return an SDL definition that formally describes them. +Instead of only providing the name of the directive, all directives must now return an SDL definition that formally describes them. ```diff - public function name() @@ -503,7 +503,8 @@ Client queries will have to be changed like this: } ``` -If you absolutely cannot break your clients, you can re-implement `@orderBy` in your project. It is a relatively simple `ArgManipulator` directive. +If you absolutely cannot break your clients, you can re-implement `@orderBy` in your project. +It is a small `ArgManipulator` directive. ### `@modelClass` and `@model` changed @@ -545,9 +546,9 @@ type Mutation { } ``` -### `@method` passes down just ordered arguments +### `@method` passes down only ordered arguments -Instead of passing down the usual resolver arguments, the `@method` directive will now pass just the arguments given to a field. +Instead of passing down the usual resolver arguments, the `@method` directive will now pass only the arguments given to a field. This behavior could previously be enabled through the `passOrdered` option, which is now removed. ```graphql @@ -662,7 +663,7 @@ $typeRegistry = app(\Nuwave\Lighthouse\Schema\TypeRegistry::class); Since GraphQL constrains allowed inputs by design, mass assignment protection is not needed. By default, Lighthouse will use `forceFill()` when populating a model with arguments in mutation directives. -This allows you to use mass assignment protection for other cases where it is actually useful. +This allows you to use mass assignment protection for other cases where it is useful. If you need to revert to the old behavior of using `fill()`, you can change your `lighthouse.php`: diff --git a/docs/master/api-reference/commands.md b/docs/master/api-reference/commands.md index d99ee18c88..dcb26e2515 100644 --- a/docs/master/api-reference/commands.md +++ b/docs/master/api-reference/commands.md @@ -89,7 +89,7 @@ Compile the GraphQL schema and print the result. php artisan lighthouse:print-schema ``` -This can be quite useful, as the root `.graphql` files do not necessarily contain the whole schema. +This is useful, as the root `.graphql` files do not necessarily contain the whole schema. Schema imports, native PHP types and schema manipulation may influence the final schema. Use the `-W` / `--write` option to output the schema to default file storage (usually `storage/app`). diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index 854b965055..b5ad11b9dc 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -370,7 +370,7 @@ type User { You may want to allow accessing data that describes the relation between the models and is stored in the intermediate table. See [retrieving intermediate table columns in Laravel](https://laravel.com/docs/eloquent-relationships#retrieving-intermediate-table-columns). -Just like in Laravel, you can access the `pivot` attribute on the models (or its alias). +Like in Laravel, you can access the `pivot` attribute on the models (or its alias). Even though this attribute is always present when querying the model through the relation, it may not be present when reaching the node through another path in the schema. It is recommended to define the field as nullable (no `!`). @@ -1546,7 +1546,7 @@ type Mutation { } ``` -Works very similar to the [@delete](#delete) directive. +Works like the [@delete](#delete) directive. ## @enum @@ -1693,12 +1693,12 @@ enum GlobalIdDecode { ARRAY """ - Return just `$type`. + Return only `$type`. """ TYPE """ - Return just `$id`. + Return only `$id`. """ ID } @@ -1742,7 +1742,7 @@ directive @guard( ) repeatable on FIELD_DEFINITION | OBJECT ``` -Note that [@guard](#guard) does not log in users. +[@guard](#guard) does not log in users. To ensure the user is logged in, add the `AttemptAuthenticate` middleware to your `lighthouse.php` middleware config. ```php @@ -3118,7 +3118,7 @@ But means that the response does not hold information about the total number of If you wish to use the `simplePaginate` method, set the `type` to `SIMPLE`. -> Please note that the `SIMPLE` paginator does not have the attributes +> The `SIMPLE` paginator does not have the attributes > `lastPage` and `total`. > > If you need those fields, you should use the default `PAGINATOR`. @@ -3236,7 +3236,7 @@ type Query { ### Custom builder -If simply querying Eloquent does not fit your use-case, you can specify a custom `builder`. +If a plain Eloquent query does not fit your use case, you can specify a custom `builder`. ```graphql type Query { @@ -3247,7 +3247,7 @@ type Query { Your method receives the typical resolver arguments. It must return an instance of `Illuminate\Database\Query\Builder`. -> If you actually want to query a model and possibly its relations through nested fields, +> If you want to query a model and possibly its relations through nested fields, > make sure to return an Eloquent builder, e.g. `Post::query()`. ```php @@ -3370,7 +3370,7 @@ type Mutation { } ``` -Works very similar to the [@delete](#delete) directive. +Works like the [@delete](#delete) directive. ## @rules @@ -3521,7 +3521,7 @@ scalar DateTime Adds a scope to the query builder. The scope method will receive the client-given value of the argument as the second parameter. -This also works with custom query builders, it simply calls its methods with the argument value. +This also works with custom query builders, it calls its methods with the argument value. """ directive @scope( """ @@ -3704,7 +3704,7 @@ Internally, the arguments are transformed into a flat structure before they are ] ``` -Note that Lighthouse spreads out the arguments **after** all other [ArgDirectives](../custom-directives/field-argument-directives) have been applied, e.g. validation, transformation. +Lighthouse spreads out the arguments **after** all other [ArgDirectives](../custom-directives/field-argument-directives) have been applied, e.g. validation, transformation. ## @subscription @@ -4044,7 +4044,7 @@ directive @upsert( ) on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -Lighthouse will try to fetch the model by its primary key, just like [@update](#update). +Lighthouse will try to fetch the model by its primary key, like [@update](#update). If the model doesn't exist, it will be newly created with a given `id`. In case no `id` is specified, an auto-generated fresh ID will be used instead. @@ -4504,7 +4504,7 @@ type User { } ``` -If you just want to return the relation as-is, see [handling Eloquent relationships](../eloquent/relationships.md). +To return the relation as-is, see [handling Eloquent relationships](../eloquent/relationships.md). ## @withCount @@ -4537,7 +4537,7 @@ type User { } ``` -If you just want to return the count itself as-is, use [@count](#count). +To return the count as-is, use [@count](#count). ## @withoutGlobalScopes diff --git a/docs/master/api-reference/events.md b/docs/master/api-reference/events.md index 2d1871e043..6d1d12eb0e 100644 --- a/docs/master/api-reference/events.md +++ b/docs/master/api-reference/events.md @@ -217,8 +217,8 @@ use GraphQL\Executor\ExecutionResult; /** * Fires after resolving each individual query. * - * This gives listeners an easy way to manipulate the query - * result without worrying about batched execution. + * This lets listeners manipulate the query result + * without worrying about batched execution. */ class ManipulateResult { diff --git a/docs/master/api-reference/scalars.md b/docs/master/api-reference/scalars.md index a06ffb6273..f38677a28e 100644 --- a/docs/master/api-reference/scalars.md +++ b/docs/master/api-reference/scalars.md @@ -63,6 +63,6 @@ scalar Upload ``` This Scalar can only be used as an argument, not as a return type. -For more information, please refer to the [file uploads guide](../digging-deeper/file-uploads.md). +For more information, see the [file uploads guide](../digging-deeper/file-uploads.md). The multipart form request is handled by Lighthouse, the resolver gets passed an instance of [`Illuminate\Http\UploadedFile`](https://laravel.com/api/9.x/Illuminate/Http/UploadedFile.html) in the argument `array $variables`. diff --git a/docs/master/concepts/arg-resolvers.md b/docs/master/concepts/arg-resolvers.md index 55c88bb130..d39fb6d74a 100644 --- a/docs/master/concepts/arg-resolvers.md +++ b/docs/master/concepts/arg-resolvers.md @@ -14,7 +14,7 @@ However, a single field resolver still has to take care of all the input argumen Handling complex input data in a single function is hard because of their dynamic nature. The input given by a client might be nested arbitrarily deep and come in many different variations. -The following example shows an example mutation that is actually composed out of multiple distinct operations. +The following example shows an example mutation that is composed out of multiple distinct operations. ```graphql type Mutation { @@ -59,7 +59,7 @@ function createTaskWithNotes(mixed $root, array $args): \App\Models\Task { // Create the new task with the remaining args $task = \App\Models\Task::create($args); - // If the client actually passed notes, create and attach them + // If the client passed notes, create and attach them if ($notes) { foreach($notes as $note) { $task->notes()->create($note); @@ -70,7 +70,7 @@ function createTaskWithNotes(mixed $root, array $args): \App\Models\Task { } ``` -In this contrived example, the function is still quite small. +In this contrived example, the function is still small. However, separation of concerns is already violated: A single function is responsible for creating both tasks and notes. We might want to extend our schema to support more operations in the future, such as updating a task and creating, updating or deleting notes or other, more deeply nested relations. @@ -78,7 +78,7 @@ Such changes would force us to duplicate code and increase the complexity of our ## Solution -Ideally, we would want to write small and focused functions that deal with just a part of the given input arguments. +Ideally, we would want to write small and focused functions that deal with only a part of the given input arguments. The execution engine should traverse the given input and take care of calling the appropriate functions with their respective arguments. ```php diff --git a/docs/master/custom-directives/field-directives.md b/docs/master/custom-directives/field-directives.md index fefe8bf3d4..03a376fb25 100644 --- a/docs/master/custom-directives/field-directives.md +++ b/docs/master/custom-directives/field-directives.md @@ -10,7 +10,7 @@ It can be a great way to reuse resolver logic within a schema. ## FieldMiddleware -A [`Nuwave\Lighthouse\Support\Contracts\FieldMiddleware`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/FieldMiddleware.php) directive allows you to wrap around the field resolver, just like [Laravel Middleware](https://laravel.com/docs/middleware). +A [`Nuwave\Lighthouse\Support\Contracts\FieldMiddleware`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/FieldMiddleware.php) directive allows you to wrap around the field resolver, like [Laravel Middleware](https://laravel.com/docs/middleware). You may use it to handle incoming values before reaching the final resolver as well as the outgoing result of resolving the field. diff --git a/docs/master/custom-directives/getting-started.md b/docs/master/custom-directives/getting-started.md index 42959b95c0..72cdccd456 100644 --- a/docs/master/custom-directives/getting-started.md +++ b/docs/master/custom-directives/getting-started.md @@ -13,7 +13,7 @@ The class name of a directive must follow the following pattern: Directive -Let's implement a simple `@upperCase` directive as a part of this introduction. +Let's implement an `@upperCase` directive as a part of this introduction. Use the artisan generator command to create it: ```shell @@ -56,7 +56,7 @@ Depending on what your directive should do, you can pick one or more of the prov They serve as the point of contact to Lighthouse. In this case, our directive needs to run after the actual resolver. -Just like [Laravel Middleware](https://laravel.com/docs/middleware), we can wrap around it by using the `FieldMiddleware` directive. +Like [Laravel Middleware](https://laravel.com/docs/middleware), we can wrap around it by using the `FieldMiddleware` directive. ```php namespace App\GraphQL\Directives; @@ -101,5 +101,5 @@ When Lighthouse encounters a directive within the schema, it starts looking for to gather namespaces defined by plugins, extensions or other listeners 1. Lighthouse's built-in directive namespace -This means that our directive is already registered, just by matter of defining it in the default namespace. +This means that our directive is already registered, because it is defined in the default namespace. Will take precedence over potential other directives with the same name. diff --git a/docs/master/custom-directives/input-value-directives.md b/docs/master/custom-directives/input-value-directives.md index 3426bc20fe..996bd9b80c 100644 --- a/docs/master/custom-directives/input-value-directives.md +++ b/docs/master/custom-directives/input-value-directives.md @@ -246,5 +246,5 @@ final class GeocodeDirective extends BaseDirective implements SaveAwareArgResolv When `runBeforeSave()` returns `true`, the resolver is invoked before `$model->save()`, allowing it to set attributes on the model. When it returns `false`, the resolver runs after the model is saved — the same timing as any `ArgResolver` that does not implement this interface. -Note that `__invoke()` receives `null` as `$args` if the client sends `null` for a nullable input field. +`__invoke()` receives `null` as `$args` if the client sends `null` for a nullable input field. Guard accordingly. diff --git a/docs/master/digging-deeper/adding-types-programmatically.md b/docs/master/digging-deeper/adding-types-programmatically.md index 80d2a55a61..f85484d51c 100644 --- a/docs/master/digging-deeper/adding-types-programmatically.md +++ b/docs/master/digging-deeper/adding-types-programmatically.md @@ -29,7 +29,7 @@ While Lighthouse is an SDL-first GraphQL server, you can also use native PHP typ Check out the [webonyx/graphql-php documentation](https://webonyx.github.io/graphql-php/type-definitions) on how to define types. -Note that you will not have access to a large portion of Lighthouse functionality that is provided through server-side directives and the definition is much more verbose. +You will not have access to a large portion of Lighthouse functionality that is provided through server-side directives and the definition is much more verbose. Because of this, we do not recommend you use native PHP types for complex object types. diff --git a/docs/master/digging-deeper/error-handling.md b/docs/master/digging-deeper/error-handling.md index 9e8a663c0a..d05b030431 100644 --- a/docs/master/digging-deeper/error-handling.md +++ b/docs/master/digging-deeper/error-handling.md @@ -39,7 +39,7 @@ However, you can choose to report client-safe errors by replacing `Nuwave\Lighth ## Additional Error Information -The interface [`GraphQL\Error\ProvidesExtensions`](https://github.com/webonyx/graphql-php/blob/master/src/Error/ProvidesExtensions.php) may be implemented to add more information than just an error message to the rendered error output. +The interface [`GraphQL\Error\ProvidesExtensions`](https://github.com/webonyx/graphql-php/blob/master/src/Error/ProvidesExtensions.php) may be implemented to add more information than an error message to the rendered error output. This custom exception contains information about the reason the exception was thrown: diff --git a/docs/master/digging-deeper/extending-lighthouse.md b/docs/master/digging-deeper/extending-lighthouse.md index 0b4aa5e4e8..98834a5c1e 100644 --- a/docs/master/digging-deeper/extending-lighthouse.md +++ b/docs/master/digging-deeper/extending-lighthouse.md @@ -43,7 +43,7 @@ You may override this by calling `GraphQL\Executor\Executor::setDefaultFieldReso The context is the third argument of any resolver function. You may replace the default `Nuwave\Lighthouse\Schema\Context` with your own implementation of the interface `Nuwave\Lighthouse\Support\Contracts\GraphQLContext`. -The following example is just a starting point of what you can do: +The following example is only a starting point of what you can do: ```php namespace Nuwave\Lighthouse\Schema; diff --git a/docs/master/digging-deeper/ordering.md b/docs/master/digging-deeper/ordering.md index 5c9819882b..377d4c972c 100644 --- a/docs/master/digging-deeper/ordering.md +++ b/docs/master/digging-deeper/ordering.md @@ -84,7 +84,7 @@ enum PostColumn { ``` Lighthouse will still automatically generate the necessary input types and the `SortOrder` enum. -Instead of generating enums for the allowed columns, it will simply use the existing `PostColumn` enum. +Instead of generating enums for the allowed columns, it uses the existing `PostColumn` enum. ### Ordering By Relations diff --git a/docs/master/eloquent/complex-where-conditions.md b/docs/master/eloquent/complex-where-conditions.md index 9cd5ac3e88..c0b9da11a2 100644 --- a/docs/master/eloquent/complex-where-conditions.md +++ b/docs/master/eloquent/complex-where-conditions.md @@ -159,13 +159,13 @@ enum PersonColumn { ``` Lighthouse will still automatically generate the necessary input types. -Instead of creating enums for the allowed columns, it will simply use the existing `PersonColumn` enum. +Instead of creating enums for the allowed columns, it uses the existing `PersonColumn` enum. It is recommended to either use the `columns` or the `columnsEnum` argument. When you don't define any allowed columns, clients can specify arbitrary column names as a `String`. This approach should by taken with care, as it carries potential performance and security risks and offers little type safety. -A simple query for a person who is exactly 42 years old would look like this: +A query for a person who is exactly 42 years old would look like this: ```graphql { @@ -175,7 +175,7 @@ A simple query for a person who is exactly 42 years old would look like this: } ``` -Note that the operator defaults to `EQ` (`=`) if not given, so you could also omit it from the previous example and get the same result. +The operator defaults to `EQ` (`=`) if not given, so you could also omit it from the previous example and get the same result. The following query gets actors over age 37 who either have red hair or are at least 150cm: @@ -278,7 +278,7 @@ directive @whereHasConditions( ) on ARGUMENT_DEFINITION ``` -This directive works very similar to [@whereConditions](#whereconditions), except that the conditions are applied to a relation sub query: +This directive works like [@whereConditions](#whereconditions), except that the conditions are applied to a relation sub query: ```graphql type Query { @@ -321,7 +321,7 @@ enum QueryPeopleHasRoleColumn { } ``` -A simple query for a person who has an access level of at least 5, through one of their roles, looks like this: +A query for a person who has an access level of at least 5, through one of their roles, looks like this: ```graphql { @@ -331,7 +331,8 @@ A simple query for a person who has an access level of at least 5, through one o } ``` -You can also query for relationship existence without any condition; simply use an empty object as argument value. +You can also query for relationship existence without any condition. +Use an empty object as argument value. This query would retrieve all persons that have a role: ```graphql @@ -342,7 +343,7 @@ This query would retrieve all persons that have a role: } ``` -Just like with the [@whereCondition](../api-reference/directives.md#whereconditions) directive, using `null` as argument value does not have any effect on the query. +Like with the [@whereCondition](../api-reference/directives.md#whereconditions) directive, using `null` as argument value does not have any effect on the query. This query would retrieve all persons, no matter if they have a role or not: ```graphql diff --git a/docs/master/eloquent/getting-started.md b/docs/master/eloquent/getting-started.md index 74d40974b8..73718d3e7d 100644 --- a/docs/master/eloquent/getting-started.md +++ b/docs/master/eloquent/getting-started.md @@ -1,6 +1,6 @@ # Eloquent: Getting Started -Lighthouse makes it easy for you to perform queries and mutations on your Eloquent models. +Lighthouse lets you perform queries and mutations on your Eloquent models. ## Defining Models @@ -292,8 +292,7 @@ To upsert multiple models at once, use the [@upsertMany](../api-reference/direct ## Delete -Deleting models is a breeze using the [@delete](../api-reference/directives.md#delete) directive. -Dangerously easy. +Delete models with the [@delete](../api-reference/directives.md#delete) directive. ```graphql type Mutation { @@ -301,7 +300,7 @@ type Mutation { } ``` -Simply call it with the ID of the user you want to delete. +Call it with the ID of the user you want to delete. ```graphql mutation { diff --git a/docs/master/eloquent/nested-mutations.md b/docs/master/eloquent/nested-mutations.md index c3beaa8455..2ebd34ecf1 100644 --- a/docs/master/eloquent/nested-mutations.md +++ b/docs/master/eloquent/nested-mutations.md @@ -69,7 +69,7 @@ input CreatePostInput { The first argument `title` is a value of the `Post` itself and corresponds to a column in the database. -The second argument `author` is named just like the relationship method that is defined on the `Post` model. +The second argument `author` is named like the relationship method that is defined on the `Post` model. A nested `BelongsTo` relationship exposes the following operations: - `connect` it to an existing model @@ -80,7 +80,7 @@ A nested `BelongsTo` relationship exposes the following operations: - `delete` the related model and the association to it Both `disconnect` and `delete` don't make much sense when creating a new model. -You can control what operations are possible by defining just what you need in the `input`. +You can control what operations are possible by defining only what you need in the `input`. We choose to expose the following operations on the related `User` model: ```graphql @@ -181,7 +181,7 @@ input UpdateUserBelongsTo { } ``` -You must pass a truthy value to `disconnect` and `delete` for them to actually run. +You must pass a truthy value to `disconnect` and `delete` for them to run. This structure was chosen as it is consistent with updating `BelongsToMany` relationships and allows the query string to be mostly static, taking a variable value to control its behavior. ```graphql @@ -217,7 +217,7 @@ If `false` or `null` is passed, it will not change. ``` When issuing an `upsert`, you may expose the same nested operations as an `update`. -In case a new model is created, they will simply be ignored. +In case a new model is created, they are ignored. ```graphql mutation UpdatePost($disconnectAuthor: Boolean) { @@ -688,7 +688,7 @@ type UserMoviePivot { Laravel's `sync()`, `syncWithoutDetach()` or `connect()` methods allow you to pass an array where the keys are IDs of related models and the values are pivot data. Lighthouse exposes this capability through the nested operations on many-to-many relations. -Instead of passing just a list of IDs, you can define an `input` type that also contains pivot data. +Instead of passing only a list of IDs, you can define an `input` type that also contains pivot data. It must contain a field called `id` to contain the ID of the related model, all other fields will be inserted into the pivot table. ```graphql diff --git a/docs/master/eloquent/polymorphic-relationships.md b/docs/master/eloquent/polymorphic-relationships.md index ef5de1f768..704278bab9 100644 --- a/docs/master/eloquent/polymorphic-relationships.md +++ b/docs/master/eloquent/polymorphic-relationships.md @@ -1,10 +1,10 @@ # Polymorphic Relationships -Just like in Laravel, you can define [Polymorphic Relationships](https://laravel.com/docs/eloquent-relationships#polymorphic-relationships) in your schema. +Like in Laravel, you can define [Polymorphic Relationships](https://laravel.com/docs/eloquent-relationships#polymorphic-relationships) in your schema. ## One to One -Suppose you have defined a model structure just like the Laravel example docs. +Suppose you have defined a model structure like the Laravel example docs. You have two models, `Post` and `User` which may both have an `Image` assigned. Let's start off with the plain type definitions, without any relations. @@ -26,7 +26,7 @@ type Image { } ``` -First, let's go ahead and add the relations to `Image` since they are straightforward. +First, add the relations to `Image`. The field name should match your relationship method name and be annotated with the [@morphOne](../api-reference/directives.md#morphone) directive. ```graphql @@ -64,7 +64,7 @@ type Image { ``` The default type resolver will be able to determine which concrete object type is returned when dealing with Eloquent models. -Your definition should just work. +Your definition works without further changes. Given you have a field `images` that returns a list of `[Image!]!`, you could query it like this: diff --git a/docs/master/eloquent/relationships.md b/docs/master/eloquent/relationships.md index 5081351649..30c912abfb 100644 --- a/docs/master/eloquent/relationships.md +++ b/docs/master/eloquent/relationships.md @@ -1,6 +1,6 @@ # Eloquent Relationships -Just like in Laravel, you can define [Eloquent Relationships](https://laravel.com/docs/eloquent-relationships) in your schema. +Like in Laravel, you can define [Eloquent Relationships](https://laravel.com/docs/eloquent-relationships) in your schema. Suppose you have defined the following model: @@ -25,7 +25,7 @@ final class Post extends Model } ``` -Add fields to your type that are named just like the relationships: +Add fields to your type that are named like the relationships: ```graphql type Post { @@ -34,12 +34,12 @@ type Post { } ``` -Because Laravel relationships can be accessed just like regular properties on your model, the default field resolver will work just fine. +Because Laravel relationships can be accessed like regular properties on your model, the default field resolver works for them. ## Avoiding the N+1 performance problem When accessing Eloquent relationships as properties, the relationship data is "lazy loaded". -This means the relationship data is not actually loaded until you first access the property. +This means the relationship data is not loaded until you first access the property. This leads to a common performance pitfall that comes with the nested nature of GraphQL queries: the so-called N+1 query problem. [Learn more](../performance/n-plus-one.md). diff --git a/docs/master/eloquent/soft-deleting.md b/docs/master/eloquent/soft-deleting.md index 3aa201488a..873d76d195 100644 --- a/docs/master/eloquent/soft-deleting.md +++ b/docs/master/eloquent/soft-deleting.md @@ -49,7 +49,7 @@ type Mutation { } ``` -Simply call the field with the ID of the flight you want to restore. +Call the field with the ID of the flight you want to restore. ```graphql mutation { @@ -72,7 +72,7 @@ type Mutation { } ``` -Simply call it with the ID of the `Flight` you want to permanently remove. +Call it with the ID of the `Flight` you want to permanently remove. ```graphql mutation { diff --git a/docs/master/federation/getting-started.md b/docs/master/federation/getting-started.md index 81df858246..1b07fcc562 100644 --- a/docs/master/federation/getting-started.md +++ b/docs/master/federation/getting-started.md @@ -55,7 +55,7 @@ In order to use federated tracing, you need to enable [tracing](../performance/t ], ``` -Note that federated tracing requires `google/protobuf` to be installed (for better performance you can also install the `protobuf` php extension). +Federated tracing requires `google/protobuf` to be installed (for better performance you can also install the `protobuf` php extension). ### Unsupported features diff --git a/docs/master/getting-started/migrating-to-lighthouse.md b/docs/master/getting-started/migrating-to-lighthouse.md index 531660db6a..ac0bc608d0 100644 --- a/docs/master/getting-started/migrating-to-lighthouse.md +++ b/docs/master/getting-started/migrating-to-lighthouse.md @@ -8,7 +8,7 @@ The most important thing to get you started using Lighthouse will be a schema th If you already have a server with another library up and running, you can use introspection to retrieve this schema and save it to a file. -A simple tool that is also generally useful is [graphql-cli](https://github.com/graphql-cli/graphql-cli). +A generally useful tool is [graphql-cli](https://github.com/graphql-cli/graphql-cli). npm install -g graphql-cli graphql init diff --git a/docs/master/performance/caching.md b/docs/master/performance/caching.md index d0e4cda179..f7209520b4 100644 --- a/docs/master/performance/caching.md +++ b/docs/master/performance/caching.md @@ -120,7 +120,7 @@ Register the service provider `Nuwave\Lighthouse\CacheControl\CacheControlServic You can change the [`Cache-Control` header](https://developer.mozilla.org/de/docs/Web/HTTP/Headers/Cache-Control) of your response regardless of [@cache](../api-reference/directives.md#cache) by adding the [@cacheControl](../api-reference/directives.md#cachecontrol) directive to a field. The directive can be defined on the field-level or type-level. -Note that field-level settings override type-level settings. +Field-level settings override type-level settings. The final header settings are calculated based on these rules: diff --git a/docs/master/performance/n-plus-one.md b/docs/master/performance/n-plus-one.md index b84307fa7e..77fbf191dd 100644 --- a/docs/master/performance/n-plus-one.md +++ b/docs/master/performance/n-plus-one.md @@ -80,7 +80,7 @@ When looking at the query path from `posts`, they may look like: In order to combine them, you need to have a single stateful batch loader instance for `users.posts`. Use `Nuwave\Lighthouse\Execution\BatchLoader\BatchLoaderRegistry` to resolve such instances. The following code is the resolver for `User.posts`. -See [resolver precedence](../the-basics/fields.md#resolver-precedence) on how it could actually be assigned to a field. +See [resolver precedence](../the-basics/fields.md#resolver-precedence) on how it could be assigned to a field. ```php use GraphQL\Deferred; @@ -145,7 +145,7 @@ final class UserPostsBatchLoader } /** - * Actually call out to the posts service and resolve them all at once. + * Call out to the posts service and resolve them all at once. */ protected function resolve(): void { diff --git a/docs/master/performance/server-configuration.md b/docs/master/performance/server-configuration.md index 561c14b335..04b7997948 100644 --- a/docs/master/performance/server-configuration.md +++ b/docs/master/performance/server-configuration.md @@ -5,7 +5,7 @@ You can tune the configuration of your PHP server for Lighthouse. ## OPcache The nature of the schema operations in Lighthouse plays nicely with [PHP's OPcache](https://php.net/manual/en/book.opcache.php). -If you have the freedom to install it on your server, it's an easy way to get a nice performance boost. +If you can install it on your server, it improves performance. ## Xdebug diff --git a/docs/master/security/authentication.md b/docs/master/security/authentication.md index db9b35d1d4..084c837980 100644 --- a/docs/master/security/authentication.md +++ b/docs/master/security/authentication.md @@ -17,9 +17,9 @@ As multiple checks for authentication or permissions may be required in a single ], ``` -Note that the `AttemptAuthentication` middleware does _not_ protect your fields from unauthenticated access, decorate them with [@guard](../api-reference/directives.md#guard) as needed. +The `AttemptAuthentication` middleware does _not_ protect your fields from unauthenticated access, decorate them with [@guard](../api-reference/directives.md#guard) as needed. -If you want to guard all your fields against unauthenticated access, you can simply add Laravel's built-in auth middleware. +If you want to guard all your fields against unauthenticated access, add Laravel's built-in auth middleware. Beware that this approach does not allow any GraphQL operations for guest users. So you will have to handle login outside GraphQL. @@ -59,7 +59,7 @@ If you are using [Laravel Sanctum](https://laravel.com/docs/sanctum) for your AP 'guards' => ['sanctum'], ``` -Note that Sanctum requires you to send an CSRF token as [header](https://laravel.com/docs/csrf#csrf-x-csrf-token) with all GraphQL requests, regardless of whether the user is authenticated or not. +Sanctum requires you to send an CSRF token as [header](https://laravel.com/docs/csrf#csrf-x-csrf-token) with all GraphQL requests, regardless of whether the user is authenticated or not. When using [mll-lab/laravel-graphiql](https://github.com/mll-lab/laravel-graphiql), follow the [instructions to add a CSRF token](https://github.com/mll-lab/laravel-graphiql#configure-session-authentication). @@ -98,7 +98,7 @@ extend type Query { ## Get the current user -Lighthouse provides a really simple way to fetch the information of the currently authenticated user. +Lighthouse can fetch the information of the currently authenticated user. Add a field that returns your `User` type and decorate it with the [@auth](../api-reference/directives.md#auth) directive. ```graphql diff --git a/docs/master/security/authorization.md b/docs/master/security/authorization.md index de84df9814..41ea2cdab7 100644 --- a/docs/master/security/authorization.md +++ b/docs/master/security/authorization.md @@ -12,7 +12,7 @@ For example, a user may only be able to see notes they created. You can use the nested nature of GraphQL queries to naturally limit access to such fields. Begin with a field that represents the currently authenticated user, commonly called `me` or `viewer`. -You can resolve that field quite easily by using the [@auth](../api-reference/directives.md#auth) directive. +Resolve that field with the [@auth](../api-reference/directives.md#auth) directive. ```graphql type Query { @@ -38,7 +38,7 @@ type Note { } ``` -Now, authenticated users can query for items that belong to them and are naturally limited to seeing just those. +Now, authenticated users can query for items that belong to them and are naturally limited to seeing only those. ```graphql { @@ -116,7 +116,7 @@ final class PostPolicy For some models, you may want to restrict access for already resolved instance of a model. Use the [@canResolved](../api-reference/directives.md#canresolved) directive to do so. -> This will actually run the field before checking permissions, do not use in mutations. +> This runs the field before checking permissions, do not use in mutations. ```graphql type Query { diff --git a/docs/master/security/resource-exhaustion.md b/docs/master/security/resource-exhaustion.md index d7147bac99..833b458ccb 100644 --- a/docs/master/security/resource-exhaustion.md +++ b/docs/master/security/resource-exhaustion.md @@ -3,8 +3,8 @@ GraphQL gives enormous power to clients. With great power, there must also come great responsibility 🕷. -Since clients have the possibility to craft very complex queries, we must be ready to handle them properly. -These queries may be abusive queries from evil clients, or may simply be huge queries used by legitimate clients. +Since clients have the possibility to craft complex queries, we must be ready to handle them properly. +These queries may be abusive queries from evil clients, or huge queries used by legitimate clients. In both of these cases, the client can potentially take your GraphQL server down. _This intro was taken from HowToGraphQL, we recommend reading their full chapter on security https://www.howtographql.com/advanced/4-security/_ diff --git a/docs/master/security/sanitization.md b/docs/master/security/sanitization.md index 5c20de2141..0e4aa0343a 100644 --- a/docs/master/security/sanitization.md +++ b/docs/master/security/sanitization.md @@ -6,7 +6,7 @@ While [validation](validation) is a great first line of defense, there are cases ## Single arguments A great way to deal with single values is to use an [`ArgTransformerDirective`](../custom-directives/field-argument-directives#argtransformerdirective). -Lighthouse offers a few built-in options, but it is also really easy to build your own. +Lighthouse offers a few built-in options, and you can build your own. Here is how you can remove whitespace of a given input string by using the built-in [@trim](../api-reference/directives.md#trim) directive: diff --git a/docs/master/security/validation.md b/docs/master/security/validation.md index 742d839f64..92aca7e0d2 100644 --- a/docs/master/security/validation.md +++ b/docs/master/security/validation.md @@ -149,7 +149,8 @@ input UpdateUserInput @validator { ``` We need to back that with a validator class. -Lighthouse uses a simple naming convention for validator classes, use the name of the input type and append `Validator`: +Lighthouse uses a naming convention for validator classes. +Use the name of the input type and append `Validator`: ```shell php artisan lighthouse:validator UpdateUserInputValidator @@ -181,7 +182,7 @@ final class UpdateUserInputValidator extends Validator } ``` -Note that this gives you access to all kinds of programmatic validation rules that Laravel provides. +This gives you access to all kinds of programmatic validation rules that Laravel provides. This can give you additional flexibility when you need it. ### Custom Validator Messages diff --git a/docs/master/testing/extensions.md b/docs/master/testing/extensions.md index f8debad0ef..d9266612e3 100644 --- a/docs/master/testing/extensions.md +++ b/docs/master/testing/extensions.md @@ -39,7 +39,7 @@ final class MyCustomDirectiveTest extends TestCase ## Mock resolvers When testing custom functionality through a dummy schema, you still need to have a way to resolve fields. -Lighthouse provides a simple way to mock resolvers in a dummy schema. +Lighthouse can mock resolvers in a dummy schema. Mark the fields to mock with the `@mock` directive: ```graphql @@ -102,8 +102,8 @@ public function testReverseField(): void ``` Since we get back an instance of PHPUnit's `InvocationMocker`, we can also assert that our resolver is called with certain values. -Note that we are not passing an explicit resolver function here. -The default resolver will simply return `null`. +We are not passing an explicit resolver function here. +The default resolver returns `null`. ```php public function testReverseInput(): void diff --git a/docs/master/testing/phpunit.md b/docs/master/testing/phpunit.md index f000307606..f13d995df0 100644 --- a/docs/master/testing/phpunit.md +++ b/docs/master/testing/phpunit.md @@ -1,13 +1,13 @@ # Testing with PHPUnit -Lighthouse makes it easy to add automated tests through [PHPUnit](https://phpunit.de). +Lighthouse supports automated tests through [PHPUnit](https://phpunit.de). ## Setup Lighthouse offers some useful test helpers. Keep in mind they only work when your test class extends `Illuminate\Foundation\Testing\TestCase`. -The `MakesGraphQLRequests` trait make it easy to call your API: +The `MakesGraphQLRequests` trait lets you call your API: ```diff +use Nuwave\Lighthouse\Testing\MakesGraphQLRequests; @@ -106,7 +106,7 @@ public function testPostsSubscription(): void Now that we know how to query our server in tests, we need to make sure the returned results match our expectations. -The returned `TestResponse` conveniently offers assertions that work quite well with the JSON data returned by GraphQL. +The returned `TestResponse` conveniently offers assertions that work well with the JSON data returned by GraphQL. The `assertJson` method asserts that the response is a superset of the given JSON. @@ -192,7 +192,7 @@ $response->assertGraphQLSubscriptionNotAuthorized($this); Once you do your subscription query and get a `TestResponse $response`, you can run the following assertions on it. -To assert the subscription actually received some broadcasts: +To assert the subscription received some broadcasts: ``` // any other way to broadcast would also work @@ -235,7 +235,7 @@ Make sure to [generate the latest IDE-helper file](../api-reference/commands.md# php artisan lighthouse:ide-helper ``` -The provided assertions are prefixed with `assertGraphQL` for easy discovery. +The provided assertions are prefixed with `assertGraphQL`, so you can find them through autocompletion. They offer useful shortcuts to common testing tasks. For example, you might want to ensure that validation works properly: diff --git a/docs/master/the-basics/best-practices.md b/docs/master/the-basics/best-practices.md index 4d8d0d9d73..d8a6f41b37 100644 --- a/docs/master/the-basics/best-practices.md +++ b/docs/master/the-basics/best-practices.md @@ -5,7 +5,7 @@ We recommend you use [GraphQL Rules](https://github.com/graphql-rules/graphql-ru ## In the mutation response, return a field of type Query -If you decide to [return the `Query` object in every mutation payload](https://github.com/graphql-rules/graphql-rules/blob/master/docs/rules/06-mutations/mutation-payload-query.md), Lighthouse makes it very easy. +If you decide to [return the `Query` object in every mutation payload](https://github.com/graphql-rules/graphql-rules/blob/master/docs/rules/06-mutations/mutation-payload-query.md), Lighthouse supports it. ```graphql type Mutation { diff --git a/docs/master/the-basics/directives.md b/docs/master/the-basics/directives.md index 482bcf5f59..edbf187395 100644 --- a/docs/master/the-basics/directives.md +++ b/docs/master/the-basics/directives.md @@ -34,9 +34,9 @@ type Query { ## Usage -Lighthouse provides a plethora of built-in schema directives that are ready to be consumed and can simply be used from within the schema. +Lighthouse provides a plethora of built-in schema directives that you can use in your schema. -The following example is quite dense, but it should give you an idea of what directives are capable of. +The following example is dense, but it should give you an idea of what directives are capable of. ```graphql type Query { diff --git a/docs/master/the-basics/fields.md b/docs/master/the-basics/fields.md index 375b7d26fe..01b90b8f27 100644 --- a/docs/master/the-basics/fields.md +++ b/docs/master/the-basics/fields.md @@ -66,7 +66,7 @@ This query will return the following response: ## Fields with arguments As we learned, _every_ field has a resolver function associated with it. -Just like functions, fields can take arguments to control their behavior. +Like functions, fields can take arguments to control their behavior. Let's construct a query that greets the user. We add a required argument `name` that is used to construct the greeting. @@ -198,7 +198,7 @@ function resolveUserAttribute(User $user, array $args, GraphQLContext $context, ``` Fortunately, the underlying GraphQL implementation already provides [a sensible default resolver](https://webonyx.github.io/graphql-php/data-fetching/#default-field-resolver). -Plays quite nicely with the data you would typically return from a root resolver, e.g. +It works well with the data you would typically return from a root resolver, e.g. `Eloquent` models or associative arrays. This means that in most cases, you will only have to provide resolvers for the root fields and make sure they return data in the proper shape. diff --git a/docs/master/the-basics/types.md b/docs/master/the-basics/types.md index 7be6281fba..4c138f2d4e 100644 --- a/docs/master/the-basics/types.md +++ b/docs/master/the-basics/types.md @@ -84,7 +84,7 @@ type Query { } ``` -In this example, the underlying values are actually integers. +In this example, the underlying values are integers. When the models are retrieved from the database, the mapping is applied and the integers are converted to the defined string keys. ```php @@ -311,7 +311,7 @@ Read more about them in the [GraphQL Reference](https://graphql.org/learn/schema ## Union -A Union is an abstract type that simply enumerates other Object Types. +A Union is an abstract type that enumerates other Object Types. They are similar to interfaces in that they can return different types. But do not prescribe any common fields. @@ -329,7 +329,7 @@ type Employee { } ``` -Just like Interfaces, you need a way to determine the concrete Object Type for a Union, based on the resolved value. +Like Interfaces, you need a way to determine the concrete Object Type for a Union, based on the resolved value. If the default type resolver does not work for you, define your own with `php artisan lighthouse:union `. It is automatically put in the default namespace where Lighthouse can discover it by itself. diff --git a/src/Cache/CacheDirective.php b/src/Cache/CacheDirective.php index ee4ec22ee1..c95386b7dc 100644 --- a/src/Cache/CacheDirective.php +++ b/src/Cache/CacheDirective.php @@ -76,7 +76,7 @@ public function handleField(FieldValue $fieldValue): void path: $path, ); - // We found a matching value in the cache, so we can return early without actually running the query. + // We found a matching value in the cache, so we can return early without running the query. $value = $cache->get($cacheKey); if ($value !== null) { // Deferring the result will allow nested deferred resolves to be bundled together, see https://github.com/nuwave/lighthouse/pull/2270#discussion_r1072414584. diff --git a/src/Events/ManipulateResult.php b/src/Events/ManipulateResult.php index 068c4d412f..dd9f1b3bf8 100644 --- a/src/Events/ManipulateResult.php +++ b/src/Events/ManipulateResult.php @@ -7,7 +7,7 @@ /** * Fires after resolving each individual query. * - * This gives listeners an easy way to manipulate the query result. + * This lets listeners manipulate the query result. * It avoids worrying about batched execution. */ class ManipulateResult diff --git a/src/Execution/Arguments/ArgumentSet.php b/src/Execution/Arguments/ArgumentSet.php index 8fecdb1206..099bd669e5 100644 --- a/src/Execution/Arguments/ArgumentSet.php +++ b/src/Execution/Arguments/ArgumentSet.php @@ -69,7 +69,7 @@ public function exists(string $key): bool /** * Add a value at the dot-separated path. * - * Works just like @see \Illuminate\Support\Arr::add(), but a path segment + * Works like @see \Illuminate\Support\Arr::add(), but a path segment * of `*` injects the value into every element of the list found at that * position instead of a single key. */ @@ -104,7 +104,7 @@ private function addValueAtKeys(array $keys, mixed $value): void // The branch leading up to a `*` might not have been given by the client // at all, e.g. an optional nested input that was omitted. In that case, - // there is nothing to inject into, so we just do nothing. + // there is nothing to inject into, so we do nothing. if ($throughWildcard && ! isset($this->arguments[$key])) { return; } diff --git a/src/Execution/Arguments/NestedManyToMany.php b/src/Execution/Arguments/NestedManyToMany.php index 8978997ac8..008b733cdb 100644 --- a/src/Execution/Arguments/NestedManyToMany.php +++ b/src/Execution/Arguments/NestedManyToMany.php @@ -108,7 +108,7 @@ protected function generateRelationArray(Argument $args): array return $relationArray; } - // The default case is simply a flat array of IDs which we don't have to transform + // The default case is a flat array of IDs which we don't have to transform return $values; } } diff --git a/src/Execution/ModelsLoader/SimpleModelsLoader.php b/src/Execution/ModelsLoader/SimpleModelsLoader.php index 1420babc6d..2b3c345959 100644 --- a/src/Execution/ModelsLoader/SimpleModelsLoader.php +++ b/src/Execution/ModelsLoader/SimpleModelsLoader.php @@ -22,7 +22,7 @@ public function extract(Model $model): mixed // Dot notation may be used to eager load nested relations $parts = explode('.', $this->relation); - // We just return the first level of relations for now. + // We only return the first level of relations for now. // They hold the nested relations in case they are needed. $firstRelation = $parts[0]; diff --git a/src/Execution/Utils/FieldPath.php b/src/Execution/Utils/FieldPath.php index 8493aa0b8f..4ab8a9ea0d 100644 --- a/src/Execution/Utils/FieldPath.php +++ b/src/Execution/Utils/FieldPath.php @@ -14,7 +14,7 @@ public static function withoutLists(array $path): string $significantPathSegments = array_filter( $path, // Ignore numeric path entries, as those signify a list of fields. - // Combining the queries for lists is the very purpose of the + // Combining the queries for lists is the purpose of the // batch loader, so they must not be included. static fn (int|string $segment): bool => ! is_numeric($segment), ); diff --git a/src/Federation/Directives/ExternalDirective.php b/src/Federation/Directives/ExternalDirective.php index e42df21267..fb5f79af16 100644 --- a/src/Federation/Directives/ExternalDirective.php +++ b/src/Federation/Directives/ExternalDirective.php @@ -31,7 +31,7 @@ public function resolveField(FieldValue $fieldValue): callable { $defaultFieldResolver = Executor::getDefaultFieldResolver(); - // The parent might just hold a foreign key to the external object, in which case we just return that. + // The parent might only hold a foreign key to the external object, in which case we return that. return static fn (mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolveInfo): mixed => is_scalar($root) ? $root : $defaultFieldResolver($root, $args, $context, $resolveInfo); diff --git a/src/Federation/Types/Any.php b/src/Federation/Types/Any.php index 4305a385e2..f332e8f781 100644 --- a/src/Federation/Types/Any.php +++ b/src/Federation/Types/Any.php @@ -66,7 +66,7 @@ public function parseValue($value): array $keyFieldsSelections = $entityResolverProvider->keyFieldsSelections($definition); $entityResolverProvider->firstSatisfiedKeyFields($keyFieldsSelections, $value); - // Ensure we actually have a resolver for the type available + // Ensure we have a resolver for the type available $entityResolverProvider->resolver($typename); // @phpstan-ignore-next-line type inference is too weak diff --git a/src/GlobalId/Base64GlobalId.php b/src/GlobalId/Base64GlobalId.php index cb2fcaa31a..e40d9658f2 100644 --- a/src/GlobalId/Base64GlobalId.php +++ b/src/GlobalId/Base64GlobalId.php @@ -5,7 +5,7 @@ /** * The default encoding of global IDs in Lighthouse. * - * The way that IDs are generated basically works like this: + * The way that IDs are generated works like this: * * 1. Take the name of a type, e.g. "User" and an ID, e.g. 123 * 2. Glue them together, separated by a colon, e.g. "User:123" diff --git a/src/GlobalId/GlobalId.php b/src/GlobalId/GlobalId.php index 5debb2c238..cd8ebe8015 100644 --- a/src/GlobalId/GlobalId.php +++ b/src/GlobalId/GlobalId.php @@ -20,9 +20,9 @@ public function encode(string $type, int|string $id): string; */ public function decode(string $globalID): array; - /** Decode the Global ID and get just the ID. */ + /** Decode the Global ID and get only the ID. */ public function decodeID(string $globalID): string; - /** Decode the Global ID and get just the type. */ + /** Decode the Global ID and get only the type. */ public function decodeType(string $globalID): string; } diff --git a/src/GlobalId/GlobalIdDirective.php b/src/GlobalId/GlobalIdDirective.php index 2e489eeba6..2b6b00f39c 100644 --- a/src/GlobalId/GlobalIdDirective.php +++ b/src/GlobalId/GlobalIdDirective.php @@ -44,12 +44,12 @@ enum GlobalIdDecode { ARRAY """ - Return just `$type`. + Return only `$type`. """ TYPE """ - Return just `$id`. + Return only `$id`. """ ID } diff --git a/src/GlobalId/NodeRegistry.php b/src/GlobalId/NodeRegistry.php index d986f785d0..477d51005e 100644 --- a/src/GlobalId/NodeRegistry.php +++ b/src/GlobalId/NodeRegistry.php @@ -24,7 +24,7 @@ class NodeRegistry * The stashed current type. * * PHP resolves fields synchronously and one after another. - * So we can safely stash just this one value. + * So we can safely stash only this one value. * Should the need arise, this can probably be a map from the unique field path to the type. */ protected string $currentType; diff --git a/src/Http/Middleware/AcceptJson.php b/src/Http/Middleware/AcceptJson.php index c7c58db8da..7da6f615df 100644 --- a/src/Http/Middleware/AcceptJson.php +++ b/src/Http/Middleware/AcceptJson.php @@ -7,7 +7,7 @@ /** * Always set the `Accept: application/json` header. * - * This makes it easier to do simple GET requests from clients with limited HTTP configuration options. + * This makes it easier to do GET requests from clients with limited HTTP configuration options. * It also ensures clients receive a proper result, even in case of unforeseen errors. */ class AcceptJson diff --git a/src/Http/routes.php b/src/Http/routes.php index 408babde77..6df44b0ee5 100644 --- a/src/Http/routes.php +++ b/src/Http/routes.php @@ -9,7 +9,7 @@ $config = $container->make(ConfigRepository::class); if ($routeConfig = $config->get('lighthouse.route')) { /** - * Not using assert() as only one of those classes will actually be installed. + * Not using assert() as only one of those classes will be installed. * * @var Illuminate\Contracts\Routing\Registrar|\Laravel\Lumen\Routing\Router $router */ diff --git a/src/Pagination/Cursor.php b/src/Pagination/Cursor.php index f4771497f5..1b1ffbe848 100644 --- a/src/Pagination/Cursor.php +++ b/src/Pagination/Cursor.php @@ -8,7 +8,7 @@ * Encode and decode pagination cursors. * * Currently, the underlying pagination query uses offset-based navigation. - * So this basically just encodes an offset. + * So this encodes an offset. * This is enough to satisfy the constraints that Relay has, but not a clean permanent solution. * * TODO Implement actual cursor pagination https://github.com/nuwave/lighthouse/issues/311 diff --git a/src/Schema/AST/ASTBuilder.php b/src/Schema/AST/ASTBuilder.php index 45ff5b5b47..41d655a18b 100644 --- a/src/Schema/AST/ASTBuilder.php +++ b/src/Schema/AST/ASTBuilder.php @@ -109,7 +109,7 @@ protected function applyTypeExtensionManipulators(): void { foreach ($this->documentAST->typeExtensions as $typeName => $typeExtensionsList) { foreach ($typeExtensionsList as $typeExtension) { - // Before we actually extend the types, we apply the manipulator directives + // Before we extend the types, we apply the manipulator directives // that are defined on type extensions themselves foreach ( $this->directiveLocator->associatedOfType($typeExtension, TypeExtensionManipulator::class) as $typeExtensionManipulator diff --git a/src/Schema/AST/ASTHelper.php b/src/Schema/AST/ASTHelper.php index f1382b3282..2585f93852 100644 --- a/src/Schema/AST/ASTHelper.php +++ b/src/Schema/AST/ASTHelper.php @@ -310,7 +310,7 @@ public static function addDirectiveToFields(DirectiveNode $directiveNode, Object * * We have to make sure it is unique in the schema. * This name is a bit verbose. - * It is very unlikely to collide with a random user-defined type. + * It is unlikely to collide with a random user-defined type. * * @example ParentNameFieldNameArgName */ diff --git a/src/Schema/Directives/ScopeDirective.php b/src/Schema/Directives/ScopeDirective.php index acb3013eae..30994a9367 100644 --- a/src/Schema/Directives/ScopeDirective.php +++ b/src/Schema/Directives/ScopeDirective.php @@ -17,7 +17,7 @@ public static function definition(): string Adds a scope to the query builder. The scope method will receive the client-given value of the argument as the second parameter. -This also works with custom query builders, it simply calls its methods with the argument value. +This also works with custom query builders, it calls its methods with the argument value. """ directive @scope( """ diff --git a/src/Schema/Directives/ThrottleDirective.php b/src/Schema/Directives/ThrottleDirective.php index 098d23ffd1..64e1074754 100644 --- a/src/Schema/Directives/ThrottleDirective.php +++ b/src/Schema/Directives/ThrottleDirective.php @@ -106,7 +106,7 @@ public function manipulateFieldDefinition(DocumentAST &$documentAST, FieldDefini { $name = $this->directiveArgValue('name'); if ($name !== null) { - // @phpstan-ignore-next-line limiter() can actually return null, some Laravel versions lie + // @phpstan-ignore-next-line limiter() can return null, some Laravel versions lie $this->limiter->limiter($name) ?? throw new DefinitionException("Named limiter {$name} is not found."); } diff --git a/src/Schema/Validator.php b/src/Schema/Validator.php index 2e0b45fc61..e43eb4174c 100644 --- a/src/Schema/Validator.php +++ b/src/Schema/Validator.php @@ -27,7 +27,7 @@ public function validate(): void $originalSchema = $this->schemaBuilder->schema(); $schemaConfig = $originalSchema->getConfig(); - // We add schema directive definitions only here, since it is very slow + // We add schema directive definitions only here, since it is slow $directiveFactory = new DirectiveFactory( new FallbackTypeNodeConverter($this->typeRegistry), ); diff --git a/src/Subscriptions/Storage/RedisStorageManager.php b/src/Subscriptions/Storage/RedisStorageManager.php index 4bf2848580..2ecae56dfb 100644 --- a/src/Subscriptions/Storage/RedisStorageManager.php +++ b/src/Subscriptions/Storage/RedisStorageManager.php @@ -117,7 +117,7 @@ public function storeSubscriber(Subscriber $subscriber, string $topic): void // In contrast to the CacheStorageManager, we use redis sets. // Instead of reading the entire list, adding the subscriber, and storing the list; - // we simply add the name of the subscriber to the set of subscribers of this topic using the sadd command... + // we add the name of the subscriber to the set of subscribers of this topic using the sadd command... $topicKey = $this->topicKey($topic); $this->connection->command('sadd', [ $topicKey, diff --git a/src/Support/AppVersion.php b/src/Support/AppVersion.php index 29696eac1e..190cd5e825 100644 --- a/src/Support/AppVersion.php +++ b/src/Support/AppVersion.php @@ -25,7 +25,7 @@ public static function below(float $version): bool protected static function version(): string { /** - * Not using assert() as only one of those classes will actually be installed. + * Not using assert() as only one of those classes will be installed. * * @var \Illuminate\Foundation\Application|\Laravel\Lumen\Application $container */ diff --git a/src/Support/DriverManager.php b/src/Support/DriverManager.php index b0a37668d4..fb200032f2 100644 --- a/src/Support/DriverManager.php +++ b/src/Support/DriverManager.php @@ -7,7 +7,7 @@ /** * NOTE: Implementation pulled from \Illuminate\Cache\CacheManager. Purpose is - * to serve as a base class to easily generate a manager that creates drivers with configuration options. + * to serve as a base class to generate a manager that creates drivers with configuration options. * * @phpstan-type CustomCreator callable(\Illuminate\Container\Container $app, array $config): object */ diff --git a/src/Support/Utils.php b/src/Support/Utils.php index d5dbe7d383..d0ae344735 100644 --- a/src/Support/Utils.php +++ b/src/Support/Utils.php @@ -15,7 +15,7 @@ class Utils /** * Attempt to find a given class in the given namespaces. * - * If the class itself exists, it is simply returned as is. + * If the class itself exists, it is returned as is. * Else, the given namespaces are tried in order. * * @param array $namespacesToTry diff --git a/src/Testing/MakesGraphQLRequests.php b/src/Testing/MakesGraphQLRequests.php index 66441363ea..6257e76424 100644 --- a/src/Testing/MakesGraphQLRequests.php +++ b/src/Testing/MakesGraphQLRequests.php @@ -26,7 +26,7 @@ trait MakesGraphQLRequests * Stores the result of the introspection query. * * On the first call to introspect() this property is set to - * cache the result, as introspection is quite expensive. + * cache the result, as introspection is expensive. * * @var \Illuminate\Testing\TestResponse<\Symfony\Component\HttpFoundation\Response> */ diff --git a/src/Testing/MakesGraphQLRequestsLumen.php b/src/Testing/MakesGraphQLRequestsLumen.php index 19320185d1..6c53ae28e0 100644 --- a/src/Testing/MakesGraphQLRequestsLumen.php +++ b/src/Testing/MakesGraphQLRequestsLumen.php @@ -28,7 +28,7 @@ trait MakesGraphQLRequestsLumen // @phpstan-ignore trait.unused (hard to set up * Stores the result of the introspection query. * * On the first call to introspect() this property is set to - * cache the result, as introspection is quite expensive. + * cache the result, as introspection is expensive. */ protected TestResponse $introspectionResult; diff --git a/src/WhereConditions/SQLOperator.php b/src/WhereConditions/SQLOperator.php index 55b5ac3b58..f6adc45a73 100644 --- a/src/WhereConditions/SQLOperator.php +++ b/src/WhereConditions/SQLOperator.php @@ -93,7 +93,7 @@ public function applyConditions(QueryBuilder|EloquentBuilder $builder, array $wh $args[] = $operator; } else { // We use the fact that the operators are named after Laravel's condition - // methods, so we can simply append the name, e.g. whereNull, whereNotBetween + // methods, so we can append the name, e.g. whereNull, whereNotBetween $method .= $operator; } diff --git a/src/lighthouse.php b/src/lighthouse.php index cd56d17277..ad4e55079b 100644 --- a/src/lighthouse.php +++ b/src/lighthouse.php @@ -81,8 +81,8 @@ |-------------------------------------------------------------------------- | | A large part of schema generation consists of parsing and AST manipulation. - | This operation is very expensive, so it is highly recommended enabling - | caching of the final schema to optimize performance of large schemas. + | This operation is expensive, so enable caching of the final schema + | to optimize performance of large schemas. | */ From c2216a7bbc14b03b83f0b37e99e847c8d112484c Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:15:16 +0100 Subject: [PATCH 13/24] Document that @trim and @convertEmptyStringsToNull apply to every field by default MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/directives.md | 22 +++++-------------- .../ConvertEmptyStringsToNullDirective.php | 2 ++ src/Schema/Directives/TrimDirective.php | 2 ++ 3 files changed, 10 insertions(+), 16 deletions(-) diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index b5ad11b9dc..e1289a36c1 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -1057,6 +1057,8 @@ Replaces incoming empty strings `""` with `null`. When used upon fields, empty strings for non-nullable inputs will pass unchanged. Only explicitly placing this on non-nullable inputs will force the conversion. + +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @convertEmptyStringsToNull on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION ``` @@ -1089,14 +1091,7 @@ type Mutation { } ``` -If you want this for all your fields, add this directive to your global field middleware in `lighthouse.php`: - -```php - 'field_middleware' => [ - \Nuwave\Lighthouse\Schema\Directives\ConvertEmptyStringsToNullDirective::class, - ... - ], -``` +The default `field_middleware` setting in `lighthouse.php` applies this directive to every field. ## @count @@ -3800,6 +3795,8 @@ Remove whitespace from the beginning and end of a given input. This can be used on: - a single argument or input field to sanitize that subtree - a field to trim all strings + +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @trim on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION ``` @@ -3820,14 +3817,7 @@ type Mutation { } ``` -If you want this for all your fields, add this directive to your global field middleware in `lighthouse.php`: - -```php - 'field_middleware' => [ - \Nuwave\Lighthouse\Schema\Directives\TrimDirective::class, - ... - ], -``` +The default `field_middleware` setting in `lighthouse.php` applies this directive to every field. ## @union diff --git a/src/Schema/Directives/ConvertEmptyStringsToNullDirective.php b/src/Schema/Directives/ConvertEmptyStringsToNullDirective.php index ea0b9dfd53..2003137702 100644 --- a/src/Schema/Directives/ConvertEmptyStringsToNullDirective.php +++ b/src/Schema/Directives/ConvertEmptyStringsToNullDirective.php @@ -20,6 +20,8 @@ public static function definition(): string When used upon fields, empty strings for non-nullable inputs will pass unchanged. Only explicitly placing this on non-nullable inputs will force the conversion. + +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @convertEmptyStringsToNull on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION GRAPHQL; diff --git a/src/Schema/Directives/TrimDirective.php b/src/Schema/Directives/TrimDirective.php index 807c791728..4b72a50322 100644 --- a/src/Schema/Directives/TrimDirective.php +++ b/src/Schema/Directives/TrimDirective.php @@ -20,6 +20,8 @@ public static function definition(): string This can be used on: - a single argument or input field to sanitize that subtree - a field to trim all strings + +Lighthouse applies this to every field by default, through the `field_middleware` setting in `lighthouse.php`. """ directive @trim on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION GRAPHQL; From c9a1bd393960fe589c363f96a726a98a7f4d2fc5 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:31:39 +0100 Subject: [PATCH 14/24] Put one sentence per line in Markdown MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- .github/PULL_REQUEST_TEMPLATE.md | 4 +- CONTRIBUTING.md | 4 +- UPGRADE.md | 11 ++-- docs/master/api-reference/directives.md | 60 +++++++------------ docs/master/api-reference/resolvers.md | 10 ++-- .../custom-directives/getting-started.md | 3 +- .../input-value-directives.md | 6 +- docs/master/digging-deeper/feature-toggles.md | 3 +- docs/master/digging-deeper/file-uploads.md | 3 +- docs/master/eloquent/relationships.md | 4 +- docs/master/performance/caching.md | 3 +- docs/master/security/authentication.md | 4 +- docs/master/subscriptions/getting-started.md | 9 +-- docs/master/the-basics/fields.md | 3 +- 14 files changed, 49 insertions(+), 78 deletions(-) diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md index eca48c266a..4de9d38037 100644 --- a/.github/PULL_REQUEST_TEMPLATE.md +++ b/.github/PULL_REQUEST_TEMPLATE.md @@ -15,7 +15,5 @@ If so, describe the necessary changes in UPGRADE.md. --> ## Changelog diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 3773eec710..a4a7867acc 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -26,9 +26,9 @@ Before you release a new version, make sure to familiarize yourself with: To create a new release, follow these steps: 1. Copy the `## Changelog` sections of the pull requests merged since the last release into [`CHANGELOG.md`](CHANGELOG.md), appending each pull request URL. -Add missing entries if needed. + Add missing entries if needed. 2. Based on those entries and the previous version, define the next version number. -Add it to [`CHANGELOG.md`](CHANGELOG.md). + Add it to [`CHANGELOG.md`](CHANGELOG.md). 3. [Draft a new release](https://github.com/nuwave/lighthouse/releases/new) 4. Add the version number as both tag and title 5. Add the changelog entries as the description diff --git a/UPGRADE.md b/UPGRADE.md index d939a8227d..7cc056d937 100644 --- a/UPGRADE.md +++ b/UPGRADE.md @@ -14,9 +14,9 @@ Compare your `lighthouse.php` against the latest [default configuration](src/lig Methods you need to explicitly call to set up test traits were removed in favor of automatic setup. - Remove calls to `Nuwave\Lighthouse\Testing\RefreshesSchemaCache::bootRefreshesSchemaCache()`. -This only works when your test class uses the trait `Nuwave\Lighthouse\Testing\MakesGraphQLRequests`. + This only works when your test class uses the trait `Nuwave\Lighthouse\Testing\MakesGraphQLRequests`. - Replace calls to `Nuwave\Lighthouse\Testing\MakesGraphQLRequests::setUpSubscriptionEnvironment()` with ` use Nuwave\Lighthouse\Testing\TestsSubscriptions`. -This only works when your test class extends `Illuminate\Foundation\Testing\TestCase`. + This only works when your test class extends `Illuminate\Foundation\Testing\TestCase`. ### `EnsureXHR` is enabled in the default configuration @@ -402,8 +402,7 @@ The recommended process for finding breaking changes is: 1. Print your schema before upgrading: `php artisan lighthouse:print-schema > old.graphql` 1. Upgrade, then re-print your schema: `php artisan lighthouse:print-schema > new.graphql` -1. Use [graphql-inspector](https://github.com/kamilkisiela/graphql-inspector) to compare your -changes: `graphql-inspector diff old.graphql new.graphql` +1. Use [graphql-inspector](https://github.com/kamilkisiela/graphql-inspector) to compare your changes: `graphql-inspector diff old.graphql new.graphql` ### Rename `resolve` to `__invoke` @@ -590,10 +589,10 @@ use Nuwave\Lighthouse\Support\Contracts\DefinedDirective; The application of directives that implement the `ArgDirective` interface is split into three distinct phases: - Sanitize: Clean the input, e.g. trim whitespace. -Directives can hook into this phase by implementing `ArgSanitizerDirective`. + Directives can hook into this phase by implementing `ArgSanitizerDirective`. - Validate: Ensure the input conforms to the expectations, e.g. check a valid email is given - Transform: Change the input before processing it further, e.g. hashing passwords. -Directives can hook into this phase by implementing `ArgTransformerDirective` + Directives can hook into this phase by implementing `ArgTransformerDirective` ### Replace custom validation directives with validator classes diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index e1289a36c1..ae4016b356 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -679,8 +679,7 @@ scalar BuilderValue You must point to a `method` that receives the builder instance. That method can apply additional constraints to the query. -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). When used on an argument, the method is only called when the argument is specified (may be `null`). @@ -2030,8 +2029,7 @@ directive @in( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -2083,8 +2081,7 @@ type Mutation { } ``` -If you need to inject a value into every element of a list, such as a nested `create` mutation -for a `HasMany` relation, use an asterisk `*` as a wildcard path segment. +If you need to inject a value into every element of a list, such as a nested `create` mutation for a `HasMany` relation, use an asterisk `*` as a wildcard path segment. ```graphql type Mutation { @@ -2233,8 +2230,7 @@ directive @like( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ## @limit @@ -2661,8 +2657,7 @@ directive @neq( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -2796,8 +2791,7 @@ directive @notIn( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -2888,8 +2882,7 @@ input OrderByRelation { } ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). See [ordering](../digging-deeper/ordering.md). @@ -2989,8 +2982,7 @@ type Query { } ``` -> When you want to paginate a relationship, use the to-many relationship -> directives such as [@hasMany](directives.md#hasmany) instead. +> When you want to paginate a relationship, use the to-many relationship directives such as [@hasMany](directives.md#hasmany) instead. The schema definition is automatically transformed to this: @@ -3113,8 +3105,7 @@ But means that the response does not hold information about the total number of If you wish to use the `simplePaginate` method, set the `type` to `SIMPLE`. -> The `SIMPLE` paginator does not have the attributes -> `lastPage` and `total`. +> The `SIMPLE` paginator does not have the attributes `lastPage` and `total`. > > If you need those fields, you should use the default `PAGINATOR`. @@ -3242,8 +3233,7 @@ type Query { Your method receives the typical resolver arguments. It must return an instance of `Illuminate\Database\Query\Builder`. -> If you want to query a model and possibly its relations through nested fields, -> make sure to return an Eloquent builder, e.g. `Post::query()`. +> If you want to query a model and possibly its relations through nested fields, make sure to return an Eloquent builder, e.g. `Post::query()`. ```php namespace App\Models; @@ -3527,8 +3517,7 @@ directive @scope( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -3772,8 +3761,7 @@ Allows to filter if trashed elements should be fetched. directive @trashed on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). The most convenient way to use this directive is through [@softDeletes](#softdeletes). @@ -4173,8 +4161,7 @@ Any constant literal value: https://graphql.github.io/graphql-spec/draft/#sec-In scalar WhereValue ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). You can specify simple operators: @@ -4245,8 +4232,7 @@ directive @whereAuth( ) on FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). The following query returns all posts that belong to the currently authenticated user. @@ -4275,8 +4261,7 @@ directive @whereBetween( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). This example defines an `input` to filter that a value is between two dates. @@ -4318,8 +4303,7 @@ directive @whereJsonContains( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -4386,8 +4370,7 @@ directive @whereNotBetween( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -4424,8 +4407,7 @@ directive @whereNotNull( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -4455,8 +4437,7 @@ directive @whereNull( ) repeatable on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION | FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```graphql @@ -4546,8 +4527,7 @@ directive @withoutGlobalScopes( ) on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -> This directive only works when the field resolver passes its builder through -> `$resolveInfo->enhanceBuilder()`. +> This directive only works when the field resolver passes its builder through `$resolveInfo->enhanceBuilder()`. > Built-in field resolver directives that query the database do this, such as [@all](#all) or [@hasMany](#hasmany). ```php diff --git a/docs/master/api-reference/resolvers.md b/docs/master/api-reference/resolvers.md index 66bc3862bb..6c2f88dc43 100644 --- a/docs/master/api-reference/resolvers.md +++ b/docs/master/api-reference/resolvers.md @@ -17,15 +17,13 @@ function (mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolv For example, for a field call like `user(name: "Bob")` it would be `['name' => 'Bob']` 3. `GraphQLContext $context`: Arbitrary data that is shared between all fields of a single query. Lighthouse passes in an instance of `Nuwave\Lighthouse\Schema\Context` by default. -4. `ResolveInfo $resolveInfo`: Information about the query itself, - such as the execution state, the field name, path to the field from the root, and more. +4. `ResolveInfo $resolveInfo`: Information about the query itself, such as the execution state, the field name, path to the field from the root, and more. The return value of this must fit the return type defined for the corresponding field from the schema. ## Root resolvers -Root resolvers are classes with an `__invoke` method that sit directly in the configured -`lighthouse.namespaces.queries` or `lighthouse.namespaces.mutations` namespaces. +Root resolvers are classes with an `__invoke` method that sit directly in the configured `lighthouse.namespaces.queries` or `lighthouse.namespaces.mutations` namespaces. Lighthouse calls them with positional arguments `($root, $args, $context, $resolveInfo)` where `$root` is always `null` for root types. Omitting `$root` causes Lighthouse's positional `null` to bind to `$args`, producing TypeErrors at runtime. @@ -61,8 +59,8 @@ You can define your own complexity function with the [@complexity](../api-refere function (int $childrenComplexity, array $args): int ``` -1. `$childrenComplexity`: The complexity of the children of the field. In case you expect to return - multiple children, it can be useful to do some maths on this. +1. `$childrenComplexity`: The complexity of the children of the field. + In case you expect to return multiple children, it can be useful to do some maths on this. 2. `array $args`: The arguments that were passed into the field. For example, for a field call like `user(name: "Bob")` it would be `['name' => 'Bob']` diff --git a/docs/master/custom-directives/getting-started.md b/docs/master/custom-directives/getting-started.md index 72cdccd456..d1210996df 100644 --- a/docs/master/custom-directives/getting-started.md +++ b/docs/master/custom-directives/getting-started.md @@ -97,8 +97,7 @@ Now that we defined and implemented the directive, how can Lighthouse find it? When Lighthouse encounters a directive within the schema, it starts looking for a matching class in the following order: 1. User-defined namespaces as configured in `config/lighthouse.php`, defaults to `App\GraphQL\Directives` -1. The [RegisterDirectiveNamespaces](../api-reference/events.md#registerdirectivenamespaces) event is dispatched - to gather namespaces defined by plugins, extensions or other listeners +1. The [RegisterDirectiveNamespaces](../api-reference/events.md#registerdirectivenamespaces) event is dispatched to gather namespaces defined by plugins, extensions or other listeners 1. Lighthouse's built-in directive namespace This means that our directive is already registered, because it is defined in the default namespace. diff --git a/docs/master/custom-directives/input-value-directives.md b/docs/master/custom-directives/input-value-directives.md index 996bd9b80c..f837fb9eb0 100644 --- a/docs/master/custom-directives/input-value-directives.md +++ b/docs/master/custom-directives/input-value-directives.md @@ -4,10 +4,8 @@ Some directives can be applied to field arguments or input fields (any [InputVal As arguments may be contained within a list in the schema definition, you must specify what your directive should apply to in addition to its function. -- If it applies to the individual items within the list, - implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirective`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirective.php) interface. -- Else, if it should apply to the whole list, - implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirectiveForArray`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirectiveForArray.php) interface. +- If it applies to the individual items within the list, implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirective`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirective.php) interface. +- Else, if it should apply to the whole list, implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirectiveForArray`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirectiveForArray.php) interface. You must implement exactly one of those two interfaces in order for an argument directive to work. diff --git a/docs/master/digging-deeper/feature-toggles.md b/docs/master/digging-deeper/feature-toggles.md index 578ea8bdbe..b863f5cfba 100644 --- a/docs/master/digging-deeper/feature-toggles.md +++ b/docs/master/digging-deeper/feature-toggles.md @@ -7,7 +7,8 @@ Lighthouse allows you to conditionally show or hide elements (fields, types, arg The directives [@show](../api-reference/directives.md#show) and [@hide](../api-reference/directives.md#hide) work in a similar way. Are logical opposites of each other. -For example, you might want to limit an experimental new field to test environments. [@show](../api-reference/directives.md#show) is most suitable for this: +For example, you might want to limit an experimental new field to test environments. +[@show](../api-reference/directives.md#show) is most suitable for this: ```graphql type Query { diff --git a/docs/master/digging-deeper/file-uploads.md b/docs/master/digging-deeper/file-uploads.md index b881ca9d81..c941f325d9 100644 --- a/docs/master/digging-deeper/file-uploads.md +++ b/docs/master/digging-deeper/file-uploads.md @@ -55,8 +55,7 @@ final class Upload In order to upload a file, you must send a `multipart/form-data` request. Use any of the [available client implementations](https://github.com/jaydenseric/graphql-multipart-request-spec#client) or look at the [specification examples](https://github.com/jaydenseric/graphql-multipart-request-spec#multipart-form-field-structure) to roll your own. -> If you are using [the EnsureXHR middleware to protect against CSRF](../security/csrf.md), -> add the header `X-Requested-With: XMLHttpRequest` to your request. +> If you are using [the EnsureXHR middleware to protect against CSRF](../security/csrf.md), add the header `X-Requested-With: XMLHttpRequest` to your request. To test the example above, prepare a file you can upload. diff --git a/docs/master/eloquent/relationships.md b/docs/master/eloquent/relationships.md index 30c912abfb..6e69475b68 100644 --- a/docs/master/eloquent/relationships.md +++ b/docs/master/eloquent/relationships.md @@ -47,8 +47,8 @@ This leads to a common performance pitfall that comes with the nested nature of When you decorate your relationship fields with Lighthouse's built-in relationship directives, queries are automatically combined through a technique called _batch loading_. That means you get fewer database requests and better performance without doing much work. -> Batch loading might not provide ideal performance for all use cases. You can turn -> it off by setting the config option `batchload_relations` to `false`. +> Batch loading might not provide ideal performance for all use cases. +> You can turn it off by setting the config option `batchload_relations` to `false`. ## One To One diff --git a/docs/master/performance/caching.md b/docs/master/performance/caching.md index f7209520b4..831afe6f58 100644 --- a/docs/master/performance/caching.md +++ b/docs/master/performance/caching.md @@ -124,7 +124,8 @@ Field-level settings override type-level settings. The final header settings are calculated based on these rules: -- `max-age` equals the lowest `maxAge` among all fields. If that value is 0, `no-cache` is used instead +- `max-age` equals the lowest `maxAge` among all fields. + If that value is 0, `no-cache` is used instead - visibility is `public` unless the scope of a queried field is `PRIVATE` The following defaults apply: diff --git a/docs/master/security/authentication.md b/docs/master/security/authentication.md index 084c837980..9d37c69fc9 100644 --- a/docs/master/security/authentication.md +++ b/docs/master/security/authentication.md @@ -121,7 +121,9 @@ It returns `null` if the request is not authenticated. ## Stateful Authentication Example -You can create or destroy a session with mutations instead of separate API endpoints (`/login`, `/logout`). **This only works when Lighthouse's guard uses a session driver.** Laravel's token based authentication does not allow logging in or out on the server side. +You can create or destroy a session with mutations instead of separate API endpoints (`/login`, `/logout`). +**This only works when Lighthouse's guard uses a session driver.** +Laravel's token based authentication does not allow logging in or out on the server side. The implementation in the docs is only an example and may have to be adapted to your specific use case. diff --git a/docs/master/subscriptions/getting-started.md b/docs/master/subscriptions/getting-started.md index 4e26b0f3d3..b41c8c2814 100644 --- a/docs/master/subscriptions/getting-started.md +++ b/docs/master/subscriptions/getting-started.md @@ -27,16 +27,14 @@ When using subscriptions with [Laravel Octane](https://laravel.com/docs/octane), Lighthouse returns the subscription channel as part of the response under `extensions`. If `subscriptions.exclude_empty` in `lighthouse.php` is set to `true`, API responses without a subscription channel will not contain `lighthouse_subscriptions` in `extensions`. -This optimizes performance by sending less data, -but clients must anticipate this appropriately. +This optimizes performance by sending less data, but clients must anticipate this appropriately. ## Expiring Subscriptions Subscriptions do not expire by themselves. Unless you delete a subscription, it will continue to broadcast events after the client has disconnected. -The easiest way to expire subscriptions automatically is to use the env `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to set an expiration time in seconds (e.g. -`LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` to expire in one hour). +The easiest way to expire subscriptions automatically is to use the env `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to set an expiration time in seconds (e.g. `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` to expire in one hour). ## Encrypted Subscriptions @@ -60,8 +58,7 @@ More details on how to enable encryption are defined in the [Pusher documentatio ### Pusher Expiration Webhook If you are using the Pusher driver, you can use a [`channel existence`](https://pusher.com/docs/channels/server_api/webhooks/#channel-existence-events) webhook to mitigate this problem. -When a Pusher channel is vacated (i.e. there are no subscribers), it will trigger the webhook, -which will instruct Lighthouse to delete the subscription. +When a Pusher channel is vacated (i.e. there are no subscribers), it will trigger the webhook, which will instruct Lighthouse to delete the subscription. The webhook URL will typically be: diff --git a/docs/master/the-basics/fields.md b/docs/master/the-basics/fields.md index 01b90b8f27..0b56bf1d9c 100644 --- a/docs/master/the-basics/fields.md +++ b/docs/master/the-basics/fields.md @@ -198,8 +198,7 @@ function resolveUserAttribute(User $user, array $args, GraphQLContext $context, ``` Fortunately, the underlying GraphQL implementation already provides [a sensible default resolver](https://webonyx.github.io/graphql-php/data-fetching/#default-field-resolver). -It works well with the data you would typically return from a root resolver, e.g. -`Eloquent` models or associative arrays. +It works well with the data you would typically return from a root resolver, e.g. `Eloquent` models or associative arrays. This means that in most cases, you will only have to provide resolvers for the root fields and make sure they return data in the proper shape. From f2cb72951b84f02ab65f73cf474df68d1fc10265 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:33:23 +0100 Subject: [PATCH 15/24] Put one sentence per line in PHP comments MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- src/Auth/BaseCanDirective.php | 6 +-- src/Auth/CanDirective.php | 3 +- src/Bind/BindDirective.php | 5 +- src/Bind/ModelBinding.php | 5 +- src/Cache/CacheDirective.php | 8 ++- src/Console/LighthouseGeneratorCommand.php | 6 +-- src/Defer/Defer.php | 3 +- src/Events/BuildExtensionsResponse.php | 3 +- src/Execution/Arguments/ArgPartitioner.php | 9 ++-- src/Execution/Arguments/ArgumentSet.php | 14 ++--- .../Arguments/ArgumentSetFactory.php | 3 +- src/Execution/Arguments/NestedBelongsTo.php | 5 +- src/Execution/Arguments/NestedManyToMany.php | 3 +- src/Execution/Arguments/ResolveNested.php | 3 +- src/Execution/Arguments/SaveModel.php | 7 +-- .../ModelsLoader/PaginatedModelsLoader.php | 3 +- src/Execution/Utils/FieldPath.php | 9 ++-- src/Execution/Utils/Subscription.php | 3 +- src/Federation/ASTManipulator.php | 3 +- src/GlobalId/NodeRegistry.php | 3 +- src/GraphQL.php | 3 +- src/Pagination/ConnectionField.php | 3 +- src/Pagination/PaginationArgs.php | 3 +- src/Schema/AST/ASTBuilder.php | 14 ++--- src/Schema/AST/ASTHelper.php | 3 +- src/Schema/AST/DocumentAST.php | 13 ++--- src/Schema/Directives/DeleteDirective.php | 6 +-- src/Schema/Directives/DropArgsDirective.php | 3 +- src/Schema/Directives/NamespaceDirective.php | 3 +- src/Schema/Directives/RelationDirective.php | 3 +- src/Schema/Directives/RenameArgsDirective.php | 3 +- src/Schema/ResolverProvider.php | 6 +-- src/Schema/SchemaBuilder.php | 7 +-- src/Schema/TypeRegistry.php | 7 +-- src/Schema/Values/FieldValue.php | 4 +- .../Storage/RedisStorageManager.php | 6 +-- .../SubscriptionResolverProvider.php | 3 +- src/Support/Contracts/ArgResolver.php | 3 +- .../Contracts/PreSaveArgumentsAware.php | 6 +-- .../ProvidesCacheableValidationRules.php | 3 +- .../Contracts/ProvidesValidationRules.php | 3 +- .../Contracts/SaveAwareArgResolver.php | 16 +++--- src/Support/DriverManager.php | 4 +- src/Testing/MakesGraphQLRequests.php | 6 +-- src/Testing/MakesGraphQLRequestsLumen.php | 6 +-- src/Testing/RefreshesSchemaCache.php | 4 +- src/Validation/BaseRulesDirective.php | 6 +-- src/Validation/RulesGatherer.php | 5 +- src/WhereConditions/SQLOperator.php | 6 +-- .../WhereHasConditionsDirective.php | 3 +- src/lighthouse.php | 54 ++++++++----------- tests/Integration/LifecycleEventsTest.php | 3 +- .../Validation/RulesDirectiveTest.php | 3 +- .../Validation/RulesForArrayDirectiveTest.php | 3 +- tests/TestCase.php | 3 +- .../Execution/Arguments/ArgumentSetTest.php | 3 +- .../RootResolverSignatureRector/bootstrap.php | 3 +- 57 files changed, 117 insertions(+), 220 deletions(-) diff --git a/src/Auth/BaseCanDirective.php b/src/Auth/BaseCanDirective.php index ffdc675482..d709773a63 100644 --- a/src/Auth/BaseCanDirective.php +++ b/src/Auth/BaseCanDirective.php @@ -103,8 +103,7 @@ public function handleField(FieldValue $fieldValue): void try { $resolved = $this->authorizeRequest($root, $args, $context, $resolveInfo, $trackedResolver, $authorizeModel); if ($hasResolved) { - // A batch loaded relation resolves to a promise, so authorization runs when - // that promise is fulfilled, which is after this try-catch has been left. + // A batch loaded relation resolves to a promise, so authorization runs when that promise is fulfilled, which is after this try-catch has been left. // Handle its failure the same way to keep `action` meaningful either way. return $resolved instanceof SyncPromise ? $resolved->then(null, fn (\Throwable $throwable): mixed => $this->handleAuthorizationFailure($throwable)) @@ -158,8 +157,7 @@ abstract protected function authorizeRequest(mixed $root, array $args, GraphQLCo */ protected function authorizeModel(Gate $gate, string|array $ability, mixed $model, array $arguments): void { - // The signature of the second argument `$arguments` of `Gate::check` - // should be [modelClassName, additionalArg, additionalArg...] + // The signature of the second argument `$arguments` of `Gate::check` should be [modelClassName, additionalArg, additionalArg...] array_unshift($arguments, $model); Utils::applyEach( diff --git a/src/Auth/CanDirective.php b/src/Auth/CanDirective.php index d73cb50fbf..b698ec86e8 100644 --- a/src/Auth/CanDirective.php +++ b/src/Auth/CanDirective.php @@ -245,8 +245,7 @@ public static function missingKeyToFindModel(string $find): Error */ protected function authorize(Gate $gate, string|array $ability, string|Model|null $model, array $arguments): void { - // The signature of the second argument `$arguments` of `Gate::check` - // should be [modelClassName, additionalArg, additionalArg...] + // The signature of the second argument `$arguments` of `Gate::check` should be [modelClassName, additionalArg, additionalArg...] array_unshift($arguments, $model); Utils::applyEach( diff --git a/src/Bind/BindDirective.php b/src/Bind/BindDirective.php index 3e25f62cd2..31b6a04bb4 100644 --- a/src/Bind/BindDirective.php +++ b/src/Bind/BindDirective.php @@ -117,9 +117,8 @@ public function attribute(): ?string public function transform(mixed $argumentValue): mixed { - // When validating required bindings, the \Nuwave\Lighthouse\Bind\Validation\BindingExists validation rule - // should call transform() before it is called by the directive resolver. To avoid resolving the bindings - // multiple times, we should remember the resolved binding and reuse it every time transform() is called. + // When validating required bindings, the \Nuwave\Lighthouse\Bind\Validation\BindingExists validation rule should call transform() before it is called by the directive resolver. + // To avoid resolving the bindings multiple times, we should remember the resolved binding and reuse it every time transform() is called. if (! $this->binding instanceof PendingBinding) { return $this->binding; } diff --git a/src/Bind/ModelBinding.php b/src/Bind/ModelBinding.php index af6adfb58f..d2387ed6ee 100644 --- a/src/Bind/ModelBinding.php +++ b/src/Bind/ModelBinding.php @@ -33,10 +33,7 @@ public function __invoke(int|string|array $value, BindDefinition $definition): M /** @param \Illuminate\Database\Eloquent\Collection $results */ protected function modelInstance(EloquentCollection $results): ?Model { - // While "too few records" errors are handled as (client-safe) validation errors by applying - // the `BindingExists` rule on the BindDirective depending on whether the binding is required, - // "too many records" should be considered as (non-client-safe) configuration errors as it - // means the binding was not resolved using a unique identifier. + // While "too few records" errors are handled as (client-safe) validation errors by applying the `BindingExists` rule on the BindDirective depending on whether the binding is required, "too many records" should be considered as (non-client-safe) configuration errors as it means the binding was not resolved using a unique identifier. if ($results->count() > 1) { throw new MultipleRecordsFoundException($results->count()); } diff --git a/src/Cache/CacheDirective.php b/src/Cache/CacheDirective.php index c95386b7dc..76e61fbff8 100644 --- a/src/Cache/CacheDirective.php +++ b/src/Cache/CacheDirective.php @@ -86,8 +86,7 @@ public function handleField(FieldValue $fieldValue): void // In Laravel cache, null is considered a non-existent value, see https://laravel.com/docs/9.x/cache#checking-for-item-existence: // > The `has` method [...] will also return false if the item exists but its value is null. // - // If caching `null` value becomes something worthwhile, one possible way to achieve it is to - // encapsulate the `$result` at writing time : + // If caching `null` value becomes something worthwhile, one possible way to achieve it is to encapsulate the `$result` at writing time : // // $storeInCache = static function ($result) use ($cacheKey, $maxAge, $cache): void { // $value = ['rawValue' => $result]; @@ -102,9 +101,8 @@ public function handleField(FieldValue $fieldValue): void // return $value['rawValue']; // } // - // Such a change would introduce some potential BC, if for instance cached value was already containing - // an object with a `rawValue` key prior the implementation change. A possible workaround is to choose a - // less collision-probable key instead of `rawValue` (e.g. "lighthouse:rawValue"). + // Such a change would introduce some potential BC, if for instance cached value was already containing an object with a `rawValue` key prior the implementation change. + // A possible workaround is to choose a less collision-probable key instead of `rawValue` (e.g. "lighthouse:rawValue"). $resolved = $resolver($root, $args, $context, $resolveInfo); diff --git a/src/Console/LighthouseGeneratorCommand.php b/src/Console/LighthouseGeneratorCommand.php index b4b077fa00..f4d16a2f79 100644 --- a/src/Console/LighthouseGeneratorCommand.php +++ b/src/Console/LighthouseGeneratorCommand.php @@ -55,8 +55,7 @@ public static function commonNamespace(array $namespaces): string // Save the first namespace $preferredNamespaceFallback = reset($namespaces); - // If the strings are sorted, any prefix common to all strings - // will be common to the sorted first and last strings. + // If the strings are sorted, any prefix common to all strings will be common to the sorted first and last strings. // All the strings in the middle can be ignored. sort($namespaces); @@ -78,8 +77,7 @@ public static function commonNamespace(array $namespaces): string $matching[] = $part; } - // We could not determine a common part of the configured namespaces, - // so we assume the user will prefer the first one in the list. + // We could not determine a common part of the configured namespaces, so we assume the user will prefer the first one in the list. if ($matching === []) { return $preferredNamespaceFallback; } diff --git a/src/Defer/Defer.php b/src/Defer/Defer.php index 5055fff566..0a8864d313 100644 --- a/src/Defer/Defer.php +++ b/src/Defer/Defer.php @@ -154,8 +154,7 @@ function (): void { // We've hit the max execution time or max nested levels of deferred fields. $this->shouldDeferFurther = false; - // We process remaining deferred fields, but are no longer allowing additional - // fields to be deferred. + // We process remaining deferred fields, but are no longer allowing additional fields to be deferred. if ($this->hasRemainingDeferred()) { $this->executeDeferred(); } diff --git a/src/Events/BuildExtensionsResponse.php b/src/Events/BuildExtensionsResponse.php index 2c1a9216f8..d59d1b6c66 100644 --- a/src/Events/BuildExtensionsResponse.php +++ b/src/Events/BuildExtensionsResponse.php @@ -7,8 +7,7 @@ /** * Fires after a query was resolved. * - * Listeners may return a @see \Nuwave\Lighthouse\Execution\ExtensionsResponse - * to include in the response. + * Listeners may return a @see \Nuwave\Lighthouse\Execution\ExtensionsResponse to include in the response. */ class BuildExtensionsResponse { diff --git a/src/Execution/Arguments/ArgPartitioner.php b/src/Execution/Arguments/ArgPartitioner.php index 498d85c50d..5874d10de2 100644 --- a/src/Execution/Arguments/ArgPartitioner.php +++ b/src/Execution/Arguments/ArgPartitioner.php @@ -20,8 +20,7 @@ class ArgPartitioner /** * Partition the arguments into nested and regular. * - * SaveAwareArgResolvers where runBeforeSave() returns true stay in the regular set - * so they reach SaveModel for execution before $model->save(). + * SaveAwareArgResolvers where runBeforeSave() returns true stay in the regular set so they reach SaveModel for execution before $model->save(). * * @return array{ * 0: \Nuwave\Lighthouse\Execution\Arguments\ArgumentSet, @@ -184,14 +183,12 @@ public static function methodReturnsRelation( } /** - * Recursively collect the pre-save resolvers within @nest arguments, - * so they can run before $root->save() instead of after it. + * Recursively collect the pre-save resolvers within @nest arguments, so they can run before $root->save() instead of after it. * * The result is an ordered list rather than a name-keyed set: * field names are unique per input type, not across a whole input tree. * - * Leaves the given arguments untouched, as they may be shared with cached - * or spread ArgumentSets that the caller still owns. + * Leaves the given arguments untouched, as they may be shared with cached or spread ArgumentSets that the caller still owns. * * @return list<\Nuwave\Lighthouse\Execution\Arguments\Argument> */ diff --git a/src/Execution/Arguments/ArgumentSet.php b/src/Execution/Arguments/ArgumentSet.php index 099bd669e5..35f25b5bb9 100644 --- a/src/Execution/Arguments/ArgumentSet.php +++ b/src/Execution/Arguments/ArgumentSet.php @@ -69,9 +69,7 @@ public function exists(string $key): bool /** * Add a value at the dot-separated path. * - * Works like @see \Illuminate\Support\Arr::add(), but a path segment - * of `*` injects the value into every element of the list found at that - * position instead of a single key. + * Works like @see \Illuminate\Support\Arr::add(), but a path segment of `*` injects the value into every element of the list found at that position instead of a single key. */ public function addValue(string $path, mixed $value): self { @@ -102,16 +100,14 @@ private function addValueAtKeys(array $keys, mixed $value): void $throughWildcard = $keys[0] === '*'; - // The branch leading up to a `*` might not have been given by the client - // at all, e.g. an optional nested input that was omitted. In that case, - // there is nothing to inject into, so we do nothing. + // The branch leading up to a `*` might not have been given by the client at all, e.g. an optional nested input that was omitted. + // In that case, there is nothing to inject into, so we do nothing. if ($throughWildcard && ! isset($this->arguments[$key])) { return; } - // If the key doesn't exist at this depth, we will create an empty ArgumentSet - // to hold the next value, allowing us to create the ArgumentSet to hold a final - // value at the correct depth. Then we'll keep digging into the ArgumentSet. + // If the key doesn't exist at this depth, we will create an empty ArgumentSet to hold the next value, allowing us to create the ArgumentSet to hold a final value at the correct depth. + // Then we'll keep digging into the ArgumentSet. if (! isset($this->arguments[$key])) { $argument = new Argument(); $argument->value = new self(); diff --git a/src/Execution/Arguments/ArgumentSetFactory.php b/src/Execution/Arguments/ArgumentSetFactory.php index 695b5f17cf..a7a17f2243 100644 --- a/src/Execution/Arguments/ArgumentSetFactory.php +++ b/src/Execution/Arguments/ArgumentSetFactory.php @@ -107,8 +107,7 @@ protected function wrapWithType(mixed $valueOrValues, ListType|NamedType $type) return null; } - // We have to do this conversion as we are resolving a client query - // because the incoming arguments put a bound on recursion depth + // We have to do this conversion as we are resolving a client query because the incoming arguments put a bound on recursion depth if ($type instanceof ListType) { $typeInList = $type->type; diff --git a/src/Execution/Arguments/NestedBelongsTo.php b/src/Execution/Arguments/NestedBelongsTo.php index 7a446f0840..71e17402fb 100644 --- a/src/Execution/Arguments/NestedBelongsTo.php +++ b/src/Execution/Arguments/NestedBelongsTo.php @@ -56,9 +56,8 @@ public function __invoke($model, $args): void public static function disconnectOrDelete(BelongsTo $relation, ArgumentSet $args): void { // We proceed with disconnecting/deleting only if the given $values is truthy. - // There is no other information to be passed when issuing those operations, - // but GraphQL forces us to pass some value. It would be unintuitive for - // the end user if the given value had no effect on the execution. + // There is no other information to be passed when issuing those operations, but GraphQL forces us to pass some value. + // It would be unintuitive for the end user if the given value had no effect on the execution. if ( $args->has('disconnect') && $args->arguments['disconnect']->value diff --git a/src/Execution/Arguments/NestedManyToMany.php b/src/Execution/Arguments/NestedManyToMany.php index 008b733cdb..dbaa6cb169 100644 --- a/src/Execution/Arguments/NestedManyToMany.php +++ b/src/Execution/Arguments/NestedManyToMany.php @@ -93,8 +93,7 @@ protected function generateRelationArray(Argument $args): array return []; } - // Since GraphQL inputs are monomorphic, we can look at the first - // given value for an argument and deduce the type of all values. + // Since GraphQL inputs are monomorphic, we can look at the first given value for an argument and deduce the type of all values. $exemplaryValue = $values[0]; // We assume that the values contain pivot information diff --git a/src/Execution/Arguments/ResolveNested.php b/src/Execution/Arguments/ResolveNested.php index fbcf86abfb..83c675bf52 100644 --- a/src/Execution/Arguments/ResolveNested.php +++ b/src/Execution/Arguments/ResolveNested.php @@ -77,8 +77,7 @@ protected function resolveNestedArguments(mixed $root, ArgumentSet $nestedArgs, assert($value instanceof ArgumentSet, 'NestDirective validates that @nest is used on non-list input object types.'); // Partitioning attaches the resolvers of the children, including implicitly detected relations. - // Its classification is irrelevant here: there is no saver to hand regular arguments to, - // and children the saver did not run must still resolve. + // Its classification is irrelevant here: there is no saver to hand regular arguments to, and children the saver did not run must still resolve. ($this->argPartitioner)($value, $root); $this->resolveNestedArguments($root, $value, $alreadyRun); continue; diff --git a/src/Execution/Arguments/SaveModel.php b/src/Execution/Arguments/SaveModel.php index 59328bb7de..2ee14b3ec9 100644 --- a/src/Execution/Arguments/SaveModel.php +++ b/src/Execution/Arguments/SaveModel.php @@ -84,8 +84,7 @@ public function __invoke($model, $args): Model } if ($this->parentRelation instanceof HasOneOrMany) { - // If we are already resolving a nested create, we might - // already have an instance of the parent relation available. + // If we are already resolving a nested create, we might already have an instance of the parent relation available. // In that case, use it to set the current model as a child. $this->parentRelation->save($model); @@ -97,9 +96,7 @@ public function __invoke($model, $args): Model if ($this->parentRelation instanceof BelongsTo) { $childModel = $this->parentRelation->associate($model); - // If the child Model does not exist (still to be saved), - // a save could break any pending belongsTo relations that still - // need to be created and associated with it. + // If the child Model does not exist (still to be saved), a save could break any pending belongsTo relations that still need to be created and associated with it. if ($childModel->exists) { $childModel->save(); } diff --git a/src/Execution/ModelsLoader/PaginatedModelsLoader.php b/src/Execution/ModelsLoader/PaginatedModelsLoader.php index 46b04c44b1..dd1def6f8c 100644 --- a/src/Execution/ModelsLoader/PaginatedModelsLoader.php +++ b/src/Execution/ModelsLoader/PaginatedModelsLoader.php @@ -80,8 +80,7 @@ protected function loadRelatedModels(EloquentCollection $parents): EloquentColle $relatedModels = $mergedRelationQuery->get(); return $relatedModels->unique( - // Compare all attributes because there might not be a unique primary key - // or there could be differing pivot attributes. + // Compare all attributes because there might not be a unique primary key or there could be differing pivot attributes. static fn (Model $relatedModel): string => serialize($relatedModel->getRawOriginal()), ); } diff --git a/src/Execution/Utils/FieldPath.php b/src/Execution/Utils/FieldPath.php index 4ab8a9ea0d..d88566bf8a 100644 --- a/src/Execution/Utils/FieldPath.php +++ b/src/Execution/Utils/FieldPath.php @@ -14,15 +14,12 @@ public static function withoutLists(array $path): string $significantPathSegments = array_filter( $path, // Ignore numeric path entries, as those signify a list of fields. - // Combining the queries for lists is the purpose of the - // batch loader, so they must not be included. + // Combining the queries for lists is the purpose of the batch loader, so they must not be included. static fn (int|string $segment): bool => ! is_numeric($segment), ); - // Using . as the separator would combine relations in nested fields with - // higher up relations using dot notation, matching the field path. - // We might optimize this in the future to enable batching them anyway, - // but employ this solution for now, as it preserves correctness. + // Using . as the separator would combine relations in nested fields with higher up relations using dot notation, matching the field path. + // We might optimize this in the future to enable batching them anyway, but employ this solution for now, as it preserves correctness. return implode('|', $significantPathSegments); } } diff --git a/src/Execution/Utils/Subscription.php b/src/Execution/Utils/Subscription.php index 2830ee927a..cc981bb59b 100644 --- a/src/Execution/Utils/Subscription.php +++ b/src/Execution/Utils/Subscription.php @@ -13,8 +13,7 @@ class Subscription /** Broadcast subscription to client(s). */ public static function broadcast(string $subscriptionField, mixed $root, ?bool $shouldQueue = null): void { - // Ensure we have a schema and registered subscription fields - // in the event we are calling this method in code. + // Ensure we have a schema and registered subscription fields in the event we are calling this method in code. $schemaBuilder = Container::getInstance()->make(SchemaBuilder::class); $schemaBuilder->schema(); diff --git a/src/Federation/ASTManipulator.php b/src/Federation/ASTManipulator.php index 240e494c44..0c16c025a6 100644 --- a/src/Federation/ASTManipulator.php +++ b/src/Federation/ASTManipulator.php @@ -70,8 +70,7 @@ protected function addEntityUnion(DocumentAST &$documentAST): void protected function addRootFields(DocumentAST &$documentAST): void { - // In federation, it is fine for a schema to not have a user-defined root query type, - // since we add two federation related fields to it here. + // In federation, it is fine for a schema to not have a user-defined root query type, since we add two federation related fields to it here. $documentAST->types[RootType::QUERY] ??= Parser::objectTypeDefinition(/** @lang GraphQL */ 'type Query'); $queryType = $documentAST->types[RootType::QUERY]; diff --git a/src/GlobalId/NodeRegistry.php b/src/GlobalId/NodeRegistry.php index 477d51005e..89b5540a34 100644 --- a/src/GlobalId/NodeRegistry.php +++ b/src/GlobalId/NodeRegistry.php @@ -56,8 +56,7 @@ public function resolve(mixed $root, array $args, GraphQLContext $context, Resol { [$decodedType, $decodedId] = $args['id']; - // This check forces Lighthouse to eagerly load the type, which might not have - // happened if the client only references it indirectly through an interface. + // This check forces Lighthouse to eagerly load the type, which might not have happened if the client only references it indirectly through an interface. // Loading the type in turn causes the TypeMiddleware to run and thus register the type in the NodeRegistry. $this->typeRegistry->has($decodedType) ?: throw new Error("[{$decodedType}] is not a type and cannot be resolved."); diff --git a/src/GraphQL.php b/src/GraphQL.php index 6c5e7918af..0bad1a5abf 100644 --- a/src/GraphQL.php +++ b/src/GraphQL.php @@ -129,8 +129,7 @@ public function executeParsedQueryRaw( ?string $operationName = null, ?string $queryHash = null, ): ExecutionResult { - // Building the executable schema might take a while to do, - // so we do it before we fire the StartExecution event. + // Building the executable schema might take a while to do, so we do it before we fire the StartExecution event. // This allows tracking the time for batched queries independently. $schema = $this->schemaBuilder->schema(); diff --git a/src/Pagination/ConnectionField.php b/src/Pagination/ConnectionField.php index 0edafcdd37..cc46096aea 100644 --- a/src/Pagination/ConnectionField.php +++ b/src/Pagination/ConnectionField.php @@ -90,8 +90,7 @@ public function edgeResolver(Paginator $paginator, array $args, GraphQLContext $ break; default: - // All other fields on the return type are assumed to be part - // of the edge, so we try to locate them in the pivot attribute + // All other fields on the return type are assumed to be part of the edge, so we try to locate them in the pivot attribute if (isset($item->pivot->{$field->name})) { $data[$field->name] = $item->pivot->{$field->name}; } diff --git a/src/Pagination/PaginationArgs.php b/src/Pagination/PaginationArgs.php index c4a732d6f7..812a93cb4a 100644 --- a/src/Pagination/PaginationArgs.php +++ b/src/Pagination/PaginationArgs.php @@ -81,8 +81,7 @@ protected static function optimalPaginationType(PaginationType $proposedType, Re } // If the result may be used in a cache, we always want to retrieve and store the full pagination data. - // Even though the query that initially creates the cache may not need additional information such as - // the total counts, following queries may need them - and use the same cached value. + // Even though the query that initially creates the cache may not need additional information such as the total counts, following queries may need them - and use the same cached value. $hasCacheDirective = $resolveInfo->argumentSet ->directives ->contains(static fn (Directive $directive): bool => $directive instanceof CacheDirective); diff --git a/src/Schema/AST/ASTBuilder.php b/src/Schema/AST/ASTBuilder.php index 41d655a18b..9f55ae4ed5 100644 --- a/src/Schema/AST/ASTBuilder.php +++ b/src/Schema/AST/ASTBuilder.php @@ -62,8 +62,7 @@ public function build(): DocumentAST $schemaString = $this->schemaSourceProvider->getSchemaString(); // Allow registering listeners that inject additional schema definitions. - // This can be used by plugins to hook into the schema building process - // while still allowing the user to define their schema as usual. + // This can be used by plugins to hook into the schema building process while still allowing the user to define their schema as usual. $additionalSchemas = (array) $this->eventsDispatcher->dispatch( new BuildSchemaString($schemaString), ); @@ -82,9 +81,8 @@ public function build(): DocumentAST $this->applyArgManipulators(); $this->applyInputFieldManipulators(); - // Listeners may manipulate the DocumentAST that is passed by reference - // into the ManipulateAST event. This can be useful for extensions - // that want to programmatically change the schema. + // Listeners may manipulate the DocumentAST that is passed by reference into the ManipulateAST event. + // This can be useful for extensions that want to programmatically change the schema. $this->eventsDispatcher->dispatch( new ManipulateAST($this->documentAST), ); @@ -109,16 +107,14 @@ protected function applyTypeExtensionManipulators(): void { foreach ($this->documentAST->typeExtensions as $typeName => $typeExtensionsList) { foreach ($typeExtensionsList as $typeExtension) { - // Before we extend the types, we apply the manipulator directives - // that are defined on type extensions themselves + // Before we extend the types, we apply the manipulator directives that are defined on type extensions themselves foreach ( $this->directiveLocator->associatedOfType($typeExtension, TypeExtensionManipulator::class) as $typeExtensionManipulator ) { $typeExtensionManipulator->manipulateTypeExtension($this->documentAST, $typeExtension); } - // After manipulation on the type extension has been done, - // we can merge them with the original type + // After manipulation on the type extension has been done, we can merge them with the original type if ( $typeExtension instanceof ObjectTypeExtensionNode || $typeExtension instanceof InputObjectTypeExtensionNode diff --git a/src/Schema/AST/ASTHelper.php b/src/Schema/AST/ASTHelper.php index 2585f93852..3168777f41 100644 --- a/src/Schema/AST/ASTHelper.php +++ b/src/Schema/AST/ASTHelper.php @@ -291,8 +291,7 @@ public static function addDirectiveToFields(DirectiveNode $directiveNode, Object $directiveDefinition = static::extractDirectiveDefinition($directive::definition()); foreach ($typeWithFields->fields as $fieldDefinition) { - // If the field already has the same directive defined, and it is not - // a repeatable directive, skip over it. + // If the field already has the same directive defined, and it is not a repeatable directive, skip over it. // Field directives are more specific than those defined on a type. if ( static::hasDirective($fieldDefinition, $name) diff --git a/src/Schema/AST/DocumentAST.php b/src/Schema/AST/DocumentAST.php index 2c15d1a653..602ac851f0 100644 --- a/src/Schema/AST/DocumentAST.php +++ b/src/Schema/AST/DocumentAST.php @@ -61,8 +61,7 @@ class DocumentAST implements Arrayable /** * The type extensions within the parsed document. * - * Will NOT be kept after unserialization, as the type - * extensions are merged with the types before. + * Will NOT be kept after unserialization, as the type extensions are merged with the types before. * * @var array> */ @@ -104,8 +103,7 @@ public static function fromSource(string $schema): self ['noLocation' => true], ); } catch (SyntaxError $syntaxError) { - // Throw our own error class instead, since otherwise a schema definition - // error would get rendered to the Client. + // Throw our own error class instead, since otherwise a schema definition error would get rendered to the Client. throw new SchemaSyntaxErrorException($syntaxError); } @@ -137,9 +135,7 @@ public static function fromSource(string $schema): self throw new DefinitionException("Failed to find a model class {$modelName} in namespaces [{$consideredNamespaces}] referenced in @model on type {$name}."); } - // It might be valid to have multiple types that correspond to a single model - // in order to hide some fields in some scenarios, so we cannot decide on a - // single object type for a given class name unambiguously right here. + // It might be valid to have multiple types that correspond to a single model in order to hide some fields in some scenarios, so we cannot decide on a single object type for a given class name unambiguously right here. $instance->classNameToObjectTypeNames[$modelClass][] = $name; } } elseif ($definition instanceof TypeExtensionNode) { @@ -188,8 +184,7 @@ public function setDirectiveDefinition(DirectiveDefinitionNode $directive): self /** * Convert to a serializable array. * - * We exclude the type extensions stored in $typeExtensions, - * as they are merged with the actual types at this point. + * We exclude the type extensions stored in $typeExtensions, as they are merged with the actual types at this point. * * @return SerializableDocumentAST */ diff --git a/src/Schema/Directives/DeleteDirective.php b/src/Schema/Directives/DeleteDirective.php index a9edfaaf90..bf4c177fca 100644 --- a/src/Schema/Directives/DeleteDirective.php +++ b/src/Schema/Directives/DeleteDirective.php @@ -72,16 +72,14 @@ public function __invoke($model, $idOrIds): void $relation = $model->{$relationName}(); assert($relation instanceof Relation); - // Those types of relations may only have one related model attached to - // it, so we don't need to use an ID to know which model to delete. + // Those types of relations may only have one related model attached to it, so we don't need to use an ID to know which model to delete. $relationIsHasOneLike = $relation instanceof HasOne || $relation instanceof MorphOne; // This includes MorphTo, which is a subclass of BelongsTo $relationIsBelongsToLike = $relation instanceof BelongsTo; if ($relationIsHasOneLike || $relationIsBelongsToLike) { assert($relation instanceof HasOne || $relation instanceof MorphOne || $relation instanceof BelongsTo); // @phpstan-ignore instanceof.alwaysTrue, booleanOr.alwaysTrue - // Only delete if the given value is truthy, since - // the client might use a variable and always pass the argument. + // Only delete if the given value is truthy, since the client might use a variable and always pass the argument. // Deleting when `false` is given seems wrong. if ($idOrIds) { if ($relationIsBelongsToLike) { diff --git a/src/Schema/Directives/DropArgsDirective.php b/src/Schema/Directives/DropArgsDirective.php index ac5697fe15..472240fb9f 100644 --- a/src/Schema/Directives/DropArgsDirective.php +++ b/src/Schema/Directives/DropArgsDirective.php @@ -35,8 +35,7 @@ protected function drop(ArgumentSet &$argumentSet): ArgumentSet unset($argumentSet->arguments[$name]); } else { // Recursively remove nested inputs using @drop directive. - // We look for further ArgumentSet instances, they - // might be contained within an array. + // We look for further ArgumentSet instances, they might be contained within an array. Utils::applyEach( function ($value): void { if ($value instanceof ArgumentSet) { diff --git a/src/Schema/Directives/NamespaceDirective.php b/src/Schema/Directives/NamespaceDirective.php index fe8733eb83..06b5308f56 100644 --- a/src/Schema/Directives/NamespaceDirective.php +++ b/src/Schema/Directives/NamespaceDirective.php @@ -15,8 +15,7 @@ * Redefine the default namespaces used in other directives. * * The args for this directive are a map from directive names to namespaces. - * For example `@namespace(field: "App\\GraphQL")` applies the namespace - * `App\GraphQL` to the `@field` directive. + * For example `@namespace(field: "App\\GraphQL")` applies the namespace `App\GraphQL` to the `@field` directive. */ class NamespaceDirective extends BaseDirective implements TypeManipulator, TypeExtensionManipulator { diff --git a/src/Schema/Directives/RelationDirective.php b/src/Schema/Directives/RelationDirective.php index 41917fe218..eeb86bc156 100644 --- a/src/Schema/Directives/RelationDirective.php +++ b/src/Schema/Directives/RelationDirective.php @@ -51,8 +51,7 @@ public function resolveField(FieldValue $fieldValue): callable $relation = $parent->{$relationName}(); assert($relation instanceof Relation); - // We can shortcut the resolution if the client only queries for a foreign key - // that we know to be present on the parent model. + // We can shortcut the resolution if the client only queries for a foreign key that we know to be present on the parent model. if ( $this->lighthouseConfig['shortcut_foreign_key_selection'] && (array_diff(array_keys($resolveInfo->getFieldSelection()), ['id', '__typename']) === []) diff --git a/src/Schema/Directives/RenameArgsDirective.php b/src/Schema/Directives/RenameArgsDirective.php index c600f8909a..a1ee45f71d 100644 --- a/src/Schema/Directives/RenameArgsDirective.php +++ b/src/Schema/Directives/RenameArgsDirective.php @@ -30,8 +30,7 @@ protected function rename(ArgumentSet &$argumentSet): ArgumentSet { foreach ($argumentSet->arguments as $name => $argument) { // Recursively apply the renaming to nested inputs. - // We look for further ArgumentSet instances, they - // might be contained within an array. + // We look for further ArgumentSet instances, they might be contained within an array. Utils::applyEach( function ($value): void { if ($value instanceof ArgumentSet) { diff --git a/src/Schema/ResolverProvider.php b/src/Schema/ResolverProvider.php index 4da836922c..a3af97b1b9 100644 --- a/src/Schema/ResolverProvider.php +++ b/src/Schema/ResolverProvider.php @@ -23,8 +23,7 @@ public function provideResolver(FieldValue $fieldValue): \Closure $this->throwMissingResolver($fieldValue); } - // Return any non-null value to continue nested field resolution - // when the root Query type is returned as part of the result. + // Return any non-null value to continue nested field resolution when the root Query type is returned as part of the result. if (ASTHelper::getUnderlyingTypeName($fieldValue->getField()) === RootType::QUERY) { return static fn (): bool => true; } @@ -53,8 +52,7 @@ protected function findResolverClass(FieldValue $fieldValue, string $methodName) /** @return never */ protected function throwMissingResolver(FieldValue $fieldValue): void { - // Since we already know we are on the root type, this is either - // query, mutation or subscription + // Since we already know we are on the root type, this is either query, mutation or subscription $parent = lcfirst($fieldValue->getParentName()); $fieldName = $fieldValue->getFieldName(); $proposedResolverClass = ucfirst($fieldName); diff --git a/src/Schema/SchemaBuilder.php b/src/Schema/SchemaBuilder.php index 0c8a950eab..f0ac2dcb7b 100644 --- a/src/Schema/SchemaBuilder.php +++ b/src/Schema/SchemaBuilder.php @@ -45,8 +45,7 @@ protected function build(DocumentAST $documentAST): Schema assert($query instanceof ObjectType); $config->setQuery($query); - // Mutation and Subscription are optional, so only add them - // if they are present in the schema + // Mutation and Subscription are optional, so only add them if they are present in the schema if (isset($documentAST->types[RootType::MUTATION])) { $mutation = $this->typeRegistry->get(RootType::MUTATION); assert($mutation instanceof ObjectType); @@ -70,9 +69,7 @@ protected function build(DocumentAST $documentAST): Schema fn (): array => $this->typeRegistry->possibleTypes(), ); - // Passing scalar overrides explicitly prevents the first lookup of a built-in scalar - // from discovering them by resolving the lazy types callable, which would eagerly - // build every type in the schema, see https://github.com/nuwave/lighthouse/issues/2771. + // Passing scalar overrides explicitly prevents the first lookup of a built-in scalar from discovering them by resolving the lazy types callable, which would eagerly build every type in the schema, see https://github.com/nuwave/lighthouse/issues/2771. // TODO remove this check when the minimum version of webonyx/graphql-php includes the method if (method_exists($config, 'setScalarOverrides')) { // @phpstan-ignore function.alreadyNarrowedType (backward compatibility with webonyx/graphql-php < 15.31) $config->setScalarOverrides($this->typeRegistry->scalarOverrides()); diff --git a/src/Schema/TypeRegistry.php b/src/Schema/TypeRegistry.php index 3919305eef..9c719cf519 100644 --- a/src/Schema/TypeRegistry.php +++ b/src/Schema/TypeRegistry.php @@ -219,9 +219,7 @@ public function overwriteLazy(string $name, callable $type): self */ public function possibleTypes(): array { - // Make sure all the types from the AST are eagerly converted - // to find orphaned types, such as an object type that is only - // ever used through its association to an interface. + // Make sure all the types from the AST are eagerly converted to find orphaned types, such as an object type that is only ever used through its association to an interface. foreach ($this->documentAST->types as $typeDefinition) { $name = $typeDefinition->getName()->value; @@ -238,8 +236,7 @@ public function possibleTypes(): array /** * Built-in scalar types that are overridden in this schema. * - * A scalar override is a type named after a built-in scalar such as `String`, - * defined in the schema or registered programmatically. + * A scalar override is a type named after a built-in scalar such as `String`, defined in the schema or registered programmatically. * * @return array */ diff --git a/src/Schema/Values/FieldValue.php b/src/Schema/Values/FieldValue.php index 3b290ca5c1..17a1e2b046 100644 --- a/src/Schema/Values/FieldValue.php +++ b/src/Schema/Values/FieldValue.php @@ -156,8 +156,8 @@ public function addArgumentSetTransformer(callable $argumentSetTransformer): sel */ public function finishResolver(callable $resolver): callable { - // We expect the wrapped resolvers to run in order, but nesting them causes the last - // applied wrapper to be run first. Thus, we reverse the wrappers before applying them. + // We expect the wrapped resolvers to run in order, but nesting them causes the last applied wrapper to be run first. + // Thus, we reverse the wrappers before applying them. foreach (array_reverse($this->resolverWrappers) as $wrapper) { $resolver = $wrapper($resolver); } diff --git a/src/Subscriptions/Storage/RedisStorageManager.php b/src/Subscriptions/Storage/RedisStorageManager.php index 2ecae56dfb..ca2b839228 100644 --- a/src/Subscriptions/Storage/RedisStorageManager.php +++ b/src/Subscriptions/Storage/RedisStorageManager.php @@ -69,8 +69,7 @@ public function subscribersByTopic(string $topic): Collection // Store all keys as missing keys to remove the ones which are expired later. $missingKeys = $subscriberIds; - // Since we store the individual subscribers with a prefix, - // but not in the set, we have to add the prefix here. + // Since we store the individual subscribers with a prefix, but not in the set, we have to add the prefix here. $subscriberIds = array_map([$this, 'channelKey'], $subscriberIds); // Using the mget command, we can retrieve multiple values from redis. @@ -116,8 +115,7 @@ public function storeSubscriber(Subscriber $subscriber, string $topic): void $subscriber->topic = $topic; // In contrast to the CacheStorageManager, we use redis sets. - // Instead of reading the entire list, adding the subscriber, and storing the list; - // we add the name of the subscriber to the set of subscribers of this topic using the sadd command... + // Instead of reading the entire list, adding the subscriber, and storing the list; we add the name of the subscriber to the set of subscribers of this topic using the sadd command... $topicKey = $this->topicKey($topic); $this->connection->command('sadd', [ $topicKey, diff --git a/src/Subscriptions/SubscriptionResolverProvider.php b/src/Subscriptions/SubscriptionResolverProvider.php index 157f1be14f..5058783a08 100644 --- a/src/Subscriptions/SubscriptionResolverProvider.php +++ b/src/Subscriptions/SubscriptionResolverProvider.php @@ -51,8 +51,7 @@ public function provideSubscriptionResolver(FieldValue $fieldValue): \Closure assert(is_subclass_of($namespacedClassName, GraphQLSubscription::class)); $subscription = Container::getInstance()->make($namespacedClassName); - // Subscriptions can only be placed on a single field on the root - // query, so there is no need to consider the field path + // Subscriptions can only be placed on a single field on the root query, so there is no need to consider the field path $this->subscriptionRegistry->register($subscription, $fieldName); return function (mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolveInfo) use ($subscription, $fieldName) { diff --git a/src/Support/Contracts/ArgResolver.php b/src/Support/Contracts/ArgResolver.php index 07b2bc4b09..96acdbf60f 100644 --- a/src/Support/Contracts/ArgResolver.php +++ b/src/Support/Contracts/ArgResolver.php @@ -5,8 +5,7 @@ /** * Resolve a slice of input arguments during mutation execution. * - * Arg resolvers compose like field resolvers: each handles only its own - * nested input, and Lighthouse orchestrates traversal of the argument tree. + * Arg resolvers compose like field resolvers: each handles only its own nested input, and Lighthouse orchestrates traversal of the argument tree. * * @see \Nuwave\Lighthouse\Support\Contracts\SaveAwareArgResolver * diff --git a/src/Support/Contracts/PreSaveArgumentsAware.php b/src/Support/Contracts/PreSaveArgumentsAware.php index 17033531e0..ca9be515b9 100644 --- a/src/Support/Contracts/PreSaveArgumentsAware.php +++ b/src/Support/Contracts/PreSaveArgumentsAware.php @@ -3,12 +3,10 @@ namespace Nuwave\Lighthouse\Support\Contracts; /** - * Implement this on ArgResolvers that can run pre-save arg resolvers - * lifted out of a @nest before persisting the model. + * Implement this on ArgResolvers that can run pre-save arg resolvers lifted out of a @nest before persisting the model. * * Lifted arguments are passed as an ordered list, not as a name-keyed map: - * field names are unique per input type, not across a whole input tree, - * so keying them would discard colliding arguments. + * field names are unique per input type, not across a whole input tree, so keying them would discard colliding arguments. */ interface PreSaveArgumentsAware { diff --git a/src/Support/Contracts/ProvidesCacheableValidationRules.php b/src/Support/Contracts/ProvidesCacheableValidationRules.php index 5ba53e5f48..e940e717c4 100644 --- a/src/Support/Contracts/ProvidesCacheableValidationRules.php +++ b/src/Support/Contracts/ProvidesCacheableValidationRules.php @@ -22,8 +22,7 @@ public function cacheableValidationRules(): array; * * These rules are always executed and their result is never cached. * - * Returning `null` enables all available rules, - * returning `[]` skips query validation entirely. + * Returning `null` enables all available rules, returning `[]` skips query validation entirely. * * @return array|null */ diff --git a/src/Support/Contracts/ProvidesValidationRules.php b/src/Support/Contracts/ProvidesValidationRules.php index 100fe13f50..a338ac41dd 100644 --- a/src/Support/Contracts/ProvidesValidationRules.php +++ b/src/Support/Contracts/ProvidesValidationRules.php @@ -7,8 +7,7 @@ interface ProvidesValidationRules /** * Rules to use for query validation. * - * Returning `null` enables all available rules, - * returning `[]` skips query validation entirely. + * Returning `null` enables all available rules, returning `[]` skips query validation entirely. * * @return array|null */ diff --git a/src/Support/Contracts/SaveAwareArgResolver.php b/src/Support/Contracts/SaveAwareArgResolver.php index c4f907da01..084b684cb5 100644 --- a/src/Support/Contracts/SaveAwareArgResolver.php +++ b/src/Support/Contracts/SaveAwareArgResolver.php @@ -5,11 +5,10 @@ use Illuminate\Database\Eloquent\Model; /** - * Implement this on ArgResolver directives that need to control whether they - * run before or after the parent model is saved during mutation execution. + * Implement this on ArgResolver directives that need to control whether they run before or after the parent model is saved during mutation execution. * - * When `runBeforeSave()` returns true, `__invoke()` receives null as `$value` - * if the client sends null for a nullable input field. Guard accordingly. + * When `runBeforeSave()` returns true, `__invoke()` receives null as `$value` if the client sends null for a nullable input field. + * Guard accordingly. * * @api */ @@ -18,16 +17,13 @@ interface SaveAwareArgResolver extends ArgResolver /** * Should this resolver run before the parent model is persisted? * - * When true, the resolver is invoked before $model->save(), allowing it - * to set attributes or foreign keys on the model. - * When false, the resolver runs after the model is saved (the default - * for any ArgResolver that does not implement this interface). + * When true, the resolver is invoked before $model->save(), allowing it to set attributes or foreign keys on the model. + * When false, the resolver runs after the model is saved (the default for any ArgResolver that does not implement this interface). * * Only consulted when the root is a Model. * In non-Model contexts, this method is not called and the resolver executes normally. * - * Implementations must base the decision on the model class and its relations, - * not on instance state — the model may not yet be hydrated when this is called. + * Implementations must base the decision on the model class and its relations, not on instance state — the model may not yet be hydrated when this is called. */ public function runBeforeSave(Model $model): bool; } diff --git a/src/Support/DriverManager.php b/src/Support/DriverManager.php index fb200032f2..b52fdf7d66 100644 --- a/src/Support/DriverManager.php +++ b/src/Support/DriverManager.php @@ -6,8 +6,8 @@ use Nuwave\Lighthouse\Exceptions\InvalidDriverException; /** - * NOTE: Implementation pulled from \Illuminate\Cache\CacheManager. Purpose is - * to serve as a base class to generate a manager that creates drivers with configuration options. + * NOTE: Implementation pulled from \Illuminate\Cache\CacheManager. + * Purpose is to serve as a base class to generate a manager that creates drivers with configuration options. * * @phpstan-type CustomCreator callable(\Illuminate\Container\Container $app, array $config): object */ diff --git a/src/Testing/MakesGraphQLRequests.php b/src/Testing/MakesGraphQLRequests.php index 6257e76424..b900ae1474 100644 --- a/src/Testing/MakesGraphQLRequests.php +++ b/src/Testing/MakesGraphQLRequests.php @@ -25,8 +25,7 @@ trait MakesGraphQLRequests /** * Stores the result of the introspection query. * - * On the first call to introspect() this property is set to - * cache the result, as introspection is expensive. + * On the first call to introspect() this property is set to cache the result, as introspection is expensive. * * @var \Illuminate\Testing\TestResponse<\Symfony\Component\HttpFoundation\Response> */ @@ -65,8 +64,7 @@ protected function graphQL( /** * Send a POST request to the GraphQL endpoint. * - * Use this over graphQL() when you need more control or want to - * test how your server behaves on incorrect inputs. + * Use this over graphQL() when you need more control or want to test how your server behaves on incorrect inputs. * * @param array $data JSON-serializable payload * @param array $headers HTTP headers to pass to the POST request diff --git a/src/Testing/MakesGraphQLRequestsLumen.php b/src/Testing/MakesGraphQLRequestsLumen.php index 6c53ae28e0..f484d2eda1 100644 --- a/src/Testing/MakesGraphQLRequestsLumen.php +++ b/src/Testing/MakesGraphQLRequestsLumen.php @@ -27,8 +27,7 @@ trait MakesGraphQLRequestsLumen // @phpstan-ignore trait.unused (hard to set up /** * Stores the result of the introspection query. * - * On the first call to introspect() this property is set to - * cache the result, as introspection is expensive. + * On the first call to introspect() this property is set to cache the result, as introspection is expensive. */ protected TestResponse $introspectionResult; @@ -66,8 +65,7 @@ protected function graphQL( /** * Send a POST request to the GraphQL endpoint. * - * Use this over graphQL() when you need more control or want to - * test how your server behaves on incorrect inputs. + * Use this over graphQL() when you need more control or want to test how your server behaves on incorrect inputs. * * @param array $data JSON-serializable payload * @param array $headers HTTP headers to pass to the POST request diff --git a/src/Testing/RefreshesSchemaCache.php b/src/Testing/RefreshesSchemaCache.php index 395363620e..0ae1d7832c 100644 --- a/src/Testing/RefreshesSchemaCache.php +++ b/src/Testing/RefreshesSchemaCache.php @@ -27,9 +27,7 @@ trait RefreshesSchemaCache protected function refreshSchemaCache(): void { if (! static::$schemaCacheWasRefreshed) { - // We use the filesystem as shared mutable state to coordinate between processes, - // since the tests might be run in parallel, and we want to ensure the schema cache - // is refreshed exactly once before all tests. + // We use the filesystem as shared mutable state to coordinate between processes, since the tests might be run in parallel, and we want to ensure the schema cache is refreshed exactly once before all tests. \Safe\touch(self::$lockFilePath); $lockFile = \Safe\fopen(self::$lockFilePath, 'r'); diff --git a/src/Validation/BaseRulesDirective.php b/src/Validation/BaseRulesDirective.php index d84cb992ea..ed7e45bb4e 100644 --- a/src/Validation/BaseRulesDirective.php +++ b/src/Validation/BaseRulesDirective.php @@ -21,10 +21,8 @@ public function rules(): array $rules = $this->directiveArgValue('apply'); // Custom rules may be referenced through their fully qualified class name. - // The Laravel validator expects a class instance to be passed, so we - // resolve any given rule where a corresponding class exists. - // Requiring a namespace separator keeps built-in rules such as `url` or `image` - // from matching global classes or facade aliases, as class names are case-insensitive. + // The Laravel validator expects a class instance to be passed, so we resolve any given rule where a corresponding class exists. + // Requiring a namespace separator keeps built-in rules such as `url` or `image` from matching global classes or facade aliases, as class names are case-insensitive. foreach ($rules as $key => $rule) { if (str_contains($rule, '\\') && class_exists($rule)) { $rules[$key] = Container::getInstance()->make($rule); diff --git a/src/Validation/RulesGatherer.php b/src/Validation/RulesGatherer.php index 3749dde10e..e19a15914f 100644 --- a/src/Validation/RulesGatherer.php +++ b/src/Validation/RulesGatherer.php @@ -192,9 +192,8 @@ protected function wrap(array $rulesOrMessages, array $path): array /** * Prepend rule arguments that refer to other arguments with the full path. * - * This may be necessary to allow certain rules to be reusable when placed - * upon input arguments. For example, `required_with:foo` may be defined - * on an input value that is nested within the arguments under `input.0`. + * This may be necessary to allow certain rules to be reusable when placed upon input arguments. + * For example, `required_with:foo` may be defined on an input value that is nested within the arguments under `input.0`. * It is thus changed to the full reference `required_with:input.0.foo`. * * @param array $rules diff --git a/src/WhereConditions/SQLOperator.php b/src/WhereConditions/SQLOperator.php index f6adc45a73..8c3e8829f8 100644 --- a/src/WhereConditions/SQLOperator.php +++ b/src/WhereConditions/SQLOperator.php @@ -88,12 +88,10 @@ public function applyConditions(QueryBuilder|EloquentBuilder $builder, array $wh $arity = $this->operatorArity($operator); if ($arity === 3) { - // Usually, the operator is passed as the second argument to the condition - // method, e.g. ->where('some_col', '=', $value) + // Usually, the operator is passed as the second argument to the condition method, e.g. ->where('some_col', '=', $value) $args[] = $operator; } else { - // We use the fact that the operators are named after Laravel's condition - // methods, so we can append the name, e.g. whereNull, whereNotBetween + // We use the fact that the operators are named after Laravel's condition methods, so we can append the name, e.g. whereNull, whereNotBetween $method .= $operator; } diff --git a/src/WhereConditions/WhereHasConditionsDirective.php b/src/WhereConditions/WhereHasConditionsDirective.php index 6053ad9388..a1b9d8ddf5 100644 --- a/src/WhereConditions/WhereHasConditionsDirective.php +++ b/src/WhereConditions/WhereHasConditionsDirective.php @@ -86,8 +86,7 @@ protected function relationName(): string { $relationName = $this->directiveArgValue('relation'); - // If the relation name is not set explicitly, we assume the argument - // name follows a convention and contains the relation name + // If the relation name is not set explicitly, we assume the argument name follows a convention and contains the relation name if (is_null($relationName)) { return lcfirst( Str::after($this->nodeName(), 'has'), diff --git a/src/lighthouse.php b/src/lighthouse.php index ad4e55079b..7f4cba1010 100644 --- a/src/lighthouse.php +++ b/src/lighthouse.php @@ -7,8 +7,7 @@ |-------------------------------------------------------------------------- | | Controls the HTTP route that your GraphQL server responds to. - | You may set `route` => false, to disable the default route - | registration and take full control. + | You may set `route` => false, to disable the default route registration and take full control. | */ @@ -34,8 +33,8 @@ // Always set the `Accept: application/json` header. Nuwave\Lighthouse\Http\Middleware\AcceptJson::class, - // Logs in a user if they are authenticated. In contrast to Laravel's 'auth' - // middleware, this delegates auth and permission checks to the field level. + // Logs in a user if they are authenticated. + // In contrast to Laravel's 'auth' middleware, this delegates auth and permission checks to the field level. Nuwave\Lighthouse\Http\Middleware\AttemptAuthentication::class, // Logs every incoming GraphQL query. @@ -81,8 +80,7 @@ |-------------------------------------------------------------------------- | | A large part of schema generation consists of parsing and AST manipulation. - | This operation is expensive, so enable caching of the final schema - | to optimize performance of large schemas. + | This operation is expensive, so enable caching of the final schema to optimize performance of large schemas. | */ @@ -182,8 +180,7 @@ |-------------------------------------------------------------------------- | | Should the source location be included in the AST nodes resulting from query parsing? - | Setting this to `false` improves performance, but omits the key `locations` from errors, - | see https://spec.graphql.org/October2021/#sec-Errors.Error-result-format. + | Setting this to `false` improves performance, but omits the key `locations` from errors, see https://spec.graphql.org/October2021/#sec-Errors.Error-result-format. | */ @@ -194,9 +191,8 @@ | Namespaces |-------------------------------------------------------------------------- | - | These are the default namespaces where Lighthouse looks for classes to - | extend functionality of the schema. You may pass in either a string - | or an array, they are tried in order and the first match is used. + | These are the default namespaces where Lighthouse looks for classes to extend functionality of the schema. + | You may pass in either a string or an array, they are tried in order and the first match is used. | */ @@ -236,8 +232,7 @@ | Pagination |-------------------------------------------------------------------------- | - | Set defaults for the pagination features within Lighthouse, such as - | the @paginate directive, or paginated relation directives. + | Set defaults for the pagination features within Lighthouse, such as the @paginate directive, or paginated relation directives. | */ @@ -290,8 +285,8 @@ | Error Handlers |-------------------------------------------------------------------------- | - | Register error handlers that receive the Errors that occur during execution - | and handle them. You may use this to log, filter or format the errors. + | Register error handlers that receive the Errors that occur during execution and handle them. + | You may use this to log, filter or format the errors. | The classes must implement \Nuwave\Lighthouse\Execution\ErrorHandler | */ @@ -342,8 +337,7 @@ | Persisted Queries |-------------------------------------------------------------------------- | - | Lighthouse supports Automatic Persisted Queries (APQ), compatible with the - | [Apollo implementation](https://www.apollographql.com/docs/apollo-server/performance/apq). + | Lighthouse supports Automatic Persisted Queries (APQ), compatible with the [Apollo implementation](https://www.apollographql.com/docs/apollo-server/performance/apq). | You may set this flag to either process or deny these queries. | */ @@ -355,10 +349,8 @@ | Transactional Mutations |-------------------------------------------------------------------------- | - | If set to true, the execution of built-in directives that mutate models - | will be wrapped in a transaction to ensure atomicity. - | The transaction is committed after the root field resolves, - | thus errors in nested fields do not cause a rollback. + | If set to true, the execution of built-in directives that mutate models will be wrapped in a transaction to ensure atomicity. + | The transaction is committed after the root field resolves, thus errors in nested fields do not cause a rollback. | */ @@ -369,9 +361,8 @@ | Mass Assignment Protection |-------------------------------------------------------------------------- | - | If set to true, mutations will use forceFill() over fill() when populating - | a model with arguments in mutation directives. Since GraphQL constrains - | allowed inputs by design, mass assignment protection is not needed. + | If set to true, mutations will use forceFill() over fill() when populating a model with arguments in mutation directives. + | Since GraphQL constrains allowed inputs by design, mass assignment protection is not needed. | */ @@ -382,8 +373,7 @@ | Batchload Relations |-------------------------------------------------------------------------- | - | If set to true, relations marked with directives like @hasMany or @belongsTo - | will be optimized by combining the queries through the BatchLoader. + | If set to true, relations marked with directives like @hasMany or @belongsTo will be optimized by combining the queries through the BatchLoader. | */ @@ -394,9 +384,8 @@ | Shortcut Foreign Key Selection |-------------------------------------------------------------------------- | - | If set to true, Lighthouse will shortcut queries where the client selects only the - | foreign key pointing to a related model. Only works if the related model's primary - | key field is called exactly `id` for every type in your schema. + | If set to true, Lighthouse will shortcut queries where the client selects only the foreign key pointing to a related model. + | Only works if the related model's primary key field is called exactly `id` for every type in your schema. | */ @@ -407,8 +396,7 @@ | GraphQL Subscriptions |-------------------------------------------------------------------------- | - | Here you can define GraphQL subscription broadcaster and storage drivers - | as well their required configuration options. + | Here you can define GraphQL subscription broadcaster and storage drivers as well their required configuration options. | */ @@ -434,8 +422,8 @@ * Default subscription storage time to live in seconds. * * Indicates how long a subscription can stay active before automatic removal from storage. - * Setting this to `null` means the subscriptions are stored forever. This may cause - * stale subscriptions to linger indefinitely in case cleanup fails for any reason. + * Setting this to `null` means the subscriptions are stored forever. + * This may cause stale subscriptions to linger indefinitely in case cleanup fails for any reason. */ 'storage_ttl' => env('LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL', null), diff --git a/tests/Integration/LifecycleEventsTest.php b/tests/Integration/LifecycleEventsTest.php index 661fb763c5..0b977714c9 100644 --- a/tests/Integration/LifecycleEventsTest.php +++ b/tests/Integration/LifecycleEventsTest.php @@ -27,8 +27,7 @@ public function testDispatchesProperLifecycleEvents(): void $eventsDispatcher->listen('*', static function (string $name, array $payload) use (&$events): void { if (str_starts_with($name, 'Nuwave\\Lighthouse')) { - // We only fire class-based events, so the payload - // always holds exactly a single class instance. + // We only fire class-based events, so the payload always holds exactly a single class instance. $events[] = $payload[0]; } }); diff --git a/tests/Integration/Validation/RulesDirectiveTest.php b/tests/Integration/Validation/RulesDirectiveTest.php index ec3518be65..7d157bc7cd 100644 --- a/tests/Integration/Validation/RulesDirectiveTest.php +++ b/tests/Integration/Validation/RulesDirectiveTest.php @@ -230,8 +230,7 @@ public function testCustomAttributes(): void public function testBuiltInRuleNotShadowedByGlobalClassWithMatchingName(): void { - // Like a facade alias such as `URL` or intervention/image's `Image`, - // which matches the built-in rule case-insensitively once loaded. + // Like a facade alias such as `URL` or intervention/image's `Image`, which matches the built-in rule case-insensitively once loaded. // The container then resolves its `url` binding, the UrlGenerator. if (! class_exists('Url')) { class_alias((new class {})::class, 'Url'); diff --git a/tests/Integration/Validation/RulesForArrayDirectiveTest.php b/tests/Integration/Validation/RulesForArrayDirectiveTest.php index a4f2eb60d7..d21a056cb1 100644 --- a/tests/Integration/Validation/RulesForArrayDirectiveTest.php +++ b/tests/Integration/Validation/RulesForArrayDirectiveTest.php @@ -59,8 +59,7 @@ public function testValidatesListSizeOfInputObjects(): void public function testBuiltInRuleNotShadowedByGlobalClassWithMatchingName(): void { - // Like a facade alias such as `URL` or intervention/image's `Image`, - // which matches the built-in rule case-insensitively once loaded. + // Like a facade alias such as `URL` or intervention/image's `Image`, which matches the built-in rule case-insensitively once loaded. if (! class_exists('Filled')) { class_alias((new class {})::class, 'Filled'); } diff --git a/tests/TestCase.php b/tests/TestCase.php index a34686617c..b1506d0a96 100644 --- a/tests/TestCase.php +++ b/tests/TestCase.php @@ -55,8 +55,7 @@ protected function setUp(): void { parent::setUp(); - // This default is only valid for testing Lighthouse itself and thus - // is not defined in the reusable test trait. + // This default is only valid for testing Lighthouse itself and thus is not defined in the reusable test trait. $this->schema ??= self::PLACEHOLDER_QUERY; $this->setUpTestSchema(); diff --git a/tests/Unit/Execution/Arguments/ArgumentSetTest.php b/tests/Unit/Execution/Arguments/ArgumentSetTest.php index fe03fae3cf..9b0e546b2e 100644 --- a/tests/Unit/Execution/Arguments/ArgumentSetTest.php +++ b/tests/Unit/Execution/Arguments/ArgumentSetTest.php @@ -185,8 +185,7 @@ public function testAddValueWithWildcardSkipsWhenNestedContainerIsMissing(): voi $set = new ArgumentSet(); $set->addValue('tasks.create.*.user_id', 123); - // The intermediary `tasks` input is created just like plain dot notation would, - // but nothing is injected because `create` was never provided by the client. + // The intermediary `tasks` input is created just like plain dot notation would, but nothing is injected because `create` was never provided by the client. $this->assertTrue($set->exists('tasks')); $tasks = $set->arguments['tasks']->value; diff --git a/tests/Unit/Rector/RootResolverSignatureRector/bootstrap.php b/tests/Unit/Rector/RootResolverSignatureRector/bootstrap.php index 9d10e91167..d83aef68d7 100644 --- a/tests/Unit/Rector/RootResolverSignatureRector/bootstrap.php +++ b/tests/Unit/Rector/RootResolverSignatureRector/bootstrap.php @@ -15,8 +15,7 @@ require_once __DIR__ . '/../../../../vendor/larastan/larastan/bootstrap.php'; -// Undo handlers registered by Laravel's HandleExceptions bootstrapper -// to avoid PHPUnit risky test warnings about leaked handlers. +// Undo handlers registered by Laravel's HandleExceptions bootstrapper to avoid PHPUnit risky test warnings about leaked handlers. for ($i = 0; $i < 10; ++$i) { if (set_error_handler(static fn (mixed ...$args): bool => false) === $errorHandler) { restore_error_handler(); From ea603dc80dfc9bc609f46763a5d7e1a4965082f8 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:43:28 +0100 Subject: [PATCH 16/24] Copy event classes into the events docs from src MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The docs held outdated copies with hard-wrapped comments. 🤖 Generated with Claude Code --- docs/master/api-reference/events.md | 85 +++++++++-------------------- 1 file changed, 26 insertions(+), 59 deletions(-) diff --git a/docs/master/api-reference/events.md b/docs/master/api-reference/events.md index 6d1d12eb0e..a9a832a8eb 100644 --- a/docs/master/api-reference/events.md +++ b/docs/master/api-reference/events.md @@ -15,23 +15,18 @@ use Illuminate\Support\Carbon; /** * Fires right after a request reaches the GraphQLController. * - * Can be used for logging or for measuring and monitoring - * the time a request takes to resolve. + * Can be used for logging or for measuring and monitoring the time a request takes to resolve. * * @see \Nuwave\Lighthouse\Http\GraphQLController */ class StartRequest { - /** - * The point in time when the request started. - */ + /** The point in time when the request started. */ public Carbon $moment; public function __construct( - /** - * The request sent from the client. - */ - public Request $request + /** The request sent from the client. */ + public Request $request, ) { $this->moment = Carbon::now(); } @@ -54,7 +49,7 @@ class StartOperationOrOperations * * @var \GraphQL\Server\OperationParams|array */ - public OperationParams|array $operationOrOperations + public OperationParams|array $operationOrOperations, ) {} } ``` @@ -72,10 +67,8 @@ class StartOperationOrOperations class BuildSchemaString { public function __construct( - /** - * The root schema that was defined by the user. - */ - public string $userSchema + /** The root schema that was defined by the user. */ + public string $userSchema, ) {} } ``` @@ -114,7 +107,7 @@ class ManipulateAST /** * The AST that can be manipulated. */ - public DocumentAST &$documentAST + public DocumentAST &$documentAST, ) {} } ``` @@ -134,37 +127,23 @@ use Nuwave\Lighthouse\Support\Contracts\GraphQLContext; */ class StartExecution { - /** - * The point in time when the query execution started. - */ + /** The point in time when the query execution started. */ public Carbon $moment; public function __construct( - /** - * The parsed schema. - */ + /** The parsed schema. */ public Schema $schema, - - /** - * The client given parsed query string. - */ + /** The client given parsed query string. */ public DocumentNode $query, - /** * The client given variables, neither validated nor transformed. * * @var array|null */ public ?array $variables, - - /** - * The client given operation name. - */ + /** The client given operation name. */ public ?string $operationName, - - /** - * The context for the operation. - */ + /** The context for the operation. */ public GraphQLContext $context, ) { $this->moment = Carbon::now(); @@ -180,8 +159,7 @@ use GraphQL\Executor\ExecutionResult; /** * Fires after a query was resolved. * - * Listeners may return a @see \Nuwave\Lighthouse\Execution\ExtensionsResponse - * to include in the response. + * Listeners may return a @see \Nuwave\Lighthouse\Execution\ExtensionsResponse to include in the response. */ class BuildExtensionsResponse { @@ -217,8 +195,8 @@ use GraphQL\Executor\ExecutionResult; /** * Fires after resolving each individual query. * - * This lets listeners manipulate the query result - * without worrying about batched execution. + * This lets listeners manipulate the query result. + * It avoids worrying about batched execution. */ class ManipulateResult { @@ -226,7 +204,7 @@ class ManipulateResult /** * The result of resolving an individual query. */ - public ExecutionResult &$result + public ExecutionResult &$result, ) {} } ``` @@ -242,16 +220,12 @@ use Illuminate\Support\Carbon; */ class EndExecution { - /** - * The point in time when the result was ready. - */ + /** The point in time when the result was ready. */ public Carbon $moment; public function __construct( - /** - * The result of resolving a single operation. - */ - public ExecutionResult $result + /** The result of resolving a single operation. */ + public ExecutionResult $result, ) { $this->moment = Carbon::now(); } @@ -272,7 +246,7 @@ class EndOperationOrOperations * * @var array|array> $resultOrResults */ - public array $resultOrResults + public array $resultOrResults, ) {} } ``` @@ -286,23 +260,18 @@ use Symfony\Component\HttpFoundation\Response; /** * Fires right after building the HTTP response in the GraphQLController. * - * Can be used for logging or for measuring and monitoring - * the time a request takes to resolve. + * Can be used for logging or for measuring and monitoring the time a request takes to resolve. * * @see \Nuwave\Lighthouse\Http\GraphQLController */ class EndRequest { - /** - * The point in time when the response was ready. - */ + /** The point in time when the response was ready. */ public Carbon $moment; public function __construct( - /** - * The response that is about to be sent to the client. - */ - public Response $response + /** The response that is about to be sent to the client. */ + public Response $response, ) { $this->moment = Carbon::now(); } @@ -326,9 +295,7 @@ use GraphQL\Type\Schema; class ValidateSchema { public function __construct( - /** - * The final schema to validate. - */ + /** The final schema to validate. */ public Schema $schema, ) {} } From 19cdc09907afae3cf8c24f10f2a7c5b03f891dc1 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:43:28 +0100 Subject: [PATCH 17/24] Put one sentence per line in comments of docs code examples MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/performance/n-plus-one.md | 3 +-- docs/master/subscriptions/defining-fields.md | 6 ++---- docs/master/subscriptions/filtering-subscriptions.md | 3 +-- 3 files changed, 4 insertions(+), 8 deletions(-) diff --git a/docs/master/performance/n-plus-one.md b/docs/master/performance/n-plus-one.md index 77fbf191dd..3c61d7d272 100644 --- a/docs/master/performance/n-plus-one.md +++ b/docs/master/performance/n-plus-one.md @@ -132,8 +132,7 @@ final class UserPostsBatchLoader { $this->users[$user->id] = $user; - // The wrapped callable will run after load() has been called - // with all users in the current query. + // The wrapped callable will run after load() has been called with all users in the current query. return new Deferred(function () use ($user): array { // Ensure we only perform the actual loading exactly once. if (! $this->hasResolved) { diff --git a/docs/master/subscriptions/defining-fields.md b/docs/master/subscriptions/defining-fields.md index ff15fe6ae8..6436a0ba25 100644 --- a/docs/master/subscriptions/defining-fields.md +++ b/docs/master/subscriptions/defining-fields.md @@ -48,8 +48,7 @@ final class PostUpdated extends GraphQLSubscription { $user = $subscriber->context->user; - // Don't broadcast the subscription to the same - // person who updated the post. + // Don't broadcast the subscription to the same person who updated the post. return $root->updated_by !== $user->id; } @@ -75,8 +74,7 @@ final class PostUpdated extends GraphQLSubscription */ public function resolve(mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolveInfo): Post { - // Optionally manipulate the `$root` item before it gets broadcasted to - // subscribed client(s). + // Optionally manipulate the `$root` item before it gets broadcasted to subscribed client(s). $root->load(['author', 'author.achievements']); return $root; diff --git a/docs/master/subscriptions/filtering-subscriptions.md b/docs/master/subscriptions/filtering-subscriptions.md index 3c6d132093..e3db7a70c6 100644 --- a/docs/master/subscriptions/filtering-subscriptions.md +++ b/docs/master/subscriptions/filtering-subscriptions.md @@ -29,8 +29,7 @@ final class PostUpdatedSubscription extends GraphQLSubscription // Clients arguments when subscribing $args = $subscriber->args; - // Ensure that the Post ($root) id matches - // the requested `post_id` + // Ensure that the Post ($root) id matches the requested `post_id` return $root->id == $args['post_id']; } } From 85f6f2a0609aac58754ed03aef2dfb34f67ba9c1 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:47:54 +0100 Subject: [PATCH 18/24] Fix grammar of JSON length operator descriptions MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- src/WhereConditions/SQLOperator.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/WhereConditions/SQLOperator.php b/src/WhereConditions/SQLOperator.php index 25dd0bb92a..7157c51eed 100644 --- a/src/WhereConditions/SQLOperator.php +++ b/src/WhereConditions/SQLOperator.php @@ -72,10 +72,10 @@ enum SQLOperator { "Whether a value is not in the JSON." JSON_DOESNT_CONTAIN @enum(value: "JsonDoesntContain") - "Whether the length of the JSON array is equals to the value." + "Whether the length of the JSON array equals the value." JSON_LENGTH_EQ @enum(value: "JsonLengthEq") - "Whether the length of the JSON array is not equals to the value." + "Whether the length of the JSON array does not equal the value." JSON_LENGTH_NEQ @enum(value: "JsonLengthNeq") "Whether the length of the JSON array is less than the value." @@ -84,10 +84,10 @@ enum SQLOperator { "Whether the length of the JSON array is greater than the value." JSON_LENGTH_GT @enum(value: "JsonLengthGt") - "Whether the length of the JSON array is less than or equals to the value." + "Whether the length of the JSON array is less than or equal to the value." JSON_LENGTH_LTE @enum(value: "JsonLengthLte") - "Whether the length of the JSON array is greater than or equals to the value." + "Whether the length of the JSON array is greater than or equal to the value." JSON_LENGTH_GTE @enum(value: "JsonLengthGte") } GRAPHQL; From 4e3928ece213611d6f5f01cfba320d772cc4ba66 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:55:30 +0100 Subject: [PATCH 19/24] Keep ManipulateResult description in one sentence MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/events.md | 3 +-- src/Events/ManipulateResult.php | 3 +-- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/docs/master/api-reference/events.md b/docs/master/api-reference/events.md index a9a832a8eb..1a0426abcf 100644 --- a/docs/master/api-reference/events.md +++ b/docs/master/api-reference/events.md @@ -195,8 +195,7 @@ use GraphQL\Executor\ExecutionResult; /** * Fires after resolving each individual query. * - * This lets listeners manipulate the query result. - * It avoids worrying about batched execution. + * This lets listeners manipulate the query result without worrying about batched execution. */ class ManipulateResult { diff --git a/src/Events/ManipulateResult.php b/src/Events/ManipulateResult.php index dd9f1b3bf8..c5fa0a8984 100644 --- a/src/Events/ManipulateResult.php +++ b/src/Events/ManipulateResult.php @@ -7,8 +7,7 @@ /** * Fires after resolving each individual query. * - * This lets listeners manipulate the query result. - * It avoids worrying about batched execution. + * This lets listeners manipulate the query result without worrying about batched execution. */ class ManipulateResult { From c911b640664490ac308524d0a09f5e58dc07d40f Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:55:30 +0100 Subject: [PATCH 20/24] Split ResolveInfo description in resolvers docs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/api-reference/resolvers.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/docs/master/api-reference/resolvers.md b/docs/master/api-reference/resolvers.md index 6c2f88dc43..3c264abdc0 100644 --- a/docs/master/api-reference/resolvers.md +++ b/docs/master/api-reference/resolvers.md @@ -17,7 +17,8 @@ function (mixed $root, array $args, GraphQLContext $context, ResolveInfo $resolv For example, for a field call like `user(name: "Bob")` it would be `['name' => 'Bob']` 3. `GraphQLContext $context`: Arbitrary data that is shared between all fields of a single query. Lighthouse passes in an instance of `Nuwave\Lighthouse\Schema\Context` by default. -4. `ResolveInfo $resolveInfo`: Information about the query itself, such as the execution state, the field name, path to the field from the root, and more. +4. `ResolveInfo $resolveInfo`: Information about the query itself. + Includes execution state, field name, path to the field from the root, and more. The return value of this must fit the return type defined for the corresponding field from the schema. From d44b613158cb010628fcb75a52a98948853a4972 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:55:30 +0100 Subject: [PATCH 21/24] Shorten subscription expiry sentence MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/subscriptions/getting-started.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/master/subscriptions/getting-started.md b/docs/master/subscriptions/getting-started.md index b41c8c2814..ac7ce17432 100644 --- a/docs/master/subscriptions/getting-started.md +++ b/docs/master/subscriptions/getting-started.md @@ -34,7 +34,7 @@ This optimizes performance by sending less data, but clients must anticipate thi Subscriptions do not expire by themselves. Unless you delete a subscription, it will continue to broadcast events after the client has disconnected. -The easiest way to expire subscriptions automatically is to use the env `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to set an expiration time in seconds (e.g. `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` to expire in one hour). +Automate expiry by setting `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to an expiration time in seconds (e.g. `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` to expire in one hour). ## Encrypted Subscriptions From d32f7fb783c9d246292f72126f54c66001f7ff73 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:55:30 +0100 Subject: [PATCH 22/24] Shorten ModelBinding comment MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- src/Bind/ModelBinding.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/Bind/ModelBinding.php b/src/Bind/ModelBinding.php index d2387ed6ee..e611abe1ec 100644 --- a/src/Bind/ModelBinding.php +++ b/src/Bind/ModelBinding.php @@ -33,7 +33,8 @@ public function __invoke(int|string|array $value, BindDefinition $definition): M /** @param \Illuminate\Database\Eloquent\Collection $results */ protected function modelInstance(EloquentCollection $results): ?Model { - // While "too few records" errors are handled as (client-safe) validation errors by applying the `BindingExists` rule on the BindDirective depending on whether the binding is required, "too many records" should be considered as (non-client-safe) configuration errors as it means the binding was not resolved using a unique identifier. + // Too few records are client-safe validation errors, see the `BindingExists` rule in BindDirective. + // Too many records mean the binding does not use a unique identifier, which is a configuration error. if ($results->count() > 1) { throw new MultipleRecordsFoundException($results->count()); } From a2514c1e5e0cde084371538249d8f1e1e4661ea3 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 09:55:30 +0100 Subject: [PATCH 23/24] Remove superlative filler from docs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- docs/master/eloquent/getting-started.md | 2 +- docs/master/security/validation.md | 2 +- docs/master/testing/extensions.md | 2 +- docs/master/testing/phpunit.md | 4 ++-- docs/master/the-basics/fields.md | 4 ++-- 5 files changed, 7 insertions(+), 7 deletions(-) diff --git a/docs/master/eloquent/getting-started.md b/docs/master/eloquent/getting-started.md index 73718d3e7d..0a356707ba 100644 --- a/docs/master/eloquent/getting-started.md +++ b/docs/master/eloquent/getting-started.md @@ -165,7 +165,7 @@ SELECT * FROM `users` WHERE `email_verified_at` IS NOT NULL ## Create -The easiest way to create data on your server is to use the [@create](../api-reference/directives.md#create) directive. +Create data on your server with the [@create](../api-reference/directives.md#create) directive. ```graphql type Mutation { diff --git a/docs/master/security/validation.md b/docs/master/security/validation.md index 92aca7e0d2..c5adfcf910 100644 --- a/docs/master/security/validation.md +++ b/docs/master/security/validation.md @@ -4,7 +4,7 @@ Lighthouse allows you to use [Laravel's validation](https://laravel.com/docs/val ## Single Arguments -The simplest way to leverage the built-in validation rules is to use the [@rules](../api-reference/directives.md#rules) directive. +Apply the built-in validation rules with the [@rules](../api-reference/directives.md#rules) directive. ```graphql type Mutation { diff --git a/docs/master/testing/extensions.md b/docs/master/testing/extensions.md index d9266612e3..405842c9a8 100644 --- a/docs/master/testing/extensions.md +++ b/docs/master/testing/extensions.md @@ -76,7 +76,7 @@ Reverses a string, e.g. 'foo' => 'oof'. directive @reverse on FIELD_DEFINITION | ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -The simplest way to mock a resolver is to have it return static data: +A mock resolver can return static data: ```php public function testReverseField(): void diff --git a/docs/master/testing/phpunit.md b/docs/master/testing/phpunit.md index f13d995df0..e714db227d 100644 --- a/docs/master/testing/phpunit.md +++ b/docs/master/testing/phpunit.md @@ -106,7 +106,7 @@ public function testPostsSubscription(): void Now that we know how to query our server in tests, we need to make sure the returned results match our expectations. -The returned `TestResponse` conveniently offers assertions that work well with the JSON data returned by GraphQL. +The returned `TestResponse` offers assertions that work well with the JSON data returned by GraphQL. The `assertJson` method asserts that the response is a superset of the given JSON. @@ -228,7 +228,7 @@ $spy->shouldNotHaveReceived('broadcast', function (Subscriber $subscriber, $broa ### TestResponse Assertion Mixins -Lighthouse conveniently provides additional assertions as mixins to the `TestResponse` class. +Lighthouse provides additional assertions as mixins to the `TestResponse` class. Make sure to [generate the latest IDE-helper file](../api-reference/commands.md#ide-helper) to get proper autocompletion: ```shell diff --git a/docs/master/the-basics/fields.md b/docs/master/the-basics/fields.md index 0b56bf1d9c..e95254b29f 100644 --- a/docs/master/the-basics/fields.md +++ b/docs/master/the-basics/fields.md @@ -36,7 +36,7 @@ final class Hello } ``` -The easiest way to create such a class is to use the built-in `artisan` commands `lighthouse:query` and `lighthouse:mutation`. +Create such a class with the built-in `artisan` commands `lighthouse:query` and `lighthouse:mutation`. They both take a single argument: the name of the field you want to generate. For example, this is how you generate a class for the field `hello`: @@ -169,7 +169,7 @@ Let's suppose it returns an instance of `App\Model\User`. Next, the field sub-selection will be resolved - the two requested fields are `id` and `name`. Since we already resolved the User in the parent field, we do not want to fetch it again to get its attributes. -Conveniently, the first argument of each resolver is the return value of the parent field, in this case a User model. +The first argument of each resolver is the return value of the parent field, in this case a User model. A naive implementation of a resolver for `id` might look like this: From d24f923b0e2e237c5e73f42beee07f870a4f4834 Mon Sep 17 00:00:00 2001 From: Benedikt Franke Date: Mon, 26 Oct 2026 10:28:16 +0100 Subject: [PATCH 24/24] Split sentences over 150 characters MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 🤖 Generated with Claude Code --- UPGRADE.md | 21 ++++++++----- docs/master/api-reference/commands.md | 3 +- docs/master/api-reference/directives.md | 30 ++++++++++++------- docs/master/api-reference/resolvers.md | 3 +- docs/master/api-reference/scalars.md | 3 +- docs/master/concepts/arg-resolvers.md | 9 ++++-- docs/master/concepts/request-lifecycle.md | 3 +- .../custom-directives/field-directives.md | 6 ++-- .../input-value-directives.md | 18 +++++++---- .../adding-types-programmatically.md | 8 +++-- .../digging-deeper/client-directives.md | 3 +- docs/master/digging-deeper/error-handling.md | 5 ++-- .../digging-deeper/extending-lighthouse.md | 2 +- docs/master/digging-deeper/feature-toggles.md | 8 +++-- docs/master/digging-deeper/ordering.md | 3 +- .../eloquent/complex-where-conditions.md | 6 ++-- docs/master/eloquent/getting-started.md | 6 ++-- docs/master/eloquent/nested-mutations.md | 11 ++++--- docs/master/eloquent/relationships.md | 3 +- docs/master/eloquent/soft-deleting.md | 3 +- docs/master/federation/entities.md | 3 +- .../federation/entity-representations.md | 2 +- docs/master/federation/getting-started.md | 3 +- docs/master/federation/reference-resolvers.md | 11 ++++--- .../migrating-to-lighthouse.md | 3 +- docs/master/performance/n-plus-one.md | 8 +++-- docs/master/performance/query-caching.md | 6 ++-- docs/master/security/authentication.md | 6 ++-- docs/master/security/authorization.md | 5 ++-- docs/master/security/sanitization.md | 6 ++-- docs/master/security/validation.md | 3 +- docs/master/subscriptions/defining-fields.md | 6 ++-- .../subscriptions/filtering-subscriptions.md | 7 +++-- docs/master/subscriptions/getting-started.md | 9 ++++-- docs/master/testing/phpunit.md | 6 ++-- docs/master/testing/rector.md | 6 ++-- docs/master/the-basics/fields.md | 16 ++++++---- src/Bind/BindDirective.php | 2 +- src/Cache/CacheDirective.php | 3 +- src/Execution/Arguments/ArgumentSet.php | 6 ++-- src/Execution/Arguments/SaveModel.php | 3 +- src/Pagination/PaginationArgs.php | 3 +- src/Schema/AST/DocumentAST.php | 3 +- src/Schema/SchemaBuilder.php | 3 +- src/Schema/TypeRegistry.php | 3 +- .../Storage/RedisStorageManager.php | 3 +- .../Contracts/SaveAwareArgResolver.php | 3 +- src/Testing/RefreshesSchemaCache.php | 3 +- src/Validation/BaseRulesDirective.php | 3 +- .../Execution/Arguments/ArgumentSetTest.php | 3 +- 50 files changed, 196 insertions(+), 105 deletions(-) diff --git a/UPGRADE.md b/UPGRADE.md index 7cc056d937..253b6b2763 100644 --- a/UPGRADE.md +++ b/UPGRADE.md @@ -306,7 +306,8 @@ Use `executeQueryString()` for executing a string query or `executeParsedQuery() See https://github.com/webonyx/graphql-php/blob/master/UPGRADE.md#breaking-removed-error-extension-field-category. You can [leverage `GraphQL\Error\ProvidesExtensions`](https://lighthouse-php.com/master/digging-deeper/error-handling.html#additional-error-information) to restore `category` in your custom exceptions. -Additionally, you may [implement a custom error handler](https://lighthouse-php.com/master/digging-deeper/error-handling.html#registering-error-handlers) that wraps well-known third-party exceptions with your own exception that adds an appropriate `category`. +Additionally, you may [implement a custom error handler](https://lighthouse-php.com/master/digging-deeper/error-handling.html#registering-error-handlers) that wraps well-known third-party exceptions with your own exception. +Your exception adds an appropriate `category`. ### Use native interface for errors with extensions @@ -359,7 +360,8 @@ If you had previously depended on the presence of the schema in your cache, then ### Register `ScoutServiceProvider` if you use `@search` -If you use the `@search` directive in your schema, you will now need to register the service provider `Nuwave\Lighthouse\Scout\ScoutServiceProvider`, it is no longer registered by default. +If you use the `@search` directive in your schema, register the service provider `Nuwave\Lighthouse\Scout\ScoutServiceProvider`. +It is no longer registered by default. See [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). ### Update `lighthouse.guard` configuration @@ -432,7 +434,8 @@ type Query { ``` [@guard](docs/master/api-reference/directives.md#guard) does not log in users. -To ensure the user is logged in, add the `AttemptAuthenticate` middleware to your `lighthouse.php` middleware config, see the [default config](src/lighthouse.php) for an example. +To ensure the user is logged in, add the `AttemptAuthenticate` middleware to your `lighthouse.php` middleware config. +See the [default config](src/lighthouse.php) for an example. If you used `@middleware` for authorization, replace it with [@can](docs/master/api-reference/directives.md#can). @@ -571,7 +574,8 @@ This affects custom directives that implemented one of the following interfaces: - `Nuwave\Lighthouse\Support\Contracts\ArgTransformerDirective` - `Nuwave\Lighthouse\Support\Contracts\ArgBuilderDirective` -Whereas those interfaces previously extended `Nuwave\Lighthouse\Support\Contracts\ArgDirective`, you now have to choose if you want them to apply to entire lists of arguments, elements within that list. +Those interfaces previously extended `Nuwave\Lighthouse\Support\Contracts\ArgDirective`. +Now you have to choose if you want them to apply to entire lists of arguments, or to elements within that list. Or both. Change them as follows to make them behave like in v4: @@ -642,13 +646,16 @@ type Mutation { The event is no longer fired, and the event class was removed. Lighthouse now uses a queued job instead. -If you manually fired the event, replace it by queuing a `Nuwave\Lighthouse\Subscriptions\BroadcastSubscriptionJob` or a call to `Nuwave\Lighthouse\Subscriptions\Contracts\BroadcastsSubscriptions::queueBroadcast()`. +If you manually fired the event, queue a `Nuwave\Lighthouse\Subscriptions\BroadcastSubscriptionJob` instead. +Alternatively, call `Nuwave\Lighthouse\Subscriptions\Contracts\BroadcastsSubscriptions::queueBroadcast()`. -In case you depend on an event being fired whenever a subscription is queued, you can bind your own implementation of `Nuwave\Lighthouse\Subscriptions\Contracts\BroadcastsSubscriptions`. +You may depend on an event being fired whenever a subscription is queued. +Then bind your own implementation of `Nuwave\Lighthouse\Subscriptions\Contracts\BroadcastsSubscriptions`. ### `TypeRegistry` does not register duplicates by default -Calling `register()` on the `Nuwave\Lighthouse\Schema\TypeRegistry` now throws when passing a type that was already registered, as this most likely is an error. +Calling `register()` on the `Nuwave\Lighthouse\Schema\TypeRegistry` now throws when passing a type that was already registered. +This is most likely an error. If you want to previous behavior of overwriting existing types, use `overwrite()` instead. diff --git a/docs/master/api-reference/commands.md b/docs/master/api-reference/commands.md index dcb26e2515..12dde2ea61 100644 --- a/docs/master/api-reference/commands.md +++ b/docs/master/api-reference/commands.md @@ -61,7 +61,8 @@ A great way to keep up to date with your current version of Lighthouse is to add ], ``` -If the generated definitions conflict with those provided by your IDE, try `--omit-built-in` to avoid redefining built-in directives such as `@deprecated`. +If the generated definitions conflict with those of your IDE, try `--omit-built-in`. +It avoids redefining built-in directives such as `@deprecated`. ## interface diff --git a/docs/master/api-reference/directives.md b/docs/master/api-reference/directives.md index ae4016b356..b39a3e1e7a 100644 --- a/docs/master/api-reference/directives.md +++ b/docs/master/api-reference/directives.md @@ -371,7 +371,8 @@ You may want to allow accessing data that describes the relation between the mod See [retrieving intermediate table columns in Laravel](https://laravel.com/docs/eloquent-relationships#retrieving-intermediate-table-columns). Like in Laravel, you can access the `pivot` attribute on the models (or its alias). -Even though this attribute is always present when querying the model through the relation, it may not be present when reaching the node through another path in the schema. +This attribute is always present when querying the model through the relation. +It may be missing when reaching the node through another path in the schema. It is recommended to define the field as nullable (no `!`). The following example assumes the intermediate table between `User` and `Role` defines a column `meta`. @@ -417,7 +418,8 @@ type RoleUserPivot { } ``` -When using the `type` argument with pagination style `CONNECTION`, you may create your own [edge type](https://facebook.github.io/relay/graphql/connections.htm#sec-Edge-Types) that either contains the attributes of the intermediate table or contains a `pivot` field with the corresponding type. +When using the `type` argument with pagination style `CONNECTION`, you may create your own [edge type](https://facebook.github.io/relay/graphql/connections.htm#sec-Edge-Types). +It contains either the attributes of the intermediate table or a `pivot` field with the corresponding type. The custom edge type must contain at least the following two fields: @@ -1295,7 +1297,8 @@ type Mutation { } ``` -If the model relates to a single other model through a `HasOne`, `MorphOne`, `BelongsTo` or `MorphTo` relationship, you can pass a Boolean instead of an ID, as there is only one possible model that can be deleted. +For a `HasOne`, `MorphOne`, `BelongsTo` or `MorphTo` relationship to a single other model, you can pass a Boolean instead of an ID. +There is only one possible model to delete. ```graphql type Mutation { @@ -1390,7 +1393,8 @@ enum FeatureState { } ``` -Requires the installation of [Laravel Pennant](https://laravel.com/docs/pennant) and manual registration of the service provider `Nuwave\Lighthouse\Pennant\PennantServiceProvider`, see [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). +Requires the installation of [Laravel Pennant](https://laravel.com/docs/pennant). +Register the service provider `Nuwave\Lighthouse\Pennant\PennantServiceProvider` manually, see [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). ## @field @@ -1420,7 +1424,8 @@ type Mutation { } ``` -You can take advantage of the default namespaces that are defined in the [configuration](../getting-started/configuration.md), The following will look for a class in `App\GraphQL\Queries` by default. +You can take advantage of the default namespaces that are defined in the [configuration](../getting-started/configuration.md). +The following will look for a class in `App\GraphQL\Queries` by default. ```graphql type Query { @@ -1698,7 +1703,8 @@ enum GlobalIdDecode { } ``` -Instead of the original ID, the `id` field will now return a base64-encoded String that globally identifies the User and can be used for querying the `node` endpoint. +Instead of the original ID, the `id` field now returns a base64-encoded String that globally identifies the User. +Clients can use it to query the `node` endpoint. ```graphql type User { @@ -2081,7 +2087,8 @@ type Mutation { } ``` -If you need to inject a value into every element of a list, such as a nested `create` mutation for a `HasMany` relation, use an asterisk `*` as a wildcard path segment. +To inject a value into every element of a list, use an asterisk `*` as a wildcard path segment. +An example is a nested `create` mutation for a `HasMany` relation. ```graphql type Mutation { @@ -3560,7 +3567,8 @@ directive @search( ) on ARGUMENT_DEFINITION | INPUT_FIELD_DEFINITION ``` -Requires the installation of [Laravel Scout](https://laravel.com/docs/scout) and manual registration of the service provider `Nuwave\Lighthouse\Scout\ScoutServiceProvider`, see [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). +Requires the installation of [Laravel Scout](https://laravel.com/docs/scout). +Register the service provider `Nuwave\Lighthouse\Scout\ScoutServiceProvider` manually, see [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). The model `search()` method is called with the argument value. It uses the Scout driver you configured. @@ -3579,7 +3587,8 @@ The [@search](#search) directive only works in combination with filter directive Scout is only activated if an argument annotated with [@search](#search) is present with a string value. Passing `null` behaves the same as leaving the argument out and falls back to a database query. -When using [@convertEmptyStringsToNull](#convertemptystringstonull), nullable `String` arguments with an empty string value may be converted to `null` and therefore not activate Scout. +With [@convertEmptyStringsToNull](#convertemptystringstonull), nullable `String` arguments with an empty string value may become `null`. +Those do not activate Scout. If you need empty-string search behavior, prefer an explicit schema contract such as a dedicated search field or a non-null search argument. Normally the search will be performed using the index specified by the model's `searchableAs` method. @@ -4098,7 +4107,8 @@ input UpsertUserInput { } ``` -For `@upsertMany`, all configured identifying columns must be present with non-null values for every input item, otherwise the upsert fails with a GraphQL error. +For `@upsertMany`, every input item must have non-null values for all configured identifying columns. +Otherwise, the upsert fails with a GraphQL error. ## @validator diff --git a/docs/master/api-reference/resolvers.md b/docs/master/api-reference/resolvers.md index 3c264abdc0..92ba2ba5da 100644 --- a/docs/master/api-reference/resolvers.md +++ b/docs/master/api-reference/resolvers.md @@ -24,7 +24,8 @@ The return value of this must fit the return type defined for the corresponding ## Root resolvers -Root resolvers are classes with an `__invoke` method that sit directly in the configured `lighthouse.namespaces.queries` or `lighthouse.namespaces.mutations` namespaces. +Root resolvers are classes with an `__invoke` method. +They sit directly in the configured `lighthouse.namespaces.queries` or `lighthouse.namespaces.mutations` namespaces. Lighthouse calls them with positional arguments `($root, $args, $context, $resolveInfo)` where `$root` is always `null` for root types. Omitting `$root` causes Lighthouse's positional `null` to bind to `$args`, producing TypeErrors at runtime. diff --git a/docs/master/api-reference/scalars.md b/docs/master/api-reference/scalars.md index f38677a28e..afdbcadf38 100644 --- a/docs/master/api-reference/scalars.md +++ b/docs/master/api-reference/scalars.md @@ -65,4 +65,5 @@ scalar Upload This Scalar can only be used as an argument, not as a return type. For more information, see the [file uploads guide](../digging-deeper/file-uploads.md). -The multipart form request is handled by Lighthouse, the resolver gets passed an instance of [`Illuminate\Http\UploadedFile`](https://laravel.com/api/9.x/Illuminate/Http/UploadedFile.html) in the argument `array $variables`. +Lighthouse handles the multipart form request. +The resolver receives an instance of [`Illuminate\Http\UploadedFile`](https://laravel.com/api/9.x/Illuminate/Http/UploadedFile.html) in the argument `array $variables`. diff --git a/docs/master/concepts/arg-resolvers.md b/docs/master/concepts/arg-resolvers.md index d39fb6d74a..aed36063d9 100644 --- a/docs/master/concepts/arg-resolvers.md +++ b/docs/master/concepts/arg-resolvers.md @@ -5,9 +5,11 @@ To understand the concept behind arg resolvers, you should familiarize yourself ## Motivation Arg resolvers are an extension of the ideas behind GraphQL field execution, applied to input arguments. -Since GraphQL queries can be used to fetch complex and deeply nested data from the client, it is natural to assume that such complex data can also be passed as the input arguments to a query. +Clients can use GraphQL queries to fetch complex and deeply nested data. +So it is natural to assume that clients can also pass such complex data as input arguments to a query. -GraphQL's execution engine allows you to write small and focused field resolver functions that only care about returning the data that it is immediately responsible for. +GraphQL's execution engine lets you write small and focused field resolver functions. +Each one only returns the data it is immediately responsible for. That makes the code much simpler and avoids duplication. However, a single field resolver still has to take care of all the input arguments that are passed to it. @@ -73,7 +75,8 @@ function createTaskWithNotes(mixed $root, array $args): \App\Models\Task { In this contrived example, the function is still small. However, separation of concerns is already violated: A single function is responsible for creating both tasks and notes. -We might want to extend our schema to support more operations in the future, such as updating a task and creating, updating or deleting notes or other, more deeply nested relations. +We might want to extend our schema to support more operations in the future. +For example, updating a task and creating, updating or deleting notes or other, more deeply nested relations. Such changes would force us to duplicate code and increase the complexity of our single function. ## Solution diff --git a/docs/master/concepts/request-lifecycle.md b/docs/master/concepts/request-lifecycle.md index e4f9716ea5..a45c91fb37 100644 --- a/docs/master/concepts/request-lifecycle.md +++ b/docs/master/concepts/request-lifecycle.md @@ -36,7 +36,8 @@ Starting from the root level, the fields within the query are executed. Each field may be wrapped with field middleware, which can add authentication, authorization, fine-grained validation, and more. Finally, the field resolver is called to produce a value for the field. -If the field contains a subselection, the same process happens for the nested fields, until we either abort with an error or traversed the entire query tree. +If the field contains a subselection, the same process happens for the nested fields. +This continues until we either abort with an error or traverse the entire query tree. [Learn more about GraphQL execution](https://graphql.org/learn/execution). diff --git a/docs/master/custom-directives/field-directives.md b/docs/master/custom-directives/field-directives.md index 03a376fb25..550ec39eb8 100644 --- a/docs/master/custom-directives/field-directives.md +++ b/docs/master/custom-directives/field-directives.md @@ -4,7 +4,8 @@ Field directives can be applied to any [FieldDefinition](https://graphql.github. ## FieldResolver -Perhaps the most important directive interface, a [`Nuwave\Lighthouse\Support\Contracts\FieldResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/FieldResolver.php) lets you add a resolver for a field through a directive. +A [`Nuwave\Lighthouse\Support\Contracts\FieldResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/FieldResolver.php) lets you add a resolver for a field through a directive. +It is perhaps the most important directive interface. It can be a great way to reuse resolver logic within a schema. @@ -76,7 +77,8 @@ A [`Nuwave\Lighthouse\Support\Contracts\FieldManipulator`](https://github.com/nu ## ValidationDirective -This directive type is implemented as an abstract class rather than a pure interface and allows you to define complex validation rules for a field with ease. +This directive type is an abstract class rather than a pure interface. +It lets you define complex validation rules for a field. [Read more about it in the Validation section](../security/validation.md#validator-for-fields). diff --git a/docs/master/custom-directives/input-value-directives.md b/docs/master/custom-directives/input-value-directives.md index f837fb9eb0..054de6b286 100644 --- a/docs/master/custom-directives/input-value-directives.md +++ b/docs/master/custom-directives/input-value-directives.md @@ -2,7 +2,8 @@ Some directives can be applied to field arguments or input fields (any [InputValueDefinition](https://graphql.github.io/graphql-spec/June2018/#InputValueDefinition)). -As arguments may be contained within a list in the schema definition, you must specify what your directive should apply to in addition to its function. +Arguments may be contained within a list in the schema definition. +Thus, in addition to its function, you must specify what your directive applies to. - If it applies to the individual items within the list, implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirective`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirective.php) interface. - Else, if it should apply to the whole list, implement the [`Nuwave\Lighthouse\Support\Contracts\ArgDirectiveForArray`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgDirectiveForArray.php) interface. @@ -69,7 +70,8 @@ final class TrimDirective extends BaseDirective implements ArgSanitizerDirective } ``` -The `sanitize` method takes an argument which represents the actual incoming value that is given to an argument in a query and is expected to modify the value, if needed. +The `sanitize` method takes the incoming value that is given to an argument in a query. +It is expected to modify the value, if needed. Return it. For example, if we have the following schema. @@ -109,7 +111,8 @@ Notable differences are: ## ArgBuilderDirective -An [`Nuwave\Lighthouse\Support\Contracts\ArgBuilderDirective`](https://github.com/nuwave/lighthouse/blob/master/src/Support/Contracts/ArgBuilderDirective.php) directive allows using arguments passed by the client to dynamically modify the database query that Lighthouse creates for a field. +An [`Nuwave\Lighthouse\Support\Contracts\ArgBuilderDirective`](https://github.com/nuwave/lighthouse/blob/master/src/Support/Contracts/ArgBuilderDirective.php) directive modifies the database query that Lighthouse creates for a field. +It uses the arguments passed by the client. Currently, the following directives use arguments to modify the query: @@ -196,16 +199,19 @@ input DateRange { ## ArgResolver -An [`Nuwave\Lighthouse\Support\Contracts\ArgResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgResolver.php) directive allows you to compose resolvers for complex nested inputs, similar to the way that field resolvers are composed together. +An [`Nuwave\Lighthouse\Support\Contracts\ArgResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ArgResolver.php) directive lets you compose resolvers for complex nested inputs. +This is similar to the way that field resolvers are composed. For an in-depth explanation of the concept of composing arg resolvers, read the [explanation of arg resolvers](../concepts/arg-resolvers.md). ## SaveAwareArgResolver -A [`Nuwave\Lighthouse\Support\Contracts\SaveAwareArgResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/SaveAwareArgResolver.php) extends `ArgResolver` and allows control over whether the resolver runs before or after the parent model is saved. +A [`Nuwave\Lighthouse\Support\Contracts\SaveAwareArgResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/SaveAwareArgResolver.php) extends `ArgResolver`. +It controls whether the resolver runs before or after the parent model is saved. This is useful when your directive needs to set attributes or foreign keys on the model before it is persisted. -For example, a directive that resolves a BelongsTo relationship must associate the related model before the parent is saved, since the foreign key column may have a NOT NULL constraint. +For example, a directive that resolves a BelongsTo relationship must associate the related model before the parent is saved. +The foreign key column may have a NOT NULL constraint. ```php use Illuminate\Database\Eloquent\Model; diff --git a/docs/master/digging-deeper/adding-types-programmatically.md b/docs/master/digging-deeper/adding-types-programmatically.md index f85484d51c..32af35e41f 100644 --- a/docs/master/digging-deeper/adding-types-programmatically.md +++ b/docs/master/digging-deeper/adding-types-programmatically.md @@ -4,7 +4,8 @@ You might want to add additional types to the schema programmatically. ## Additional Schema Definitions -If you want to use the SDL to define additional types dynamically, you can listen for the [`BuildSchemaString`](../api-reference/events.md#buildschemastring) event and return additional schema definitions as a string: +To define additional types dynamically with SDL, listen for the [`BuildSchemaString`](../api-reference/events.md#buildschemastring) event. +Return additional schema definitions as a string: ```php $dispatcher = app(\Illuminate\Contracts\Events\Dispatcher::class); @@ -16,7 +17,7 @@ $dispatcher->listen( ); ``` -When your schema is defined within files and you want to use `#import` to combine them, you can use the `Nuwave\Lighthouse\Schema\Source\SchemaStitcher` to load your file: +When your schema is split into files that you combine with `#import`, load them with `Nuwave\Lighthouse\Schema\Source\SchemaStitcher`: ```php $stitcher = new \Nuwave\Lighthouse\Schema\Source\SchemaStitcher(__DIR__ . '/path/to/schema.graphql'); @@ -29,7 +30,8 @@ While Lighthouse is an SDL-first GraphQL server, you can also use native PHP typ Check out the [webonyx/graphql-php documentation](https://webonyx.github.io/graphql-php/type-definitions) on how to define types. -You will not have access to a large portion of Lighthouse functionality that is provided through server-side directives and the definition is much more verbose. +You will not have access to a large portion of Lighthouse functionality that is provided through server-side directives. +The definition is also much more verbose. Because of this, we do not recommend you use native PHP types for complex object types. diff --git a/docs/master/digging-deeper/client-directives.md b/docs/master/digging-deeper/client-directives.md index 40bd4207cd..2344331180 100644 --- a/docs/master/digging-deeper/client-directives.md +++ b/docs/master/digging-deeper/client-directives.md @@ -93,7 +93,8 @@ The following example illustrates how a field `foo` can be referenced three time } ``` -You can get all arguments for every node that is referencing the field you are currently resolving, passing the fourth [resolver argument `ResolveInfo $resolveInfo`](../api-reference/resolvers.md#resolver-function-signature): +You can get all arguments for every node that references the field you are resolving. +Pass the fourth [resolver argument `ResolveInfo $resolveInfo`](../api-reference/resolvers.md#resolver-function-signature): ```php $arguments = $clientDirective->forField($resolveInfo); diff --git a/docs/master/digging-deeper/error-handling.md b/docs/master/digging-deeper/error-handling.md index d05b030431..1bcd9c4a25 100644 --- a/docs/master/digging-deeper/error-handling.md +++ b/docs/master/digging-deeper/error-handling.md @@ -17,7 +17,8 @@ Head over their [Error Handling docs](https://webonyx.github.io/graphql-php/erro Lighthouse will catch exceptions thrown during the execution of a query and return them as part of the response. -The error handler `Nuwave\Lighthouse\Execution\ReportingErrorHandler` is included in the default configuration and reports non-client-safe errors through the default Laravel exception handler. +The default configuration includes the error handler `Nuwave\Lighthouse\Execution\ReportingErrorHandler`. +It reports non-client-safe errors through the default Laravel exception handler. Client-safe errors are assumed to be something that: @@ -26,7 +27,7 @@ Client-safe errors are assumed to be something that: Thus, they are typically not actionable for server developers. -However, you can choose to report client-safe errors by replacing `Nuwave\Lighthouse\Execution\ReportingErrorHandler` with `Nuwave\Lighthouse\Execution\AlwaysReportingErrorHandler` in the `lighthouse.php` config: +To also report client-safe errors, replace `Nuwave\Lighthouse\Execution\ReportingErrorHandler` with `Nuwave\Lighthouse\Execution\AlwaysReportingErrorHandler` in the `lighthouse.php` config: ```diff 'error_handlers' => [ diff --git a/docs/master/digging-deeper/extending-lighthouse.md b/docs/master/digging-deeper/extending-lighthouse.md index 98834a5c1e..b30a4f1045 100644 --- a/docs/master/digging-deeper/extending-lighthouse.md +++ b/docs/master/digging-deeper/extending-lighthouse.md @@ -42,7 +42,7 @@ You may override this by calling `GraphQL\Executor\Executor::setDefaultFieldReso The context is the third argument of any resolver function. -You may replace the default `Nuwave\Lighthouse\Schema\Context` with your own implementation of the interface `Nuwave\Lighthouse\Support\Contracts\GraphQLContext`. +You may replace the default `Nuwave\Lighthouse\Schema\Context` with your own implementation of `Nuwave\Lighthouse\Support\Contracts\GraphQLContext`. The following example is only a starting point of what you can do: ```php diff --git a/docs/master/digging-deeper/feature-toggles.md b/docs/master/digging-deeper/feature-toggles.md index b863f5cfba..50b570ed64 100644 --- a/docs/master/digging-deeper/feature-toggles.md +++ b/docs/master/digging-deeper/feature-toggles.md @@ -27,7 +27,7 @@ type Query { ## @feature -The [@feature](../api-reference/directives.md#feature) directive allows to include fields, types, arguments, or input fields in the schema depending on whether a [Laravel Pennant](https://laravel.com/docs/pennant) feature is active. +The [@feature](../api-reference/directives.md#feature) directive allows to include fields, types, arguments, or input fields in the schema if a [Laravel Pennant](https://laravel.com/docs/pennant) feature is active. For example, you might want a new experimental field only to be available when the according feature is active: @@ -73,9 +73,11 @@ type Query { ## Interaction With Schema Cache [@show](../api-reference/directives.md#show) and [@hide](../api-reference/directives.md#hide) work by manipulating the schema. -This means that when using their `env` option, the inclusion or exclusion of elements depends on the value of `app()->environment()` at the time the schema is built and not update on later environment changes. +With their `env` option, the inclusion or exclusion of elements depends on the value of `app()->environment()` at the time the schema is built. +It does not update on later environment changes. If you are pre-generating your schema cache, make sure to match the environment to your deployment target. The same goes for [@feature](../api-reference/directives.md#feature). Whether a field is included in the schema will be based on the state of a feature at the time the schema is built. -In addition, if you are pre-generating your schema cache, you will only be able to use features that support [nullable scopes](https://laravel.com/docs/pennant#nullable-scope), as there won't be an authenticated user to check the feature against. +In addition, if you pre-generate your schema cache, you can only use features that support [nullable scopes](https://laravel.com/docs/pennant#nullable-scope). +There is no authenticated user to check the feature against. diff --git a/docs/master/digging-deeper/ordering.md b/docs/master/digging-deeper/ordering.md index 377d4c972c..a730fbced9 100644 --- a/docs/master/digging-deeper/ordering.md +++ b/docs/master/digging-deeper/ordering.md @@ -10,7 +10,8 @@ type Query { } ``` -The type of the argument can be left blank as `_` , as Lighthouse will automatically generate an input that takes enumerated column names, together with the `SortOrder` enum. +You can leave the type of the argument blank as `_`. +Lighthouse then generates an input that takes enumerated column names, together with the `SortOrder` enum. Add that to your schema: ```graphql diff --git a/docs/master/eloquent/complex-where-conditions.md b/docs/master/eloquent/complex-where-conditions.md index c0b9da11a2..16fe31291d 100644 --- a/docs/master/eloquent/complex-where-conditions.md +++ b/docs/master/eloquent/complex-where-conditions.md @@ -3,7 +3,8 @@ **Experimental: not enabled by default, not guaranteed to be stable.** Adding query conditions ad-hoc can be cumbersome and limiting when you require manifold ways to filter query results. -Lighthouse's `WhereConditions` extension can give advanced query capabilities to clients and allow them to apply complex, dynamic WHERE conditions to queries. +Lighthouse's `WhereConditions` extension gives clients advanced query capabilities. +They can apply complex, dynamic WHERE conditions to queries. ## Setup @@ -16,7 +17,8 @@ return [ ] ``` -For other versions, register the service provider `Nuwave\Lighthouse\WhereConditions\WhereConditionsServiceProvider`, see [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). +For other versions, register the service provider `Nuwave\Lighthouse\WhereConditions\WhereConditionsServiceProvider`. +See [registering providers in Laravel](https://laravel.com/docs/providers#registering-providers). Install the dependency [mll-lab/graphql-php-scalars](https://github.com/mll-lab/graphql-php-scalars): diff --git a/docs/master/eloquent/getting-started.md b/docs/master/eloquent/getting-started.md index 0a356707ba..3a59986b45 100644 --- a/docs/master/eloquent/getting-started.md +++ b/docs/master/eloquent/getting-started.md @@ -26,7 +26,8 @@ type Query { } ``` -The [@all](../api-reference/directives.md#all) directive will assume the name of your model to be the same as the return type of the Field you are trying to resolve and automatically uses Eloquent to resolve the field. +The [@all](../api-reference/directives.md#all) directive assumes that your model has the same name as the return type of the field. +It uses Eloquent to resolve the field. The following query: @@ -262,7 +263,8 @@ type Mutation { } ``` -When using `identifyingColumns`, all configured identifying columns must be provided with non-null values, otherwise the upsert fails with a GraphQL error. +When using `identifyingColumns`, all configured identifying columns must have non-null values. +Otherwise, the upsert fails with a GraphQL error. Since upsert can create or update your data, your input should mark the minimum required fields as non-nullable. diff --git a/docs/master/eloquent/nested-mutations.md b/docs/master/eloquent/nested-mutations.md index 2ebd34ecf1..212f5df27a 100644 --- a/docs/master/eloquent/nested-mutations.md +++ b/docs/master/eloquent/nested-mutations.md @@ -37,7 +37,8 @@ Because the GraphQL Specification does not support polymorphic Input types (yet) It is not possible to have an argument that can contain different types. Would be necessary to pass the attributes the different related models might have. -For now, we can only support cases where the input type does not change across related models, e.g. connecting through an ID, disconnecting or deleting the relation. +For now, we only support cases where the input type does not change across related models. +Examples are connecting through an ID, disconnecting or deleting the relation. See [this issue](https://github.com/nuwave/lighthouse/issues/900) for further discussion. @@ -182,7 +183,8 @@ input UpdateUserBelongsTo { ``` You must pass a truthy value to `disconnect` and `delete` for them to run. -This structure was chosen as it is consistent with updating `BelongsToMany` relationships and allows the query string to be mostly static, taking a variable value to control its behavior. +This structure is consistent with updating `BelongsToMany` relationships. +It allows the query string to be mostly static, with a variable value to control its behavior. ```graphql mutation UpdatePost($disconnectAuthor: Boolean) { @@ -251,7 +253,8 @@ mutation UpdatePost($disconnectAuthor: Boolean) { ## MorphTo -The basic structure of this nested mutation type is similar to [BelongsTo](#belongsto), the main difference being that the `connect` operation requires an input type with both the `id` and `type` of the related model. +The basic structure of this nested mutation type is similar to [BelongsTo](#belongsto). +The main difference is that the `connect` operation requires an input type with both the `id` and `type` of the related model. ```graphql type Task { @@ -685,7 +688,7 @@ type UserMoviePivot { } ``` -Laravel's `sync()`, `syncWithoutDetach()` or `connect()` methods allow you to pass an array where the keys are IDs of related models and the values are pivot data. +Laravel's `sync()`, `syncWithoutDetach()` or `connect()` methods accept an array with IDs of related models as keys and pivot data as values. Lighthouse exposes this capability through the nested operations on many-to-many relations. Instead of passing only a list of IDs, you can define an `input` type that also contains pivot data. diff --git a/docs/master/eloquent/relationships.md b/docs/master/eloquent/relationships.md index 6e69475b68..2053cefdd9 100644 --- a/docs/master/eloquent/relationships.md +++ b/docs/master/eloquent/relationships.md @@ -44,7 +44,8 @@ This means the relationship data is not loaded until you first access the proper This leads to a common performance pitfall that comes with the nested nature of GraphQL queries: the so-called N+1 query problem. [Learn more](../performance/n-plus-one.md). -When you decorate your relationship fields with Lighthouse's built-in relationship directives, queries are automatically combined through a technique called _batch loading_. +When you decorate your relationship fields with Lighthouse's built-in relationship directives, Lighthouse combines their queries. +This technique is called _batch loading_. That means you get fewer database requests and better performance without doing much work. > Batch loading might not provide ideal performance for all use cases. diff --git a/docs/master/eloquent/soft-deleting.md b/docs/master/eloquent/soft-deleting.md index 873d76d195..411b8d1c71 100644 --- a/docs/master/eloquent/soft-deleting.md +++ b/docs/master/eloquent/soft-deleting.md @@ -4,7 +4,8 @@ Lighthouse offers convenient helpers to work with models that use [soft deletes] ## Filter Soft Deleted Models -If your model uses the `Illuminate\Database\Eloquent\SoftDeletes` trait, you can add the [@softDeletes](../api-reference/directives.md#softdeletes) directive to a field to be able to query `onlyTrashed`, `withTrashed` or `withoutTrashed` elements. +If your model uses the `Illuminate\Database\Eloquent\SoftDeletes` trait, add the [@softDeletes](../api-reference/directives.md#softdeletes) directive to a field. +Then you can query `onlyTrashed`, `withTrashed` or `withoutTrashed` elements. ```graphql type Query { diff --git a/docs/master/federation/entities.md b/docs/master/federation/entities.md index dd0da3499c..4006f5b6ec 100644 --- a/docs/master/federation/entities.md +++ b/docs/master/federation/entities.md @@ -6,4 +6,5 @@ For a given `__typename` in the given `$representations`, Lighthouse will look f ## Extends You have to use `@extends` in place of `extend type` to annotate type references. -This is because Lighthouse merges type extensions before the final schema is produced, thus they would not be preserved to appear in the federation schema SDL. +This is because Lighthouse merges type extensions before it produces the final schema. +Thus, they would not appear in the federation schema SDL. diff --git a/docs/master/federation/entity-representations.md b/docs/master/federation/entity-representations.md index a600a5817d..cd9b8f18e5 100644 --- a/docs/master/federation/entity-representations.md +++ b/docs/master/federation/entity-representations.md @@ -28,7 +28,7 @@ type Comment @extends @key(fields: "id") { ## Non-Eloquent representation -If entities don't have an Eloquent relationship within the subgraph, it's necessary to specify a separate resolver that will return the required information. +If entities don't have an Eloquent relationship within the subgraph, specify a separate resolver that returns the required information. The resolver should return data containing information about the `__typename` field. This corresponds to the entity's name and the primary key that can identify the entity. The `__typename` can either be provided as an explicit field or implicitly by returning an object with a matching class name. diff --git a/docs/master/federation/getting-started.md b/docs/master/federation/getting-started.md index 1b07fcc562..8a35b0ce77 100644 --- a/docs/master/federation/getting-started.md +++ b/docs/master/federation/getting-started.md @@ -47,7 +47,8 @@ extend schema ## Federated tracing -In order to use federated tracing, you need to enable [tracing](../performance/tracing.md) and set the driver to `Nuwave\Lighthouse\Tracing\FederatedTracing\FederatedTracing::class` in your `config/lighthouse.php`: +To use federated tracing, enable [tracing](../performance/tracing.md). +Then set the driver to `Nuwave\Lighthouse\Tracing\FederatedTracing\FederatedTracing::class` in your `config/lighthouse.php`: ```php 'tracing' => [ diff --git a/docs/master/federation/reference-resolvers.md b/docs/master/federation/reference-resolvers.md index c2703f0806..217f23a682 100644 --- a/docs/master/federation/reference-resolvers.md +++ b/docs/master/federation/reference-resolvers.md @@ -4,7 +4,7 @@ To enable the current subgraph to provide entities for other subgraphs, you need These reference resolvers act as helpers to enable cross-subgraph communication and provide data from one subgraph to another when needed. Read more about reference resolvers in the [Apollo Federation docs](https://www.apollographql.com/docs/federation/v1/entities#reference-resolvers). -Lighthouse will look for a class which name is equivalent to `__typename` in the namespace configured in `lighthouse.federation.entities_resolver_namespace`. +Lighthouse looks for a class named like `__typename` in the namespace configured in `lighthouse.federation.entities_resolver_namespace`. When you need to retrieve information from subgraphs, the gateway automatically generates a request to the corresponding endpoint of the subgraph. More details about this can be found in section [Query.\_entities of the Apollo Federation docs](https://www.apollographql.com/docs/federation/building-supergraphs/subgraphs-overview#query_entities). @@ -23,7 +23,8 @@ An example of such a request is shown below: ## Single Entity Resolvers -After validating that type `Foo` exists, Lighthouse will look for a resolver class in the namespace configured in `lighthouse.federation.entities_resolver_namespace`. +After validating that type `Foo` exists, Lighthouse looks for a resolver class. +It searches the namespace configured in `lighthouse.federation.entities_resolver_namespace`. The resolver class is expected to contain a method `__invoke()` which takes a single argument: the array form of the representation. ```php @@ -62,7 +63,8 @@ final class Foo ## Batched Entity Resolvers When the client requests a large number of entities with the same type, it can be more efficient to resolve them all at once. -When your entity resolver class implements `Nuwave\Lighthouse\Federation\BatchedEntityResolver`, Lighthouse will call it a single time with an array of all representations of its type. +When your entity resolver class implements `Nuwave\Lighthouse\Federation\BatchedEntityResolver`, Lighthouse calls it once. +It passes an array of all representations of its type. The resolver can then do some kind of batch query to resolve them and return them all at once. ```php @@ -112,7 +114,8 @@ final class Product implements BatchedEntityResolver ## Eloquent Model Resolvers -When no resolver class can be found, Lighthouse will attempt to find the model that matches the type `__typename`, using the namespaces configured in `lighthouse.namespaces.models`. +When no resolver class can be found, Lighthouse tries to find the model that matches the type `__typename`. +It uses the namespaces configured in `lighthouse.namespaces.models`. ```graphql { diff --git a/docs/master/getting-started/migrating-to-lighthouse.md b/docs/master/getting-started/migrating-to-lighthouse.md index ac0bc608d0..38e0000f23 100644 --- a/docs/master/getting-started/migrating-to-lighthouse.md +++ b/docs/master/getting-started/migrating-to-lighthouse.md @@ -20,7 +20,8 @@ Sometimes, additional annotations or a PHP implementation is required. ## Resolver logic -If you are coming from libraries such as [Folkloreatelier/laravel-graphql](https://github.com/Folkloreatelier/laravel-graphql), [rebing/laravel-graphql](https://github.com/rebing/graphql-laravel) or any other library that is originally based upon [webonyx/graphql-php](https://github.com/webonyx/graphql-php), you should be able to reuse much of your existing code. +Many libraries are based upon [webonyx/graphql-php](https://github.com/webonyx/graphql-php), such as [Folkloreatelier/laravel-graphql](https://github.com/Folkloreatelier/laravel-graphql) and [rebing/laravel-graphql](https://github.com/rebing/graphql-laravel). +If you are coming from one of them, you should be able to reuse much of your existing code. You can also register your existing types within Lighthouse's type registry, so you won't have to rewrite them in SDL. [Use native PHP types](../digging-deeper/adding-types-programmatically.md#native-php-types). diff --git a/docs/master/performance/n-plus-one.md b/docs/master/performance/n-plus-one.md index 3c61d7d272..b40aaccda9 100644 --- a/docs/master/performance/n-plus-one.md +++ b/docs/master/performance/n-plus-one.md @@ -22,7 +22,8 @@ The associated author for each post would be lazily loaded, querying the databas When dealing with Laravel relationships, [eager loading](https://laravel.com/docs/eloquent-relationships#eager-loading) is commonly used to alleviate the N+1 query problem. -You can leverage eager loading by informing Lighthouse of the relationships between your models, using directives such as [@belongsTo](../api-reference/directives.md#belongsto), [@hasMany](../api-reference/directives.md#hasmany) and [@with](../api-reference/directives.md#with). +Lighthouse can use eager loading when you tell it about the relationships between your models. +Use directives such as [@belongsTo](../api-reference/directives.md#belongsto), [@hasMany](../api-reference/directives.md#hasmany) and [@with](../api-reference/directives.md#with). ```graphql type Post { @@ -71,7 +72,7 @@ Since we have multiple users, `User.posts` would be resolved multiple times in t We want to have a batch loader for `User.posts`, since it loads posts from a third party and the call to fetch them is slow when run sequentially. This is assuming the posts service offers a method to query posts for multiple users in one call. -In order for Lighthouse to perform batch loading, it needs to group fields that are on the same level in the query tree, but nested under different indices. +To perform batch loading, Lighthouse groups fields that are on the same level in the query tree, but nested under different indices. When looking at the query path from `posts`, they may look like: - `users.0.posts` @@ -98,7 +99,8 @@ function (User $user, array $args, GraphQLContext $context, ResolveInfo $resolve } ``` -The implementation of `UserPostsBatchLoader` is up to you, the only important thing is that the resolver returns an instance of `GraphQL\Deferred`, see [webonyx/graphql-php docs](https://webonyx.github.io/graphql-php/data-fetching/#solving-n1-problem). +The implementation of `UserPostsBatchLoader` is up to you. +The resolver must return an instance of `GraphQL\Deferred`, see [webonyx/graphql-php docs](https://webonyx.github.io/graphql-php/data-fetching/#solving-n1-problem). The following example illustrates some common patterns that may be found in a batch loader implementation: ```php diff --git a/docs/master/performance/query-caching.md b/docs/master/performance/query-caching.md index d79910cafb..1ccdc6bf0e 100644 --- a/docs/master/performance/query-caching.md +++ b/docs/master/performance/query-caching.md @@ -42,7 +42,8 @@ In some scenarios, you may need to clear the query cache completely. The Artisan command works based on your current configuration for `query_cache` in `config/lighthouse.php`. -- When using the modes [`store`](#mode-store) or [`hybrid`](#mode-hybrid), all entries in the configured cache store will be removed regardless of their age or whether they even belong to Lighthouse. +- When using the modes [`store`](#mode-store) or [`hybrid`](#mode-hybrid), the command removes all entries in the configured cache store. + That includes entries of any age and entries that do not belong to Lighthouse. - When using the modes [`opcache`](#mode-opcache) or [`hybrid`](#mode-hybrid), all cached query files will be removed. When you plan to change `query_cache.mode`, clear your cache while your current configuration is still in place. @@ -74,7 +75,8 @@ You can enable it by setting `validation_cache.enable` to `true` in `config/ligh ## Testing caveats -If you are mocking Laravel cache classes like `Illuminate\Support\Facades\Cache` or `Illuminate\Cache\Repository` and asserting expectations in your unit tests, it might be best to disable the query cache in your `phpunit.xml`: +Your unit tests might mock Laravel cache classes like `Illuminate\Support\Facades\Cache` or `Illuminate\Cache\Repository` and assert expectations. +In that case, it might be best to disable the query cache in your `phpunit.xml`: ```diff diff --git a/docs/master/security/authentication.md b/docs/master/security/authentication.md index 9d37c69fc9..ae0e9edd0e 100644 --- a/docs/master/security/authentication.md +++ b/docs/master/security/authentication.md @@ -4,7 +4,8 @@ You can use [standard Laravel mechanisms](https://laravel.com/docs/authenticatio ## AttemptAuthentication middleware -As all GraphQL requests are served at a single HTTP endpoint, middleware added through the `lighthouse.php` config will run for all queries against your server. +All GraphQL requests are served at a single HTTP endpoint. +Thus, middleware added through the `lighthouse.php` config runs for all queries against your server. In most cases, your schema will have some publicly accessible fields and others that require authentication. As multiple checks for authentication or permissions may be required in a single request, it is convenient to attempt authentication once per request. @@ -45,7 +46,8 @@ Stateless guards are recommended for most use cases, such as the default `api` g ### Laravel Sanctum -If you are using [Laravel Sanctum](https://laravel.com/docs/sanctum) for your API, set the guard to `sanctum` and register Sanctum's `EnsureFrontendRequestsAreStateful` as the first middleware for Lighthouse's route. +If you are using [Laravel Sanctum](https://laravel.com/docs/sanctum) for your API, set the guard to `sanctum`. +Then register Sanctum's `EnsureFrontendRequestsAreStateful` as the first middleware for Lighthouse's route. ```php 'route' => [ diff --git a/docs/master/security/authorization.md b/docs/master/security/authorization.md index 41ea2cdab7..0108e04270 100644 --- a/docs/master/security/authorization.md +++ b/docs/master/security/authorization.md @@ -3,7 +3,8 @@ Not every user in your application may be allowed to see all data or do any action. You can control what they can do by enforcing authorization rules. -Before you can apply authorization, make sure you cover [authentication](authentication.md) first - it's a prerequisite to have your users logged in before checking what they can do. +Before you apply authorization, cover [authentication](authentication.md) first. +Your users must be logged in before you check what they can do. ## Use the Viewer pattern @@ -203,7 +204,7 @@ final class PostPolicy } ``` -When you combine both ways of passing arguments, the policy will be passed the `injectArgs` as the second parameter and the static `args` as the third parameter: +When you combine both ways, the policy receives `injectArgs` as the second parameter and the static `args` as the third: ```php final class PostPolicy diff --git a/docs/master/security/sanitization.md b/docs/master/security/sanitization.md index 0e4aa0343a..6768dc72ad 100644 --- a/docs/master/security/sanitization.md +++ b/docs/master/security/sanitization.md @@ -1,7 +1,8 @@ # Sanitization When dealing with user input, you need to make sure the given data is valid. -While [validation](validation) is a great first line of defense, there are cases where it is most practical to modify the given input to ensure it is valid or safe to use. +[Validation](validation) is a great first line of defense. +In some cases, it is most practical to modify the given input to ensure it is valid or safe to use. ## Single arguments @@ -18,4 +19,5 @@ type Mutation { ## Complex arguments -When you need to look at multiple input fields in order to run sanitization, you can use a [`FieldMiddlewareDirective`](../custom-directives/field-directives.md#fieldmiddleware) to transform the given inputs before passing them along to the final resolver. +When sanitization needs to look at multiple input fields, use a [`FieldMiddlewareDirective`](../custom-directives/field-directives.md#fieldmiddleware). +It can transform the given inputs before passing them along to the final resolver. diff --git a/docs/master/security/validation.md b/docs/master/security/validation.md index c5adfcf910..f51971f6b1 100644 --- a/docs/master/security/validation.md +++ b/docs/master/security/validation.md @@ -311,7 +311,8 @@ type Mutation { By default, Lighthouse enables all default query validation rules from `webonyx/graphql-php`. This covers fundamental checks, e.g. queried fields match the schema, variables have values of the correct type. -If you want to add custom rules or change which ones are used, you can bind a custom implementation of the interface `Nuwave\Lighthouse\Support\Contracts\ProvidesCacheableValidationRules` through a service provider. +To add custom rules or change which ones are used, implement the interface `Nuwave\Lighthouse\Support\Contracts\ProvidesCacheableValidationRules`. +Bind your implementation through a service provider. ```php use Nuwave\Lighthouse\Support\Contracts\ProvidesValidationRules; diff --git a/docs/master/subscriptions/defining-fields.md b/docs/master/subscriptions/defining-fields.md index 6436a0ba25..7c81c894ac 100644 --- a/docs/master/subscriptions/defining-fields.md +++ b/docs/master/subscriptions/defining-fields.md @@ -17,7 +17,8 @@ php artisan lighthouse:subscription PostUpdated Lighthouse will look for a class matching the capitalized name of the field within the default subscription namespace. For example, the field `postUpdated` should have a corresponding class at `App\GraphQL\Subscriptions\PostUpdated`. -All subscription field classes **must** implement the abstract class `Nuwave\Lighthouse\Schema\Types\GraphQLSubscription` and implement the two methods `authorize` and `filter`. +All subscription field classes **must** extend the abstract class `Nuwave\Lighthouse\Schema\Types\GraphQLSubscription`. +They implement the two methods `authorize` and `filter`. ```php namespace App\GraphQL\Subscriptions; @@ -82,4 +83,5 @@ final class PostUpdated extends GraphQLSubscription } ``` -If the default namespaces are not working with your application structure or you want to be more explicit, you can use the [@subscription](../api-reference/directives.md#subscription) directive to point to a different class. +If the default namespaces do not fit your application structure, or you want to be more explicit, use the [@subscription](../api-reference/directives.md#subscription) directive. +It points to a different class. diff --git a/docs/master/subscriptions/filtering-subscriptions.md b/docs/master/subscriptions/filtering-subscriptions.md index e3db7a70c6..8e980fe50f 100644 --- a/docs/master/subscriptions/filtering-subscriptions.md +++ b/docs/master/subscriptions/filtering-subscriptions.md @@ -37,7 +37,7 @@ final class PostUpdatedSubscription extends GraphQLSubscription ## Only To Others -When building an application that uses event broadcasting, you may occasionally need to broadcast an event to all subscribers of a channel except for the current user. +An application that uses event broadcasting may need to broadcast an event to all subscribers of a channel except the current user. You may accomplish this using the filter function, this following snippet is equivalent to [the `toOthers()` method from Laravel's broadcast helper](https://laravel.com/docs/9.x/broadcasting#only-to-others). ```php @@ -60,10 +60,11 @@ final class PostUpdatedSubscription extends GraphQLSubscription ``` When you initialize a Laravel Echo instance, a socket ID is assigned to the connection. -If you are using a global [Axios](https://github.com/mzabriskie/axios) instance to make HTTP requests from your JavaScript application, the socket ID will automatically be attached to every outgoing request in the `X-Socket-ID` header. +If your JavaScript application uses a global [Axios](https://github.com/mzabriskie/axios) instance for HTTP requests, the socket ID is attached to every outgoing request. +It is sent in the `X-Socket-ID` header. Then, you can access that in your filter function. -If you are not using a global Axios instance, you will need to manually configure your JavaScript application to send the `X-Socket-ID` header with all outgoing requests. +Without a global Axios instance, configure your JavaScript application to send the `X-Socket-ID` header with all outgoing requests. You may retrieve the socket ID using the `Echo.socketId()` method: ```js diff --git a/docs/master/subscriptions/getting-started.md b/docs/master/subscriptions/getting-started.md index ac7ce17432..f1cd9dc850 100644 --- a/docs/master/subscriptions/getting-started.md +++ b/docs/master/subscriptions/getting-started.md @@ -26,7 +26,8 @@ When using subscriptions with [Laravel Octane](https://laravel.com/docs/octane), ### Empty Response Optimization Lighthouse returns the subscription channel as part of the response under `extensions`. -If `subscriptions.exclude_empty` in `lighthouse.php` is set to `true`, API responses without a subscription channel will not contain `lighthouse_subscriptions` in `extensions`. +Set `subscriptions.exclude_empty` in `lighthouse.php` to `true` to change this. +Then responses without a subscription channel omit `lighthouse_subscriptions` from `extensions`. This optimizes performance by sending less data, but clients must anticipate this appropriately. ## Expiring Subscriptions @@ -34,7 +35,8 @@ This optimizes performance by sending less data, but clients must anticipate thi Subscriptions do not expire by themselves. Unless you delete a subscription, it will continue to broadcast events after the client has disconnected. -Automate expiry by setting `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to an expiration time in seconds (e.g. `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` to expire in one hour). +Automate expiry by setting `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL` to an expiration time in seconds. +For example, `LIGHTHOUSE_SUBSCRIPTION_STORAGE_TTL=3600` expires subscriptions after one hour. ## Encrypted Subscriptions @@ -58,7 +60,8 @@ More details on how to enable encryption are defined in the [Pusher documentatio ### Pusher Expiration Webhook If you are using the Pusher driver, you can use a [`channel existence`](https://pusher.com/docs/channels/server_api/webhooks/#channel-existence-events) webhook to mitigate this problem. -When a Pusher channel is vacated (i.e. there are no subscribers), it will trigger the webhook, which will instruct Lighthouse to delete the subscription. +When a Pusher channel is vacated (i.e. there are no subscribers), it triggers the webhook. +The webhook instructs Lighthouse to delete the subscription. The webhook URL will typically be: diff --git a/docs/master/testing/phpunit.md b/docs/master/testing/phpunit.md index e714db227d..3a0a825a05 100644 --- a/docs/master/testing/phpunit.md +++ b/docs/master/testing/phpunit.md @@ -251,9 +251,11 @@ $this ## Testing Errors -Depending on your debug and error handling configuration, Lighthouse catches most if not all errors produced within queries and includes them within the result. +Depending on your debug and error handling configuration, Lighthouse catches most if not all errors produced within queries. +It includes them in the result. -One way to test for errors is to examine the `TestResponse`, either by looking at the JSON response manually or by using the provided [assertion mixins](#testresponse-assertion-mixins) such as `assertGraphQLErrorMessage()`: +One way to test for errors is to examine the `TestResponse`. +Look at the JSON response manually or use the provided [assertion mixins](#testresponse-assertion-mixins) such as `assertGraphQLErrorMessage()`: ```php $this diff --git a/docs/master/testing/rector.md b/docs/master/testing/rector.md index fc2b3d1728..bcff2461a5 100644 --- a/docs/master/testing/rector.md +++ b/docs/master/testing/rector.md @@ -84,9 +84,11 @@ $rectorConfig->ruleWithConfiguration(RootResolverSignatureRector::class, [ ### Known Limitation -The rule assumes every class with an `__invoke` method found under the resolver directories (e.g. `App\GraphQL\Queries`, `App\GraphQL\Mutations`) is a root resolver. +The rule assumes that every class with an `__invoke` method in the resolver directories is a root resolver. +Examples of those directories are `App\GraphQL\Queries` and `App\GraphQL\Mutations`. -Classes that are **not** root resolvers — such as nested field resolvers that receive a parent model as their first argument — will be incorrectly rewritten. +The rule incorrectly rewrites classes that are **not** root resolvers. +Examples are nested field resolvers that receive a parent model as their first argument. **Mitigations:** diff --git a/docs/master/the-basics/fields.md b/docs/master/the-basics/fields.md index e95254b29f..11512278a2 100644 --- a/docs/master/the-basics/fields.md +++ b/docs/master/the-basics/fields.md @@ -20,7 +20,8 @@ type Query { This defines the shape of our data and informs the client what they can expect. You need to implement the actual resolver next. -By default, Lighthouse looks for a class with the capitalized name of the field in `App\GraphQL\Queries` or `App\GraphQL\Mutations` and calls its `__invoke` function with [the usual resolver arguments](../api-reference/resolvers.md#resolver-function-signature). +By default, Lighthouse looks for a class with the capitalized name of the field in `App\GraphQL\Queries` or `App\GraphQL\Mutations`. +It calls its `__invoke` function with [the usual resolver arguments](../api-reference/resolvers.md#resolver-function-signature). In this case, our field is a query and is called `hello`, so we need to define our class as follows: @@ -202,7 +203,8 @@ It works well with the data you would typically return from a root resolver, e.g This means that in most cases, you will only have to provide resolvers for the root fields and make sure they return data in the proper shape. -If you need to implement custom resolvers for fields that are not on one of the root types `Query` or `Mutation`, you can create a resolver class using the built-in `artisan` command `lighthouse:field`. +Fields that are not on the root types `Query` or `Mutation` may need custom resolvers. +Create a resolver class for them with the `artisan` command `lighthouse:field`. For example, this is how you generate a class for the field `name` on type `User`: ```shell @@ -216,8 +218,8 @@ Lighthouse uses the following logic to locate field resolvers. First, it checks if the field definition in the schema is annotated with a [FieldResolver](../custom-directives/field-directives.md#fieldresolver) directive. If so, it uses the resolver provided by the directive. -The interface [`Nuwave\Lighthouse\Support\Contracts\ProvidesResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ProvidesResolver.php) is expected to provide a resolver in case no resolver directive is defined for a field. -When the field is defined on the root `Subscription` type, the [`Nuwave\Lighthouse\Support\Contracts\ProvidesSubscriptionResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ProvidesSubscriptionResolver.php) interface is used instead. +The interface [`Nuwave\Lighthouse\Support\Contracts\ProvidesResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ProvidesResolver.php) provides a resolver when a field has no resolver directive. +On the root `Subscription` type, the [`Nuwave\Lighthouse\Support\Contracts\ProvidesSubscriptionResolver`](https://github.com/nuwave/lighthouse/tree/master/src/Support/Contracts/ProvidesSubscriptionResolver.php) interface is used instead. The default implementation of those interfaces check if there is a class that matches the capitalized name of the field. Defines a method `__invoke`, in one of the configured default namespaces, depending on the parent type the field is a part of. @@ -229,11 +231,13 @@ Defines a method `__invoke`, in one of the configured default namespaces, depend | `Subscription` | `lighthouse.namespaces.subscriptions` | | Any other type | `lighthouse.namespaces.types` | -For example, given `lighthouse.namespaces.queries` is defined as `'App\GraphQL\Queries'` and the field `Query.users`, Lighthouse would expect a resolver class `App\GraphQL\Queries\User`. +For example, take `lighthouse.namespaces.queries` defined as `'App\GraphQL\Queries'` and the field `Query.users`. +Lighthouse expects a resolver class `App\GraphQL\Queries\Users`. If there are multiple namespaces, they are checked in order and the first found class is used. Non-root types are combined with the configured namespaces. -For example, given `lighthouse.namespaces.types` is defined as `['App\GraphQL\Types', 'MyModule\GraphQL\Types']` and the field `User.name`, Lighthouse would look for the resolver class `App\GraphQL\Types\User\Name`, then `MyModule\GraphQL\Types\User\Name`. +For example, take `lighthouse.namespaces.types` defined as `['App\GraphQL\Types', 'MyModule\GraphQL\Types']` and the field `User.name`. +Lighthouse looks for the resolver class `App\GraphQL\Types\User\Name`, then `MyModule\GraphQL\Types\User\Name`. Resolvers for root fields are mandatory, Lighthouse will throw during schema validation if a root field has no resolver. Non-root fields fall back to [webonyx's default resolver](https://webonyx.github.io/graphql-php/data-fetching/#default-field-resolver). diff --git a/src/Bind/BindDirective.php b/src/Bind/BindDirective.php index 31b6a04bb4..2a2fbb9f2c 100644 --- a/src/Bind/BindDirective.php +++ b/src/Bind/BindDirective.php @@ -117,7 +117,7 @@ public function attribute(): ?string public function transform(mixed $argumentValue): mixed { - // When validating required bindings, the \Nuwave\Lighthouse\Bind\Validation\BindingExists validation rule should call transform() before it is called by the directive resolver. + // When validating required bindings, the \Nuwave\Lighthouse\Bind\Validation\BindingExists rule calls transform() before the directive resolver does. // To avoid resolving the bindings multiple times, we should remember the resolved binding and reuse it every time transform() is called. if (! $this->binding instanceof PendingBinding) { return $this->binding; diff --git a/src/Cache/CacheDirective.php b/src/Cache/CacheDirective.php index 76e61fbff8..923d7e82ac 100644 --- a/src/Cache/CacheDirective.php +++ b/src/Cache/CacheDirective.php @@ -101,7 +101,8 @@ public function handleField(FieldValue $fieldValue): void // return $value['rawValue']; // } // - // Such a change would introduce some potential BC, if for instance cached value was already containing an object with a `rawValue` key prior the implementation change. + // Such a change could break backwards compatibility. + // For instance, a value cached before the change might already contain an object with a `rawValue` key. // A possible workaround is to choose a less collision-probable key instead of `rawValue` (e.g. "lighthouse:rawValue"). $resolved = $resolver($root, $args, $context, $resolveInfo); diff --git a/src/Execution/Arguments/ArgumentSet.php b/src/Execution/Arguments/ArgumentSet.php index 35f25b5bb9..03cb7e89f9 100644 --- a/src/Execution/Arguments/ArgumentSet.php +++ b/src/Execution/Arguments/ArgumentSet.php @@ -69,7 +69,8 @@ public function exists(string $key): bool /** * Add a value at the dot-separated path. * - * Works like @see \Illuminate\Support\Arr::add(), but a path segment of `*` injects the value into every element of the list found at that position instead of a single key. + * Works like @see \Illuminate\Support\Arr::add(). + * A path segment of `*` injects the value into every element of the list at that position, instead of a single key. */ public function addValue(string $path, mixed $value): self { @@ -106,7 +107,8 @@ private function addValueAtKeys(array $keys, mixed $value): void return; } - // If the key doesn't exist at this depth, we will create an empty ArgumentSet to hold the next value, allowing us to create the ArgumentSet to hold a final value at the correct depth. + // If the key doesn't exist at this depth, we create an empty ArgumentSet to hold the next value. + // This lets us create the ArgumentSet for the final value at the correct depth. // Then we'll keep digging into the ArgumentSet. if (! isset($this->arguments[$key])) { $argument = new Argument(); diff --git a/src/Execution/Arguments/SaveModel.php b/src/Execution/Arguments/SaveModel.php index 2ee14b3ec9..41827b2cc9 100644 --- a/src/Execution/Arguments/SaveModel.php +++ b/src/Execution/Arguments/SaveModel.php @@ -96,7 +96,8 @@ public function __invoke($model, $args): Model if ($this->parentRelation instanceof BelongsTo) { $childModel = $this->parentRelation->associate($model); - // If the child Model does not exist (still to be saved), a save could break any pending belongsTo relations that still need to be created and associated with it. + // If the child Model does not exist yet, saving it could break pending belongsTo relations. + // Those still need to be created and associated with it. if ($childModel->exists) { $childModel->save(); } diff --git a/src/Pagination/PaginationArgs.php b/src/Pagination/PaginationArgs.php index 812a93cb4a..9fed10633f 100644 --- a/src/Pagination/PaginationArgs.php +++ b/src/Pagination/PaginationArgs.php @@ -81,7 +81,8 @@ protected static function optimalPaginationType(PaginationType $proposedType, Re } // If the result may be used in a cache, we always want to retrieve and store the full pagination data. - // Even though the query that initially creates the cache may not need additional information such as the total counts, following queries may need them - and use the same cached value. + // The query that creates the cache may not need additional information such as the total counts. + // Following queries may need them and use the same cached value. $hasCacheDirective = $resolveInfo->argumentSet ->directives ->contains(static fn (Directive $directive): bool => $directive instanceof CacheDirective); diff --git a/src/Schema/AST/DocumentAST.php b/src/Schema/AST/DocumentAST.php index 602ac851f0..d393506643 100644 --- a/src/Schema/AST/DocumentAST.php +++ b/src/Schema/AST/DocumentAST.php @@ -135,7 +135,8 @@ public static function fromSource(string $schema): self throw new DefinitionException("Failed to find a model class {$modelName} in namespaces [{$consideredNamespaces}] referenced in @model on type {$name}."); } - // It might be valid to have multiple types that correspond to a single model in order to hide some fields in some scenarios, so we cannot decide on a single object type for a given class name unambiguously right here. + // Multiple types may correspond to a single model, e.g. to hide some fields in some scenarios. + // So we cannot pick a single object type for a given class name here. $instance->classNameToObjectTypeNames[$modelClass][] = $name; } } elseif ($definition instanceof TypeExtensionNode) { diff --git a/src/Schema/SchemaBuilder.php b/src/Schema/SchemaBuilder.php index f0ac2dcb7b..ecce25bec1 100644 --- a/src/Schema/SchemaBuilder.php +++ b/src/Schema/SchemaBuilder.php @@ -69,7 +69,8 @@ protected function build(DocumentAST $documentAST): Schema fn (): array => $this->typeRegistry->possibleTypes(), ); - // Passing scalar overrides explicitly prevents the first lookup of a built-in scalar from discovering them by resolving the lazy types callable, which would eagerly build every type in the schema, see https://github.com/nuwave/lighthouse/issues/2771. + // Passing scalar overrides explicitly keeps the first lookup of a built-in scalar from resolving the lazy types callable. + // That would eagerly build every type in the schema, see https://github.com/nuwave/lighthouse/issues/2771. // TODO remove this check when the minimum version of webonyx/graphql-php includes the method if (method_exists($config, 'setScalarOverrides')) { // @phpstan-ignore function.alreadyNarrowedType (backward compatibility with webonyx/graphql-php < 15.31) $config->setScalarOverrides($this->typeRegistry->scalarOverrides()); diff --git a/src/Schema/TypeRegistry.php b/src/Schema/TypeRegistry.php index 9c719cf519..4f6a6bb37b 100644 --- a/src/Schema/TypeRegistry.php +++ b/src/Schema/TypeRegistry.php @@ -219,7 +219,8 @@ public function overwriteLazy(string $name, callable $type): self */ public function possibleTypes(): array { - // Make sure all the types from the AST are eagerly converted to find orphaned types, such as an object type that is only ever used through its association to an interface. + // Eagerly convert all types from the AST to find orphaned types. + // An example is an object type that is only ever used through its interface. foreach ($this->documentAST->types as $typeDefinition) { $name = $typeDefinition->getName()->value; diff --git a/src/Subscriptions/Storage/RedisStorageManager.php b/src/Subscriptions/Storage/RedisStorageManager.php index ca2b839228..5c5979fa99 100644 --- a/src/Subscriptions/Storage/RedisStorageManager.php +++ b/src/Subscriptions/Storage/RedisStorageManager.php @@ -115,7 +115,8 @@ public function storeSubscriber(Subscriber $subscriber, string $topic): void $subscriber->topic = $topic; // In contrast to the CacheStorageManager, we use redis sets. - // Instead of reading the entire list, adding the subscriber, and storing the list; we add the name of the subscriber to the set of subscribers of this topic using the sadd command... + // We do not read the entire list, add the subscriber and store the list. + // Instead, we add the name of the subscriber to the set of subscribers of this topic using the sadd command... $topicKey = $this->topicKey($topic); $this->connection->command('sadd', [ $topicKey, diff --git a/src/Support/Contracts/SaveAwareArgResolver.php b/src/Support/Contracts/SaveAwareArgResolver.php index 084b684cb5..49e1426dd9 100644 --- a/src/Support/Contracts/SaveAwareArgResolver.php +++ b/src/Support/Contracts/SaveAwareArgResolver.php @@ -23,7 +23,8 @@ interface SaveAwareArgResolver extends ArgResolver * Only consulted when the root is a Model. * In non-Model contexts, this method is not called and the resolver executes normally. * - * Implementations must base the decision on the model class and its relations, not on instance state — the model may not yet be hydrated when this is called. + * Implementations must base the decision on the model class and its relations, not on instance state. + * The model may not yet be hydrated when this is called. */ public function runBeforeSave(Model $model): bool; } diff --git a/src/Testing/RefreshesSchemaCache.php b/src/Testing/RefreshesSchemaCache.php index 0ae1d7832c..ab8e516339 100644 --- a/src/Testing/RefreshesSchemaCache.php +++ b/src/Testing/RefreshesSchemaCache.php @@ -27,7 +27,8 @@ trait RefreshesSchemaCache protected function refreshSchemaCache(): void { if (! static::$schemaCacheWasRefreshed) { - // We use the filesystem as shared mutable state to coordinate between processes, since the tests might be run in parallel, and we want to ensure the schema cache is refreshed exactly once before all tests. + // Tests might run in parallel, so we coordinate processes through the filesystem. + // This refreshes the schema cache exactly once before all tests. \Safe\touch(self::$lockFilePath); $lockFile = \Safe\fopen(self::$lockFilePath, 'r'); diff --git a/src/Validation/BaseRulesDirective.php b/src/Validation/BaseRulesDirective.php index ed7e45bb4e..e859125120 100644 --- a/src/Validation/BaseRulesDirective.php +++ b/src/Validation/BaseRulesDirective.php @@ -22,7 +22,8 @@ public function rules(): array // Custom rules may be referenced through their fully qualified class name. // The Laravel validator expects a class instance to be passed, so we resolve any given rule where a corresponding class exists. - // Requiring a namespace separator keeps built-in rules such as `url` or `image` from matching global classes or facade aliases, as class names are case-insensitive. + // Requiring a namespace separator keeps built-in rules such as `url` or `image` from matching global classes or facade aliases. + // This matters because class names are case-insensitive. foreach ($rules as $key => $rule) { if (str_contains($rule, '\\') && class_exists($rule)) { $rules[$key] = Container::getInstance()->make($rule); diff --git a/tests/Unit/Execution/Arguments/ArgumentSetTest.php b/tests/Unit/Execution/Arguments/ArgumentSetTest.php index 9b0e546b2e..dd7b5bf3c3 100644 --- a/tests/Unit/Execution/Arguments/ArgumentSetTest.php +++ b/tests/Unit/Execution/Arguments/ArgumentSetTest.php @@ -185,7 +185,8 @@ public function testAddValueWithWildcardSkipsWhenNestedContainerIsMissing(): voi $set = new ArgumentSet(); $set->addValue('tasks.create.*.user_id', 123); - // The intermediary `tasks` input is created just like plain dot notation would, but nothing is injected because `create` was never provided by the client. + // The intermediary `tasks` input is created like plain dot notation would. + // Nothing is injected, because the client never provided `create`. $this->assertTrue($set->exists('tasks')); $tasks = $set->arguments['tasks']->value;