diff --git a/cmd/admin-handlers-pools.go b/cmd/admin-handlers-pools.go index 5b3ac6151..d3227b6ab 100644 --- a/cmd/admin-handlers-pools.go +++ b/cmd/admin-handlers-pools.go @@ -259,7 +259,7 @@ func (a adminAPIHandlers) RebalanceStart(w http.ResponseWriter, r *http.Request) if ep := globalEndpoints[0].Endpoints[0]; !ep.IsLocal { for nodeIdx, proxyEp := range globalProxyEndpoints { if proxyEp.Endpoint.Host == ep.Host { - if proxyRequestByNodeIndex(ctx, w, r, nodeIdx) { + if proxied, success := proxyRequestByNodeIndex(ctx, w, r, nodeIdx, false); proxied && success { return } } @@ -330,7 +330,7 @@ func (a adminAPIHandlers) RebalanceStatus(w http.ResponseWriter, r *http.Request if ep := globalEndpoints[0].Endpoints[0]; !ep.IsLocal { for nodeIdx, proxyEp := range globalProxyEndpoints { if proxyEp.Endpoint.Host == ep.Host { - if proxyRequestByNodeIndex(ctx, w, r, nodeIdx) { + if proxied, success := proxyRequestByNodeIndex(ctx, w, r, nodeIdx, false); proxied && success { return } } @@ -384,7 +384,7 @@ func proxyDecommissionRequest(ctx context.Context, defaultEndPoint Endpoint, w h } for nodeIdx, proxyEp := range globalProxyEndpoints { if proxyEp.Endpoint.Host == host && !proxyEp.IsLocal { - if proxyRequestByNodeIndex(ctx, w, r, nodeIdx) { + if proxied, success := proxyRequestByNodeIndex(ctx, w, r, nodeIdx, false); proxied && success { return true } } diff --git a/cmd/admin-handlers.go b/cmd/admin-handlers.go index 471705d8b..57a4c7aa7 100644 --- a/cmd/admin-handlers.go +++ b/cmd/admin-handlers.go @@ -1320,7 +1320,7 @@ func (a adminAPIHandlers) HealHandler(w http.ResponseWriter, r *http.Request) { } // Analyze the heal token and route the request accordingly - token, success := proxyRequestByToken(ctx, w, r, hip.clientToken) + token, _, success := proxyRequestByToken(ctx, w, r, hip.clientToken, false) if success { return } diff --git a/cmd/batch-expire.go b/cmd/batch-expire.go index 07f56a79d..300d4a8e1 100644 --- a/cmd/batch-expire.go +++ b/cmd/batch-expire.go @@ -445,14 +445,14 @@ func batchObjsForDelete(ctx context.Context, r *BatchJobExpire, ri *batchJobInfo oiCache.Add(od, &exp.ObjectInfo) } - var done bool // DeleteObject(deletePrefix: true) to expire all versions of an object for _, exp := range toExpireAll { var success bool for attempts := 1; attempts <= retryAttempts; attempts++ { select { case <-ctx.Done(): - done = true + ri.trackMultipleObjectVersions(exp, success) + return default: } stopFn := globalBatchJobsMetrics.trace(batchJobMetricExpire, ri.JobID, attempts) @@ -469,14 +469,7 @@ func batchObjsForDelete(ctx context.Context, r *BatchJobExpire, ri *batchJobInfo break } } - ri.trackMultipleObjectVersions(r.Bucket, exp, success) - if done { - break - } - } - - if done { - return + ri.trackMultipleObjectVersions(exp, success) } // DeleteMultiple objects diff --git a/cmd/batch-handlers.go b/cmd/batch-handlers.go index 853fe34cd..64d255f10 100644 --- a/cmd/batch-handlers.go +++ b/cmd/batch-handlers.go @@ -996,7 +996,7 @@ func (ri *batchJobInfo) updateAfter(ctx context.Context, api ObjectLayer, durati // Note: to be used only with batch jobs that affect multiple versions through // a single action. e.g batch-expire has an option to expire all versions of an // object which matches the given filters. -func (ri *batchJobInfo) trackMultipleObjectVersions(bucket string, info ObjectInfo, success bool) { +func (ri *batchJobInfo) trackMultipleObjectVersions(info ObjectInfo, success bool) { if success { ri.Objects += int64(info.NumVersions) } else { @@ -1829,7 +1829,7 @@ func (a adminAPIHandlers) CancelBatchJob(w http.ResponseWriter, r *http.Request) return } - if _, success := proxyRequestByToken(ctx, w, r, jobID); success { + if _, proxied, _ := proxyRequestByToken(ctx, w, r, jobID, true); proxied { return } diff --git a/cmd/bucket-listobjects-handlers.go b/cmd/bucket-listobjects-handlers.go index 7f3134f17..d7664e220 100644 --- a/cmd/bucket-listobjects-handlers.go +++ b/cmd/bucket-listobjects-handlers.go @@ -243,26 +243,26 @@ func parseRequestToken(token string) (subToken string, nodeIndex int) { return subToken, nodeIndex } -func proxyRequestByToken(ctx context.Context, w http.ResponseWriter, r *http.Request, token string) (string, bool) { - subToken, nodeIndex := parseRequestToken(token) - if nodeIndex >= 0 { - return subToken, proxyRequestByNodeIndex(ctx, w, r, nodeIndex) +func proxyRequestByToken(ctx context.Context, w http.ResponseWriter, r *http.Request, token string, returnErr bool) (subToken string, proxied bool, success bool) { + var nodeIndex int + if subToken, nodeIndex = parseRequestToken(token); nodeIndex >= 0 { + proxied, success = proxyRequestByNodeIndex(ctx, w, r, nodeIndex, returnErr) } - return subToken, false + return } -func proxyRequestByNodeIndex(ctx context.Context, w http.ResponseWriter, r *http.Request, index int) (success bool) { +func proxyRequestByNodeIndex(ctx context.Context, w http.ResponseWriter, r *http.Request, index int, returnErr bool) (proxied, success bool) { if len(globalProxyEndpoints) == 0 { - return false + return } if index < 0 || index >= len(globalProxyEndpoints) { - return false + return } ep := globalProxyEndpoints[index] if ep.IsLocal { - return false + return } - return proxyRequest(ctx, w, r, ep) + return true, proxyRequest(ctx, w, r, ep, returnErr) } // ListObjectsV1Handler - GET Bucket (List Objects) Version 1. diff --git a/cmd/endpoint.go b/cmd/endpoint.go index 48d1ce9c6..979702480 100644 --- a/cmd/endpoint.go +++ b/cmd/endpoint.go @@ -1194,7 +1194,7 @@ func GetProxyEndpointLocalIndex(proxyEps []ProxyEndpoint) int { } // GetProxyEndpoints - get all endpoints that can be used to proxy list request. -func GetProxyEndpoints(endpointServerPools EndpointServerPools) []ProxyEndpoint { +func GetProxyEndpoints(endpointServerPools EndpointServerPools, transport http.RoundTripper) []ProxyEndpoint { var proxyEps []ProxyEndpoint proxyEpSet := set.NewStringSet() @@ -1213,7 +1213,7 @@ func GetProxyEndpoints(endpointServerPools EndpointServerPools) []ProxyEndpoint proxyEps = append(proxyEps, ProxyEndpoint{ Endpoint: endpoint, - Transport: globalRemoteTargetTransport, + Transport: transport, }) } } diff --git a/cmd/handler-utils.go b/cmd/handler-utils.go index 5f7bf2b39..a69b5504b 100644 --- a/cmd/handler-utils.go +++ b/cmd/handler-utils.go @@ -447,7 +447,7 @@ func getHostName(r *http.Request) (hostName string) { } // Proxy any request to an endpoint. -func proxyRequest(ctx context.Context, w http.ResponseWriter, r *http.Request, ep ProxyEndpoint) (success bool) { +func proxyRequest(ctx context.Context, w http.ResponseWriter, r *http.Request, ep ProxyEndpoint, returnErr bool) (success bool) { success = true // Make sure we remove any existing headers before @@ -462,7 +462,10 @@ func proxyRequest(ctx context.Context, w http.ResponseWriter, r *http.Request, e ErrorHandler: func(w http.ResponseWriter, r *http.Request, err error) { success = false if err != nil && !errors.Is(err, context.Canceled) { - replLogIf(GlobalContext, err) + proxyLogIf(GlobalContext, err) + } + if returnErr { + writeErrorResponse(ctx, w, toAPIError(ctx, err), r.URL) } }, }) diff --git a/cmd/server-main.go b/cmd/server-main.go index 62014c846..000f7ef8c 100644 --- a/cmd/server-main.go +++ b/cmd/server-main.go @@ -425,9 +425,10 @@ func serverHandleCmdArgs(ctxt serverCtxt) { } // allow transport to be HTTP/1.1 for proxying. - globalProxyEndpoints = GetProxyEndpoints(globalEndpoints) globalInternodeTransport = NewInternodeHTTPTransport(ctxt.MaxIdleConnsPerHost)() globalRemoteTargetTransport = NewRemoteTargetHTTPTransport(false)() + globalProxyEndpoints = GetProxyEndpoints(globalEndpoints, globalRemoteTargetTransport) + globalForwarder = handlers.NewForwarder(&handlers.Forwarder{ PassHost: true, RoundTripper: globalRemoteTargetTransport,