Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Graphql Laravel Laravel Package

rebing/graphql-laravel

Code-first GraphQL integration for Laravel built on webonyx/graphql-php. Define schemas, types, queries and mutations in PHP with support for multiple schemas, middleware, resolver middleware, privacy rules, and n+1 avoidance via dataloaders or SelectFields.

View on GitHub
Deep Wiki
Context7
## Getting Started

### Minimal Steps to First Query (Updated for RC4)
1. **Installation**:
   ```bash
   composer require rebing/graphql-laravel
   php artisan vendor:publish --provider="Rebing\GraphQL\GraphQLServiceProvider"

Review config/graphql.php for updated default settings (e.g., batching.default = false).

  1. Install SelectFields Package (Required for Eloquent Optimization):

    composer require rebing/graphql-laravel-select-fields
    
  2. Generate a Type:

    php artisan make:graphql:type UserType
    

    Edit app/GraphQL/Types/UserType.php:

    public function fields(): array {
        return [
            'id' => ['type' => Type::nonNull(Type::int())],
            'name' => ['type' => Type::string()],
        ];
    }
    
  3. Generate a Query (No SelectFields Boilerplate):

    php artisan make:graphql:query UsersQuery
    

    Edit app/GraphQL/Queries/UsersQuery.php:

    public function type(): Type { return Type::listOf(GraphQL::type('User')); }
    public function resolve($root, array $args) {
        return User::all(); // No auto-injected SelectFields
    }
    
  4. Register in Config: Add to config/graphql.php under schemas.default.types and schemas.default.query:

    'types' => [App\GraphQL\Types\UserType::class],
    'query' => [App\GraphQL\Queries\UsersQuery::class],
    
  5. Enable SelectFields Manually: In your resolver, explicitly use the new package:

    use Rebing\GraphQL\Laravel\SelectFields;
    
    public function resolve($root, array $args) {
        return SelectFields::resolve(
            User::query(),
            $args,
            UserType::class
        );
    }
    
  6. Test:

    curl -X POST -H "Content-Type: application/json" \
      -d '{"query": "{ users { id name } }"}' \
      http://localhost:8000/graphql
    

Implementation Patterns

Core Workflow: Type-Driven Development (Updated)

  1. Define Types First: Create types for all models/DTOs. Use make:graphql:type for scaffolding.

    // app/GraphQL/Types/UserType.php
    public function fields() {
        return [
            'posts' => [
                'type' => Type::listOf(GraphQL::type('Post')),
                'resolve' => function ($root) {
                    return $root->posts()->get();
                },
            ],
        ];
    }
    
  2. Leverage Generators (No SelectFields Boilerplate): Use make:graphql:query, make:graphql:mutation, and make:graphql:input to scaffold operations. Example mutation (updated for RC4):

    // app/GraphQL/Mutations/CreateUser.php
    public function args() {
        return [
            'input' => ['type' => GraphQL::type('UserInput')],
        ];
    }
    public function resolve($root, array $args) {
        return User::create($args['input']);
    }
    
  3. Schema Organization: Group related types/queries in schema classes for modularity:

    // app/GraphQL/Schemas/UserSchema.php
    use Rebing\GraphQL\Support\Config;
    
    class UserSchema implements Config {
        public function __invoke() {
            return [
                'query' => [App\GraphQL\Queries\UserQuery::class],
                'mutation' => [App\GraphQL\Mutations\UserMutation::class],
                'types' => [App\GraphQL\Types\UserType::class],
            ];
        }
    }
    

    Register in config/graphql.php:

    'schemas' => [
        'users' => App\GraphQL\Schemas\UserSchema::class,
    ],
    
  4. Data Loading Strategies (Updated for RC4):

    • Dataloaders (for batching):

      // app/GraphQL/Types/UserType.php
      public function fields() {
          return [
              'posts' => [
                  'type' => Type::listOf(GraphQL::type('Post')),
                  'resolve' => fn($root) => $this->loadPosts->load($root->id),
              ],
          ];
      }
      

      Register loader in GraphQLServiceProvider:

      $this->loaders->addLoader('posts', fn() => new UserPostLoader());
      
    • SelectFields (Explicit Usage): Install rebing/graphql-laravel-select-fields and use it manually:

      use Rebing\GraphQL\Laravel\SelectFields;
      
      public function resolve($root, array $args) {
          return SelectFields::resolve(
              User::query(),
              $args,
              UserType::class
          );
      }
      
  5. Middleware Integration (Updated for RC4):

    • HTTP Middleware: Protect routes (now defaults to POST only):
      Route::graphql([
          'middleware' => ['auth:sanctum'],
      ]);
      
    • Execution Middleware: Add auth context:
      // app/GraphQL/Middleware/AddAuthUser.php
      public function handle($root, array $args, $context, ResolveInfo $info, Closure $next) {
          $context['user'] = auth()->user();
          return $next($root, $args, $context, $info);
      }
      
      Register in config/graphql.php:
      'execution_middleware' => [
          App\GraphQL\Middleware\AddAuthUser::class,
      ],
      
  6. Validation (Updated for RC4): Use Laravel validation rules in queries/mutations:

    public function args() {
        return [
            'email' => [
                'type' => Type::nonNull(Type::string()),
                'rules' => ['required', 'email'],
            ],
        ];
    }
    
  7. Testing (Updated for RC4): Use TestCase for unit tests and TestCaseDatabase for integration:

    public function test_users_query() {
        $response = $this->httpGraphql('{ users { id name } }');
        $response->assertJson([
            'data' => [
                'users' => [
                    ['id' => 1, 'name' => 'John Doe'],
                ],
            ],
        ]);
    }
    
  8. New: Resolver Parameter Injection (RC4): Extend resolver dependency injection with custom injectors:

    // Register injector
    Field::registerParameterInjector(
        fn($field, $root, array $args, $context, ResolveInfo $info) => [
            'customService' => app(CustomService::class),
        ]
    );
    

Gotchas and Tips

Pitfalls (Updated for RC4)

  1. SelectFields Moved to Separate Package:

    • Issue: SelectFields is no longer auto-injected in resolvers.
    • Fix: Install rebing/graphql-laravel-select-fields and use it explicitly:
      use Rebing\GraphQL\Laravel\SelectFields;
      return SelectFields::resolve(User::query(), $args, UserType::class);
      
  2. N+1 Queries Without SelectFields: Always use SelectFields (now explicit) or implement custom dataloaders for batching.

  3. Circular Dependencies in Types: Avoid mutual recursion in type resolvers. Use lazy loading or dataloaders.

  4. Forgetting to Register Types/Queries: Ensure all types and queries are listed in config/graphql.php under the correct schema.

  5. Introspection Disabled by Default (RC4): Introspection is now disabled in production (GRAPHQL_DISABLE_INTROSPECTION=true). Enable only in development:

    GRAPHQL_DISABLE_INTROSPECTION=false
    
  6. Query Depth Limits (RC4): Unbounded queries can crash your server. Configure depth limits in config/graphql.php:

    'query_depth_limit' => 10,
    'query_max_complexity' => 500,
    
  7. Type Name Collisions: GraphQL type names must be unique across schemas. Use namespaces or prefixes:

    protected $attributes = [
        'name' => 'UserProfile', // Not just 'User'
    ];
    
  8. Batching Disabled by Default (RC4): Batching is now disabled by default (batching.default = false). Enable in config/graphql.php if needed:

    'batching' => [
        'default' => true,
    
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
hexters/coinpayment
rjcodes/rjcms
act-training/laravel-permissions-manager
alimarchal/laravel-chart-of-accounts
babenkoivan/elastic-scout-driver
mkwebdesign/filament-watchdog-v5
renatomarinho/laravel-page-speed
zedmagdy/filament-business-hours
renatovdemoura/blade-elements-ui
devgeek/beacon-admin
benjamin-rqt/data-watcher-bundle
atriumphp/atrium
sandermuller/package-boost-laravel
sandermuller/boost-skills
redaxo/core
yusufgenc/filament-api-forge
l3aro/rating-star-for-filament
leek/filament-subtenant-scope
anil/file-picker
broqit/fields-ai