Add index to map iteration
This commit is contained in:
parent
4501ef63d6
commit
d91eef09bf
32
for_tag.go
32
for_tag.go
@ -1,6 +1,7 @@
|
|||||||
package salix
|
package salix
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"errors"
|
||||||
"reflect"
|
"reflect"
|
||||||
|
|
||||||
"go.elara.ws/salix/ast"
|
"go.elara.ws/salix/ast"
|
||||||
@ -10,35 +11,27 @@ import (
|
|||||||
type forTag struct{}
|
type forTag struct{}
|
||||||
|
|
||||||
func (ft forTag) Run(tc *TagContext, block, args []ast.Node) error {
|
func (ft forTag) Run(tc *TagContext, block, args []ast.Node) error {
|
||||||
if len(args) == 0 || len(args) > 2 {
|
if len(args) == 0 || len(args) > 3 {
|
||||||
return tc.PosError(tc.Tag, "invalid argument amount")
|
return tc.PosError(tc.Tag, "invalid argument amount")
|
||||||
}
|
}
|
||||||
|
|
||||||
var expr ast.Expr
|
expr, ok := args[len(args)-1].(ast.Expr)
|
||||||
if len(args) == 1 {
|
|
||||||
expr2, ok := args[0].(ast.Expr)
|
|
||||||
if !ok {
|
if !ok {
|
||||||
return tc.PosError(args[0], "invalid argument type: %T (expected ast.Expr)", args[0])
|
return tc.PosError(args[0], "invalid argument type: %T (expected ast.Expr)", args[0])
|
||||||
}
|
}
|
||||||
expr = expr2
|
|
||||||
} else if len(args) == 2 {
|
|
||||||
expr2, ok := args[1].(ast.Expr)
|
|
||||||
if !ok {
|
|
||||||
return tc.PosError(args[1], "invalid argument type: %T (expected ast.Expr)", args[1])
|
|
||||||
}
|
|
||||||
expr = expr2
|
|
||||||
}
|
|
||||||
|
|
||||||
var vars []string
|
var vars []string
|
||||||
var in reflect.Value
|
var in reflect.Value
|
||||||
|
|
||||||
if len(args) == 2 {
|
if len(args) > 1 {
|
||||||
varName, ok := unwrap(args[0]).(ast.Ident)
|
for _, arg := range args[:len(args)-1] {
|
||||||
|
varName, ok := unwrap(arg).(ast.Ident)
|
||||||
if !ok {
|
if !ok {
|
||||||
return tc.PosError(args[0], "invalid argument type: %T (expected ast.Ident)", expr.First)
|
return tc.PosError(arg, "invalid argument type: %T (expected ast.Ident)", expr.First)
|
||||||
}
|
}
|
||||||
vars = append(vars, varName.Value)
|
vars = append(vars, varName.Value)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
varName, ok := unwrap(expr.First).(ast.Ident)
|
varName, ok := unwrap(expr.First).(ast.Ident)
|
||||||
if !ok {
|
if !ok {
|
||||||
@ -70,6 +63,8 @@ func (ft forTag) Run(tc *TagContext, block, args []ast.Node) error {
|
|||||||
} else if len(vars) == 2 {
|
} else if len(vars) == 2 {
|
||||||
local[vars[0]] = i
|
local[vars[0]] = i
|
||||||
local[vars[1]] = in.Index(i).Interface()
|
local[vars[1]] = in.Index(i).Interface()
|
||||||
|
} else {
|
||||||
|
return errors.New("slices and arrays can only use two for loop variables")
|
||||||
}
|
}
|
||||||
|
|
||||||
err = tc.Execute(block, local)
|
err = tc.Execute(block, local)
|
||||||
@ -80,18 +75,25 @@ func (ft forTag) Run(tc *TagContext, block, args []ast.Node) error {
|
|||||||
case reflect.Map:
|
case reflect.Map:
|
||||||
local := map[string]any{}
|
local := map[string]any{}
|
||||||
iter := in.MapRange()
|
iter := in.MapRange()
|
||||||
|
i := 0
|
||||||
for iter.Next() {
|
for iter.Next() {
|
||||||
if len(vars) == 1 {
|
if len(vars) == 1 {
|
||||||
local[vars[0]] = iter.Value().Interface()
|
local[vars[0]] = iter.Value().Interface()
|
||||||
} else if len(vars) == 2 {
|
} else if len(vars) == 2 {
|
||||||
local[vars[0]] = iter.Key().Interface()
|
local[vars[0]] = iter.Key().Interface()
|
||||||
local[vars[1]] = iter.Value().Interface()
|
local[vars[1]] = iter.Value().Interface()
|
||||||
|
} else if len(vars) == 3 {
|
||||||
|
local[vars[0]] = i
|
||||||
|
local[vars[1]] = iter.Key().Interface()
|
||||||
|
local[vars[2]] = iter.Value().Interface()
|
||||||
}
|
}
|
||||||
|
|
||||||
err = tc.Execute(block, local)
|
err = tc.Execute(block, local)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
i++
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user