github.com/wallyworld/juju@v0.0.0-20161013125918-6cf1bc9d917a/worker/agent/manifold.go (about) 1 // Copyright 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package agent 5 6 import ( 7 "github.com/juju/errors" 8 "gopkg.in/tomb.v1" 9 10 "github.com/juju/juju/agent" 11 "github.com/juju/juju/worker" 12 "github.com/juju/juju/worker/dependency" 13 ) 14 15 // Manifold returns a manifold that starts a worker proxying the supplied Agent 16 // for use by other workers. 17 func Manifold(a agent.Agent) dependency.Manifold { 18 return dependency.Manifold{ 19 Start: startFunc(a), 20 Output: outputFunc, 21 } 22 } 23 24 // startFunc returns a StartFunc that starts a worker holding a reference to 25 // the supplied Agent. 26 func startFunc(a agent.Agent) dependency.StartFunc { 27 return func(_ dependency.Context) (worker.Worker, error) { 28 w := &agentWorker{agent: a} 29 go func() { 30 defer w.tomb.Done() 31 <-w.tomb.Dying() 32 }() 33 return w, nil 34 } 35 } 36 37 // outputFunc extracts an Agent from its *agentWorker. 38 func outputFunc(in worker.Worker, out interface{}) error { 39 inWorker, _ := in.(*agentWorker) 40 outPointer, _ := out.(*agent.Agent) 41 if inWorker == nil || outPointer == nil { 42 return errors.Errorf("expected %T->%T; got %T->%T", inWorker, outPointer, in, out) 43 } 44 *outPointer = inWorker.agent 45 return nil 46 } 47 48 // agentWorker is a degenerate worker.Worker that exists only to make an Agent 49 // accessible via the manifold's Output. 50 type agentWorker struct { 51 tomb tomb.Tomb 52 agent agent.Agent 53 } 54 55 // Kill is part of the worker.Worker interface. 56 func (w *agentWorker) Kill() { 57 w.tomb.Kill(nil) 58 } 59 60 // Wait is part of the worker.Worker interface. 61 func (w *agentWorker) Wait() error { 62 return w.tomb.Wait() 63 }