github.com/cloud-green/juju@v0.0.0-20151002100041-a00291338d3d/cmd/juju/common/constraints.go (about) 1 // Copyright 2013 - 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package common 5 6 import ( 7 "fmt" 8 9 "github.com/juju/cmd" 10 "github.com/juju/names" 11 "launchpad.net/gnuflag" 12 13 "github.com/juju/juju/cmd/envcmd" 14 "github.com/juju/juju/cmd/juju/block" 15 "github.com/juju/juju/constraints" 16 ) 17 18 const getConstraintsDoc = ` 19 get-constraints returns a list of constraints that have been set on 20 the environment using juju set-constraints. You can also view constraints set 21 for a specific service by using juju get-constraints <service>. 22 23 See Also: 24 juju help constraints 25 juju help set-constraints 26 ` 27 28 const setConstraintsDoc = ` 29 set-constraints sets machine constraints on the system, which are used as the 30 default constraints for all new machines provisioned in the environment (unless 31 overridden). You can also set constraints on a specific service by using juju 32 set-constraints <service>. 33 34 Constraints set on a service are combined with environment constraints for 35 commands (such as juju deploy) that provision machines for services. Where 36 environment and service constraints overlap, the service constraints take 37 precedence. 38 39 Examples: 40 41 set-constraints mem=8G (all new machines in the environment must have at least 8GB of RAM) 42 set-constraints --service wordpress mem=4G (all new wordpress machines can ignore the 8G constraint above, and require only 4G) 43 44 See Also: 45 juju help constraints 46 juju help get-constraints 47 juju help deploy 48 juju help add-machine 49 juju help add-unit 50 ` 51 52 // GetConstraintsCommand shows the constraints for a service or environment. 53 type GetConstraintsCommand struct { 54 envcmd.EnvCommandBase 55 ServiceName string 56 out cmd.Output 57 api ConstraintsAPI 58 } 59 60 // Constraints API defines methods on the client API that 61 // the get-constraints and set-constraints commands call 62 type ConstraintsAPI interface { 63 Close() error 64 GetEnvironmentConstraints() (constraints.Value, error) 65 GetServiceConstraints(string) (constraints.Value, error) 66 SetEnvironmentConstraints(constraints.Value) error 67 SetServiceConstraints(string, constraints.Value) error 68 } 69 70 func (c *GetConstraintsCommand) getAPI() (ConstraintsAPI, error) { 71 if c.api != nil { 72 return c.api, nil 73 } 74 return c.NewAPIClient() 75 } 76 77 func (c *GetConstraintsCommand) Info() *cmd.Info { 78 return &cmd.Info{ 79 Name: "get-constraints", 80 Args: "[<service>]", 81 Purpose: "view constraints on the environment or a service", 82 Doc: getConstraintsDoc, 83 } 84 } 85 86 func formatConstraints(value interface{}) ([]byte, error) { 87 return []byte(value.(constraints.Value).String()), nil 88 } 89 90 func (c *GetConstraintsCommand) SetFlags(f *gnuflag.FlagSet) { 91 c.out.AddFlags(f, "constraints", map[string]cmd.Formatter{ 92 "constraints": formatConstraints, 93 "yaml": cmd.FormatYaml, 94 "json": cmd.FormatJson, 95 }) 96 } 97 98 func (c *GetConstraintsCommand) Init(args []string) error { 99 if len(args) > 0 { 100 if !names.IsValidService(args[0]) { 101 return fmt.Errorf("invalid service name %q", args[0]) 102 } 103 c.ServiceName, args = args[0], args[1:] 104 } 105 return cmd.CheckEmpty(args) 106 } 107 108 func (c *GetConstraintsCommand) Run(ctx *cmd.Context) error { 109 apiclient, err := c.getAPI() 110 if err != nil { 111 return err 112 } 113 defer apiclient.Close() 114 115 var cons constraints.Value 116 if c.ServiceName == "" { 117 cons, err = apiclient.GetEnvironmentConstraints() 118 } else { 119 cons, err = apiclient.GetServiceConstraints(c.ServiceName) 120 } 121 if err != nil { 122 return err 123 } 124 return c.out.Write(ctx, cons) 125 } 126 127 // SetConstraintsCommand shows the constraints for a service or environment. 128 type SetConstraintsCommand struct { 129 envcmd.EnvCommandBase 130 ServiceName string 131 api ConstraintsAPI 132 Constraints constraints.Value 133 } 134 135 func (c *SetConstraintsCommand) getAPI() (ConstraintsAPI, error) { 136 if c.api != nil { 137 return c.api, nil 138 } 139 return c.NewAPIClient() 140 } 141 142 func (c *SetConstraintsCommand) Info() *cmd.Info { 143 return &cmd.Info{ 144 Name: "set-constraints", 145 Args: "[key=[value] ...]", 146 Purpose: "set constraints on the environment or a service", 147 Doc: setConstraintsDoc, 148 } 149 } 150 151 func (c *SetConstraintsCommand) SetFlags(f *gnuflag.FlagSet) { 152 f.StringVar(&c.ServiceName, "s", "", "set service constraints") 153 f.StringVar(&c.ServiceName, "service", "", "") 154 } 155 156 func (c *SetConstraintsCommand) Init(args []string) (err error) { 157 if c.ServiceName != "" && !names.IsValidService(c.ServiceName) { 158 return fmt.Errorf("invalid service name %q", c.ServiceName) 159 } 160 c.Constraints, err = constraints.Parse(args...) 161 return err 162 } 163 164 func (c *SetConstraintsCommand) Run(_ *cmd.Context) (err error) { 165 apiclient, err := c.getAPI() 166 if err != nil { 167 return err 168 } 169 defer apiclient.Close() 170 171 if c.ServiceName == "" { 172 err = apiclient.SetEnvironmentConstraints(c.Constraints) 173 } else { 174 err = apiclient.SetServiceConstraints(c.ServiceName, c.Constraints) 175 } 176 return block.ProcessBlockedError(err, block.BlockChange) 177 }