github.com/makyo/juju@v0.0.0-20160425123129-2608902037e9/worker/instancepoller/worker.go (about)

     1  // Copyright 2013 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package instancepoller
     5  
     6  import (
     7  	"github.com/juju/errors"
     8  	"github.com/juju/names"
     9  
    10  	"github.com/juju/juju/api/instancepoller"
    11  	"github.com/juju/juju/environs"
    12  	"github.com/juju/juju/instance"
    13  	"github.com/juju/juju/worker"
    14  	"github.com/juju/juju/worker/catacomb"
    15  )
    16  
    17  type Config struct {
    18  	Facade  *instancepoller.API
    19  	Environ environs.Environ
    20  }
    21  
    22  func (config Config) Validate() error {
    23  	if config.Facade == nil {
    24  		return errors.NotValidf("nil Facade")
    25  	}
    26  	if config.Environ == nil {
    27  		return errors.NotValidf("nil Environ")
    28  	}
    29  	return nil
    30  }
    31  
    32  type updaterWorker struct {
    33  	config     Config
    34  	aggregator *aggregator
    35  	catacomb   catacomb.Catacomb
    36  }
    37  
    38  // NewWorker returns a worker that keeps track of
    39  // the machines in the state and polls their instance
    40  // addresses and status periodically to keep them up to date.
    41  func NewWorker(config Config) (worker.Worker, error) {
    42  	if err := config.Validate(); err != nil {
    43  		return nil, errors.Trace(err)
    44  	}
    45  	u := &updaterWorker{
    46  		config: config,
    47  	}
    48  	err := catacomb.Invoke(catacomb.Plan{
    49  		Site: &u.catacomb,
    50  		Work: u.loop,
    51  	})
    52  	if err != nil {
    53  		return nil, errors.Trace(err)
    54  	}
    55  	return u, nil
    56  }
    57  
    58  // Kill is part of the worker.Worker interface.
    59  func (u *updaterWorker) Kill() {
    60  	u.catacomb.Kill(nil)
    61  }
    62  
    63  // Wait is part of the worker.Worker interface.
    64  func (u *updaterWorker) Wait() error {
    65  	return u.catacomb.Wait()
    66  }
    67  
    68  func (u *updaterWorker) loop() (err error) {
    69  	u.aggregator = newAggregator(u.config.Environ)
    70  	if err := u.catacomb.Add(u.aggregator); err != nil {
    71  		return errors.Trace(err)
    72  	}
    73  	watcher, err := u.config.Facade.WatchModelMachines()
    74  	if err != nil {
    75  		return err
    76  	}
    77  	if err := u.catacomb.Add(watcher); err != nil {
    78  		return errors.Trace(err)
    79  	}
    80  	return watchMachinesLoop(u, watcher)
    81  }
    82  
    83  // newMachineContext is part of the updaterContext interface.
    84  func (u *updaterWorker) newMachineContext() machineContext {
    85  	return u
    86  }
    87  
    88  // getMachine is part of the machineContext interface.
    89  func (u *updaterWorker) getMachine(tag names.MachineTag) (machine, error) {
    90  	return u.config.Facade.Machine(tag)
    91  }
    92  
    93  // instanceInfo is part of the machineContext interface.
    94  func (u *updaterWorker) instanceInfo(id instance.Id) (instanceInfo, error) {
    95  	return u.aggregator.instanceInfo(id)
    96  }
    97  
    98  // kill is part of the lifetimeContext interface.
    99  func (u *updaterWorker) kill(err error) {
   100  	u.catacomb.Kill(err)
   101  }
   102  
   103  // dying is part of the lifetimeContext interface.
   104  func (u *updaterWorker) dying() <-chan struct{} {
   105  	return u.catacomb.Dying()
   106  }
   107  
   108  // errDying is part of the lifetimeContext interface.
   109  func (u *updaterWorker) errDying() error {
   110  	return u.catacomb.ErrDying()
   111  }