github.com/niedbalski/juju@v0.0.0-20190215020005-8ff100488e47/cmd/juju/model/grantrevokecloud.go (about)

     1  // Copyright 2018 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package model
     5  
     6  import (
     7  	"github.com/juju/cmd"
     8  	"github.com/juju/errors"
     9  	"github.com/juju/juju/api/cloud"
    10  	"gopkg.in/juju/names.v2"
    11  
    12  	jujucmd "github.com/juju/juju/cmd"
    13  	"github.com/juju/juju/cmd/juju/block"
    14  	"github.com/juju/juju/cmd/modelcmd"
    15  	"github.com/juju/juju/permission"
    16  )
    17  
    18  var usageGrantCloudSummary = `
    19  Grants access level to a Juju user for a cloud.`[1:]
    20  
    21  var usageGrantCloudDetails = `
    22  Valid access levels are:
    23      add-model
    24      admin
    25  
    26  Examples:
    27  Grant user 'joe' 'add-model' access to cloud 'fluffy':
    28  
    29      juju grant-cloud joe add-model fluffy
    30  
    31  See also: 
    32      revoke-cloud
    33      add-user`[1:]
    34  
    35  var usageRevokeCloudSummary = `
    36  Revokes access from a Juju user for a cloud.`[1:]
    37  
    38  var usageRevokeCloudDetails = `
    39  Revoking admin access, from a user who has that permission, will leave
    40  that user with add-model access. Revoking add-model access, however, also revokes
    41  admin access.
    42  
    43  Examples:
    44  Revoke 'add-model' (and 'admin') access from user 'joe' for cloud 'fluffy':
    45  
    46      juju revoke-cloud joe add-model fluffy
    47  
    48  Revoke 'admin' access from user 'sam' for clouds 'fluffy' and 'rainy':
    49  
    50      juju revoke-cloud sam admin fluffy rainy
    51  
    52  See also: 
    53      grant-cloud`[1:]
    54  
    55  type accessCloudCommand struct {
    56  	modelcmd.ControllerCommandBase
    57  
    58  	User   string
    59  	Clouds []string
    60  	Access string
    61  }
    62  
    63  // Init implements cmd.Command.
    64  func (c *accessCloudCommand) Init(args []string) error {
    65  	if len(args) < 1 {
    66  		return errors.New("no user specified")
    67  	}
    68  
    69  	if len(args) < 2 {
    70  		return errors.New("no permission level specified")
    71  	}
    72  
    73  	c.User = args[0]
    74  	c.Access = args[1]
    75  	// The remaining args are cloud names.
    76  	for _, arg := range args[2:] {
    77  		if !names.IsValidCloud(arg) {
    78  			return errors.NotValidf("cloud name %q", arg)
    79  		}
    80  		c.Clouds = append(c.Clouds, arg)
    81  	}
    82  
    83  	// Special case for backwards compatibility.
    84  	if c.Access == "addmodel" {
    85  		c.Access = "add-model"
    86  	}
    87  	if len(c.Clouds) > 0 {
    88  		return permission.ValidateCloudAccess(permission.Access(c.Access))
    89  	}
    90  	return errors.Errorf("You need to specify one or more cloud names.\n" +
    91  		"See 'juju help grant-cloud'.")
    92  }
    93  
    94  // NewGrantCloudCommand returns a new grant command.
    95  func NewGrantCloudCommand() cmd.Command {
    96  	return modelcmd.WrapController(&grantCloudCommand{})
    97  }
    98  
    99  // grantCloudCommand represents the command to grant a user access to one or more clouds.
   100  type grantCloudCommand struct {
   101  	accessCloudCommand
   102  	cloudsApi GrantCloudAPI
   103  }
   104  
   105  // Info implements Command.Info.
   106  func (c *grantCloudCommand) Info() *cmd.Info {
   107  	return jujucmd.Info(&cmd.Info{
   108  		Name:    "grant-cloud",
   109  		Args:    "<user name> <permission> <cloud name> ...",
   110  		Purpose: usageGrantCloudSummary,
   111  		Doc:     usageGrantCloudDetails,
   112  	})
   113  }
   114  
   115  func (c *grantCloudCommand) getCloudsAPI() (GrantCloudAPI, error) {
   116  	if c.cloudsApi != nil {
   117  		return c.cloudsApi, nil
   118  	}
   119  	root, err := c.NewAPIRoot()
   120  	if err != nil {
   121  		return nil, errors.Trace(err)
   122  	}
   123  	return cloud.NewClient(root), nil
   124  }
   125  
   126  // GrantCloudAPI defines the API functions used by the grant command.
   127  type GrantCloudAPI interface {
   128  	Close() error
   129  	GrantCloud(user, access string, clouds ...string) error
   130  }
   131  
   132  // Run implements cmd.Command.
   133  func (c *grantCloudCommand) Run(ctx *cmd.Context) error {
   134  	client, err := c.getCloudsAPI()
   135  	if err != nil {
   136  		return err
   137  	}
   138  	defer client.Close()
   139  
   140  	return block.ProcessBlockedError(client.GrantCloud(c.User, c.Access, c.Clouds...), block.BlockChange)
   141  }
   142  
   143  // NewRevokeCloudCommand returns a new revoke command.
   144  func NewRevokeCloudCommand() cmd.Command {
   145  	return modelcmd.WrapController(&revokeCloudCommand{})
   146  }
   147  
   148  // revokeCloudCommand revokes a user's access to clouds.
   149  type revokeCloudCommand struct {
   150  	accessCloudCommand
   151  	cloudsApi RevokeCloudAPI
   152  }
   153  
   154  // Info implements cmd.Command.
   155  func (c *revokeCloudCommand) Info() *cmd.Info {
   156  	return jujucmd.Info(&cmd.Info{
   157  		Name:    "revoke-cloud",
   158  		Args:    "<user name> <permission> <cloud name> ...",
   159  		Purpose: usageRevokeCloudSummary,
   160  		Doc:     usageRevokeCloudDetails,
   161  	})
   162  }
   163  
   164  func (c *revokeCloudCommand) getCloudAPI() (RevokeCloudAPI, error) {
   165  	if c.cloudsApi != nil {
   166  		return c.cloudsApi, nil
   167  	}
   168  	root, err := c.NewAPIRoot()
   169  	if err != nil {
   170  		return nil, errors.Trace(err)
   171  	}
   172  	return cloud.NewClient(root), nil
   173  }
   174  
   175  // RevokeCloudAPI defines the API functions used by the revoke cloud command.
   176  type RevokeCloudAPI interface {
   177  	Close() error
   178  	RevokeCloud(user, access string, clouds ...string) error
   179  }
   180  
   181  // Run implements cmd.Command.
   182  func (c *revokeCloudCommand) Run(ctx *cmd.Context) error {
   183  	client, err := c.getCloudAPI()
   184  	if err != nil {
   185  		return err
   186  	}
   187  	defer client.Close()
   188  
   189  	return block.ProcessBlockedError(client.RevokeCloud(c.User, c.Access, c.Clouds...), block.BlockChange)
   190  }