Skip to content

Commit

Permalink
Merge pull request #185 from sangria-graphql/easier_directives
Browse files Browse the repository at this point in the history
easier API to add federation directives
  • Loading branch information
yanns authored Oct 18, 2022
2 parents bc6d8da + e75728c commit c03cb9d
Show file tree
Hide file tree
Showing 10 changed files with 400 additions and 112 deletions.
94 changes: 65 additions & 29 deletions core/src/main/scala/sangria/federation/v1/Directives.scala
Original file line number Diff line number Diff line change
Expand Up @@ -5,45 +5,81 @@ import sangria.schema.{Argument, Directive, DirectiveLocation}

object Directives {

val definitions: List[Directive] = List(
Directive(
/** [@key](https://www.apollographql.com/docs/federation/federated-types/federated-directives#key)
* directive
*/
object Key {
val definition: Directive = Directive(
name = "key",
arguments = Argument(
name = "fields",
argumentType = _FieldSet.Type
) :: Nil,
arguments = Argument("fields", _FieldSet.Type) :: Nil,
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface),
repeatable = true
),
Directive(name = "external", locations = Set(DirectiveLocation.FieldDefinition)),
Directive(
name = "extends",
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface)),
Directive(
)

def apply(fields: String): ast.Directive =
ast.Directive(
name = "key",
arguments = Vector(ast.Argument("fields", ast.StringValue(fields))))
}

/** [@extends](https://www.apollographql.com/docs/federation/federated-types/federated-directives#extends)
* directive definition
*/
val ExtendsDefinition: Directive = Directive(
name = "extends",
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface))

/** [@extends](https://www.apollographql.com/docs/federation/federated-types/federated-directives#extends)
* directive
*/
val Extends: ast.Directive = ast.Directive("extends")

/** [@requires](https://www.apollographql.com/docs/federation/federated-types/federated-directives#requires)
* directive
*/
object Requires {
val definition: Directive = Directive(
name = "requires",
arguments = Argument(
name = "fields",
argumentType = _FieldSet.Type
) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition)),
Directive(
name = "provides",
arguments = Argument(
name = "fields",
argumentType = _FieldSet.Type
) :: Nil,
arguments = Argument("fields", _FieldSet.Type) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition))
)

object Key {
def apply(fields: String): ast.Directive =
ast.Directive(
name = "requires",
arguments = Vector(ast.Argument("fields", ast.StringValue(fields))))
}

/** [@external](https://www.apollographql.com/docs/federation/federated-types/federated-directives#external)
* directive definition
*/
val ExternalDefinition: Directive =
Directive(name = "external", locations = Set(DirectiveLocation.FieldDefinition))

/** [@external](https://www.apollographql.com/docs/federation/federated-types/federated-directives#external)
* directive
*/
val External: ast.Directive = ast.Directive("external")

/** [@provides](https://www.apollographql.com/docs/federation/federated-types/federated-directives#provides)
* directive
*/
object Provides {
val definition: Directive = Directive(
name = "provides",
arguments = Argument("fields", _FieldSet.Type) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition))

def apply(fields: String): ast.Directive =
ast.Directive(
name = "key",
name = "provides",
arguments = Vector(ast.Argument(name = "fields", value = ast.StringValue(fields))))
}

val External: ast.Directive = ast.Directive(name = "external", arguments = Vector.empty)

val Extends: ast.Directive = ast.Directive(name = "extends", arguments = Vector.empty)
val definitions: List[Directive] = List(
Key.definition,
ExternalDefinition,
ExtendsDefinition,
Requires.definition,
Provides.definition
)
}
246 changes: 175 additions & 71 deletions core/src/main/scala/sangria/federation/v2/Directives.scala
Original file line number Diff line number Diff line change
Expand Up @@ -5,78 +5,178 @@ import sangria.schema._

object Directives {

val definitions: List[Directive] = List(
Directive(
name = "key",
arguments = List(
Argument(
name = "fields",
argumentType = _FieldSet.Type
),
Argument(
name = "resolvable",
argumentType = OptionInputType(BooleanType),
defaultValue = true
)),
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface),
repeatable = true
),
Directive(name = "external", locations = Set(DirectiveLocation.FieldDefinition)),
Directive(
name = "extends",
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface)),
Directive(
name = "requires",
arguments = Argument(
name = "fields",
argumentType = _FieldSet.Type
) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition)),
Directive(
name = "provides",
arguments = Argument(
name = "fields",
argumentType = _FieldSet.Type
) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition)),
Directive(
object Link {
val definition: Directive = Directive(
name = "link",
arguments = List(
Argument("url", OptionInputType(StringType)),
Argument("url", StringType),
Argument("as", OptionInputType(StringType)),
Argument("for", OptionInputType(Link__Purpose.Type)),
Argument("import", OptionInputType(ListInputType(OptionInputType(Link__Import.Type))))
),
locations = Set(DirectiveLocation.Schema),
repeatable = true
),
Directive(
name = "shareable",
locations = Set(DirectiveLocation.Object, DirectiveLocation.FieldDefinition)
),
Directive(
name = "inaccessible",
locations = Set(
DirectiveLocation.FieldDefinition,
DirectiveLocation.Object,
DirectiveLocation.Interface,
DirectiveLocation.Union,
DirectiveLocation.ArgumentDefinition,
DirectiveLocation.Scalar,
DirectiveLocation.Enum,
DirectiveLocation.EnumValue,
DirectiveLocation.InputObject,
DirectiveLocation.InputFieldDefinition
)

def apply(url: String, as: String): ast.Directive =
apply(url = url, as = Some(as))

def apply(url: String, `for`: Link__Purpose.Value): ast.Directive =
apply(url = url, `for` = Some(`for`))

def apply(
url: String,
as: Option[String] = None,
`for`: Option[Link__Purpose.Value] = None,
`import`: Option[Vector[Abstract_Link__Import]] = None): ast.Directive =
ast.Directive(
name = "link",
arguments = Vector(
Some(ast.Argument("url", ast.StringValue(url))),
as.map(v => ast.Argument("as", ast.StringValue(v))),
`for`.map(v => ast.Argument("for", ast.EnumValue(Link__Purpose.Type.coerceOutput(v)))),
`import`.map(v =>
ast.Argument("import", ast.ListValue(v.map(v => Abstract_Link__Import.toAst(v)))))
).flatten
)
),
Directive(
name = "override",
}

/** [@key](https://www.apollographql.com/docs/federation/federated-types/federated-directives#key)
* directive
*/
object Key {
val definition: Directive = Directive(
name = "key",
arguments = List(
Argument("from", StringType)
),
Argument("fields", _FieldSet.Type),
Argument("resolvable", OptionInputType(BooleanType), defaultValue = true)),
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface),
repeatable = true
)

def apply(fields: String, resolvable: Boolean): ast.Directive =
apply(fields, resolvable = Some(resolvable))

def apply(fields: String, resolvable: Option[Boolean] = None): ast.Directive =
ast.Directive(
name = "key",
arguments = Vector(
Some(ast.Argument("fields", ast.StringValue(fields))),
resolvable.map(r => ast.Argument("resolvable", ast.BooleanValue(r)))).flatten
)
}

/** [@extends](https://www.apollographql.com/docs/federation/federated-types/federated-directives#extends)
* directive definition
*/
val ExtendsDefinition: Directive = Directive(
name = "extends",
locations = Set(DirectiveLocation.Object, DirectiveLocation.Interface))

/** [@extends](https://www.apollographql.com/docs/federation/federated-types/federated-directives#extends)
* directive
*/
val Extends: ast.Directive = ast.Directive(name = "extends")

/** [@shareable](https://www.apollographql.com/docs/federation/federated-types/federated-directives#shareable)
* directive definition
*/
val ShareableDefinition: Directive = Directive(
name = "shareable",
locations = Set(DirectiveLocation.Object, DirectiveLocation.FieldDefinition)
)

/** [@shareable](https://www.apollographql.com/docs/federation/federated-types/federated-directives#shareable)
* directive
*/
val Shareable: ast.Directive = ast.Directive(name = "shareable")

/** [@inaccessible](https://www.apollographql.com/docs/federation/federated-types/federated-directives#inaccessible)
* directive definition
*/
val InaccessibleDefinition: Directive = Directive(
name = "inaccessible",
locations = Set(
DirectiveLocation.FieldDefinition,
DirectiveLocation.Object,
DirectiveLocation.Interface,
DirectiveLocation.Union,
DirectiveLocation.ArgumentDefinition,
DirectiveLocation.Scalar,
DirectiveLocation.Enum,
DirectiveLocation.EnumValue,
DirectiveLocation.InputObject,
DirectiveLocation.InputFieldDefinition
)
)

/** [@inaccessible](https://www.apollographql.com/docs/federation/federated-types/federated-directives#inaccessible)
* directive
*/
val Inaccessible: ast.Directive = ast.Directive(name = "inaccessible")

/** [@override](https://www.apollographql.com/docs/federation/federated-types/federated-directives#override)
* directive
*/
object Override {
val Definition: Directive = Directive(
name = "override",
arguments = List(Argument("from", StringType)),
locations = Set(DirectiveLocation.FieldDefinition)
),
Directive(
)

def apply(from: String): ast.Directive =
ast.Directive(
name = "override",
arguments = Vector(ast.Argument("from", ast.StringValue(from))))
}

/** [@external](https://www.apollographql.com/docs/federation/federated-types/federated-directives#external)
* directive definition
*/
val ExternalDefinition: Directive =
Directive(name = "external", locations = Set(DirectiveLocation.FieldDefinition))

/** [@external](https://www.apollographql.com/docs/federation/federated-types/federated-directives#external)
* directive
*/
val External: ast.Directive = ast.Directive(name = "external")

/** [@provides](https://www.apollographql.com/docs/federation/federated-types/federated-directives#provides)
* directive
*/
object Provides {
val definition: Directive = Directive(
name = "provides",
arguments = Argument("fields", _FieldSet.Type) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition))

def apply(fields: String): ast.Directive =
ast.Directive(
name = "provides",
arguments = Vector(ast.Argument("fields", ast.StringValue(fields))))
}

/** [@requires](https://www.apollographql.com/docs/federation/federated-types/federated-directives#requires)
* directive
*/
object Requires {
val definition: Directive = Directive(
name = "requires",
arguments = Argument("fields", _FieldSet.Type) :: Nil,
locations = Set(DirectiveLocation.FieldDefinition))

def apply(fields: String): ast.Directive =
ast.Directive(
name = "requires",
arguments = Vector(ast.Argument("fields", ast.StringValue(fields))))
}

/** [@tag](https://www.apollographql.com/docs/federation/federated-types/federated-directives#tag)
* directive
*/
object Tag {
val definition: Directive = Directive(
name = "tag",
arguments = List(
Argument("name", StringType)
Expand All @@ -95,17 +195,21 @@ object Directives {
),
repeatable = true
)
)

object Key {

def apply(fields: String): ast.Directive =
ast.Directive(
name = "key",
arguments = Vector(ast.Argument(name = "fields", value = ast.StringValue(fields))))
def apply(name: String): ast.Directive =
ast.Directive(name = "tag", arguments = Vector(ast.Argument("name", ast.StringValue(name))))
}

val External: ast.Directive = ast.Directive(name = "external", arguments = Vector.empty)

val Extends: ast.Directive = ast.Directive(name = "extends", arguments = Vector.empty)
val definitions: List[Directive] = List(
Link.definition,
Key.definition,
ExtendsDefinition,
ShareableDefinition,
InaccessibleDefinition,
Override.Definition,
ExternalDefinition,
Provides.definition,
Requires.definition,
Tag.definition
)
}
Loading

0 comments on commit c03cb9d

Please sign in to comment.