package {{packageName}}

{{#operations}}
import (
    "strings"
    "fmt"
    "encoding/json"
    "errors"
    "github.com/dghubble/sling"
{{#imports}}    "{{import}}"
{{/imports}}
)

type {{classname}} struct {
    basePath  string
}

func New{{classname}}() *{{classname}}{
    return &{{classname}} {
        basePath:   "{{basePath}}",
    }
}

func New{{classname}}WithBasePath(basePath string) *{{classname}}{
    return &{{classname}} {
        basePath:   basePath,
    }
}

{{#operation}}
/**
 * {{summary}}
 * {{notes}}
{{#allParams}} * @param {{paramName}} {{description}}
{{/allParams}} * @return {{#returnType}}{{{returnType}}}{{/returnType}}{{^returnType}}void{{/returnType}}
 */
//func (a {{classname}}) {{nickname}} ({{#allParams}}{{paramName}} {{{dataType}}}{{#hasMore}}, {{/hasMore}}{{/allParams}}) ({{#returnType}}{{{returnType}}}, {{/returnType}}error) {
func (a {{classname}}) {{nickname}} ({{#allParams}}{{paramName}} {{{dataType}}}{{#hasMore}}, {{/hasMore}}{{/allParams}}) ({{#returnType}}{{{returnType}}}, {{/returnType}}error) {

    _sling := sling.New().{{httpMethod}}(a.basePath)

    // create path and map variables
    path := "{{basePathWithoutHost}}{{path}}"
{{#pathParams}}    path = strings.Replace(path, "{" + "{{baseName}}" + "}", fmt.Sprintf("%v", {{paramName}}), -1)
{{/pathParams}}

    _sling = _sling.Path(path)

{{#hasQueryParams}}    type QueryParams struct {
        {{#queryParams}}{{paramName}}    {{dataType}} `url:"{{baseName}},omitempty"`
        {{/queryParams}}
}
    _sling = _sling.QueryStruct(&QueryParams{ {{#queryParams}}{{paramName}}: {{paramName}}{{#hasMore}},{{/hasMore}}{{/queryParams}} })
{{/hasQueryParams}}
    // accept header
    accepts := []string { {{#produces}}"{{mediaType}}"{{#hasMore}}, {{/hasMore}}{{/produces}} }
    for key := range accepts {
        _sling = _sling.Set("Accept", accepts[key])
        break // only use the first Accept
    }
{{#hasHeaderParams}}{{#headerParams}}    // header params "{{baseName}}"
    _sling = _sling.Set("{{baseName}}", {{paramName}})
{{/headerParams}}{{/hasHeaderParams}}
{{#hasFormParams}}    type FormParams struct {
{{#formParams}}        {{paramName}}    {{dataType}} `url:"{{baseName}},omitempty"`
{{/formParams}}
    }
    _sling = _sling.BodyForm(&FormParams{ {{#formParams}}{{paramName}}: {{paramName}}{{#hasMore}},{{/hasMore}}{{/formParams}} })
{{/hasFormParams}}
{{#hasBodyParam}}{{#bodyParams}}// body params
    _sling = _sling.BodyJSON({{paramName}})
{{/bodyParams}}{{/hasBodyParam}}
{{#returnType}}  var successPayload = new({{returnType}}){{/returnType}}

  // We use this map (below) so that any arbitrary error JSON can be handled.
  // FIXME: This is in the absence of this Go generator honoring the non-2xx
  // response (error) models, which needs to be implemented at some point.
  var failurePayload map[string]interface{}

  httpResponse, err := _sling.Receive({{#returnType}}successPayload{{/returnType}}{{^returnType}}nil{{/returnType}}, &failurePayload)

  if err == nil {
    // err == nil only means that there wasn't a sub-application-layer error (e.g. no network error)
    if failurePayload != nil {
      // If the failurePayload is present, there likely was some kind of non-2xx status
      // returned (and a JSON payload error present)
      var str []byte
      str, err = json.Marshal(failurePayload)
      if err == nil { // For safety, check for an error marshalling... probably superfluous
        // This will return the JSON error body as a string
        err = errors.New(string(str))
      }
  } else {
    // So, there was no network-type error, and nothing in the failure payload,
    // but we should still check the status code
    if httpResponse == nil {
      // This should never happen...
      err = errors.New("No HTTP Response received.")
    } else if code := httpResponse.StatusCode; 200 > code || code > 299 {
        err = errors.New("HTTP Error: " + string(httpResponse.StatusCode))
      }
    }
  }

  return {{#returnType}}*successPayload, {{/returnType}}err
}
{{/operation}}
{{/operations}}
