elastic / elastic/beats

[bug-hunter] append processor flattens []byte values into integer elements

Open
#49,349 2 comments 1 reaction 2 assignees Claimed by @strawgate View on GitHub
needs_team
Dominant language
Go
Stars
12.7k
Forks
5k
Avg merge
2d 15m
Merged PRs (30d)
385

Description

## Impact
Users whose events include binary fields (`[]byte`) and use the `append` processor get corrupted output shape: a single binary value is expanded into many numeric elements. This can break downstream mappings and queries expecting one value.

## Reproduction Steps
1. Create `libbeat/processors/actions/append_bug_repro_test.go` with this test:

```go
package actions

import "testing"

func TestBugRepro_ByteSliceShouldRemainAtomic(t *testing.T) {
got := valueToArray([]byte("ab"))
if len(got) != 1 {
t.Fatalf("expected byte slice to remain single element, got len=%d values=%#v", len(got), got)
}
b, ok := got[0].([]byte)
if !ok {
t.Fatalf("expected first element []byte, got %T (%#v)", got[0], got[0])
}
if string(b) != "ab" {
t.Fatalf("expected \"ab\", got %q", string(b))
}
}
```

2. Run:

```bash
go test ./libbeat/processors/actions -run TestBugRepro_ByteSliceShouldRemainAtomic -count=1
```

## Expected vs Actual
**Expected:** `[]byte("ab")` is treated as one value (`len == 1`) when normalized for append.

**Actual:** test fails because `[]byte("ab")` is flattened to per-byte integers.

Actual output:

```text
--- FAIL: TestBugRepro_ByteSliceShouldRemainAtomic (0.00s)
append_bug_repro_test.go:8: expected byte slice to remain single element, got len=2 values=[]interface {}{0x61, 0x62}
FAIL
FAIL github.com/elastic/beats/v7/libbeat/processors/actions 0.005s
FAIL
```

## Failing Test
(See reproduction test above; it is minimal and deterministic.)

## Evidence
- Current flattening logic handles all slices/arrays indiscriminately in `libbeat/processors/actions/append.go:208-215`.
- This behavior feeds append normalization via `valueToArray` in `libbeat/processors/actions/append.go:193-219`.
- Pre-change behavior (parent of `4ebd7ba616`) only flattened `[]interface{}` and kept non-`[]interface{}` values atomic (`libbeat/processors/actions/append.go` old lines 106-111 and 123-128), so `[]byte` was not expanded into byte elements.

---
[What is this?](https://ela.st/github-ai-tools) | [From workflow: Bug Hunter](https://github.com/elastic/beats/actions/runs/22850833410)

Give us feedback! React with 🚀 if perfect, 👍 if helpful, 👎 if not.
> - [x] expires on Mar 16, 2026, 11:25 AM UTC

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.