github.com/cloud-green/juju@v0.0.0-20151002100041-a00291338d3d/worker/uniter/operation/factory.go (about) 1 // Copyright 2014-2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package operation 5 6 import ( 7 "github.com/juju/errors" 8 "github.com/juju/names" 9 corecharm "gopkg.in/juju/charm.v6-unstable" 10 11 "github.com/juju/juju/worker/uniter/charm" 12 "github.com/juju/juju/worker/uniter/hook" 13 "github.com/juju/juju/worker/uniter/runner" 14 ) 15 16 // FactoryParams holds all the necessary parameters for a new operation factory. 17 type FactoryParams struct { 18 Deployer charm.Deployer 19 RunnerFactory runner.Factory 20 Callbacks Callbacks 21 StorageUpdater StorageUpdater 22 Abort <-chan struct{} 23 MetricSpoolDir string 24 } 25 26 // NewFactory returns a Factory that creates Operations backed by the supplied 27 // parameters. 28 func NewFactory(params FactoryParams) Factory { 29 return &factory{ 30 config: params, 31 } 32 } 33 34 type factory struct { 35 config FactoryParams 36 } 37 38 // newDeploy is the common code for creating arbitrary deploy operations. 39 func (f *factory) newDeploy(kind Kind, charmURL *corecharm.URL, revert, resolved bool) (Operation, error) { 40 if charmURL == nil { 41 return nil, errors.New("charm url required") 42 } else if kind != Install && kind != Upgrade { 43 return nil, errors.Errorf("unknown deploy kind: %s", kind) 44 } 45 return &deploy{ 46 kind: kind, 47 charmURL: charmURL, 48 revert: revert, 49 resolved: resolved, 50 callbacks: f.config.Callbacks, 51 deployer: f.config.Deployer, 52 abort: f.config.Abort, 53 }, nil 54 } 55 56 // NewInstall is part of the Factory interface. 57 func (f *factory) NewInstall(charmURL *corecharm.URL) (Operation, error) { 58 return f.newDeploy(Install, charmURL, false, false) 59 } 60 61 // NewUpgrade is part of the Factory interface. 62 func (f *factory) NewUpgrade(charmURL *corecharm.URL) (Operation, error) { 63 return f.newDeploy(Upgrade, charmURL, false, false) 64 } 65 66 // NewRevertUpgrade is part of the Factory interface. 67 func (f *factory) NewRevertUpgrade(charmURL *corecharm.URL) (Operation, error) { 68 return f.newDeploy(Upgrade, charmURL, true, false) 69 } 70 71 // NewResolvedUpgrade is part of the Factory interface. 72 func (f *factory) NewResolvedUpgrade(charmURL *corecharm.URL) (Operation, error) { 73 return f.newDeploy(Upgrade, charmURL, false, true) 74 } 75 76 // NewRunHook is part of the Factory interface. 77 func (f *factory) NewRunHook(hookInfo hook.Info) (Operation, error) { 78 if err := hookInfo.Validate(); err != nil { 79 return nil, err 80 } 81 return &runHook{ 82 info: hookInfo, 83 callbacks: f.config.Callbacks, 84 runnerFactory: f.config.RunnerFactory, 85 }, nil 86 } 87 88 // NewSkipHook is part of the Factory interface. 89 func (f *factory) NewSkipHook(hookInfo hook.Info) (Operation, error) { 90 hookOp, err := f.NewRunHook(hookInfo) 91 if err != nil { 92 return nil, err 93 } 94 return &skipOperation{hookOp}, nil 95 } 96 97 // NewAction is part of the Factory interface. 98 func (f *factory) NewAction(actionId string) (Operation, error) { 99 if !names.IsValidAction(actionId) { 100 return nil, errors.Errorf("invalid action id %q", actionId) 101 } 102 return &runAction{ 103 actionId: actionId, 104 callbacks: f.config.Callbacks, 105 runnerFactory: f.config.RunnerFactory, 106 }, nil 107 } 108 109 // NewCommands is part of the Factory interface. 110 func (f *factory) NewCommands(args CommandArgs, sendResponse CommandResponseFunc) (Operation, error) { 111 if args.Commands == "" { 112 return nil, errors.New("commands required") 113 } else if sendResponse == nil { 114 return nil, errors.New("response sender required") 115 } 116 if args.RemoteUnitName != "" { 117 if args.RelationId == -1 { 118 return nil, errors.New("remote unit not valid without relation") 119 } else if !names.IsValidUnit(args.RemoteUnitName) { 120 return nil, errors.Errorf("invalid remote unit name %q", args.RemoteUnitName) 121 } 122 } 123 return &runCommands{ 124 args: args, 125 sendResponse: sendResponse, 126 callbacks: f.config.Callbacks, 127 runnerFactory: f.config.RunnerFactory, 128 }, nil 129 } 130 131 // NewUpdateStorage is part of the Factory interface. 132 func (f *factory) NewUpdateStorage(tags []names.StorageTag) (Operation, error) { 133 return &updateStorage{ 134 tags: tags, 135 storageUpdater: f.config.StorageUpdater, 136 }, nil 137 } 138 139 // NewResignLeadership is part of the Factory interface. 140 func (f *factory) NewResignLeadership() (Operation, error) { 141 return &resignLeadership{}, nil 142 } 143 144 // NewAcceptLeadership is part of the Factory interface. 145 func (f *factory) NewAcceptLeadership() (Operation, error) { 146 return &acceptLeadership{}, nil 147 }