Skip to content

Instantly share code, notes, and snippets.

@dwhitney
Created August 14, 2015 19:43
Show Gist options
  • Save dwhitney/2dc821d2fe6b46bd8b72 to your computer and use it in GitHub Desktop.
Save dwhitney/2dc821d2fe6b46bd8b72 to your computer and use it in GitHub Desktop.
Got Interfaces working in Sangria using the facebook spec examples
import sangria.schema._
import sangria.execution.Executor
import sangria.introspection.introspectionQuery
import sangria.integration.PlayJsonSupport._
import sangria.parser.{SyntaxError, QueryParser}
import sangria.renderer.SchemaRenderer
import scala.util.{Success,Failure}
trait NamedEntity{ val name: String }
case class Person(name: String, age: Int) extends NamedEntity
case class Business(name: String, employeeCount: Int) extends NamedEntity
case class Contact(entity: NamedEntity, phoneNumber: String, address: String)
object ContactRepo{
val map = Map(
"bob" -> Contact(Person("Bob Jones", 55), "555-1212", "1234 Rickshaw Drive"),
"walmart" -> Contact(Business("Walmart", 200), "121-1555", "4321 Wahskcir Drive")
)
def get(name: String): Option[Contact] = map.get(name)
}
object GraphQL{
val NamedEntityInterface: InterfaceType[Unit,NamedEntity] = InterfaceType[Unit,NamedEntity](
name = "NamedEntity",
fields = List[Field[Unit,NamedEntity]](Field("name", StringType, resolve = _.value.name))
)
val PersonObject = ObjectType[Unit,Person](
name = "Person",
fields = List[Field[Unit,Person]](Field("age", IntType, resolve = _.value.age)),
interfaces = List(NamedEntityInterface)
)
val BusinessObject = ObjectType[Unit,Business](
name = "Business",
fields = List[Field[Unit,Business]](Field("employeeCount", IntType, resolve = _.value.employeeCount)),
interfaces = List(NamedEntityInterface)
)
val ContactObject = ObjectType[Unit,Contact](
name = "Contact",
fields = List[Field[Unit,Contact]](
Field("entity", NamedEntityInterface, resolve = _.value.entity),
Field("phoneNumber", StringType, resolve = _.value.phoneNumber),
Field("address", StringType, resolve = _.value.address)
)
)
val NAME = Argument("name", StringType)
val Query = ObjectType[ContactRepo.type,Unit](
"Query",
List[Field[ContactRepo.type, Unit]](
Field("contact", OptionType(ContactObject), arguments = NAME :: Nil, resolve = (ctx) => ctx.ctx.get(ctx arg NAME)
)
)
)
val schema = Schema(
query = Query,
additionalTypes = List(NamedEntityInterface,PersonObject,BusinessObject)
)
}
object Example extends App{
import scala.concurrent.ExecutionContext.Implicits.global
val executor = Executor(schema = GraphQL.schema, userContext = ContactRepo)
val query = """
{
contact(name:"walmart"){
entity{
name
}
}
}
"""
val query2 = """
{
contact(name:"bob"){
entity{
name
... on Person {
age
}
},
phoneNumber
}
}
"""
for{
q <- List(query, query2)
} {
QueryParser.parse(q) match {
case Success(queryAst) => executor.execute(queryAst).map(println)
case Failure(error) => println(error)
}
}
executor.execute(introspectionQuery) map (res =>
SchemaRenderer.renderSchema(res) map println
)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment