AlistGo/alist · error
[doubao_new] v3 fallback payload out of range: seq=%d offset
Error message
[doubao_new] v3 fallback payload out of range: seq=%d offset=%d size=%d total=%d
What it means
Second guard in the v3 fallback loop: the cumulative offset plus the block's size would slice past the end of data, meaning sum(sizeList) > len(data). The concatenated payloads no longer match the declared sizes, so re-upload cannot proceed.
Source
Thrown at drivers/doubao_new/util.go:793
msg := fmt.Sprintf("[doubao_new] decode response failed (status: %s, content-type: %s, body: %s): %v",
res.Status(),
res.Header().Get("Content-Type"),
string(body),
err,
)
return UploadMergeData{}, fmt.Errorf(msg)
}
if resp.Code != 0 {
if res != nil && res.StatusCode() == http.StatusBadRequest && resp.Code == 2 {
success := make([]int, 0, len(seqList))
offset := 0
for i, seq := range seqList {
size := sizeList[i]
if size <= 0 {
return UploadMergeData{SuccessSeqList: success}, fmt.Errorf("[doubao_new] v3 fallback invalid size: seq=%d size=%d", seq, size)
}
if offset+int(size) > len(data) {
return UploadMergeData{SuccessSeqList: success}, fmt.Errorf("[doubao_new] v3 fallback payload out of range: seq=%d offset=%d size=%d total=%d", seq, offset, size, len(data))
}
payload := data[offset : offset+int(size)]
block := UploadBlockNeed{
Seq: seq,
Size: size,
Checksum: checksumList[i],
}
if err := d.uploadBlockV3(ctx, uploadID, block, payload); err != nil {
return UploadMergeData{SuccessSeqList: success}, err
}
success = append(success, seq)
offset += int(size)
}
return UploadMergeData{SuccessSeqList: success}, nil
}
errMsg := resp.Msg
if errMsg == "" {
errMsg = resp.MessageView on GitHub (pinned to 843d9dc814)
Solutions
- Restart the upload end-to-end with a fresh upload_id; partial state is inconsistent.
- Add a pre-check where data is assembled: fail if int64(len(data)) != sum(groupSizes) (the flushGroup check exists but only compares against groupExpectSum — make sure groupExpectSum is derived from the same sizeList).
- Ensure the source file is immutable for the duration of the upload (copy-on-write snapshot or lock).
Example fix
// before
payload := data[offset : offset+int(size)]
// after
total := int64(0)
for _, s := range sizeList { total += s }
if total != int64(len(data)) {
return UploadMergeData{}, fmt.Errorf("[doubao_new] sizes/data mismatch: sum=%d len=%d", total, len(data))
} Defensive patterns
Strategy: validation
Validate before calling
total := int64(0)
for _, s := range sizeList { total += s }
if total != int64(len(data)) {
return fmt.Errorf("sizes/data mismatch: sum=%d len=%d", total, len(data))
} Prevention
- Derive groupExpectSum and sizeList from the same slice so they cannot diverge.
- Keep the source file immutable during upload (snapshot/lock).
When it happens
Trigger: mergeUploadBlocks is invoked with sizeList that sums to more than the actual data buffer length — e.g., data was truncated after sizes were computed, sizes come from a different file version, or a caller passes mismatched parallel slices. Reached only after a 400/code-2 merge rejection triggers the fallback.
Common situations: File modified during upload (size changed between hashing and reading); tmpFile shorter than expected; bug in group accumulation where groupSizes retains entries from a previous group.
Related errors
- [doubao_new] v3 fallback invalid size: seq=%d size=%d
- invalid URL format: %w
- failed to refresh token: %w
- get upload_config failed: %s
- upload failed: %s
AI-assisted analysis of AlistGo/alist@843d9dc814 (2026-08-15).
Data as JSON: /api/errors/c03df6bb40bc57df.
Report an issue: GitHub.