mirror of
https://github.com/rclone/rclone.git
synced 2025-01-10 00:08:44 +01:00
fs: fix FixRangeOption make SeekOptions into absolute RangeOptions
Cloudflare R2 doesn't support range options like `Range: bytes=21-`. This patch makes FixRangeOption turn a SeekOption into an absolute RangeOption like this `Range: bytes=21-25` to interoperate with R2. See: #5642
This commit is contained in:
parent
1e66d052fd
commit
f6fd6ee777
@ -138,6 +138,9 @@ func (o *RangeOption) Decode(size int64) (offset, limit int64) {
|
|||||||
// absolute fetch using the size passed in and makes sure the range does
|
// absolute fetch using the size passed in and makes sure the range does
|
||||||
// not exceed filesize. Some remotes (e.g. Onedrive, Box) don't support
|
// not exceed filesize. Some remotes (e.g. Onedrive, Box) don't support
|
||||||
// range requests which index from the end.
|
// range requests which index from the end.
|
||||||
|
//
|
||||||
|
// It also adjusts any SeekOption~s, turning them into absolute
|
||||||
|
// RangeOption~s instead.
|
||||||
func FixRangeOption(options []OpenOption, size int64) {
|
func FixRangeOption(options []OpenOption, size int64) {
|
||||||
if size == 0 {
|
if size == 0 {
|
||||||
// if size 0 then remove RangeOption~s
|
// if size 0 then remove RangeOption~s
|
||||||
@ -150,9 +153,9 @@ func FixRangeOption(options []OpenOption, size int64) {
|
|||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
for i := range options {
|
for i, option := range options {
|
||||||
option := options[i]
|
switch x := option.(type) {
|
||||||
if x, ok := option.(*RangeOption); ok {
|
case *RangeOption:
|
||||||
// If start is < 0 then fetch from the end
|
// If start is < 0 then fetch from the end
|
||||||
if x.Start < 0 {
|
if x.Start < 0 {
|
||||||
x = &RangeOption{Start: size - x.End, End: -1}
|
x = &RangeOption{Start: size - x.End, End: -1}
|
||||||
@ -163,6 +166,8 @@ func FixRangeOption(options []OpenOption, size int64) {
|
|||||||
x = &RangeOption{Start: x.Start, End: size - 1}
|
x = &RangeOption{Start: x.Start, End: size - 1}
|
||||||
options[i] = x
|
options[i] = x
|
||||||
}
|
}
|
||||||
|
case *SeekOption:
|
||||||
|
options[i] = &RangeOption{Start: x.Offset, End: size - 1}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -207,6 +207,20 @@ func TestFixRangeOptions(t *testing.T) {
|
|||||||
},
|
},
|
||||||
size: 100,
|
size: 100,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "SeekOption",
|
||||||
|
in: []OpenOption{
|
||||||
|
&HTTPOption{Key: "a", Value: "1"},
|
||||||
|
&SeekOption{Offset: 10},
|
||||||
|
&HTTPOption{Key: "b", Value: "2"},
|
||||||
|
},
|
||||||
|
want: []OpenOption{
|
||||||
|
&HTTPOption{Key: "a", Value: "1"},
|
||||||
|
&RangeOption{Start: 10, End: 99},
|
||||||
|
&HTTPOption{Key: "b", Value: "2"},
|
||||||
|
},
|
||||||
|
size: 100,
|
||||||
|
},
|
||||||
} {
|
} {
|
||||||
FixRangeOption(test.in, test.size)
|
FixRangeOption(test.in, test.size)
|
||||||
assert.Equal(t, test.want, test.in, test.name)
|
assert.Equal(t, test.want, test.in, test.name)
|
||||||
|
Loading…
Reference in New Issue
Block a user