49 lines
1.1 KiB
Go
49 lines
1.1 KiB
Go
package notice
|
|
|
|
import (
|
|
"fmt"
|
|
"sync"
|
|
)
|
|
|
|
type Factory struct {
|
|
mu sync.RWMutex `json:"-" dc:"实例缓存读写锁"`
|
|
configs map[Channel]Config `json:"-" dc:"按渠道保存的初始化配置"`
|
|
instances map[Channel]Sender `json:"-" dc:"按渠道缓存的 Sender 实例"`
|
|
}
|
|
|
|
func NewFactory(configs map[Channel]Config) *Factory {
|
|
cloned := make(map[Channel]Config, len(configs))
|
|
for channel, config := range configs {
|
|
cloned[channel] = config
|
|
}
|
|
return &Factory{configs: cloned, instances: make(map[Channel]Sender)}
|
|
}
|
|
|
|
func (f *Factory) Get(channel Channel) (Sender, error) {
|
|
if f == nil {
|
|
return nil, fmt.Errorf("%w: factory is nil", ErrChannelNotConfigured)
|
|
}
|
|
f.mu.RLock()
|
|
instance, ok := f.instances[channel]
|
|
f.mu.RUnlock()
|
|
if ok {
|
|
return instance, nil
|
|
}
|
|
|
|
f.mu.Lock()
|
|
defer f.mu.Unlock()
|
|
if instance, ok = f.instances[channel]; ok {
|
|
return instance, nil
|
|
}
|
|
config, ok := f.configs[channel]
|
|
if !ok {
|
|
return nil, fmt.Errorf("%w: %s", ErrChannelNotConfigured, channel)
|
|
}
|
|
instance, err := New(channel, config)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
f.instances[channel] = instance
|
|
return instance, nil
|
|
}
|