Skip to content

Commit 49579ae

Browse files
VihasMakwanaandrzej-stencelcmacknz
authoredOct 21, 2024··
[chore][otel] Enable persistence in otel.yml (#5549)
* chore: update config, docs * fix: spelling mistake * fix: go tidy * remove comments * fix: go tidy * fix: add filestorage to extension * Update changelog/fragments/1726572104-enable-persistence-by-default.yaml Co-authored-by: Andrzej Stencel <andrzej.stencel@elastic.co> * chore: update readme * chore: update readme * go.mod * chore: go.mod * comments * comments * chore: update notice * chore: go.sum and notice * chore: go.sum and notice * Update internal/pkg/otel/templates/README.md.tmpl Co-authored-by: Craig MacKenzie <craig.mackenzie@elastic.co> * Update internal/pkg/otel/templates/README.md.tmpl Co-authored-by: Craig MacKenzie <craig.mackenzie@elastic.co> * chore: address comments * chore: use STATE_PATH * chore: update readme * fix: add missing import --------- Co-authored-by: Andrzej Stencel <andrzej.stencel@elastic.co> Co-authored-by: Craig MacKenzie <craig.mackenzie@elastic.co>
1 parent 283429a commit 49579ae

File tree

5 files changed

+154
-1
lines changed

5 files changed

+154
-1
lines changed
 
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
# Kind can be one of:
2+
# - breaking-change: a change to previously-documented behavior
3+
# - deprecation: functionality that is being removed in a later release
4+
# - bug-fix: fixes a problem in a previous version
5+
# - enhancement: extends functionality but does not break or fix existing behavior
6+
# - feature: new functionality
7+
# - known-issue: problems that we are aware of in a given version
8+
# - security: impacts on the security of a product or a user’s deployment.
9+
# - upgrade: important information for someone upgrading from a prior version
10+
# - other: does not fit into any of the other categories
11+
kind: feature
12+
13+
# Change summary; a 80ish characters long description of the change.
14+
summary: Enable persistence in the configuration provided with our OTel Collector distribution.
15+
16+
# Long description; in case the summary is not enough to describe the change
17+
# this field accommodate a description without length limits.
18+
# NOTE: This field will be rendered only for breaking-change and known-issue kinds at the moment.
19+
#description:
20+
21+
# Affected component; usually one of "elastic-agent", "fleet-server", "filebeat", "metricbeat", "auditbeat", "all", etc.
22+
component: elastic-agent,otel
23+
24+
# PR URL; optional; the PR number that added the changeset.
25+
# If not present is automatically filled by the tooling finding the PR where this changelog fragment has been added.
26+
# NOTE: the tooling supports backports, so it's able to fill the original PR number instead of the backport PR number.
27+
# Please provide it if you are adding a fragment for a different PR.
28+
pr:
29+
30+
# Issue URL; optional; the GitHub issue related to this changeset (either closes or is part of).
31+
# If not present is automatically filled by the tooling with the issue linked to the PR number.
32+
#issue: https://github.com/owner/repo/1234

‎internal/pkg/agent/cmd/otel.go

+19
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ package cmd
88

99
import (
1010
"context"
11+
"os"
1112

1213
"github.com/spf13/cobra"
1314
"github.com/spf13/pflag"
@@ -27,6 +28,9 @@ func newOtelCommandWithArgs(args []string, streams *cli.IOStreams) *cobra.Comman
2728
if err != nil {
2829
return err
2930
}
31+
if err := prepareEnv(); err != nil {
32+
return err
33+
}
3034
return runCollector(cmd.Context(), cfgFiles)
3135
},
3236
PreRun: func(c *cobra.Command, args []string) {
@@ -78,3 +82,18 @@ func runCollector(cmdCtx context.Context, configFiles []string) error {
7882

7983
return otel.Run(ctx, stop, configFiles)
8084
}
85+
86+
func prepareEnv() error {
87+
if _, ok := os.LookupEnv("STATE_PATH"); !ok {
88+
// STATE_PATH is not set. Set it to defaultStateDirectory because we do not want to use any of the paths, that are also used by Beats or Agent
89+
// because a standalone OTel collector must be able to run alongside them without issue.
90+
91+
// The filestorage extension will handle directory creation since create_directory: true is set by default.
92+
// If the user hasn’t specified the env:STATE_PATH in filestorage config, they may have opted for a custom path, and the extension will create the directory accordingly.
93+
// In this case, setting env:STATE_PATH will have no effect.
94+
if err := os.Setenv("STATE_PATH", defaultStateDirectory); err != nil {
95+
return err
96+
}
97+
}
98+
return nil
99+
}

‎internal/pkg/otel/README.md

+48
Original file line numberDiff line numberDiff line change
@@ -81,3 +81,51 @@ This section provides a summary of components included in the Elastic Distributi
8181
|---|---|
8282
| [signaltometricsconnector](https://github.com/elastic/opentelemetry-collector-components/blob/connector/signaltometricsconnector/v0.2.1/connector/signaltometricsconnector/README.md) | v0.2.1 |
8383
| [spanmetricsconnector](https://github.com/open-telemetry/opentelemetry-collector-contrib/blob/connector/spanmetricsconnector/v0.111.0/connector/spanmetricsconnector/README.md) | v0.111.0 |
84+
## Persistence in OpenTelemetry Collector
85+
86+
By default, the OpenTelemetry Collector is stateless, which means it doesn't store offsets on disk while reading files. As a result, if you restart the collector, it won't retain the last read offset, potentially leading to data duplication or loss. However, we have configured persistence in the settings provided with the Elastic Agent package.
87+
88+
To enable persistence for the `filelogreceiver`, we add the `file_storage` extension and activate it for `filelog`.
89+
Execute `export STATE_PATH=/path/to/store/otel/offsets` and use the following configuration to enable persistence:
90+
91+
```yaml
92+
receivers:
93+
filelog/platformlogs:
94+
include: [ /var/log/system.log ]
95+
start_at: beginning
96+
storage: file_storage/filelogreceiver
97+
extensions:
98+
file_storage/filelogreceiver:
99+
directory: ${env:STATE_PATH}
100+
create_directory: true
101+
exporters:
102+
...
103+
processors:
104+
...
105+
service:
106+
extensions: [file_storage]
107+
pipelines:
108+
logs/platformlogs:
109+
receivers: [filelog/platformlogs]
110+
processors: [...]
111+
exporters: [...]
112+
```
113+
114+
> [!WARNING]
115+
Removing the storage key from the filelog section will disable persistence, which will lead to data duplication or loss when the collector restarts.
116+
117+
> [!IMPORTANT]
118+
If you remove the `create_directory: true` option, you'll need to manually create a directory to store the data. You can ignore this option if the directory already exists.
119+
120+
### Persistence in standalone Docker mode
121+
122+
By default, when running Elastic Distribution for OpenTelemetry Collector in Docker, checkpoints are stored in `/usr/share/elastic-agent/otel_registry` by default. To ensure data persists across container restarts, you can use the following command:
123+
124+
```bash
125+
docker run --rm -ti --entrypoint="elastic-agent" --mount type=bind,source=/path/on/host,target=/usr/share/elastic-agent/otel_registry docker.elastic.co/beats/elastic-agent:9.0.0-SNAPSHOT otel
126+
```
127+
128+
### Known issues:
129+
- You face following `failed to build extensions: failed to create extension "file_storage/filelogreceiver": mkdir ...: permission denied` error while running the otel mode
130+
- Cause: This issue is likely because the user running the executable lacks sufficient permissions to create the directory.
131+
- Resolution: You can either create the directory manually or specify a path with necessary permissions.

‎internal/pkg/otel/templates/README.md.tmpl

+50
Original file line numberDiff line numberDiff line change
@@ -74,3 +74,53 @@ This section provides a summary of components included in the Elastic Distributi
7474
| [{{ .Name }}]({{ .Link }}) | {{ .Version }} |
7575
{{ end -}}
7676
{{ end -}}
77+
78+
79+
## Persistence in OpenTelemetry Collector
80+
81+
By default, the OpenTelemetry Collector is stateless, which means it doesn't store offsets on disk while reading files. As a result, if you restart the collector, it won't retain the last read offset, potentially leading to data duplication or loss. However, we have configured persistence in the settings provided with the Elastic Agent package.
82+
83+
To enable persistence for the `filelogreceiver`, we add the `file_storage` extension and activate it for `filelog`.
84+
Execute `export STATE_PATH=/path/to/store/otel/offsets` and use the following configuration to enable persistence:
85+
86+
```yaml
87+
receivers:
88+
filelog/platformlogs:
89+
include: [ /var/log/system.log ]
90+
start_at: beginning
91+
storage: file_storage/filelogreceiver
92+
extensions:
93+
file_storage/filelogreceiver:
94+
directory: ${env:STATE_PATH}
95+
create_directory: true
96+
exporters:
97+
...
98+
processors:
99+
...
100+
service:
101+
extensions: [file_storage]
102+
pipelines:
103+
logs/platformlogs:
104+
receivers: [filelog/platformlogs]
105+
processors: [...]
106+
exporters: [...]
107+
```
108+
109+
> [!WARNING]
110+
Removing the storage key from the filelog section will disable persistence, which will lead to data duplication or loss when the collector restarts.
111+
112+
> [!IMPORTANT]
113+
If you remove the `create_directory: true` option, you'll need to manually create a directory to store the data. You can ignore this option if the directory already exists.
114+
115+
### Persistence in standalone Docker mode
116+
117+
By default, when running Elastic Distribution for OpenTelemetry Collector in Docker, checkpoints are stored in `/usr/share/elastic-agent/otel_registry` by default. To ensure data persists across container restarts, you can use the following command:
118+
119+
```bash
120+
docker run --rm -ti --entrypoint="elastic-agent" --mount type=bind,source=/path/on/host,target=/usr/share/elastic-agent/otel_registry docker.elastic.co/beats/elastic-agent:9.0.0-SNAPSHOT otel
121+
```
122+
123+
### Known issues:
124+
- You face following `failed to build extensions: failed to create extension "file_storage/filelogreceiver": mkdir ...: permission denied` error while running the otel mode
125+
- Cause: This issue is likely because the user running the executable lacks sufficient permissions to create the directory.
126+
- Resolution: You can either create the directory manually or specify a path with necessary permissions.

‎otel.yml

+5-1
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ receivers:
22
filelog:
33
include: [ /var/log/system.log ]
44
start_at: beginning
5+
storage: file_storage/filelogreceiver
56

67
processors:
78
resource:
@@ -24,9 +25,12 @@ extensions:
2425
health_check:
2526
endpoint: "localhost:13133"
2627
path: "/health/status"
28+
file_storage/filelogreceiver:
29+
create_directory: true
30+
directory: ${env:STATE_PATH}
2731

2832
service:
29-
extensions: [health_check, memory_limiter]
33+
extensions: [health_check, memory_limiter, file_storage/filelogreceiver]
3034
pipelines:
3135
logs:
3236
receivers: [filelog]

0 commit comments

Comments
 (0)
Please sign in to comment.