func (h *Handler) newFanoutRequests(fanoutCtx context.Context, original *http.Request) ([]*http.Request, error) {
	body, err := ioutil.ReadAll(original.Body)
	if err != nil {
		return nil, err
	}
	urls, err := h.endpoints.FanoutURLs(original)
	if err != nil {
		return nil, err
	} else if len(urls) == 0 {
		return nil, errNoFanoutURLs
	}
	requests := make([]*http.Request, len(urls))
	for i := 0; i < len(urls); i++ {
		fanout := &http.Request{
			Method:     original.Method,
			URL:        urls[i],
			Proto:      "HTTP/1.1",
			ProtoMajor: 1,
			ProtoMinor: 1,
			Header:     make(http.Header),
			Host:       urls[i].Host,
		}
		endpointCtx := fanoutCtx
		var err error
		for _, rf := range h.before {
			endpointCtx, err = rf(endpointCtx, original, fanout, body)
			if err != nil {
				return nil, err
			}
		}
		requests[i] = fanout.WithContext(endpointCtx)
	}
	return requests, nil
}
newFanoutRequests uses the Endpoints strategy and builds (1) HTTP request for each endpoint.  The configured
FanoutRequestFunc options are used to build each request.  This method returns an error if no endpoints were returned
by the strategy or if an error reading the original request body occurred.
package fanout
import (
	"context"
	"errors"
	"fmt"
	"io/ioutil"
	"net/http"
	"net/url"
	"github.com/go-kit/kit/log"
	"github.com/go-kit/kit/log/level"
	gokithttp "github.com/go-kit/kit/transport/http"
	"github.com/xmidt-org/webpa-common/v2/logging"
	"github.com/xmidt-org/webpa-common/v2/tracing"
	"github.com/xmidt-org/webpa-common/v2/tracing/tracinghttp"
)
var (
	errNoFanoutURLs  = errors.New("No fanout URLs")
	errBadTransactor = errors.New("Transactor did not conform to stdlib API")
)
type Option func(*Handler)
func WithShouldTerminate(terminate ShouldTerminateFunc) Option {
	return func(h *Handler) {
		if terminate != nil {
			h.shouldTerminate = terminate
		} else {
			h.shouldTerminate = DefaultShouldTerminate
		}
	}
}
func WithErrorEncoder(encoder gokithttp.ErrorEncoder) Option {
	return func(h *Handler) {
		if encoder != nil {
			h.errorEncoder = encoder
		} else {
			h.errorEncoder = gokithttp.DefaultErrorEncoder
		}
	}
}
func WithTransactor(transactor func(*http.Request) (*http.Response, error)) Option {
	return func(h *Handler) {
		if transactor != nil {
			h.transactor = transactor
		} else {
			h.transactor = http.DefaultClient.Do
		}
	}
}
func WithFanoutBefore(before ...FanoutRequestFunc) Option {
	return func(h *Handler) {
		h.before = append(h.before, before...)
	}
}
func WithClientBefore(before ...gokithttp.RequestFunc) Option {
	return func(h *Handler) {
		for _, rf := range before {
			h.before = append(
				h.before,
				func(ctx context.Context, _, fanout *http.Request, _ []byte) (context.Context, error) {
					return rf(ctx, fanout), nil
				},
			)
		}
	}
}
func WithFanoutAfter(after ...FanoutResponseFunc) Option {
	return func(h *Handler) {
		h.after = append(h.after, after...)
	}
}
func WithClientAfter(after ...gokithttp.ClientResponseFunc) Option {
	return func(h *Handler) {
		for _, rf := range after {
			h.after = append(
				h.after,
				func(ctx context.Context, response http.ResponseWriter, result Result) context.Context {
					return rf(ctx, result.Response)
				},
			)
		}
	}
}
func WithFanoutFailure(failure ...FanoutResponseFunc) Option {
	return func(h *Handler) {
		h.failure = append(h.failure, failure...)
	}
}
func WithClientFailure(failure ...gokithttp.ClientResponseFunc) Option {
	return func(h *Handler) {
		for _, rf := range failure {
			h.failure = append(
				h.failure,
				func(ctx context.Context, response http.ResponseWriter, result Result) context.Context {
					return rf(ctx, result.Response)
				},
			)
		}
	}
}
func WithConfiguration(c Configuration) Option {
	return func(h *Handler) {
		WithTransactor(NewTransactor(c))(h)
		authorization := c.authorization()
		if len(authorization) > 0 {
			WithClientBefore(gokithttp.SetRequestHeader("Authorization", authorization))(h)
		}
	}
}
type Handler struct {
	endpoints       Endpoints
	errorEncoder    gokithttp.ErrorEncoder
	before          []FanoutRequestFunc
	after           []FanoutResponseFunc
	failure         []FanoutResponseFunc
	shouldTerminate ShouldTerminateFunc
	transactor      func(*http.Request) (*http.Response, error)
}
func New(e Endpoints, options ...Option) *Handler {
	if e == nil {
		panic("An Endpoints strategy is required")
	}
	h := &Handler{
		endpoints:       e,
		errorEncoder:    gokithttp.DefaultErrorEncoder,
		shouldTerminate: DefaultShouldTerminate,
		transactor:      http.DefaultClient.Do,
	}
	for _, o := range options {
		o(h)
	}
	return h
}