GraphQL SPQR(GraphQl架构发布者和Query Resolver,发音为Speaker )是一个简单使用的库,用于快速开发Java中GraphQL API。
GraphQL SPQR的目的是使在任何Java项目中添加GraphQl API简单。它通过动态生成Java代码的GraphQL模式来起作用。
在开发启用GraphQL的应用程序时,通常首先定义架构并在以后连接业务逻辑。这被称为架构优先风格。尽管它具有优势,但具有强烈和静态的语言,例如Java,但会导致很多重复。
例如,简单的GraphQl类型的模式定义可以喜欢:
type Link {
id : ID !
url : String !
description : String
}
而且,通常,系统中存在相应的Java类型,类似于以下几个:
public class Link {
private final String id ;
private final String url ;
private final String description ;
//constructors, getters and setters
//...
}
这两个块都包含完全相同的信息。更糟糕的是,更改需要立即改变另一个。这使重构风险和笨拙,编译器无法帮助。另一方面,如果您试图将GraphQl API引入现有项目,则编写模式实际上意味着重新描述整个现有模型。这既昂贵又容易出错,仍然遭受重复和缺乏工具的困扰。
相反,GraphQL SPQR通过从现有模型中生成架构来采用代码优先的方法。这使模式和模型保持同步,从而减轻了重构。它在现有代码库顶部引入GraphQL的项目中也可以很好地工作。
请注意,以代码优先的方式开发仍然有效地是架构优先,其不同是,您不是使用另一种语言来开发模式,而是在Java中使用IDE,编译器和所有工具为您提供帮助。破坏模式的变化意味着编译将失败。无需衬里或其他脆弱的黑客。
GraphQL SPQR部署到Maven Central。
小牛
< dependency >
< groupId >io.leangen.graphql</ groupId >
< artifactId >spqr</ artifactId >
< version >0.12.3</ version >
</ dependency >
gradle
compile ' io.leangen.graphql:spqr:0.12.3 '
该示例将使用GraphQl SPQR本身提供的注释,但是这些是可选的,并且映射是完全可配置的,从而使现有服务可以通过GraphQL实现而无需修改。
服务课:
class UserService {
@ GraphQLQuery ( name = "user" )
public User getById ( @ GraphQLArgument ( name = "id" ) Integer id ) {
...
}
}
如果要跳过添加@GraphQLArgument
,则使用-parameters
选项编译,否则名称将丢失。
域类:
public class User {
private String name ;
private Integer id ;
private Date registrationDate ;
@ GraphQLQuery ( name = "name" , description = "A person's name" )
public String getName () {
return name ;
}
@ GraphQLQuery
public Integer getId () {
return id ;
}
@ GraphQLQuery ( name = "regDate" , description = "Date of registration" )
public Date getRegistrationDate () {
return registrationDate ;
}
}
要将其他字段附加到User
GraphQL类型,而无需修改User
类,只需添加一个将User
作为上下文的查询即可。最简单的方法是使用@GraphQLContext
注释:
class UserService {
... //regular queries, as above
// Attach a new field called twitterProfile to the User GraphQL type
@ GraphQLQuery
public TwitterProfile twitterProfile ( @ GraphQLContext User user ) {
...
}
}
用GraphQL-SPQR公开服务:
UserService userService = new UserService (); //instantiate the service (or inject by Spring or another framework)
GraphQLSchema schema = new GraphQLSchemaGenerator ()
. withBasePackages ( "io.leangen" ) //not mandatory but strongly recommended to set your "root" packages
. withOperationsFromSingleton ( userService ) //register the service
. generate (); //done ;)
GraphQL graphQL = new GraphQL . Builder ( schema )
. build ();
//keep the reference to GraphQL instance and execute queries against it.
//this operation selects a user by ID and requests name, regDate and twitterProfile fields only
ExecutionResult result = graphQL . execute (
"{ user (id: 123) {
name,
regDate,
twitterProfile {
handle
numberOfTweets
}
}}" );
我们正在研究SPQR驱动的弹簧靴启动器。该项目还很年轻,但已经起作用。
在https://github.com/leangen/graphql-spqr-samples上查看更多完整的示例
即将推出
为了获得最佳兼容性,编译器参数-Xemit-jvm-type-annotations
需要Kotlin 1.3.70或更高版本。这指示Kotlin编译器正确地产生类型使用注释(在JDK8中引入)。有关详细信息,请参见KT-35843和KT-13228。
在版本16 B17之前,OpenJDK的注释解析器中有一个错误,该错误导致对通用类型参数的注释被重复。您可能会以一种神秘的形式体验到这一点
AnnotationFormatError: Duplicate annotation for class: interface io.leangen.graphql.annotations.GraphQLNonNull
在类型和其通用参数上使用@GraphQLNonNull
时被抛弃,例如@GraphQLNonNull List<@GraphQLNonNull Item>
。
幸运的是,即使在受影响的JDK上,很少有用户似乎会遇到这个问题。请注意,Java编译源的仅相关,而不是Java运行代码。另请注意,Intellij Idea与自己的JDK捆绑在一起,因此在Idea中构建项目可能会导致此错误。如果您的IDE不同,则应配置IDE以使用系统Java。