Created by: enriquebarba97
This pull request adds the automatic generation of assertions for inter-parameter dependencies using IDL in some Java generators. You can find full context and details in the corresponding issue #8722.
The dependencies are defined in an x-dependencies
vendor extension in each operation. As an example, here is a Youtube API operation with its dependencies:
/youtube/v3/commentThreads:
get:
description: Retrieves a list of resources, possibly filtered.
operationId: youtube.commentThreads.list
parameters:
- description: The *part* parameter specifies a comma-separated list of one or more commentThread resource properties that the API response will include.
explode: true
in: query
name: part
required: true
schema:
items:
type: string
type: array
style: form
- description: Returns the comment threads of all videos of the channel and the channel comments as well.
in: query
name: allThreadsRelatedToChannelId
schema:
type: string
- description: Returns the comment threads for all the channel comments (ie does not include comments left on videos).
in: query
name: channelId
schema:
type: string
- description: Returns the comment threads with the given IDs for Stubby or Apiary.
explode: true
in: query
name: id
schema:
items:
type: string
type: array
style: form
- description: The *maxResults* parameter specifies the maximum number of items that should be returned in the result set.
in: query
name: maxResults
schema:
maximum: 100
minimum: 1
type: integer
- description: "Limits the returned comment threads to those with the specified moderation status. Not compatible with the 'id' filter. Valid values: published, heldForReview, likelySpam."
in: query
name: moderationStatus
schema:
enum:
- published
- heldForReview
- likelySpam
- rejected
type: string
- in: query
name: order
schema:
enum:
- orderUnspecified
- time
- relevance
type: string
- description: The *pageToken* parameter identifies a specific page in the result set that should be returned. In an API response, the nextPageToken and prevPageToken properties identify other pages that could be retrieved.
in: query
name: pageToken
schema:
type: string
- description: Limits the returned comment threads to those matching the specified key words. Not compatible with the 'id' filter.
in: query
name: searchTerms
schema:
type: string
- description: The requested text format for the returned comments.
in: query
name: textFormat
schema:
enum:
- textFormatUnspecified
- html
- plainText
type: string
- description: Returns the comment threads of the specified video.
in: query
name: videoId
schema:
type: string
x-dependencies:
- OnlyOne(allThreadsRelatedToChannelId, channelId, id, videoId);
- ZeroOrOne(id, maxResults);
- ZeroOrOne(id, moderationStatus);
- ZeroOrOne(id, order);
- ZeroOrOne(id, pageToken);
- ZeroOrOne(id, searchTerms);
responses:
"200":
content:
application/json:
schema:
$ref: "#/components/schemas/CommentThreadListResponse"
description: Successful response
"400":
description: 400
"403":
description: 403
"404":
description: 404
security:
- Oauth2:
- https://www.googleapis.com/auth/youtube.force-ssl
Oauth2c:
- https://www.googleapis.com/auth/youtube.force-ssl
tags:
- commentThreads
And this is how the generated assertions look like in a Spring server stub.
// Check dependency: OnlyOne(allThreadsRelatedToChannelId, channelId, id, videoId);
if(!DependencyUtil.OnlyOneDependency((allThreadsRelatedToChannelId != null),(channelId != null),(id != null && !id.isEmpty()),(videoId != null))){
return new ResponseEntity("Dependency not satisfied: OnlyOne(allThreadsRelatedToChannelId, channelId, id, videoId);", HttpStatus.BAD_REQUEST);
}
// Check dependency: ZeroOrOne(id, maxResults);
if(!DependencyUtil.ZeroOrOneDependency((id != null && !id.isEmpty()),(maxResults != null))){
return new ResponseEntity("Dependency not satisfied: ZeroOrOne(id, maxResults);", HttpStatus.BAD_REQUEST);
}
// Check dependency: ZeroOrOne(id, moderationStatus);
if(!DependencyUtil.ZeroOrOneDependency((id != null && !id.isEmpty()),(moderationStatus != null))){
return new ResponseEntity("Dependency not satisfied: ZeroOrOne(id, moderationStatus);", HttpStatus.BAD_REQUEST);
}
// Check dependency: ZeroOrOne(id, order);
if(!DependencyUtil.ZeroOrOneDependency((id != null && !id.isEmpty()),(order != null))){
return new ResponseEntity("Dependency not satisfied: ZeroOrOne(id, order);", HttpStatus.BAD_REQUEST);
}
// Check dependency: ZeroOrOne(id, pageToken);
if(!DependencyUtil.ZeroOrOneDependency((id != null && !id.isEmpty()),(pageToken != null))){
return new ResponseEntity("Dependency not satisfied: ZeroOrOne(id, pageToken);", HttpStatus.BAD_REQUEST);
}
// Check dependency: ZeroOrOne(id, searchTerms);
if(!DependencyUtil.ZeroOrOneDependency((id != null && !id.isEmpty()),(searchTerms != null))){
return new ResponseEntity("Dependency not satisfied: ZeroOrOne(id, searchTerms);", HttpStatus.BAD_REQUEST);
}
To check the dependencies, a DependenciesUtil.java
file with static methods is generated. The code checks for the x-dependencies
extensions in the preprocessOpenAPI
method, and adds the supporting file if found, so the DependenciesUtil.java
file is not generated if IDL is not used. I am not convinced that is the best way of doing this, so any suggestions are welcome.
The generators supported right now are the following Java client library:
- google-api-client
- jersey2
- native
- okhttp-gson
- resteasy
- resttemplate
- webclient
And the following servers:
- Spring
- java-msf4j-server
To check the files and expressions generated, you can use the youtubeIDL.yaml OAS specification with dependencies for the Youtube API. More OAS files for other APIs with IDL dependencies can be found here
Any feedback or suggestions are appreciated.
PR checklist
-
Read the contribution guidelines. -
Pull Request title clearly describes the work in the pull request and Pull Request description provides details about how to validate the work. Missing information here may result in delayed response from the community. -
Run the following to build the project and update samples: ./mvnw clean package ./bin/generate-samples.sh ./bin/utils/export_docs_generators.sh
./bin/generate-samples.sh bin/configs/java*
. For Windows users, please run the script in Git BASH. -
File the PR against the correct branch: master
,5.3.x
,6.0.x
-
If your PR is targeting a particular programming language, @mention the technical committee members, so they are more likely to review the pull request.
@bbdouglas @sreeshas @jfiala @lukoyanov @cbornet @jeff9finger @karismann @Zomzog @lwlee2608 @nmuesch @wing328