diff --git a/src/pkg/p2p/preheat/provider/client/http_client.go b/src/pkg/p2p/preheat/provider/client/http_client.go index a08e9117f..2c82a36f7 100644 --- a/src/pkg/p2p/preheat/provider/client/http_client.go +++ b/src/pkg/p2p/preheat/provider/client/http_client.go @@ -13,6 +13,8 @@ import ( "github.com/goharbor/harbor/src/lib/log" "github.com/goharbor/harbor/src/pkg/p2p/preheat/provider/auth" + + common_http "github.com/goharbor/harbor/src/common/http" ) const ( @@ -193,6 +195,10 @@ func (hc *HTTPClient) post(url string, cred *auth.Credential, body interface{}, if (res.StatusCode / 100) != 2 { // Return the server error content in the error. return nil, fmt.Errorf("%s '%s' error: %s %s", http.MethodPost, res.Request.URL.String(), res.Status, bytes) + } else if res.StatusCode == http.StatusAlreadyReported { + // Currently because if image was already preheated at least once, Dragonfly will return StatusAlreadyReported. + // And we should preserve http status code info to process this case later. + return bytes, &common_http.Error{Code: http.StatusAlreadyReported, Message: "status already reported"} } return bytes, nil diff --git a/src/pkg/p2p/preheat/provider/dragonfly.go b/src/pkg/p2p/preheat/provider/dragonfly.go index b0c5b5289..b59cd1d36 100644 --- a/src/pkg/p2p/preheat/provider/dragonfly.go +++ b/src/pkg/p2p/preheat/provider/dragonfly.go @@ -4,8 +4,10 @@ import ( "encoding/json" "errors" "fmt" + "net/http" "strings" + common_http "github.com/goharbor/harbor/src/common/http" "github.com/goharbor/harbor/src/pkg/p2p/preheat/models/provider" "github.com/goharbor/harbor/src/pkg/p2p/preheat/provider/auth" "github.com/goharbor/harbor/src/pkg/p2p/preheat/provider/client" @@ -76,10 +78,17 @@ func (dd *DragonflyDriver) Preheat(preheatingImage *PreheatImage) (*PreheatingSt return nil, errors.New("no image specified") } + taskStatus := provider.PreheatingStatusPending // default url := fmt.Sprintf("%s%s", strings.TrimSuffix(dd.instance.Endpoint, "/"), preheatEndpoint) bytes, err := client.GetHTTPClient(dd.instance.Insecure).Post(url, dd.getCred(), preheatingImage, nil) if err != nil { - return nil, err + if httpErr, ok := err.(*common_http.Error); ok && httpErr.Code == http.StatusAlreadyReported { + // If the resource was preheated already with empty task ID, we should set preheat status to success. + // Otherwise later querying for the task + taskStatus = provider.PreheatingStatusSuccess + } else { + return nil, err + } } result := &dragonflyPreheatCreateResp{} @@ -89,7 +98,7 @@ func (dd *DragonflyDriver) Preheat(preheatingImage *PreheatImage) (*PreheatingSt return &PreheatingStatus{ TaskID: result.ID, - Status: provider.PreheatingStatusPending, // default + Status: taskStatus, }, nil }