Skip to content

Commit

Permalink
refactor(hass,linux): ♻️ rearrange fields for sensor type
Browse files Browse the repository at this point in the history
  • Loading branch information
joshuar committed Dec 22, 2024
1 parent 5d55cc6 commit 0e1282a
Show file tree
Hide file tree
Showing 32 changed files with 107 additions and 118 deletions.
2 changes: 1 addition & 1 deletion internal/agent/agentsensor/connection_latency.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ var ErrEmptyResponse = errors.New("empty response")
func newConnectionLatencySensor(info resty.TraceInfo) sensor.Entity {
return sensor.NewSensor(
sensor.WithName("Connection Latency"),
sensor.WithID("connection_latency"),
sensor.WithUnits(connectionLatencyUnits),
sensor.WithDeviceClass(types.SensorDeviceClassDuration),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID("connection_latency"),
sensor.WithIcon("mdi:connection"),
sensor.WithValue(info.TotalTime.Milliseconds()),
sensor.WithAttribute("DNS Lookup Time", info.DNSLookup.Milliseconds()),
Expand Down
2 changes: 1 addition & 1 deletion internal/agent/agentsensor/external_ip.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,9 +55,9 @@ func newExternalIPSensor(addr net.IP) sensor.Entity {

return sensor.NewSensor(
sensor.WithName(name),
sensor.WithID(id),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID(id),
sensor.WithIcon(icon),
sensor.WithValue(addr.String()),
sensor.WithAttribute("last_updated", time.Now().Format(time.RFC3339)),
Expand Down
2 changes: 1 addition & 1 deletion internal/agent/agentsensor/version.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@ const (
func newVersionSensor() sensor.Entity {
return sensor.NewSensor(
sensor.WithName("Go Hass Agent Version"),
sensor.WithID("agent_version"),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID("agent_version"),
sensor.WithIcon("mdi:face-agent"),
sensor.WithValue(preferences.AppVersion),
),
Expand Down
62 changes: 31 additions & 31 deletions internal/hass/sensor/entities.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,11 +23,9 @@ type requestMetadata struct {
}

type State struct {
Value any `json:"state" validate:"required"`
Attributes map[string]any `json:"attributes,omitempty" validate:"omitempty"`
Icon string `json:"icon,omitempty" validate:"omitempty,startswith=mdi:"`
ID string `json:"unique_id" validate:"required"`
EntityType types.SensorType `json:"type" validate:"omitempty"`
Value any `json:"state" validate:"required"`
Attributes map[string]any `json:"attributes,omitempty" validate:"omitempty"`
Icon string `json:"icon,omitempty" validate:"omitempty,startswith=mdi:"`
}

// WithValue assigns a value to the sensor.
Expand Down Expand Up @@ -86,32 +84,6 @@ func WithIcon(icon string) Option[State] {
}
}

// WithID sets the entity ID of the sensor.
func WithID(id string) Option[State] {
return func(state State) State {
state.ID = id
return state
}
}

// AsTypeSensor ensures the sensor is treated as a Sensor Entity.
// https://developers.home-assistant.io/docs/core/entity/sensor/
func AsTypeSensor() Option[State] {
return func(state State) State {
state.EntityType = types.Sensor
return state
}
}

// AsTypeBinarySensor ensures the sensor is treated as a Binary Sensor Entity.
// https://developers.home-assistant.io/docs/core/entity/binary-sensor
func AsTypeBinarySensor() Option[State] {
return func(state State) State {
state.EntityType = types.BinarySensor
return state
}
}

// UpdateValue will update the sensor state with the given value.
func (s *State) UpdateValue(value any) {
s.Value = value
Expand Down Expand Up @@ -143,8 +115,10 @@ func (s *State) Validate() error {
type Entity struct {
*State
requestMetadata
ID string `json:"unique_id" validate:"required"`
Name string `json:"name" validate:"required"`
Units string `json:"unit_of_measurement,omitempty" validate:"omitempty"`
EntityType types.SensorType `json:"type" validate:"omitempty"`
DeviceClass types.DeviceClass `json:"device_class,omitempty" validate:"omitempty"`
StateClass types.StateClass `json:"state_class,omitempty" validate:"omitempty"`
Category types.Category `json:"entity_category,omitempty" validate:"omitempty"`
Expand Down Expand Up @@ -174,6 +148,32 @@ func WithName(name string) Option[Entity] {
}
}

// WithID sets the entity ID of the sensor.
func WithID(id string) Option[Entity] {
return func(entity Entity) Entity {
entity.ID = id
return entity
}
}

// AsTypeSensor ensures the sensor is treated as a Sensor Entity.
// https://developers.home-assistant.io/docs/core/entity/sensor/
func AsTypeSensor() Option[Entity] {
return func(entity Entity) Entity {
entity.EntityType = types.Sensor
return entity
}
}

// AsTypeBinarySensor ensures the sensor is treated as a Binary Sensor Entity.
// https://developers.home-assistant.io/docs/core/entity/binary-sensor
func AsTypeBinarySensor() Option[Entity] {
return func(entity Entity) Entity {
entity.EntityType = types.BinarySensor
return entity
}
}

// WithUnits defines the native unit of measurement of the sensor entity.
func WithUnits(units string) Option[Entity] {
return func(entity Entity) Entity {
Expand Down
73 changes: 31 additions & 42 deletions internal/hass/sensor/tracker_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,17 @@ import (
"github.com/stretchr/testify/assert"
)

func TestTracker_Get(t *testing.T) {
mockEntity := &Entity{
Name: "Mock Entity",
State: &State{
ID: "mock_entity",
},
}
var mockEntity = NewSensor(
WithName("Mock Entity"),
WithID("mock_entity"),
WithState(
WithValue("mockValue"),
),
)

func TestTracker_Get(t *testing.T) {
mockSensorMap := map[string]*Entity{
mockEntity.ID: mockEntity,
mockEntity.ID: &mockEntity,
}

type fields struct {
Expand All @@ -41,7 +42,7 @@ func TestTracker_Get(t *testing.T) {
fields: fields{sensor: mockSensorMap},
args: args{id: "mock_entity"},
wantErr: false,
want: mockEntity,
want: &mockEntity,
},
{
name: "unsuccessful get",
Expand All @@ -68,15 +69,8 @@ func TestTracker_Get(t *testing.T) {
}

func TestTracker_SensorList(t *testing.T) {
mockEntity := &Entity{
Name: "Mock Entity",
State: &State{
ID: "mock_entity",
},
}

mockSensorMap := map[string]*Entity{
mockEntity.ID: mockEntity,
mockEntity.ID: &mockEntity,
}

type fields struct {
Expand Down Expand Up @@ -110,22 +104,24 @@ func TestTracker_SensorList(t *testing.T) {
}

func TestTracker_Add(t *testing.T) {
newEntity := &Entity{
Name: "New Entity",
State: &State{
ID: "new_entity",
},
}

existingEntity := &Entity{
Name: "Existing Entity",
State: &State{
ID: "existing_entity",
},
}
newEntity := NewSensor(
WithName("New Entity"),
WithID("new_entity"),
WithState(
WithValue("new"),
),
)

existingEntity := NewSensor(
WithName("Existing Entity"),
WithID("existing_entity"),
WithState(
WithValue("existing"),
),
)

mockSensorMap := map[string]*Entity{
existingEntity.ID: existingEntity,
existingEntity.ID: &existingEntity,
}

type fields struct {
Expand All @@ -143,16 +139,16 @@ func TestTracker_Add(t *testing.T) {
{
name: "new sensor",
fields: fields{sensor: mockSensorMap},
args: args{sensor: newEntity},
args: args{sensor: &newEntity},
},
{
name: "existing sensor",
fields: fields{sensor: mockSensorMap},
args: args{sensor: existingEntity},
args: args{sensor: &existingEntity},
},
{
name: "invalid tracker",
args: args{sensor: newEntity},
args: args{sensor: &newEntity},
wantErr: true,
},
}
Expand All @@ -169,15 +165,8 @@ func TestTracker_Add(t *testing.T) {
}

func TestTracker_Reset(t *testing.T) {
mockEntity := &Entity{
Name: "Mock Entity",
State: &State{
ID: "mock_entity",
},
}

mockSensorMap := map[string]*Entity{
mockEntity.ID: mockEntity,
mockEntity.ID: &mockEntity,
}

type fields struct {
Expand Down
6 changes: 3 additions & 3 deletions internal/linux/apps/apps.go
Original file line number Diff line number Diff line change
Expand Up @@ -119,10 +119,10 @@ func (w *sensorWorker) Sensors(_ context.Context) ([]sensor.Entity, error) {
sensors = append(sensors,
sensor.NewSensor(
sensor.WithName(activeAppsName),
sensor.WithID(activeAppsID),
sensor.AsTypeSensor(),
sensor.WithState(
sensor.WithID(activeAppsID),
sensor.WithIcon(activeAppsIcon),
sensor.AsTypeSensor(),
sensor.WithValue(name),
sensor.WithDataSourceAttribute(linux.DataSrcDbus),
),
Expand All @@ -136,10 +136,10 @@ func (w *sensorWorker) Sensors(_ context.Context) ([]sensor.Entity, error) {
sensors = append(sensors,
sensor.NewSensor(
sensor.WithName(runningAppsName),
sensor.WithID(runningAppsID),
sensor.WithUnits(runningAppsUnits),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.WithState(
sensor.WithID(runningAppsID),
sensor.WithIcon(runningAppsIcon),
sensor.WithValue(len(runningApps)),
sensor.WithDataSourceAttribute(linux.DataSrcDbus),
Expand Down
2 changes: 1 addition & 1 deletion internal/linux/battery/sensor.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,12 +57,12 @@ func newBatterySensor(battery *upowerBattery, sensorType batterySensor, value db

return sensor.NewSensor(
sensor.WithName(name),
sensor.WithID(id),
sensor.WithDeviceClass(deviceClass),
sensor.WithStateClass(stateClass),
sensor.WithUnits(units),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID(id),
sensor.WithIcon(icon),
sensor.WithValue(generateSensorState(sensorType, value.Value())),
sensor.WithAttributes(generateSensorAttributes(sensorType, battery)),
Expand Down
4 changes: 2 additions & 2 deletions internal/linux/cpu/cpufreq.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,14 +84,14 @@ func newCPUFreqSensor(id string) sensor.Entity {

return sensor.NewSensor(
sensor.WithName("Core "+num+" Frequency"),
sensor.WithID("cpufreq_core"+num+"_frequency"),
sensor.AsTypeSensor(),
sensor.WithUnits(cpuFreqUnits),
sensor.WithDeviceClass(types.SensorDeviceClassFrequency),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID("cpufreq_core"+num+"_frequency"),
sensor.WithIcon(cpuFreqIcon),
sensor.AsTypeSensor(),
sensor.WithValue(info.freq),
sensor.WithAttributes(map[string]any{
"governor": info.governor,
Expand Down
2 changes: 1 addition & 1 deletion internal/linux/cpu/loadAvgs.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,10 +70,10 @@ func newLoadAvgSensors() []sensor.Entity {
for idx, loadType := range []string{"CPU load average (1 min)", "CPU load average (5 min)", "CPU load average (15 min)"} {
loadAvgSensor := sensor.NewSensor(
sensor.WithName(loadType),
sensor.WithID(strcase.ToSnake(loadType)),
sensor.WithUnits(loadAvgUnit),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.WithState(
sensor.WithID(strcase.ToSnake(loadType)),
sensor.WithIcon(loadAvgIcon),
sensor.WithDataSourceAttribute(linux.DataSrcProcfs),
),
Expand Down
6 changes: 3 additions & 3 deletions internal/linux/cpu/usage.go
Original file line number Diff line number Diff line change
Expand Up @@ -206,11 +206,11 @@ func (s *rateSensor) update(delta time.Duration, valueStr string) {
func newRateSensor(name, icon, units string) *rateSensor {
sensorDetails := sensor.NewSensor(
sensor.WithName(name),
sensor.WithID(strcase.ToSnake(name)),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.AsDiagnostic(),
sensor.WithUnits(units),
sensor.WithState(
sensor.WithID(strcase.ToSnake(name)),
sensor.WithIcon(icon),
sensor.WithDataSourceAttribute(linux.DataSrcProcfs),
),
Expand Down Expand Up @@ -238,10 +238,10 @@ func newUsageSensor(clktck int64, details []string, category types.Category) sen

usageSensor := sensor.NewSensor(
sensor.WithName(name),
sensor.WithID(id),
sensor.WithUnits("%"),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.WithState(
sensor.WithID(id),
sensor.WithValue(value),
sensor.WithAttributes(attributes),
sensor.WithIcon("mdi:chip"),
Expand Down Expand Up @@ -285,10 +285,10 @@ func newCountSensor(name, icon, valueStr string) sensor.Entity {

return sensor.NewSensor(
sensor.WithName(name),
sensor.WithID(strcase.ToSnake(name)),
sensor.WithStateClass(types.StateClassMeasurement),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID(strcase.ToSnake(name)),
sensor.WithIcon(icon),
sensor.WithValue(valueInt),
sensor.WithDataSourceAttribute(linux.DataSrcProcfs),
Expand Down
4 changes: 2 additions & 2 deletions internal/linux/cpu/vulnerabilities.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,12 @@ func (w *cpuVulnWorker) Sensors(_ context.Context) ([]sensor.Entity, error) {

cpuVulnSensor := sensor.NewSensor(
sensor.WithName("CPU Vulnerabilities"),
sensor.WithID("cpu_vulnerabilities"),
sensor.AsTypeBinarySensor(),
sensor.WithDeviceClass(types.BinarySensorDeviceClassProblem),
sensor.AsDiagnostic(),
sensor.WithState(
sensor.WithID("cpu_vulnerabilities"),
sensor.WithIcon("mdi:security"),
sensor.AsTypeBinarySensor(),
sensor.WithValue(cpuVulnerabilitiesFound),
sensor.WithAttributes(attrs),
),
Expand Down
Loading

0 comments on commit 0e1282a

Please sign in to comment.