如何将 OpenAPI 客户端添加为子项目?
How to add OpenAPI client as a subproject?
我可以成功。但是然后我必须将依赖项复制到主 build-gradle
中,解决冲突 -> 我认为将客户端作为一个子项目具有自己的 build.gradle
.
会是一个更好的设计
所以我将 include = 'build:openapi-java-client'
添加到我的 settings.gradle
并将 compile project(':build:openapi-java-client')
添加到我的依赖项。这样我就有了以下文件:
build.gradle
:
plugins {
id 'java'
id 'application'
id "org.openapi.generator" version "4.3.1"
}
repositories {
jcenter()
}
openApiGenerate {
generatorName = "java"
inputSpec = "$rootDir/specs/petstore.yaml".toString()
outputDir = "$buildDir/openapi-java-client".toString()
apiPackage = "org.openapi.example.api"
invokerPackage = "org.openapi.example.invoker"
modelPackage = "org.openapi.example.model"
configOptions = [
dateLibrary: "java8"
]
}
dependencies {
implementation 'com.google.guava:guava:29.0-jre'
testImplementation 'junit:junit:4.13'
compile project(':build:openapi-java-client')
}
application {
mainClassName = 'a.aa.App'
}
和settings.gradle
:
rootProject.name = 'simple-java-app'
include = 'build:openapi-java-client'
我提前执行openApiGenerate
,添加为子项目后,我做Gradle -> 刷新Gradle 项目和刷新
Eclipse 然后向我展示了一个问题:
Could not run phased build action using Gradle distribution 'https://services.gradle.org/distributions/gradle-6.5.1-bin.zip'.
Settings file 'C:\...\simple-java-app\settings.gradle' line: 11
A problem occurred evaluating settings 'simple-java-app'.
Could not set unknown property 'include' for settings 'simple-java-app' of type org.gradle.initialization.DefaultSettings.
我不知道从这里去哪里,当我处理 https://guides.gradle.org/creating-multi-project-builds/ 并将 greeting-library
放在子文件夹中时,在子文件夹中寻址子项目工作得很好。
您不能这样配置它,因为 build
很可能是一个输出目录,它会创建一个循环引用。最好尝试添加一个新模块并将该生成器插件添加到该模块中。如果你可以配置另一个模块outputDir
,这个可以参考。
即使插件驻留在根项目中,目标也必须是模块。
关键是,根项目始终执行,与模块配置相反。
您正在尝试创建 build/
一个项目,但该目录并不是一个项目目录。它是 Gradle 默认的 build 目录,可能还有 99% 的其他插件和其他 Gradle 插件。
只需将 output
目录更改为 build/
以外的目录:
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$rootDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
}
然后使用正确的语法将项目包含在您的构建中:
// settings.gradle
include("openapi-java-client")
但是,使用 org.openapi.generator
似乎会生成无效的 build.gradle
,因为我收到以下错误:
FAILURE: Build failed with an exception.
* Where:
Build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle' line: 23
* What went wrong:
Could not compile build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle'.
> startup failed:
build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle': 23: unexpected char: '\' @ line 23, column 35.
main.java.srcDirs = ['src/main\java']
这显然不会像您希望的那样工作,因为它似乎是 Gradle 插件本身的问题。如果您只需要在您的项目中包含生成代码,那么只需将生成的 Java 代码作为您的主要 Java 来源的一部分:
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$buildDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
}
tasks {
compileJava {
dependsOn(openApiGenerate)
}
}
sourceSets {
main {
java {
srcDir(files("${openApiGenerate.outputDir.get()}/src/main"))
}
}
}
但是使用这种方法,您会 运行 丢失 imports/dependencies。看起来这个插件并没有提供仅生成 models/POJOs 的能力,所以 updating the library
property to native
并手动包含一些缺失的依赖项,一切正常:
plugins {
java
id("org.openapi.generator") version "5.0.0-beta"
}
repositories {
mavenCentral()
}
group = "io.mateo.test"
dependencies {
implementation(platform("com.fasterxml.jackson:jackson-bom:2.11.1"))
implementation("com.fasterxml.jackson.core:jackson-databind")
implementation("com.fasterxml.jackson.datatype:jackson-datatype-jsr310")
implementation("org.openapitools:jackson-databind-nullable:0.2.1")
implementation("com.google.code.findbugs:jsr305:3.0.2")
implementation("io.swagger:swagger-core:1.6.2")
}
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$buildDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
library.set("native")
configOptions.put("dateLibrary", "java8")
}
tasks {
compileJava {
dependsOn(openApiGenerate)
}
}
sourceSets {
main {
java {
srcDir(files("${openApiGenerate.outputDir.get()}/src/main"))
}
}
}
我刚 有一个非常相似的问题。虽然我的回答并不完美,但我个人仍然更喜欢那里建议的方法——并在此处重复:
建议的方法
我会将依赖生成的 API 的模块的 builds 与生成的 build 完全分开API。此类构建之间的唯一联系应该是依赖声明。这意味着,您必须手动确保首先构建 API 生成项目,然后才构建依赖项目。
默认情况下,这意味着在构建依赖项目之前还要发布 API 模块。此默认值的替代方法是 Gradle composite builds – 例如,允许您在发布之前先在本地测试新生成的 API。但是,在 creating/running 复合构建之前,每次打开 API 文档更改时,您都必须手动 运行 生成 API 生成构建。
例子
假设您有项目 A,这取决于生成的 API。它的 Gradle 构建将包含如下内容:
dependencies {
implementation 'com.example:api:1.0'
}
当然,问题中描述的 simple-java-app
构建必须进行调整才能生成具有这些坐标的模块:
openApiGenerate {
// …
groupId = "com.example"
id = "api"
version = "1.0"
}
在运行宁A的构建之前,你首先必须运行
./gradlew openApiGenerate
来自您的 simple-java-app
项目。
./gradlew publish
来自 simple-java-app/build/openapi-java-client/
目录。
然后 A 的构建可以从发布存储库中获取已发布的依赖项。
或者,您可以在本地删除第 2 步,然后 运行 A 使用额外的 Gradle CLI 选项构建:
./gradlew --include-build $path_to/simple-java-app/build/openapi-java-client/ …
我可以成功build-gradle
中,解决冲突 -> 我认为将客户端作为一个子项目具有自己的 build.gradle
.
所以我将 include = 'build:openapi-java-client'
添加到我的 settings.gradle
并将 compile project(':build:openapi-java-client')
添加到我的依赖项。这样我就有了以下文件:
build.gradle
:
plugins {
id 'java'
id 'application'
id "org.openapi.generator" version "4.3.1"
}
repositories {
jcenter()
}
openApiGenerate {
generatorName = "java"
inputSpec = "$rootDir/specs/petstore.yaml".toString()
outputDir = "$buildDir/openapi-java-client".toString()
apiPackage = "org.openapi.example.api"
invokerPackage = "org.openapi.example.invoker"
modelPackage = "org.openapi.example.model"
configOptions = [
dateLibrary: "java8"
]
}
dependencies {
implementation 'com.google.guava:guava:29.0-jre'
testImplementation 'junit:junit:4.13'
compile project(':build:openapi-java-client')
}
application {
mainClassName = 'a.aa.App'
}
和settings.gradle
:
rootProject.name = 'simple-java-app'
include = 'build:openapi-java-client'
我提前执行openApiGenerate
,添加为子项目后,我做Gradle -> 刷新Gradle 项目和刷新
Eclipse 然后向我展示了一个问题:
Could not run phased build action using Gradle distribution 'https://services.gradle.org/distributions/gradle-6.5.1-bin.zip'.
Settings file 'C:\...\simple-java-app\settings.gradle' line: 11
A problem occurred evaluating settings 'simple-java-app'.
Could not set unknown property 'include' for settings 'simple-java-app' of type org.gradle.initialization.DefaultSettings.
我不知道从这里去哪里,当我处理 https://guides.gradle.org/creating-multi-project-builds/ 并将 greeting-library
放在子文件夹中时,在子文件夹中寻址子项目工作得很好。
您不能这样配置它,因为 build
很可能是一个输出目录,它会创建一个循环引用。最好尝试添加一个新模块并将该生成器插件添加到该模块中。如果你可以配置另一个模块outputDir
,这个可以参考。
即使插件驻留在根项目中,目标也必须是模块。
关键是,根项目始终执行,与模块配置相反。
您正在尝试创建 build/
一个项目,但该目录并不是一个项目目录。它是 Gradle 默认的 build 目录,可能还有 99% 的其他插件和其他 Gradle 插件。
只需将 output
目录更改为 build/
以外的目录:
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$rootDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
}
然后使用正确的语法将项目包含在您的构建中:
// settings.gradle
include("openapi-java-client")
但是,使用 org.openapi.generator
似乎会生成无效的 build.gradle
,因为我收到以下错误:
FAILURE: Build failed with an exception.
* Where:
Build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle' line: 23
* What went wrong:
Could not compile build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle'.
> startup failed:
build file 'C:\Users\fmate\code\example\openapi-java-client\build.gradle': 23: unexpected char: '\' @ line 23, column 35.
main.java.srcDirs = ['src/main\java']
这显然不会像您希望的那样工作,因为它似乎是 Gradle 插件本身的问题。如果您只需要在您的项目中包含生成代码,那么只需将生成的 Java 代码作为您的主要 Java 来源的一部分:
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$buildDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
}
tasks {
compileJava {
dependsOn(openApiGenerate)
}
}
sourceSets {
main {
java {
srcDir(files("${openApiGenerate.outputDir.get()}/src/main"))
}
}
}
但是使用这种方法,您会 运行 丢失 imports/dependencies。看起来这个插件并没有提供仅生成 models/POJOs 的能力,所以 updating the library
property to native
并手动包含一些缺失的依赖项,一切正常:
plugins {
java
id("org.openapi.generator") version "5.0.0-beta"
}
repositories {
mavenCentral()
}
group = "io.mateo.test"
dependencies {
implementation(platform("com.fasterxml.jackson:jackson-bom:2.11.1"))
implementation("com.fasterxml.jackson.core:jackson-databind")
implementation("com.fasterxml.jackson.datatype:jackson-datatype-jsr310")
implementation("org.openapitools:jackson-databind-nullable:0.2.1")
implementation("com.google.code.findbugs:jsr305:3.0.2")
implementation("io.swagger:swagger-core:1.6.2")
}
openApiGenerate {
generatorName.set("java")
inputSpec.set("$rootDir/specs/petstore.json")
outputDir.set("$buildDir/openapi-java-client")
apiPackage.set("org.openapi.example.api")
invokerPackage.set("org.openapi.example.invoker")
modelPackage.set("org.openapi.example.model")
library.set("native")
configOptions.put("dateLibrary", "java8")
}
tasks {
compileJava {
dependsOn(openApiGenerate)
}
}
sourceSets {
main {
java {
srcDir(files("${openApiGenerate.outputDir.get()}/src/main"))
}
}
}
我刚
建议的方法
我会将依赖生成的 API 的模块的 builds 与生成的 build 完全分开API。此类构建之间的唯一联系应该是依赖声明。这意味着,您必须手动确保首先构建 API 生成项目,然后才构建依赖项目。
默认情况下,这意味着在构建依赖项目之前还要发布 API 模块。此默认值的替代方法是 Gradle composite builds – 例如,允许您在发布之前先在本地测试新生成的 API。但是,在 creating/running 复合构建之前,每次打开 API 文档更改时,您都必须手动 运行 生成 API 生成构建。
例子
假设您有项目 A,这取决于生成的 API。它的 Gradle 构建将包含如下内容:
dependencies {
implementation 'com.example:api:1.0'
}
当然,问题中描述的 simple-java-app
构建必须进行调整才能生成具有这些坐标的模块:
openApiGenerate {
// …
groupId = "com.example"
id = "api"
version = "1.0"
}
在运行宁A的构建之前,你首先必须运行
./gradlew openApiGenerate
来自您的simple-java-app
项目。./gradlew publish
来自simple-java-app/build/openapi-java-client/
目录。
然后 A 的构建可以从发布存储库中获取已发布的依赖项。
或者,您可以在本地删除第 2 步,然后 运行 A 使用额外的 Gradle CLI 选项构建:
./gradlew --include-build $path_to/simple-java-app/build/openapi-java-client/ …