Fail request when error occurs during download (#3214)

This commit is contained in:
Cesar N
2024-01-26 13:06:25 -08:00
committed by GitHub
parent 96923aed75
commit d4c5e1b51c
3 changed files with 30 additions and 16 deletions

View File

@@ -120,7 +120,7 @@ func processInspectResponse(params *inspectApi.InspectParams, k []byte, r io.Rea
_, err := io.Copy(w, r)
if err != nil {
LogError("Unable to write all the data: %v", err)
LogError("unable to write all the data: %v", err)
}
}
}

View File

@@ -448,6 +448,8 @@ func getDownloadObjectResponse(session *models.Principal, params objectApi.Downl
// override filename is set
decodeOverride, err := base64.StdEncoding.DecodeString(*params.OverrideFileName)
if err != nil {
fmtError := ErrorWithContext(ctx, fmt.Errorf("unable to decode OverrideFileName: %v", err))
http.Error(rw, fmtError.APIError.DetailedMessage, http.StatusBadRequest)
return
}
@@ -472,16 +474,16 @@ func getDownloadObjectResponse(session *models.Principal, params objectApi.Downl
stat, err := resp.Stat()
if err != nil {
minErr := minio.ToErrorResponse(err)
rw.WriteHeader(minErr.StatusCode)
ErrorWithContext(ctx, fmt.Errorf("Failed to get Stat() response from server for %s (version %s): %v", prefix, opts.VersionID, minErr.Error()))
fmtError := ErrorWithContext(ctx, fmt.Errorf("failed to get Stat() response from server for %s (version %s): %v", prefix, opts.VersionID, minErr.Error()))
http.Error(rw, fmtError.APIError.DetailedMessage, http.StatusInternalServerError)
return
}
// if we are getting a Range Request (video) handle that specially
ranges, err := parseRange(params.HTTPRequest.Header.Get("Range"), stat.Size)
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to parse range header input %s: %v", params.HTTPRequest.Header.Get("Range"), err))
rw.WriteHeader(400)
fmtError := ErrorWithContext(ctx, fmt.Errorf("unable to parse range header input %s: %v", params.HTTPRequest.Header.Get("Range"), err))
http.Error(rw, fmtError.APIError.DetailedMessage, http.StatusInternalServerError)
return
}
contentType := stat.ContentType
@@ -510,8 +512,8 @@ func getDownloadObjectResponse(session *models.Principal, params objectApi.Downl
_, err = resp.Seek(start, io.SeekStart)
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to seek at offset %d: %v", start, err))
rw.WriteHeader(400)
fmtError := ErrorWithContext(ctx, fmt.Errorf("unable to seek at offset %d: %v", start, err))
http.Error(rw, fmtError.APIError.DetailedMessage, http.StatusInternalServerError)
return
}
@@ -524,7 +526,9 @@ func getDownloadObjectResponse(session *models.Principal, params objectApi.Downl
rw.Header().Set("Content-Length", fmt.Sprintf("%d", length))
_, err = io.Copy(rw, io.LimitReader(resp, length))
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to write all data to client: %v", err))
ErrorWithContext(ctx, fmt.Errorf("unable to write all data to client: %v", err))
// You can't change headers after you already started writing the body.
// Handle incomplete write in client.
return
}
}), nil
@@ -610,7 +614,8 @@ func getDownloadFolderResponse(session *models.Principal, params objectApi.Downl
encodedPrefix := SanitizeEncodedPrefix(params.Prefix)
decodedPrefix, err := base64.StdEncoding.DecodeString(encodedPrefix)
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to parse encoded prefix %s: %v", encodedPrefix, err))
fmtError := ErrorWithContext(ctx, fmt.Errorf("unable to parse encoded prefix %s: %v", encodedPrefix, err))
http.Error(rw, fmtError.APIError.DetailedMessage, http.StatusInternalServerError)
return
}
@@ -632,7 +637,10 @@ func getDownloadFolderResponse(session *models.Principal, params objectApi.Downl
// Copy the stream
_, err := io.Copy(rw, resp)
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to write all the requested data: %v", err))
ErrorWithContext(ctx, fmt.Errorf("unable to write all the requested data: %v", err))
// You can't change headers after you already started writing the body.
// Handle incomplete write in client.
return
}
}), nil
}
@@ -754,7 +762,10 @@ func getMultipleFilesDownloadResponse(session *models.Principal, params objectAp
// Copy the stream
_, err := io.Copy(rw, resp)
if err != nil {
ErrorWithContext(ctx, fmt.Errorf("Unable to write all the requested data: %v", err))
ErrorWithContext(ctx, fmt.Errorf("unable to write all the requested data: %v", err))
// You can't change headers after you already started writing the body.
// Handle incomplete write in client.
return
}
}), nil
}

View File

@@ -21,7 +21,7 @@ import store from "../../../../../store";
import { ContentType, PermissionResource } from "api/consoleApi";
import { api } from "../../../../../api";
import { setErrorSnackMessage } from "../../../../../systemSlice";
import { StatusCodes } from "http-status-codes";
const downloadWithLink = (href: string, downloadFileName: string) => {
const link = document.createElement("a");
link.href = href;
@@ -78,6 +78,7 @@ export const download = (
toastCallback: () => void,
) => {
let basename = document.baseURI.replace(window.location.origin, "");
let bytesLoaded = 0;
const state = store.getState();
const anonymousMode = state.system.anonymousMode;
@@ -106,7 +107,7 @@ export const download = (
"progress",
function (evt) {
let percentComplete = Math.round((evt.loaded / fileSize) * 100);
bytesLoaded = evt.loaded;
if (progressCallback) {
progressCallback(percentComplete);
}
@@ -116,8 +117,10 @@ export const download = (
req.responseType = "blob";
req.onreadystatechange = () => {
if (req.readyState === 4) {
if (req.status === 200) {
if (req.readyState === XMLHttpRequest.DONE) {
let completeDownload = bytesLoaded === fileSize;
if (req.status === StatusCodes.OK && completeDownload) {
const rspHeader = req.getResponseHeader("Content-Disposition");
let filename = "download";
@@ -143,7 +146,7 @@ export const download = (
return;
}
}
errorCallback(`Unexpected response status code (${req.status}).`);
errorCallback(`Unexpected response, download incomplete.`);
}
}
};