Skip to content

Commit d32dfc1

Browse files
authored
[chore] Update connection method of Cisco OS Receiver (open-telemetry#43920)
<!--Ex. Fixing a bug - Describe the bug and how this fixes the issue. Ex. Adding a feature - Explain what this achieves.--> #### Description Refactors the Cisco OS receiver connection handling: <!-- Issue number (e.g. open-telemetry#1234) or full URL to issue, if applicable. --> #### Link to tracking issue open-telemetry#42647 Fixes - Centralized connection establishment logic into shared connection factory - Removed duplicate validation checks across receiver and connection layers - Simplified scraper nil checks and updated related tests - Cleaned up linting issues (unused imports, context usage) <!--Describe what testing was performed and which tests were added.--> #### Testing - Connection factory tests for password and key file authentication - Scraper initialization and shutdown tests added <!--Describe the documentation added.--> #### Documentation - Simplified inline documentation throughout connection handling code <!--Please delete paragraphs that you did not use before submitting.-->
1 parent 3c02288 commit d32dfc1

File tree

15 files changed

+579
-280
lines changed

15 files changed

+579
-280
lines changed

receiver/ciscoosreceiver/config.go

Lines changed: 3 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -8,48 +8,21 @@ import (
88
"fmt"
99

1010
"go.opentelemetry.io/collector/component"
11-
"go.opentelemetry.io/collector/config/configopaque"
1211
"go.opentelemetry.io/collector/confmap"
1312
"go.opentelemetry.io/collector/confmap/xconfmap"
1413
"go.opentelemetry.io/collector/scraper/scraperhelper"
1514
"go.uber.org/multierr"
15+
16+
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/connection"
1617
)
1718

1819
// Config defines configuration for Cisco OS receiver.
1920
type Config struct {
2021
scraperhelper.ControllerConfig `mapstructure:",squash"`
21-
Device DeviceConfig `mapstructure:"device"`
22+
Device connection.DeviceConfig `mapstructure:"device"`
2223
Scrapers map[component.Type]component.Config `mapstructure:"-"`
2324
}
2425

25-
// DeviceConfig represents configuration for a single Cisco device using semantic conventions
26-
type DeviceConfig struct {
27-
Device DeviceInfo `mapstructure:"device"`
28-
Auth AuthConfig `mapstructure:"auth"`
29-
}
30-
31-
// DeviceInfo follows semantic conventions for device identification
32-
type DeviceInfo struct {
33-
// DO NOT USE unkeyed struct initialization
34-
_ struct{} `mapstructure:"-"`
35-
36-
Host HostInfo `mapstructure:"host"`
37-
}
38-
39-
// HostInfo contains host-specific information
40-
type HostInfo struct {
41-
Name string `mapstructure:"name"`
42-
IP string `mapstructure:"ip"`
43-
Port int `mapstructure:"port"`
44-
}
45-
46-
// AuthConfig represents authentication configuration
47-
type AuthConfig struct {
48-
Username string `mapstructure:"username"`
49-
Password configopaque.String `mapstructure:"password"`
50-
KeyFile string `mapstructure:"key_file"`
51-
}
52-
5326
var (
5427
_ xconfmap.Validator = (*Config)(nil)
5528
_ confmap.Unmarshaler = (*Config)(nil)

receiver/ciscoosreceiver/config_test.go

Lines changed: 27 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ import (
1212
"go.opentelemetry.io/collector/component"
1313
"go.opentelemetry.io/collector/config/configopaque"
1414
"go.opentelemetry.io/collector/scraper/scraperhelper"
15+
16+
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/connection"
1517
)
1618

1719
func TestConfigValidate(t *testing.T) {
@@ -27,15 +29,15 @@ func TestConfigValidate(t *testing.T) {
2729
Timeout: 30 * time.Second,
2830
CollectionInterval: 60 * time.Second,
2931
},
30-
Device: DeviceConfig{
31-
Device: DeviceInfo{
32-
Host: HostInfo{
32+
Device: connection.DeviceConfig{
33+
Device: connection.DeviceInfo{
34+
Host: connection.HostInfo{
3335
Name: "test-device",
3436
IP: "192.168.1.1",
3537
Port: 22,
3638
},
3739
},
38-
Auth: AuthConfig{
40+
Auth: connection.AuthConfig{
3941
Username: "admin",
4042
Password: configopaque.String("password"),
4143
},
@@ -53,15 +55,15 @@ func TestConfigValidate(t *testing.T) {
5355
Timeout: 30 * time.Second,
5456
CollectionInterval: 60 * time.Second,
5557
},
56-
Device: DeviceConfig{
57-
Device: DeviceInfo{
58-
Host: HostInfo{
58+
Device: connection.DeviceConfig{
59+
Device: connection.DeviceInfo{
60+
Host: connection.HostInfo{
5961
Name: "test-device",
6062
IP: "192.168.1.1",
6163
Port: 22,
6264
},
6365
},
64-
Auth: AuthConfig{
66+
Auth: connection.AuthConfig{
6567
Username: "admin",
6668
KeyFile: "/path/to/key",
6769
},
@@ -79,7 +81,7 @@ func TestConfigValidate(t *testing.T) {
7981
Timeout: 30 * time.Second,
8082
CollectionInterval: 60 * time.Second,
8183
},
82-
Device: DeviceConfig{},
84+
Device: connection.DeviceConfig{},
8385
Scrapers: map[component.Type]component.Config{
8486
component.MustNewType("system"): nil,
8587
},
@@ -93,15 +95,15 @@ func TestConfigValidate(t *testing.T) {
9395
Timeout: 30 * time.Second,
9496
CollectionInterval: 60 * time.Second,
9597
},
96-
Device: DeviceConfig{
97-
Device: DeviceInfo{
98-
Host: HostInfo{
98+
Device: connection.DeviceConfig{
99+
Device: connection.DeviceInfo{
100+
Host: connection.HostInfo{
99101
Name: "test-device",
100102
IP: "192.168.1.1",
101103
Port: 0,
102104
},
103105
},
104-
Auth: AuthConfig{
106+
Auth: connection.AuthConfig{
105107
Username: "admin",
106108
Password: configopaque.String("password"),
107109
},
@@ -119,15 +121,15 @@ func TestConfigValidate(t *testing.T) {
119121
Timeout: 30 * time.Second,
120122
CollectionInterval: 60 * time.Second,
121123
},
122-
Device: DeviceConfig{
123-
Device: DeviceInfo{
124-
Host: HostInfo{
124+
Device: connection.DeviceConfig{
125+
Device: connection.DeviceInfo{
126+
Host: connection.HostInfo{
125127
Name: "test-device",
126128
IP: "192.168.1.1",
127129
Port: 22,
128130
},
129131
},
130-
Auth: AuthConfig{
132+
Auth: connection.AuthConfig{
131133
Username: "",
132134
Password: configopaque.String("password"),
133135
},
@@ -145,15 +147,15 @@ func TestConfigValidate(t *testing.T) {
145147
Timeout: 30 * time.Second,
146148
CollectionInterval: 60 * time.Second,
147149
},
148-
Device: DeviceConfig{
149-
Device: DeviceInfo{
150-
Host: HostInfo{
150+
Device: connection.DeviceConfig{
151+
Device: connection.DeviceInfo{
152+
Host: connection.HostInfo{
151153
Name: "test-device",
152154
IP: "192.168.1.1",
153155
Port: 22,
154156
},
155157
},
156-
Auth: AuthConfig{
158+
Auth: connection.AuthConfig{
157159
Username: "admin",
158160
},
159161
},
@@ -170,15 +172,15 @@ func TestConfigValidate(t *testing.T) {
170172
Timeout: 30 * time.Second,
171173
CollectionInterval: 60 * time.Second,
172174
},
173-
Device: DeviceConfig{
174-
Device: DeviceInfo{
175-
Host: HostInfo{
175+
Device: connection.DeviceConfig{
176+
Device: connection.DeviceInfo{
177+
Host: connection.HostInfo{
176178
Name: "test-device",
177179
IP: "192.168.1.1",
178180
Port: 22,
179181
},
180182
},
181-
Auth: AuthConfig{
183+
Auth: connection.AuthConfig{
182184
Username: "admin",
183185
Password: configopaque.String("password"),
184186
},

receiver/ciscoosreceiver/factory.go

Lines changed: 2 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -66,10 +66,10 @@ func createMetricsReceiver(
6666

6767
// Inject device configuration into scraper config
6868
if sysCfg, ok := scraperCfg.(*systemscraper.Config); ok {
69-
sysCfg.Device = convertToSystemScraperDeviceConfig(conf.Device)
69+
sysCfg.Device = conf.Device
7070
}
7171
if intfCfg, ok := scraperCfg.(*interfacesscraper.Config); ok {
72-
intfCfg.Device = convertToInterfacesScraperDeviceConfig(conf.Device)
72+
intfCfg.Device = conf.Device
7373
}
7474

7575
scraperOptions = append(scraperOptions, scraperhelper.AddFactoryWithConfig(factory, scraperCfg))
@@ -87,36 +87,6 @@ func createMetricsReceiver(
8787
)
8888
}
8989

90-
func convertToSystemScraperDeviceConfig(device DeviceConfig) systemscraper.DeviceConfig {
91-
return systemscraper.DeviceConfig{
92-
Host: systemscraper.HostInfo{
93-
Name: device.Device.Host.Name,
94-
IP: device.Device.Host.IP,
95-
Port: device.Device.Host.Port,
96-
},
97-
Auth: systemscraper.AuthConfig{
98-
Username: device.Auth.Username,
99-
Password: string(device.Auth.Password),
100-
KeyFile: device.Auth.KeyFile,
101-
},
102-
}
103-
}
104-
105-
func convertToInterfacesScraperDeviceConfig(device DeviceConfig) interfacesscraper.DeviceConfig {
106-
return interfacesscraper.DeviceConfig{
107-
Host: interfacesscraper.HostInfo{
108-
Name: device.Device.Host.Name,
109-
IP: device.Device.Host.IP,
110-
Port: device.Device.Host.Port,
111-
},
112-
Auth: interfacesscraper.AuthConfig{
113-
Username: device.Auth.Username,
114-
Password: string(device.Auth.Password),
115-
KeyFile: device.Auth.KeyFile,
116-
},
117-
}
118-
}
119-
12090
type nopMetricsReceiver struct{}
12191

12292
func (*nopMetricsReceiver) Start(_ context.Context, _ component.Host) error { return nil }

receiver/ciscoosreceiver/factory_test.go

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import (
1515
"go.opentelemetry.io/collector/consumer/consumertest"
1616
"go.opentelemetry.io/collector/receiver/receivertest"
1717

18+
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/connection"
1819
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/metadata"
1920
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/scraper/interfacesscraper"
2021
"github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/scraper/systemscraper"
@@ -45,15 +46,15 @@ func TestCreateMetricsReceiver(t *testing.T) {
4546

4647
// Add a device and scraper to make config valid
4748
config := cfg.(*Config)
48-
config.Device = DeviceConfig{
49-
Device: DeviceInfo{
50-
Host: HostInfo{
49+
config.Device = connection.DeviceConfig{
50+
Device: connection.DeviceInfo{
51+
Host: connection.HostInfo{
5152
Name: "test-device",
5253
IP: "192.168.1.1",
5354
Port: 22,
5455
},
5556
},
56-
Auth: AuthConfig{
57+
Auth: connection.AuthConfig{
5758
Username: "admin",
5859
Password: configopaque.String("password"),
5960
},
@@ -85,15 +86,15 @@ func TestCreateMetricsReceiverWithInterfacesScraper(t *testing.T) {
8586

8687
// Add a device and interfaces scraper
8788
config := cfg.(*Config)
88-
config.Device = DeviceConfig{
89-
Device: DeviceInfo{
90-
Host: HostInfo{
89+
config.Device = connection.DeviceConfig{
90+
Device: connection.DeviceInfo{
91+
Host: connection.HostInfo{
9192
Name: "test-device",
9293
IP: "192.168.1.1",
9394
Port: 22,
9495
},
9596
},
96-
Auth: AuthConfig{
97+
Auth: connection.AuthConfig{
9798
Username: "admin",
9899
Password: configopaque.String("password"),
99100
},
@@ -118,15 +119,15 @@ func TestCreateMetricsReceiverWithBothScrapers(t *testing.T) {
118119

119120
// Add a device and both scrapers
120121
config := cfg.(*Config)
121-
config.Device = DeviceConfig{
122-
Device: DeviceInfo{
123-
Host: HostInfo{
122+
config.Device = connection.DeviceConfig{
123+
Device: connection.DeviceInfo{
124+
Host: connection.HostInfo{
124125
Name: "test-device",
125126
IP: "192.168.1.1",
126127
Port: 22,
127128
},
128129
},
129-
Auth: AuthConfig{
130+
Auth: connection.AuthConfig{
130131
Username: "admin",
131132
Password: configopaque.String("password"),
132133
},
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
// Copyright The OpenTelemetry Authors
2+
// SPDX-License-Identifier: Apache-2.0
3+
4+
package connection // import "github.com/open-telemetry/opentelemetry-collector-contrib/receiver/ciscoosreceiver/internal/connection"
5+
6+
import "go.opentelemetry.io/collector/config/configopaque"
7+
8+
// DeviceConfig represents configuration for a single Cisco device using semantic conventions
9+
type DeviceConfig struct {
10+
Device DeviceInfo `mapstructure:"device"`
11+
Auth AuthConfig `mapstructure:"auth"`
12+
}
13+
14+
// DeviceInfo follows semantic conventions for device identification
15+
type DeviceInfo struct {
16+
// DO NOT USE unkeyed struct initialization
17+
_ struct{} `mapstructure:"-"`
18+
19+
Host HostInfo `mapstructure:"host"`
20+
}
21+
22+
// HostInfo contains host-specific information
23+
type HostInfo struct {
24+
Name string `mapstructure:"name"`
25+
IP string `mapstructure:"ip"`
26+
Port int `mapstructure:"port"`
27+
}
28+
29+
// AuthConfig represents authentication configuration
30+
type AuthConfig struct {
31+
Username string `mapstructure:"username"`
32+
Password configopaque.String `mapstructure:"password"`
33+
KeyFile string `mapstructure:"key_file"`
34+
}

0 commit comments

Comments
 (0)