github.com/mhilton/juju-juju@v0.0.0-20150901100907-a94dd2c73455/cmd/juju/storage/storage.go (about)

     1  // Copyright 2015 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package storage
     5  
     6  import (
     7  	"github.com/juju/cmd"
     8  	"github.com/juju/errors"
     9  	"github.com/juju/loggo"
    10  	"github.com/juju/names"
    11  
    12  	"github.com/juju/juju/api/storage"
    13  	"github.com/juju/juju/apiserver/params"
    14  	"github.com/juju/juju/cmd/envcmd"
    15  )
    16  
    17  var logger = loggo.GetLogger("juju.cmd.juju.storage")
    18  
    19  const storageCmdDoc = `
    20  "juju storage" is used to manage storage instances in
    21   the Juju environment.
    22  `
    23  
    24  const storageCmdPurpose = "manage storage instances"
    25  
    26  // NewSuperCommand creates the storage supercommand and
    27  // registers the subcommands that it supports.
    28  func NewSuperCommand() cmd.Command {
    29  	storagecmd := cmd.NewSuperCommand(
    30  		cmd.SuperCommandParams{
    31  			Name:        "storage",
    32  			Doc:         storageCmdDoc,
    33  			UsagePrefix: "juju",
    34  			Purpose:     storageCmdPurpose,
    35  		})
    36  	storagecmd.Register(envcmd.Wrap(&ShowCommand{}))
    37  	storagecmd.Register(envcmd.Wrap(&ListCommand{}))
    38  	storagecmd.Register(envcmd.Wrap(&AddCommand{}))
    39  	storagecmd.Register(NewPoolSuperCommand())
    40  	storagecmd.Register(NewVolumeSuperCommand())
    41  	return storagecmd
    42  }
    43  
    44  // StorageCommandBase is a helper base structure that has a method to get the
    45  // storage managing client.
    46  type StorageCommandBase struct {
    47  	envcmd.EnvCommandBase
    48  }
    49  
    50  // NewStorageAPI returns a storage api for the root api endpoint
    51  // that the environment command returns.
    52  func (c *StorageCommandBase) NewStorageAPI() (*storage.Client, error) {
    53  	root, err := c.NewAPIRoot()
    54  	if err != nil {
    55  		return nil, err
    56  	}
    57  	return storage.NewClient(root), nil
    58  }
    59  
    60  // StorageInfo defines the serialization behaviour of the storage information.
    61  type StorageInfo struct {
    62  	StorageName string `yaml:"storage" json:"storage"`
    63  	Kind        string `yaml:"kind" json:"kind"`
    64  	Status      string `yaml:"status,omitempty" json:"status,omitempty"`
    65  	Persistent  bool   `yaml:"persistent" json:"persistent"`
    66  	Location    string `yaml:"location,omitempty" json:"location,omitempty"`
    67  }
    68  
    69  // formatStorageDetails takes a set of StorageDetail and creates a
    70  // mapping keyed on unit and storage id.
    71  func formatStorageDetails(storages []params.StorageDetails) (map[string]map[string]StorageInfo, error) {
    72  	if len(storages) == 0 {
    73  		return nil, nil
    74  	}
    75  	output := make(map[string]map[string]StorageInfo)
    76  	for _, one := range storages {
    77  		storageTag, err := names.ParseStorageTag(one.StorageTag)
    78  		if err != nil {
    79  			return nil, errors.Annotate(err, "invalid storage tag")
    80  		}
    81  		unitTag, err := names.ParseTag(one.UnitTag)
    82  		if err != nil {
    83  			return nil, errors.Annotate(err, "invalid unit tag")
    84  		}
    85  
    86  		storageName, err := names.StorageName(storageTag.Id())
    87  		if err != nil {
    88  			panic(err) // impossible
    89  		}
    90  		si := StorageInfo{
    91  			StorageName: storageName,
    92  			Kind:        one.Kind.String(),
    93  			Status:      one.Status,
    94  			Location:    one.Location,
    95  			Persistent:  one.Persistent,
    96  		}
    97  		unit := unitTag.Id()
    98  		unitColl, ok := output[unit]
    99  		if !ok {
   100  			unitColl = map[string]StorageInfo{}
   101  			output[unit] = unitColl
   102  		}
   103  		unitColl[storageTag.Id()] = si
   104  	}
   105  	return output, nil
   106  }