Files
showbridge-go/internal/processor/processor.go
2026-03-08 13:09:22 -05:00

117 lines
2.3 KiB
Go

package processor
import (
"context"
"fmt"
"math"
"reflect"
"sync"
"github.com/jwetzell/showbridge-go/internal/common"
"github.com/jwetzell/showbridge-go/internal/config"
)
type Processor interface {
Type() string
Process(context.Context, any) (any, error)
}
type ProcessorRegistration struct {
Type string `json:"type"`
New func(config.ProcessorConfig) (Processor, error)
}
func RegisterProcessor(processor ProcessorRegistration) {
if processor.Type == "" {
panic("processor type is missing")
}
if processor.New == nil {
panic("missing ProcessorRegistration.New")
}
processorRegistryMu.Lock()
defer processorRegistryMu.Unlock()
if _, ok := ProcessorRegistry[string(processor.Type)]; ok {
panic(fmt.Sprintf("processor already registered: %s", processor.Type))
}
ProcessorRegistry[string(processor.Type)] = processor
}
var (
processorRegistryMu sync.RWMutex
ProcessorRegistry = make(map[string]ProcessorRegistration)
)
func GetAnyAs[T any](p any) (T, bool) {
typed, ok := p.(T)
return typed, ok
}
func GetAnyAsByteSlice(p any) ([]byte, bool) {
v := reflect.ValueOf(p)
if v.Kind() != reflect.Slice {
return nil, false
}
result := make([]byte, v.Len())
for i := 0; i < v.Len(); i++ {
elem := v.Index(i).Interface()
byteValue, ok := elem.(byte)
if ok {
result[i] = byteValue
continue
}
uintValue, ok := elem.(uint)
if ok {
if uintValue > 255 {
return nil, false
}
result[i] = byte(uintValue)
continue
}
intValue, ok := elem.(int)
if ok {
if intValue < 0 || intValue > 255 {
return nil, false
}
result[i] = byte(intValue)
continue
}
floatValue, ok := elem.(float64)
if ok {
if floatValue != math.Floor(floatValue) {
return nil, false
}
if floatValue < 0 || floatValue > 255 {
return nil, false
}
result[i] = byte(floatValue)
continue
}
return nil, false
}
return result, true
}
type TemplateData struct {
Payload any
Modules any
Sender any
}
func GetTemplateData(ctx context.Context, payload any) TemplateData {
templateData := TemplateData{Payload: payload}
modules := ctx.Value(common.ModulesContextKey)
if modules != nil {
templateData.Modules = modules
}
sender := ctx.Value(common.SenderContextKey)
if sender != nil {
templateData.Sender = sender
}
return templateData
}