diff --git a/internal/drivers/hue2/bridge.go b/internal/drivers/hue2/bridge.go index e087e06..2839acf 100644 --- a/internal/drivers/hue2/bridge.go +++ b/internal/drivers/hue2/bridge.go @@ -222,17 +222,31 @@ func (b *Bridge) Update(devices ...models.Device) { } func (b *Bridge) MakeCongruent(ctx context.Context) (int, error) { - // Eat the event if there's a pending update. - select { - case <-b.needsUpdate: - default: + // Eat all event if there's a pending update. + exhausted := false + for !exhausted { + select { + case <-b.needsUpdate: + default: + exhausted = true + } } b.mu.Lock() - dur := time.Millisecond * 200 + dur := time.Millisecond * 100 updates := make(map[string]ResourceUpdate) for _, device := range b.devices { resource := b.resources[device.InternalID] + + // Update device + if resource.Metadata.Name != device.Name { + name := device.Name + updates["device/"+resource.ID] = ResourceUpdate{ + Name: &name, + } + } + + // Update light if lightID := resource.ServiceID("light"); lightID != nil { light := b.resources[*lightID] update := ResourceUpdate{TransitionDuration: &dur} @@ -286,13 +300,14 @@ func (b *Bridge) MakeCongruent(ctx context.Context) (int, error) { return 0, nil } - log.Println(fmt.Sprintf("[Bridge %d]", b.externalID), "Updating", len(updates), "services...") + log.Println(fmt.Sprintf("[Bridge %d]", b.externalID), "Updating", len(updates), "hue services...") eg, ctx := errgroup.WithContext(ctx) for key := range updates { update := updates[key] split := strings.SplitN(key, "/", 2) link := ResourceLink{Kind: split[0], ID: split[1]} + eg.Go(func() error { return b.client.UpdateResource(ctx, link, update) }) @@ -334,6 +349,7 @@ func (b *Bridge) GenerateDevices() []models.Device { } device := models.Device{ + BridgeID: b.externalID, InternalID: resource.ID, Name: resource.Metadata.Name, DriverProperties: map[string]interface{}{ @@ -530,6 +546,7 @@ func (b *Bridge) applyPatches(patches []ResourceData) { if patch.Status != nil { resCopy.Status = patch.Status } + resCopy.Metadata.Name = patch.Metadata.Name newResources[patch.ID] = &resCopy } diff --git a/internal/drivers/hue2/client.go b/internal/drivers/hue2/client.go index 3980cd3..de71a72 100644 --- a/internal/drivers/hue2/client.go +++ b/internal/drivers/hue2/client.go @@ -19,7 +19,7 @@ import ( func NewClient(host, token string) *Client { ch := make(chan struct{}, 5) - for i := 0; i < 3; i++ { + for i := 0; i < 2; i++ { ch <- struct{}{} } @@ -93,7 +93,7 @@ func (c *Client) UpdateResource(ctx context.Context, link ResourceLink, update R } func (c *Client) SSE(ctx context.Context) <-chan SSEUpdate { - ch := make(chan SSEUpdate, 4) + ch := make(chan SSEUpdate, 4)0 go func() { defer close(ch) diff --git a/internal/drivers/hue2/data.go b/internal/drivers/hue2/data.go index fae6e76..da2a947 100644 --- a/internal/drivers/hue2/data.go +++ b/internal/drivers/hue2/data.go @@ -1,9 +1,11 @@ package hue2 import ( + "encoding/json" "encoding/xml" "fmt" "git.aiterp.net/lucifer/new-server/models" + "log" "strings" "time" ) @@ -89,6 +91,9 @@ func (res *ResourceData) ServiceIndex(kind string, id string) int { func (res *ResourceData) WithUpdate(update ResourceUpdate) *ResourceData { resCopy := *res + if update.Name != nil { + resCopy.Metadata.Name = *update.Name + } if update.Power != nil { cp := *resCopy.Power resCopy.Power = &cp @@ -170,6 +175,7 @@ type LightAlert struct { } type ResourceUpdate struct { + Name *string Power *bool ColorXY *models.ColorXY Brightness *float64 @@ -179,6 +185,10 @@ type ResourceUpdate struct { func (r ResourceUpdate) MarshalJSON() ([]byte, error) { chunks := make([]string, 0, 4) + if r.Name != nil { + s, _ := json.Marshal(*r.Name) + chunks = append(chunks, fmt.Sprintf(`"metadata":{"name":%s}`, string(s))) + } if r.Power != nil { chunks = append(chunks, fmt.Sprintf(`"on":{"on":%v}`, *r.Power)) } @@ -195,6 +205,8 @@ func (r ResourceUpdate) MarshalJSON() ([]byte, error) { chunks = append(chunks, fmt.Sprintf(`"dynamics":{"duration":%d}`, r.TransitionDuration.Truncate(time.Millisecond*100).Milliseconds())) } + log.Println(fmt.Sprintf("{%s}", strings.Join(chunks, ","))) + return []byte(fmt.Sprintf("{%s}", strings.Join(chunks, ","))), nil }