Skip to content

Commit

Permalink
Improve httpjson template function join
Browse files Browse the repository at this point in the history
  • Loading branch information
marc-gr committed Sep 20, 2021
1 parent c347f46 commit 1956601
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 6 deletions.
2 changes: 1 addition & 1 deletion x-pack/filebeat/docs/inputs/input-httpjson.asciidoc
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ Some built-in helper functions are provided to work with the input state inside
- `hmac`: calculates the hmac signature of a list of strings concatenated together. Supports sha1 or sha256. Example `[[hmac "sha256" "secret" "string1" "string2" (formatDate (now) "RFC1123")]]`
- `base64Encode`: Joins and base64 encodes all supplied strings. Example `[[base64Encode "string1" "string2"]]`
- `base64EncodeNoPad`: Joins and base64 encodes all supplied strings without padding. Example `[[base64EncodeNoPad "string1" "string2"]]`
- `join`: joins a list of strings using the specified separator. Example: `[[join .body.arr ","]]`
- `join`: joins a list using the specified separator. Example: `[[join .body.arr ","]]`
- `sprintf`: formats according to a format specifier and returns the resulting string. Refer to https://pkg.go.dev/fmt#Sprintf[the Go docs] for usage. Example: `[[sprintf "%d:%q" 34 "quote this"]]`

In addition to the provided functions, any of the native functions for https://golang.org/pkg/time/#Time[`time.Time`], https://golang.org/pkg/net/http/#Header[`http.Header`], and https://golang.org/pkg/net/url/#Values[`url.Values`] types can be used on the corresponding objects. Examples: `[[(now).Day]]`, `[[.last_response.header.Get "key"]]`
Expand Down
29 changes: 28 additions & 1 deletion x-pack/filebeat/input/httpjson/internal/v2/value_tpl.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ func (t *valueTpl) Unpack(in string) error {
"hmac": hmacString,
"base64Encode": base64Encode,
"base64EncodeNoPad": base64EncodeNoPad,
"join": strings.Join,
"join": join,
"sprintf": fmt.Sprintf,
}).
Delims(leftDelim, rightDelim).
Expand Down Expand Up @@ -289,3 +289,30 @@ func hmacString(hmacType string, hmacKey string, values ...string) string {
// Get result and encode as hexadecimal string
return hex.EncodeToString(mac.Sum(nil))
}

// join concatenates the elements of its first argument to create a single string. The separator
// string sep is placed between elements in the resulting string. If the first argument is not of
// type string or []string, its elements will be stringified.
func join(v interface{}, sep string) string {
// check for []string or string to avoid using reflect
switch t := v.(type) {
case []string:
return strings.Join(t, sep)
case string:
return t
}

// if we have a slice of a different type, convert it to []string
switch reflect.TypeOf(v).Kind() {
case reflect.Slice, reflect.Array:
s := reflect.ValueOf(v)
vs := make([]string, s.Len())
for i := 0; i < s.Len(); i++ {
vs[i] = fmt.Sprint(s.Index(i))
}
return strings.Join(vs, sep)
}

// return the stringified single value
return fmt.Sprint(v)
}
20 changes: 16 additions & 4 deletions x-pack/filebeat/input/httpjson/internal/v2/value_tpl_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -292,24 +292,36 @@ func TestValueTpl(t *testing.T) {
expectedError: errEmptyTemplateResult.Error(),
},
{
name: "func join",
value: `[[join .last_response.body.arr ","]]`,
name: "func join",
value: `[[join .last_response.body.strarr ","]] [[join .last_response.body.iarr ","]] ` +
`[[join .last_response.body.narr ","]] [[join .last_response.body.singlevalstr ","]] ` +
`[[join .last_response.body.singlevalint ","]]`,
paramCtx: &transformContext{
firstEvent: &common.MapStr{},
lastEvent: &common.MapStr{},
lastResponse: newTestResponse(
common.MapStr{
"arr": []string{
"strarr": []string{
"foo",
"bar",
},
"iarr": []interface{}{
"foo",
2,
},
"narr": []int{
1,
2,
},
"singlevalstr": "foo",
"singlevalint": 2,
},
http.Header{},
"",
),
},
paramTr: transformable{},
expectedVal: "foo,bar",
expectedVal: "foo,bar foo,2 1,2 foo 2",
},
{
name: "func sprintf",
Expand Down

0 comments on commit 1956601

Please sign in to comment.