Add `basename` and `dirname` functions
Adds `basename` and `dirname` interpolation. I want to add a `stack` tag to our infrastructure, the value of which is set to `${basename(path.cwd)}`. We currently use `${replace(path.cwd, "/^.+\\//", "")}` instead, but this is extremeley unreadable. The existance of a `basename` function would be very useful for this use case. I don't have an immediate use case for a `dirname` function, but it seemed reasonable to add it as well.
This commit is contained in:
parent
8b1df456eb
commit
af2c84de5a
|
@ -11,6 +11,7 @@ import (
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"math"
|
"math"
|
||||||
"net"
|
"net"
|
||||||
|
"path/filepath"
|
||||||
"regexp"
|
"regexp"
|
||||||
"sort"
|
"sort"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
@ -52,6 +53,7 @@ func listVariableValueToStringSlice(values []ast.Variable) ([]string, error) {
|
||||||
// Funcs is the mapping of built-in functions for configuration.
|
// Funcs is the mapping of built-in functions for configuration.
|
||||||
func Funcs() map[string]ast.Function {
|
func Funcs() map[string]ast.Function {
|
||||||
return map[string]ast.Function{
|
return map[string]ast.Function{
|
||||||
|
"basename": interpolationFuncBasename(),
|
||||||
"base64decode": interpolationFuncBase64Decode(),
|
"base64decode": interpolationFuncBase64Decode(),
|
||||||
"base64encode": interpolationFuncBase64Encode(),
|
"base64encode": interpolationFuncBase64Encode(),
|
||||||
"base64sha256": interpolationFuncBase64Sha256(),
|
"base64sha256": interpolationFuncBase64Sha256(),
|
||||||
|
@ -62,6 +64,7 @@ func Funcs() map[string]ast.Function {
|
||||||
"coalesce": interpolationFuncCoalesce(),
|
"coalesce": interpolationFuncCoalesce(),
|
||||||
"compact": interpolationFuncCompact(),
|
"compact": interpolationFuncCompact(),
|
||||||
"concat": interpolationFuncConcat(),
|
"concat": interpolationFuncConcat(),
|
||||||
|
"dirname": interpolationFuncDirname(),
|
||||||
"distinct": interpolationFuncDistinct(),
|
"distinct": interpolationFuncDistinct(),
|
||||||
"element": interpolationFuncElement(),
|
"element": interpolationFuncElement(),
|
||||||
"file": interpolationFuncFile(),
|
"file": interpolationFuncFile(),
|
||||||
|
@ -600,6 +603,17 @@ func interpolationFuncIndex() ast.Function {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// interpolationFuncBasename implements the "dirname" function.
|
||||||
|
func interpolationFuncDirname() ast.Function {
|
||||||
|
return ast.Function{
|
||||||
|
ArgTypes: []ast.Type{ast.TypeString},
|
||||||
|
ReturnType: ast.TypeString,
|
||||||
|
Callback: func(args []interface{}) (interface{}, error) {
|
||||||
|
return filepath.Dir(args[0].(string)), nil
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// interpolationFuncDistinct implements the "distinct" function that
|
// interpolationFuncDistinct implements the "distinct" function that
|
||||||
// removes duplicate elements from a list.
|
// removes duplicate elements from a list.
|
||||||
func interpolationFuncDistinct() ast.Function {
|
func interpolationFuncDistinct() ast.Function {
|
||||||
|
@ -1006,6 +1020,17 @@ func interpolationFuncValues(vs map[string]ast.Variable) ast.Function {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// interpolationFuncBasename implements the "basename" function.
|
||||||
|
func interpolationFuncBasename() ast.Function {
|
||||||
|
return ast.Function{
|
||||||
|
ArgTypes: []ast.Type{ast.TypeString},
|
||||||
|
ReturnType: ast.TypeString,
|
||||||
|
Callback: func(args []interface{}) (interface{}, error) {
|
||||||
|
return filepath.Base(args[0].(string)), nil
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// interpolationFuncBase64Encode implements the "base64encode" function that
|
// interpolationFuncBase64Encode implements the "base64encode" function that
|
||||||
// allows Base64 encoding.
|
// allows Base64 encoding.
|
||||||
func interpolationFuncBase64Encode() ast.Function {
|
func interpolationFuncBase64Encode() ast.Function {
|
||||||
|
|
|
@ -852,6 +852,18 @@ func TestInterpolateFuncMerge(t *testing.T) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestInterpolateFuncDirname(t *testing.T) {
|
||||||
|
testFunction(t, testFunctionConfig{
|
||||||
|
Cases: []testFunctionCase{
|
||||||
|
{
|
||||||
|
`${dirname("/foo/bar/baz")}`,
|
||||||
|
"/foo/bar",
|
||||||
|
false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
func TestInterpolateFuncDistinct(t *testing.T) {
|
func TestInterpolateFuncDistinct(t *testing.T) {
|
||||||
testFunction(t, testFunctionConfig{
|
testFunction(t, testFunctionConfig{
|
||||||
Cases: []testFunctionCase{
|
Cases: []testFunctionCase{
|
||||||
|
@ -1777,6 +1789,18 @@ func TestInterpolateFuncElement(t *testing.T) {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestInterpolateFuncBasename(t *testing.T) {
|
||||||
|
testFunction(t, testFunctionConfig{
|
||||||
|
Cases: []testFunctionCase{
|
||||||
|
{
|
||||||
|
`${basename("/foo/bar/baz")}`,
|
||||||
|
"baz",
|
||||||
|
false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
func TestInterpolateFuncBase64Encode(t *testing.T) {
|
func TestInterpolateFuncBase64Encode(t *testing.T) {
|
||||||
testFunction(t, testFunctionConfig{
|
testFunction(t, testFunctionConfig{
|
||||||
Cases: []testFunctionCase{
|
Cases: []testFunctionCase{
|
||||||
|
|
|
@ -140,6 +140,8 @@ syntax `name(arg, arg2, ...)`. For example, to read a file:
|
||||||
|
|
||||||
The supported built-in functions are:
|
The supported built-in functions are:
|
||||||
|
|
||||||
|
* `basename(path)` - Returns the last element of a path.
|
||||||
|
|
||||||
* `base64decode(string)` - Given a base64-encoded string, decodes it and
|
* `base64decode(string)` - Given a base64-encoded string, decodes it and
|
||||||
returns the original string.
|
returns the original string.
|
||||||
|
|
||||||
|
@ -183,6 +185,8 @@ The supported built-in functions are:
|
||||||
* `concat(list1, list2, ...)` - Combines two or more lists into a single list.
|
* `concat(list1, list2, ...)` - Combines two or more lists into a single list.
|
||||||
Example: `concat(aws_instance.db.*.tags.Name, aws_instance.web.*.tags.Name)`
|
Example: `concat(aws_instance.db.*.tags.Name, aws_instance.web.*.tags.Name)`
|
||||||
|
|
||||||
|
* `dirname(path)` - Returns all but the last element of path, typically the path's directory.
|
||||||
|
|
||||||
* `distinct(list)` - Removes duplicate items from a list. Keeps the first
|
* `distinct(list)` - Removes duplicate items from a list. Keeps the first
|
||||||
occurrence of each element, and removes subsequent occurrences. This
|
occurrence of each element, and removes subsequent occurrences. This
|
||||||
function is only valid for flat lists. Example: `distinct(var.usernames)`
|
function is only valid for flat lists. Example: `distinct(var.usernames)`
|
||||||
|
|
Loading…
Reference in New Issue