AlistGo/alist · error

string(data)

Error message

string(data)

What it means

CloudreveV4 OneDrive-policy upload: a chunk response had a status outside {200, 201, 202} and the raw body is returned verbatim as the error. Like the V3 variant, the body is typically Microsoft Graph JSON or a proxy error page.

Source

Thrown at drivers/cloudreve_v4/util.go:374

		res, err := base.HttpClient.Do(req)
		if err != nil {
			return err
		}
		// https://learn.microsoft.com/zh-cn/onedrive/developer/rest-api/api/driveitem_createuploadsession
		switch {
		case res.StatusCode >= 500 && res.StatusCode <= 504:
			retryCount++
			if retryCount > maxRetries {
				res.Body.Close()
				return fmt.Errorf("upload failed after %d retries due to server errors, error %d", maxRetries, res.StatusCode)
			}
			backoff := time.Duration(1<<retryCount) * time.Second
			utils.Log.Warnf("[CloudreveV4-OneDrive] server errors %d while uploading, retrying after %v...", res.StatusCode, backoff)
			time.Sleep(backoff)
		case res.StatusCode != 201 && res.StatusCode != 202 && res.StatusCode != 200:
			data, _ := io.ReadAll(res.Body)
			res.Body.Close()
			return errors.New(string(data))
		default:
			res.Body.Close()
			retryCount = 0
			finish += byteSize
			up(float64(finish) * 100 / float64(file.GetSize()))
		}
	}
	// 上传成功发送回调请求
	return d.request(http.MethodPost, "/callback/onedrive/"+u.SessionID+"/"+u.CallbackSecret, func(req *resty.Request) {
		req.SetBody("{}")
	}, nil)
}

func (d *CloudreveV4) upS3(ctx context.Context, file model.FileStreamer, u FileUploadResp, up driver.UpdateProgress) error {
	var finish int64 = 0
	var chunk int = 0
	var etags []string
	DEFAULT := int64(u.ChunkSize)

View on GitHub (pinned to 843d9dc814)

Solutions

  1. Retry as a brand-new upload session.
  2. Back off on 429s and lower upload concurrency/parallel chunk count.
  3. Read the body — Graph error code/message states the exact problem.
  4. Ensure no intermediary rewrites or caches PUT requests to the Graph upload URL.
Defensive patterns

Strategy: try-catch

Type guard

func isGraphErrorBody(b string) bool { return strings.Contains(b, "\"error\":{\"code\"") }

Try / catch

if res.StatusCode != 200 && res.StatusCode != 201 && res.StatusCode != 202 {
    data, _ := io.ReadAll(res.Body)
    var g struct{ Error struct{ Code, Message string } }
    if json.Unmarshal(data, &g) == nil && g.Error.Code != "" {
        return fmt.Errorf("graph upload %s: %s", g.Error.Code, g.Error.Message)
    }
    return errors.New(string(data))
}

Prevention

When it happens

Trigger: upOneDrive chunk PUT returns e.g. 416 (range mismatch on resume), 404 (expired upload session URL), or 429 (throttle) — anything not 2xx and not 500-504 (those retry with backoff).

Common situations: Upload session URL expired (~15 min lifetime); resumed upload with wrong byte offset; Graph throttling under heavy parallelism; proxy stripping auth headers to Graph.

Related errors


AI-assisted analysis of AlistGo/alist@843d9dc814 (2026-08-15). Data as JSON: /api/errors/43e0d8fe3676a705. Report an issue: GitHub.