mirror of
https://github.com/3ybactuk/marketplace-go-service-project.git
synced 2025-10-30 22:13:44 +03:00
75 lines
1.2 KiB
Go
75 lines
1.2 KiB
Go
package controller
|
|
|
|
import (
|
|
"context"
|
|
"errors"
|
|
"fmt"
|
|
"sync"
|
|
)
|
|
|
|
type NotifierService interface {
|
|
RunFetchEvents(ctx context.Context) error
|
|
}
|
|
|
|
type Controller struct {
|
|
notifier NotifierService
|
|
|
|
wg sync.WaitGroup
|
|
errCh chan error
|
|
cancel context.CancelFunc
|
|
}
|
|
|
|
func NewController(notifierService NotifierService) *Controller {
|
|
return &Controller{
|
|
notifier: notifierService,
|
|
wg: sync.WaitGroup{},
|
|
errCh: make(chan error, 1),
|
|
}
|
|
}
|
|
|
|
// Run service asynchroniously.
|
|
func (c *Controller) Run(ctx context.Context) {
|
|
ctx, cancel := context.WithCancel(ctx)
|
|
c.cancel = cancel
|
|
|
|
c.wg.Add(1)
|
|
go func() {
|
|
defer c.wg.Done()
|
|
|
|
if err := c.notifier.RunFetchEvents(ctx); err != nil && !errors.Is(err, context.Canceled) {
|
|
select {
|
|
case c.errCh <- fmt.Errorf("RunFetchEvents: %w", err):
|
|
default:
|
|
}
|
|
}
|
|
}()
|
|
}
|
|
|
|
// Gracefully stop service.
|
|
func (c *Controller) Stop(ctx context.Context) error {
|
|
if c.cancel != nil {
|
|
c.cancel()
|
|
}
|
|
|
|
done := make(chan struct{})
|
|
go func() {
|
|
c.wg.Wait()
|
|
close(done)
|
|
}()
|
|
|
|
select {
|
|
case <-done:
|
|
case <-ctx.Done():
|
|
return ctx.Err()
|
|
}
|
|
|
|
close(c.errCh)
|
|
|
|
select {
|
|
case err := <-c.errCh:
|
|
return err
|
|
default:
|
|
return nil
|
|
}
|
|
}
|