spackler

package module
v0.0.0-...-5b6d22c Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 29, 2017 License: BSD-3-Clause Imports: 6 Imported by: 0

README

spackler

Spackler enables graceful application termination. It allows running tasks to complete while preventing new tasks from starting. Spackler accomplishes this by managing goroutines and exiting timer loops. This can be of value, for example, in preserving data integrity.

Other features:

  • Stop signal available for custom use such as exiting loops
  • Custom registration for system signals (SIGINT, SIGIO, etc.)
  • Programmatic termination

Build Status Coverage GoDoc

Install

go get github.com/Hearst-DD/spackler

And import:


import "github.com/Hearst-DD/spackler"
Package Name

This package is named for Carl Spackler, the fictional golf caddy and greenskeeper portrayed by actor Bill Murray in the film, 'Caddyshack', who is entrusted with the graceful termination of gophers.

Documentation

Overview

Package spackler enables graceful application termination. It allows running tasks to complete while preventing new tasks from starting. Spackler accomplishes this by managing goroutines and exiting timer loops. This can be of value, for example, in preserving data integrity.

Operation

Caddy is composed of reference fields that maintain a common system state, as well as a single value field. The value field indicates whether the current instance was created in a tracked goroutine. This value determines whether Go() reads stopChan.

The first time Go() or Looper() is called, Spackler starts a goroutine that blocks on sigChan. sigChan may be registered to receive system signals, such as SIGINT. When a signal is received, this goroutine closes stopChan, effectively broadcasting "stop!" to any one reading from that channel.

Both Go() and Looper() read from stopChan. Looper() exits when stopChan is closed. Go() conditionally reads from stopChan if it has been called from an untracked goroutine. In this case, Go() returns an error if stopChan has been closed.

Example

The following example illustrates the main features of this package.

func doSomething(caddy *spackler.Caddy) {
  for i := 0; i < 10; i++ {

    //return on stop signal
    select {
    case <-caddy.Stopping():
      return
    default:
    }

    // do things

    // this will never fail
    caddy.Go(func(c *spackler.Caddy) {
      // do more things
    })
  }

}

func doSomethingElse() {
  //do something else
}

func main() {

  caddy := spackler.New(true)

  // doSomething() in a tracked goroutine
  caddy.Looper(1000, true, func() {
    caddy.Go(doSomething)
  })

  // this will always fail
  err := caddy.Go(func(c *spackler.Caddy) {
    doSomethingElse()
  })

  caddy.Wait()
}

On SIGINT, Looper() will return. The following call to Go() will fail because main() is not executing in a tracked goroutine and doSomethingElse() will never get called. Then main() will block on Wait() until all tracked goroutines have completed. Any running doSomething() threads will exit in the select statement. If a stop signal is sent when a doSomething() thread is between select and Go(), the call to Go() will still succeed because doSomething() is running in a tracked goroutine.

Index

Constants

This section is empty.

Variables

View Source
var ErrStopping = errors.New("spackler: stopping")

Functions

This section is empty.

Types

type Caddy

type Caddy struct {
	// contains filtered or unexported fields
}

Caddy tracks multiple goroutines ensuring they exit before the main routine exits.

func New

func New(stopOnOS bool) *Caddy

New returns a new, initilized Caddy instance. If true is passed in, this instance will stop on SIGINT and SIGTERM.

func (*Caddy) Go

func (c *Caddy) Go(f func(caddy *Caddy)) error

Go provides goroutine tracking. It is used in place of the go statement. It calls the provided function passing in a *Caddy which may be used to make subsequent calls to Go() and Looper().

func (*Caddy) Looper

func (c *Caddy) Looper(interval time.Duration, runImmediately bool, f func())

Looper provides cancelable task execution on the specified interval. It does not start new goroutines, but the provided function may. On the stop signal, the loop exits and Looper returns. Function execution is synchronous and delays due to long function run time are handled per time.Ticker.

func (*Caddy) SigChan

func (c *Caddy) SigChan() (ch chan<- os.Signal)

SigChan exposes write access to the sigChan for the purpose of making os.signal calls such as Notify(). Writing to or closing this channel is equivalent to calling Stop().

func (*Caddy) Stop

func (c *Caddy) Stop()

Stop sends a stop signal.

func (*Caddy) Stopping

func (c *Caddy) Stopping() (ch <-chan bool)

Stopping exposes read access to stopChan.

func (*Caddy) Wait

func (c *Caddy) Wait()

Wait wraps sync.WaitGroup.Wait() on all tracked goroutines.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL