From fed322a67f7b095cd0a0603ee5b156048e55549f Mon Sep 17 00:00:00 2001 From: Erik Sulymosi Date: Thu, 18 Jun 2026 15:57:30 +0200 Subject: [PATCH 1/2] Add authentication and authorization directives for federation --- .../Directives/AuthenticatedDirective.php | 32 +++++++++++++++ src/Federation/Directives/PolicyDirective.php | 38 ++++++++++++++++++ .../Directives/RequiresScopesDirective.php | 39 +++++++++++++++++++ src/Federation/FederationPrinter.php | 6 +++ .../Federation/FederationSchemaTest.php | 22 +++++++++++ 5 files changed, 137 insertions(+) create mode 100644 src/Federation/Directives/AuthenticatedDirective.php create mode 100644 src/Federation/Directives/PolicyDirective.php create mode 100644 src/Federation/Directives/RequiresScopesDirective.php diff --git a/src/Federation/Directives/AuthenticatedDirective.php b/src/Federation/Directives/AuthenticatedDirective.php new file mode 100644 index 0000000000..c735075bd4 --- /dev/null +++ b/src/Federation/Directives/AuthenticatedDirective.php @@ -0,0 +1,32 @@ +assertStringContainsString('type SimplePaginatorInfo @shareable {', $sdl); } + public function testServiceQueryShouldReturnFederationV2AccessControlDirectives(): void + { + $schemaExtension = /** @lang GraphQL */ <<<'GRAPHQL' + extend schema @link(url: "https://specs.apollo.dev/federation/v2.9", import: ["@key", "@authenticated", "@requiresScopes", "@policy"]) + GRAPHQL; + + $typeUser = /** @lang GraphQL */ <<<'GRAPHQL' + type User @key(fields: "id") @authenticated @requiresScopes(scopes: [["profile.read"], ["admin"]]) @policy(policies: [["read:user"], ["admin"]]) { + id: ID! + email: String! @authenticated @requiresScopes(scopes: [["email.read"]]) @policy(policies: [["email_policy"]]) + } + GRAPHQL; + + $this->schema = "{$schemaExtension} {$typeUser}"; + + $sdl = $this->_serviceSdl(); + + $this->assertSdlContainsString($schemaExtension, $sdl); + $this->assertStringContainsString('type User @key(fields: "id") @authenticated @requiresScopes(scopes: [["profile.read"], ["admin"]]) @policy(policies: [["read:user"], ["admin"]]) {', $sdl); + $this->assertStringContainsString('email: String! @authenticated @requiresScopes(scopes: [["email.read"]]) @policy(policies: [["email_policy"]])', $sdl); + } + private function _serviceSdl(): string { $response = $this->graphQL(/** @lang GraphQL */ <<<'GRAPHQL' From 203bf52f5903d87db8b46bfdfe95a2f25f653904 Mon Sep 17 00:00:00 2001 From: Erik Sulymosi Date: Thu, 18 Jun 2026 16:18:10 +0200 Subject: [PATCH 2/2] Update federation getting started guide with new directive imports and updated federation spec URL --- docs/6/federation/getting-started.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/docs/6/federation/getting-started.md b/docs/6/federation/getting-started.md index 9074497dc4..979894c359 100644 --- a/docs/6/federation/getting-started.md +++ b/docs/6/federation/getting-started.md @@ -28,8 +28,9 @@ See [the Apollo documentation on federated directives](https://www.apollographql ```graphql extend schema @link( - url: "https://specs.apollo.dev/federation/v2.3" + url: "https://specs.apollo.dev/federation/v2.9" import: [ + "@authenticated" "@composeDirective" "@extends" "@external" @@ -37,8 +38,10 @@ extend schema "@interfaceObject" "@key" "@override" + "@policy" "@provides" "@requires" + "@requiresScopes" "@shareable" "@tag" ]