Skip to content

Commit

Permalink
Match Liquid/Ruby array[float]
Browse files Browse the repository at this point in the history
  • Loading branch information
osteele committed Jul 21, 2017
1 parent 8040e9e commit fa5de60
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 7 deletions.
24 changes: 17 additions & 7 deletions evaluator/value.go
Original file line number Diff line number Diff line change
Expand Up @@ -148,13 +148,23 @@ func (v structValue) Contains(elem Value) bool {

func (v arrayValue) IndexValue(index Value) Value {
rv := reflect.ValueOf(v.basis)
if n, ok := index.Interface().(int); ok {
if n < 0 {
n += rv.Len()
}
if 0 <= n && n < rv.Len() {
return ValueOf(rv.Index(n).Interface())
}
var n int
switch ix := index.Interface().(type) {
case int:
n = ix
case float32:
// this how Ruby arrays, and therefore Liquid arrays, work
n = int(ix)
case float64:
n = int(ix)
default:
return nilValue
}
if n < 0 {
n += rv.Len()
}
if 0 <= n && n < rv.Len() {
return ValueOf(rv.Index(n).Interface())
}
return nilValue
}
Expand Down
2 changes: 2 additions & 0 deletions evaluator/value_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,8 @@ func TestValue_IndexValue(t *testing.T) {
av := ValueOf([]string{"first", "second", "third"})
require.Equal(t, "first", av.IndexValue(ValueOf(0)).Interface())
require.Equal(t, "third", av.IndexValue(ValueOf(-1)).Interface())
require.Equal(t, "second", av.IndexValue(ValueOf(1.0)).Interface())
require.Equal(t, "second", av.IndexValue(ValueOf(1.1)).Interface())

hv := ValueOf(map[string]interface{}{"key": "value"})
require.Equal(t, "value", hv.IndexValue(ValueOf("key")).Interface())
Expand Down

0 comments on commit fa5de60

Please sign in to comment.