Skip to content

Commit

Permalink
[go-experimental] Use builder pattern for requests (#4787)
Browse files Browse the repository at this point in the history
* [go-experimental] Use builder pattern for requests
  • Loading branch information
zippolyte authored and jimschubert committed Jan 15, 2020
1 parent 55c6c03 commit e09f1c9
Show file tree
Hide file tree
Showing 35 changed files with 3,879 additions and 1,644 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,8 @@ public abstract class AbstractGoCodegen extends DefaultCodegen implements Codege
protected String packageName = "openapi";
protected Set<String> numberTypes;

protected boolean usesOptionals = true;

public AbstractGoCodegen() {
super();

Expand Down Expand Up @@ -400,7 +402,7 @@ public Map<String, Object> postProcessOperationsWithModels(Map<String, Object> o
}

// import "time" if the operation has a required time parameter.
if (param.required) {
if (param.required || !usesOptionals) {
if (!addedTimeImport && "time.Time".equals(param.dataType)) {
imports.add(createMapping("import", "time"));
addedTimeImport = true;
Expand All @@ -414,7 +416,7 @@ public Map<String, Object> postProcessOperationsWithModels(Map<String, Object> o
}

// import "optionals" package if the parameter is optional
if (!param.required) {
if (!param.required && usesOptionals) {
if (!addedOptionalImport) {
imports.add(createMapping("import", "github.com/antihax/optional"));
addedOptionalImport = true;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,8 @@ public GoClientExperimentalCodegen() {
outputFolder = "generated-code/go-experimental";
embeddedTemplateDir = templateDir = "go-experimental";

usesOptionals = false;

generatorMetadata = GeneratorMetadata.newBuilder(generatorMetadata).stability(Stability.EXPERIMENTAL).build();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,127 +18,116 @@ var (

// {{classname}}Service {{classname}} service
type {{classname}}Service service
{{#operation}}

{{#hasOptionalParams}}
// {{#structPrefix}}{{&classname}}{{/structPrefix}}{{{nickname}}}Opts Optional parameters for the method '{{{nickname}}}'
type {{#structPrefix}}{{&classname}}{{/structPrefix}}{{{nickname}}}Opts struct {
{{#allParams}}
{{^required}}
{{#isPrimitiveType}}
{{^isBinary}}
{{vendorExtensions.x-exportParamName}} optional.{{vendorExtensions.x-optionalDataType}}
{{/isBinary}}
{{#isBinary}}
{{vendorExtensions.x-exportParamName}} optional.Interface
{{/isBinary}}
{{/isPrimitiveType}}
{{^isPrimitiveType}}
{{vendorExtensions.x-exportParamName}} optional.Interface
{{/isPrimitiveType}}
{{/required}}
{{/allParams}}
{{#operation}}
type api{{operationId}}Request struct {
ctx _context.Context
apiService *{{classname}}Service{{#allParams}}
{{paramName}} {{^isPathParam}}*{{/isPathParam}}{{{dataType}}}{{/allParams}}
}

{{/hasOptionalParams}}
{{#allParams}}{{^isPathParam}}
func (r api{{operationId}}Request) {{vendorExtensions.x-exportParamName}}({{paramName}} {{{dataType}}}) api{{operationId}}Request {
r.{{paramName}} = &{{paramName}}
return r
}
{{/isPathParam}}{{/allParams}}
/*
{{operationId}}{{#summary}} {{{.}}}{{/summary}}{{^summary}} Method for {{operationId}}{{/summary}}
{{#notes}}
{{notes}}
{{{unescapedNotes}}}
{{/notes}}
* @param ctx _context.Context - for authentication, logging, cancellation, deadlines, tracing, etc. Passed from http.Request or context.Background().
{{#allParams}}
{{#required}}
* @param {{paramName}}{{#description}} {{{.}}}{{/description}}
{{/required}}
{{/allParams}}
{{#hasOptionalParams}}
* @param optional nil or *{{#structPrefix}}{{&classname}}{{/structPrefix}}{{{nickname}}}Opts - Optional Parameters:
{{#allParams}}
{{^required}}
* @param "{{vendorExtensions.x-exportParamName}}" ({{#isPrimitiveType}}{{^isBinary}}optional.{{vendorExtensions.x-optionalDataType}}{{/isBinary}}{{#isBinary}}optional.Interface of {{dataType}}{{/isBinary}}{{/isPrimitiveType}}{{^isPrimitiveType}}optional.Interface of {{dataType}}{{/isPrimitiveType}}) - {{#description}} {{{.}}}{{/description}}
{{/required}}
{{/allParams}}
{{/hasOptionalParams}}
{{#returnType}}
@return {{{returnType}}}
{{/returnType}}
* @param ctx _context.Context - for authentication, logging, cancellation, deadlines, tracing, etc. Passed from http.Request or context.Background().{{#pathParams}}
* @param {{paramName}}{{#description}} {{{.}}}{{/description}}{{/pathParams}}
@return api{{operationId}}Request
*/
func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams}}, {{/hasParams}}{{#allParams}}{{#required}}{{paramName}} {{{dataType}}}{{#hasMore}}, {{/hasMore}}{{/required}}{{/allParams}}{{#hasOptionalParams}}localVarOptionals *{{#structPrefix}}{{&classname}}{{/structPrefix}}{{{nickname}}}Opts{{/hasOptionalParams}}) ({{#returnType}}{{{returnType}}}, {{/returnType}}*_nethttp.Response, error) {
func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#pathParams}}, {{paramName}} {{{dataType}}}{{/pathParams}}) api{{operationId}}Request {
return api{{operationId}}Request{
apiService: a,
ctx: ctx,{{#pathParams}}
{{paramName}}: {{paramName}},{{/pathParams}}
}
}

/*
Execute executes the request
{{#returnType}} @return {{{.}}}{{/returnType}}
*/
func (r api{{operationId}}Request) Execute() ({{#returnType}}{{{.}}}, {{/returnType}}*_nethttp.Response, error) {
var (
localVarHTTPMethod = _nethttp.Method{{httpMethod}}
localVarPostBody interface{}
localVarFormFileName string
localVarFileName string
localVarFileBytes []byte
{{#returnType}}
localVarReturnValue {{{returnType}}}
{{/returnType}}
{{#returnType}}localVarReturnValue {{{.}}}{{/returnType}}
)

localBasePath, err := a.client.cfg.ServerURLWithContext(ctx, "{{{classname}}}Service.{{{nickname}}}")
localBasePath, err := r.apiService.client.cfg.ServerURLWithContext(r.ctx, "{{{classname}}}Service.{{{nickname}}}")
if err != nil {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, GenericOpenAPIError{error: err.Error()}
}

localVarPath := localBasePath + "{{{path}}}"{{#pathParams}}
localVarPath = strings.Replace(localVarPath, "{"+"{{baseName}}"+"}", _neturl.QueryEscape(parameterToString({{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")) , -1){{/pathParams}}
localVarPath = strings.Replace(localVarPath, "{"+"{{baseName}}"+"}", _neturl.QueryEscape(parameterToString(r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")) , -1){{/pathParams}}

localVarHeaderParams := make(map[string]string)
localVarQueryParams := _neturl.Values{}
localVarFormParams := _neturl.Values{}
{{#allParams}}
{{#required}}
{{#required}}{{^isPathParam}}
if r.{{paramName}} == nil {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} is required and must be specified")
}{{/isPathParam}}
{{#minItems}}
if len({{paramName}}) < {{minItems}} {
if len({{^isPathParam}}*{{/isPathParam}}r.{{paramName}}) < {{minItems}} {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must have at least {{minItems}} elements")
}
{{/minItems}}
{{#maxItems}}
if len({{paramName}}) > {{maxItems}} {
if len({{^isPathParam}}*{{/isPathParam}}r.{{paramName}}) > {{maxItems}} {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must have less than {{maxItems}} elements")
}
{{/maxItems}}
{{#minLength}}
if strlen({{paramName}}) < {{minLength}} {
if strlen({{^isPathParam}}*{{/isPathParam}}r.{{paramName}}) < {{minLength}} {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must have at least {{minLength}} elements")
}
{{/minLength}}
{{#maxLength}}
if strlen({{paramName}}) > {{maxLength}} {
if strlen({{^isPathParam}}*{{/isPathParam}}r.{{paramName}}) > {{maxLength}} {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must have less than {{maxLength}} elements")
}
{{/maxLength}}
{{#minimum}}
{{#isString}}
{{paramName}}Txt, err := atoi({{paramName}})
{{paramName}}Txt, err := atoi({{^isPathParam}}*{{/isPathParam}}r.{{paramName}})
if {{paramName}}Txt < {{minimum}} {
{{/isString}}
{{^isString}}
if {{paramName}} < {{minimum}} {
if {{^isPathParam}}*{{/isPathParam}}r.{{paramName}} < {{minimum}} {
{{/isString}}
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must be greater than {{minimum}}")
}
{{/minimum}}
{{#maximum}}
{{#isString}}
{{paramName}}Txt, err := atoi({{paramName}})
{{paramName}}Txt, err := atoi({{^isPathParam}}*{{/isPathParam}}r.{{paramName}})
if {{paramName}}Txt > {{maximum}} {
{{/isString}}
{{^isString}}
if {{paramName}} > {{maximum}} {
if {{^isPathParam}}*{{/isPathParam}}r.{{paramName}} > {{maximum}} {
{{/isString}}
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} must be less than {{maximum}}")
}
{{/maximum}}
{{/required}}
{{/allParams}}

{{#hasQueryParams}}
{{#queryParams}}
{{#required}}
{{#isCollectionFormatMulti}}
t:={{paramName}}
t := *r.{{paramName}}
if reflect.TypeOf(t).Kind() == reflect.Slice {
s := reflect.ValueOf(t)
for i := 0; i < s.Len(); i++ {
Expand All @@ -149,13 +138,13 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
}
{{/isCollectionFormatMulti}}
{{^isCollectionFormatMulti}}
localVarQueryParams.Add("{{baseName}}", parameterToString({{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
localVarQueryParams.Add("{{baseName}}", parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
{{/isCollectionFormatMulti}}
{{/required}}
{{^required}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
if r.{{paramName}} != nil {
{{#isCollectionFormatMulti}}
t:=localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value()
t := *r.{{paramName}}
if reflect.TypeOf(t).Kind() == reflect.Slice {
s := reflect.ValueOf(t)
for i := 0; i < s.Len(); i++ {
Expand All @@ -166,12 +155,11 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
}
{{/isCollectionFormatMulti}}
{{^isCollectionFormatMulti}}
localVarQueryParams.Add("{{baseName}}", parameterToString(localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value(), "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
localVarQueryParams.Add("{{baseName}}", parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
{{/isCollectionFormatMulti}}
}
{{/required}}
{{/queryParams}}
{{/hasQueryParams}}
// to determine the Content-Type header
{{=<% %>=}}
localVarHTTPContentTypes := []string{<%#consumes%>"<%&mediaType%>"<%^-last%>, <%/-last%><%/consumes%>}
Expand All @@ -193,33 +181,26 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
if localVarHTTPHeaderAccept != "" {
localVarHeaderParams["Accept"] = localVarHTTPHeaderAccept
}
{{#hasHeaderParams}}
{{#headerParams}}
{{#required}}
localVarHeaderParams["{{baseName}}"] = parameterToString({{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")
localVarHeaderParams["{{baseName}}"] = parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")
{{/required}}
{{^required}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
localVarHeaderParams["{{baseName}}"] = parameterToString(localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value(), "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")
if r.{{paramName}} != nil {
localVarHeaderParams["{{baseName}}"] = parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}")
}
{{/required}}
{{/headerParams}}
{{/hasHeaderParams}}
{{#hasFormParams}}
{{#formParams}}
{{#isFile}}
localVarFormFileName = "{{baseName}}"
{{#required}}
localVarFile := {{paramName}}
localVarFile := *r.{{paramName}}
{{/required}}
{{^required}}
var localVarFile {{dataType}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
localVarFileOk := false
localVarFile, localVarFileOk = localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value().({{dataType}})
if !localVarFileOk {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} should be {{dataType}}")
}
if r.{{paramName}} != nil {
localVarFile = *r.{{paramName}}
}
{{/required}}
if localVarFile != nil {
Expand All @@ -231,56 +212,36 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
{{/isFile}}
{{^isFile}}
{{#required}}
localVarFormParams.Add("{{baseName}}", parameterToString({{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
localVarFormParams.Add("{{baseName}}", parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
{{/required}}
{{^required}}
{{#isModel}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
paramJson, err := parameterToJson(localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value())
if r.{{paramName}} != nil {
paramJson, err := parameterToJson(*r.{{paramName}})
if err != nil {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, err
}
localVarFormParams.Add("{{baseName}}", paramJson)
}
{{/isModel}}
{{^isModel}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
localVarFormParams.Add("{{baseName}}", parameterToString(localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value(), "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
if r.{{paramName}} != nil {
localVarFormParams.Add("{{baseName}}", parameterToString(*r.{{paramName}}, "{{#collectionFormat}}{{collectionFormat}}{{/collectionFormat}}"))
}
{{/isModel}}
{{/required}}
{{/isFile}}
{{/formParams}}
{{/hasFormParams}}
{{#hasBodyParam}}
{{#bodyParams}}
// body params
{{#required}}
localVarPostBody = &{{paramName}}
{{/required}}
{{^required}}
if localVarOptionals != nil && localVarOptionals.{{vendorExtensions.x-exportParamName}}.IsSet() {
{{#isPrimitiveType}}
localVarPostBody = localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value()
{{/isPrimitiveType}}
{{^isPrimitiveType}}
localVarOptional{{vendorExtensions.x-exportParamName}}, localVarOptional{{vendorExtensions.x-exportParamName}}ok := localVarOptionals.{{vendorExtensions.x-exportParamName}}.Value().({{{dataType}}})
if !localVarOptional{{vendorExtensions.x-exportParamName}}ok {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, reportError("{{paramName}} should be {{dataType}}")
}
localVarPostBody = &localVarOptional{{vendorExtensions.x-exportParamName}}
{{/isPrimitiveType}}
}

{{/required}}
localVarPostBody = r.{{paramName}}
{{/bodyParams}}
{{/hasBodyParam}}
{{#authMethods}}
{{#isApiKey}}
{{^isKeyInCookie}}
if ctx != nil {
if r.ctx != nil {
// API Key Authentication
if auth, ok := ctx.Value(ContextAPIKeys).(map[string]APIKey); ok {
if auth, ok := r.ctx.Value(ContextAPIKeys).(map[string]APIKey); ok {
if auth, ok := auth["{{keyParamName}}"]; ok {
var key string
if auth.Prefix != "" {
Expand All @@ -300,12 +261,12 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
{{/isKeyInCookie}}
{{/isApiKey}}
{{/authMethods}}
r, err := a.client.prepareRequest(ctx, localVarPath, localVarHTTPMethod, localVarPostBody, localVarHeaderParams, localVarQueryParams, localVarFormParams, localVarFormFileName, localVarFileName, localVarFileBytes)
req, err := r.apiService.client.prepareRequest(r.ctx, localVarPath, localVarHTTPMethod, localVarPostBody, localVarHeaderParams, localVarQueryParams, localVarFormParams, localVarFormFileName, localVarFileName, localVarFileBytes)
if err != nil {
return {{#returnType}}localVarReturnValue, {{/returnType}}nil, err
}

localVarHTTPResponse, err := a.client.callAPI(r)
localVarHTTPResponse, err := r.apiService.client.callAPI(req)
if err != nil || localVarHTTPResponse == nil {
return {{#returnType}}localVarReturnValue, {{/returnType}}localVarHTTPResponse, err
}
Expand All @@ -327,7 +288,7 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
if localVarHTTPResponse.StatusCode == {{{code}}} {
{{/wildcard}}
var v {{{dataType}}}
err = a.client.decode(&v, localVarBody, localVarHTTPResponse.Header.Get("Content-Type"))
err = r.apiService.client.decode(&v, localVarBody, localVarHTTPResponse.Header.Get("Content-Type"))
if err != nil {
newErr.error = err.Error()
return {{#returnType}}localVarReturnValue, {{/returnType}}localVarHTTPResponse, newErr
Expand All @@ -345,7 +306,7 @@ func (a *{{{classname}}}Service) {{{nickname}}}(ctx _context.Context{{#hasParams
}

{{#returnType}}
err = a.client.decode(&localVarReturnValue, localVarBody, localVarHTTPResponse.Header.Get("Content-Type"))
err = r.apiService.client.decode(&localVarReturnValue, localVarBody, localVarHTTPResponse.Header.Get("Content-Type"))
if err != nil {
newErr := GenericOpenAPIError{
body: localVarBody,
Expand Down
Loading

0 comments on commit e09f1c9

Please sign in to comment.