github.com/wfusion/gofusion@v1.1.14/common/infra/asynq/healthcheck.go (about)

     1  // Copyright 2020 Kentaro Hibino. All rights reserved.
     2  // Use of this source code is governed by a MIT license
     3  // that can be found in the LICENSE file.
     4  
     5  package asynq
     6  
     7  import (
     8  	"sync"
     9  	"time"
    10  
    11  	"github.com/wfusion/gofusion/common/infra/asynq/pkg/base"
    12  	"github.com/wfusion/gofusion/common/infra/asynq/pkg/log"
    13  )
    14  
    15  // healthchecker is responsible for pinging broker periodically
    16  // and call user provided HeathCheckFunc with the ping result.
    17  type healthchecker struct {
    18  	logger *log.Logger
    19  	broker base.Broker
    20  
    21  	// channel to communicate back to the long running "healthchecker" goroutine.
    22  	done chan struct{}
    23  
    24  	// interval between healthchecks.
    25  	interval time.Duration
    26  
    27  	// function to call periodically.
    28  	healthcheckFunc func(error)
    29  }
    30  
    31  type healthcheckerParams struct {
    32  	logger          *log.Logger
    33  	broker          base.Broker
    34  	interval        time.Duration
    35  	healthcheckFunc func(error)
    36  }
    37  
    38  func newHealthChecker(params healthcheckerParams) *healthchecker {
    39  	return &healthchecker{
    40  		logger:          params.logger,
    41  		broker:          params.broker,
    42  		done:            make(chan struct{}),
    43  		interval:        params.interval,
    44  		healthcheckFunc: params.healthcheckFunc,
    45  	}
    46  }
    47  
    48  func (hc *healthchecker) shutdown() {
    49  	if hc.healthcheckFunc == nil {
    50  		return
    51  	}
    52  
    53  	hc.logger.Debug("[Common] asynq healthchecker shutting down...")
    54  	// Signal the healthchecker goroutine to stop.
    55  	hc.done <- struct{}{}
    56  }
    57  
    58  func (hc *healthchecker) start(wg *sync.WaitGroup) {
    59  	if hc.healthcheckFunc == nil {
    60  		return
    61  	}
    62  
    63  	wg.Add(1)
    64  	go func() {
    65  		defer wg.Done()
    66  		timer := time.NewTimer(hc.interval)
    67  		for {
    68  			select {
    69  			case <-hc.done:
    70  				hc.logger.Debug("[Common] asynq healthchecker done")
    71  				timer.Stop()
    72  				return
    73  			case <-timer.C:
    74  				err := hc.broker.Ping()
    75  				hc.healthcheckFunc(err)
    76  				timer.Reset(hc.interval)
    77  			}
    78  		}
    79  	}()
    80  }