in codegen/service.go [258:386]
func (ms *ModuleSpec) SetDownstream(
e *EndpointSpec,
h *PackageHelper,
) error {
var (
service *ServiceSpec
method *MethodSpec
serviceName = e.ThriftServiceName
methodName = e.ThriftMethodName
clientSpec = e.ClientSpec
clientMethod = e.ClientMethod
// TODO: move generated middlewares out of zanzibar
headersPropagate = e.HeadersPropagate
reqTransforms = e.ReqTransforms
respTransforms = e.RespTransforms
dummyReqTransforms = e.DummyReqTransforms
)
for _, v := range ms.Services {
if v.Name == serviceName {
service = v
break
}
}
if service == nil {
return errors.Errorf(
"Module does not have service %q\n", serviceName,
)
}
for _, v := range service.Methods {
if v.Name == methodName {
method = v
break
}
}
if method == nil {
return errors.Errorf(
"Service %q does not have method %q\n", serviceName, methodName,
)
}
if e.IsClientlessEndpoint {
funcSpec := method.CompiledThriftSpec
err := method.setClientlessTypeConverters(funcSpec, reqTransforms, headersPropagate, respTransforms, dummyReqTransforms, h)
if err != nil {
return errors.Errorf(
"unable to set dummy type convertors for dummy endpoint")
}
return nil
}
serviceMethod, ok := clientSpec.ExposedMethods[clientMethod]
if !ok {
return errors.Errorf("Client %q does not expose method %q", clientSpec.ClientName, clientMethod)
}
sm := strings.Split(serviceMethod, "::")
err := method.setDownstream(clientSpec.ModuleSpec, sm[0], sm[1])
if err != nil {
return err
}
// Exception validation
for en := range method.DownstreamMethod.ExceptionsIndex {
if _, ok := method.ExceptionsIndex[en]; !ok {
return fmt.Errorf("Missing exception %s in Endpoint schema", en)
}
}
// If this is an endpoint then a downstream will be defined.
// If if it a client it will not be.
if method.Downstream != nil {
downstreamMethod := method.DownstreamMethod
downstreamSpec := downstreamMethod.CompiledThriftSpec
funcSpec := method.CompiledThriftSpec
err = method.setTypeConverters(funcSpec, downstreamSpec, reqTransforms, headersPropagate, respTransforms, h, downstreamMethod)
if err != nil {
return err
}
}
if method.Downstream != nil && len(headersPropagate) > 0 {
downstreamMethod, err := findMethodByName(method.Name, method.Downstream.Services)
if err != nil {
return err
}
downstreamSpec := downstreamMethod.CompiledThriftSpec
err = method.setHeaderPropagator(sortedHeaders(e.ReqHeaders, false), downstreamSpec, headersPropagate, h, downstreamMethod)
if err != nil {
return err
}
}
// Adds imports for downstream services.
if !ms.isPackageIncluded(clientSpec.ImportPackagePath) {
ms.IncludedPackages = append(
ms.IncludedPackages, GoPackageImport{
PackageName: clientSpec.ImportPackagePath,
AliasName: clientSpec.ImportPackageAlias,
},
)
}
// Adds imports for thrift types used by downstream services.
for _, service := range ms.Services {
for _, method := range service.Methods {
d := method.Downstream
if d != nil && !ms.isPackageIncluded(d.GoThriftTypesFilePath) {
// thrift types file is optional...
if d.GoThriftTypesFilePath == "" {
continue
}
ms.IncludedPackages = append(
ms.IncludedPackages, GoPackageImport{
PackageName: d.GoThriftTypesFilePath,
AliasName: "",
},
)
}
}
}
return nil
}