Skip to content

Commit 82dbe6a

Browse files
[receiver/statsdreceiver] add ability to customize socket permissions when transport is unixgram (open-telemetry#37807)
Signed-off-by: thomas-gouveia <[email protected]>
1 parent 1e69310 commit 82dbe6a

File tree

9 files changed

+84
-2
lines changed

9 files changed

+84
-2
lines changed
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
change_type: enhancement
2+
component: statsdreceiver
3+
note: Add new config to customize socket permissions when transport is set to `unixgram`.
4+
issues:
5+
- 37807
6+
7+
subtext:
8+
change_logs: [user]

receiver/statsdreceiver/README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@ The Following settings are optional:
2727

2828
- `transport` (default = `udp`): Protocol used by the StatsD server. Currently supported transports can be found in [this file](https://github.com/open-telemetry/opentelemetry-collector-contrib/blob/main/receiver/statsdreceiver/internal/transport/transport.go).
2929

30+
- `socket_permissions` (default = `0622`): When transport is set to `unixgram`, can be used to customize permissions of the binded socket.
31+
3032
- `aggregation_interval: 70s`(default value is 60s): The aggregation time that the receiver aggregates the metrics (similar to the flush interval in StatsD server)
3133

3234
- `enable_metric_type: true`(default value is false): Enable the statsd receiver to be able to emit the metric type(gauge, counter, timer(in the future), histogram(in the future)) as a label.

receiver/statsdreceiver/config.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ package statsdreceiver // import "github.com/open-telemetry/opentelemetry-collec
66
import (
77
"errors"
88
"fmt"
9+
"os"
910
"time"
1011

1112
"github.com/lightstep/go-expohisto/structure"
@@ -24,6 +25,8 @@ type Config struct {
2425
EnableSimpleTags bool `mapstructure:"enable_simple_tags"`
2526
IsMonotonicCounter bool `mapstructure:"is_monotonic_counter"`
2627
TimerHistogramMapping []protocol.TimerHistogramMapping `mapstructure:"timer_histogram_mapping"`
28+
// Will only be used when transport set to 'unixgram'.
29+
SocketPermissions os.FileMode `mapstructure:"socket_permissions"`
2730
}
2831

2932
func (c *Config) Validate() error {

receiver/statsdreceiver/config_test.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ func TestLoadConfig(t *testing.T) {
4242
Endpoint: "localhost:12345",
4343
Transport: confignet.TransportTypeUDP6,
4444
},
45+
SocketPermissions: 0o622,
4546
AggregationInterval: 70 * time.Second,
4647
TimerHistogramMapping: []protocol.TimerHistogramMapping{
4748
{

receiver/statsdreceiver/factory.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ package statsdreceiver // import "github.com/open-telemetry/opentelemetry-collec
55

66
import (
77
"context"
8+
"os"
89
"time"
910

1011
"go.opentelemetry.io/collector/component"
@@ -21,6 +22,7 @@ const (
2122
defaultAggregationInterval = 60 * time.Second
2223
defaultEnableMetricType = false
2324
defaultIsMonotonicCounter = false
25+
defaultSocketPermissions = os.FileMode(0o622)
2426
)
2527

2628
var defaultTimerHistogramMapping = []protocol.TimerHistogramMapping{{StatsdType: "timer", ObserverType: "gauge"}, {StatsdType: "histogram", ObserverType: "gauge"}, {StatsdType: "distribution", ObserverType: "gauge"}}
@@ -44,6 +46,7 @@ func createDefaultConfig() component.Config {
4446
EnableMetricType: defaultEnableMetricType,
4547
IsMonotonicCounter: defaultIsMonotonicCounter,
4648
TimerHistogramMapping: defaultTimerHistogramMapping,
49+
SocketPermissions: defaultSocketPermissions,
4750
}
4851
}
4952

receiver/statsdreceiver/internal/transport/uds_server.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ type udsServer struct {
1717
var _ (Server) = (*udsServer)(nil)
1818

1919
// NewUDSServer creates a transport.Server using Unixgram as its transport.
20-
func NewUDSServer(transport Transport, socketPath string) (Server, error) {
20+
func NewUDSServer(transport Transport, socketPath string, socketPermissions os.FileMode) (Server, error) {
2121
if !transport.IsPacketTransport() {
2222
return nil, fmt.Errorf("NewUDSServer with %s: %w", transport.String(), ErrUnsupportedPacketTransport)
2323
}
@@ -27,6 +27,10 @@ func NewUDSServer(transport Transport, socketPath string) (Server, error) {
2727
return nil, fmt.Errorf("starting to listen %s socket: %w", transport.String(), err)
2828
}
2929

30+
if err := os.Chmod(socketPath, socketPermissions); err != nil {
31+
return nil, fmt.Errorf("running chmod %v: %w", socketPermissions, err)
32+
}
33+
3034
return &udsServer{
3135
packetServer: packetServer{
3236
packetConn: conn,
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
// Copyright The OpenTelemetry Authors
2+
// SPDX-License-Identifier: Apache-2.0
3+
4+
package transport
5+
6+
import (
7+
"os"
8+
"testing"
9+
10+
"github.com/stretchr/testify/assert"
11+
"github.com/stretchr/testify/require"
12+
)
13+
14+
func Test_NewUDSServer_ListenPacketFailure(t *testing.T) {
15+
invalidPath := "/invalid_path/test_socket"
16+
17+
server, err := NewUDSServer("unixgram", invalidPath, 0o622)
18+
19+
assert.Error(t, err)
20+
assert.Nil(t, server)
21+
assert.Contains(t, err.Error(), "starting to listen")
22+
}
23+
24+
func Test_UDSServer_Close(t *testing.T) {
25+
socketPath := "/tmp/test_socket_close"
26+
defer os.Remove(socketPath)
27+
28+
server, err := NewUDSServer("unixgram", socketPath, 0o622)
29+
require.NoError(t, err)
30+
require.NotNil(t, server)
31+
32+
_, err = os.Stat(socketPath)
33+
require.NoError(t, err)
34+
35+
err = server.Close()
36+
assert.NoError(t, err)
37+
38+
_, err = os.Stat(socketPath)
39+
assert.True(t, os.IsNotExist(err))
40+
}
41+
42+
func Test_NewUDSServer_AppliesChmod(t *testing.T) {
43+
socketPath := "/tmp/test_socket_chmod"
44+
defer os.Remove(socketPath) // Cleanup after test
45+
46+
expectedPermissions := os.FileMode(0o622)
47+
48+
server, err := NewUDSServer("unixgram", socketPath, expectedPermissions)
49+
require.NoError(t, err)
50+
require.NotNil(t, server)
51+
52+
fileInfo, err := os.Stat(socketPath)
53+
require.NoError(t, err)
54+
55+
actualPermissions := fileInfo.Mode().Perm()
56+
assert.Equal(t, expectedPermissions, actualPermissions, "Expected file permissions to be set correctly")
57+
58+
server.Close()
59+
}

receiver/statsdreceiver/receiver.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ func buildTransportServer(config Config) (transport.Server, error) {
9292
case transport.TCP, transport.TCP4, transport.TCP6:
9393
return transport.NewTCPServer(trans, config.NetAddr.Endpoint)
9494
case transport.UDS:
95-
return transport.NewUDSServer(trans, config.NetAddr.Endpoint)
95+
return transport.NewUDSServer(trans, config.NetAddr.Endpoint, config.SocketPermissions)
9696
}
9797

9898
return nil, fmt.Errorf("unsupported transport %q", string(config.NetAddr.Transport))

receiver/statsdreceiver/receiver_test.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,7 @@ func Test_statsdreceiver_EndToEnd(t *testing.T) {
9999
Endpoint: defaultBindEndpoint,
100100
Transport: confignet.TransportTypeUDP,
101101
},
102+
SocketPermissions: defaultSocketPermissions,
102103
AggregationInterval: 4 * time.Second,
103104
}
104105
},
@@ -117,6 +118,7 @@ func Test_statsdreceiver_EndToEnd(t *testing.T) {
117118
Endpoint: "/tmp/statsd_test.sock",
118119
Transport: confignet.TransportTypeUnixgram,
119120
},
121+
SocketPermissions: defaultSocketPermissions,
120122
AggregationInterval: 4 * time.Second,
121123
}
122124
},

0 commit comments

Comments
 (0)