github.com/altoros/juju-vmware@v0.0.0-20150312064031-f19ae857ccca/storage/pool/pool.go (about) 1 // Copyright 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package pool 5 6 import ( 7 "github.com/juju/errors" 8 9 "github.com/juju/juju/storage" 10 ) 11 12 const ( 13 // Pool configuration attribute names. 14 Name = "name" 15 Type = "type" 16 ) 17 18 var ( 19 MissingTypeError = errors.New("provider type is missing") 20 MissingNameError = errors.New("pool name is missing") 21 ) 22 23 // config encapsulates the config attributes for a storage pool. 24 type config struct { 25 attrs map[string]interface{} 26 } 27 28 func (c *config) values() map[string]interface{} { 29 copy := make(map[string]interface{}) 30 for k, v := range c.attrs { 31 copy[k] = v 32 } 33 return copy 34 } 35 36 func (c *config) validate() error { 37 //TODO: properly validate the config attributes. 38 if c.attrs[Type] == "" { 39 return MissingTypeError 40 } 41 if c.attrs[Name] == "" { 42 return MissingNameError 43 } 44 return nil 45 } 46 47 var _ Pool = (*pool)(nil) 48 49 type pool struct { 50 cfg *config 51 } 52 53 // Name is defined on Pool interface. 54 func (p *pool) Name() string { 55 return p.cfg.attrs[Name].(string) 56 } 57 58 // Type is defined on Pool interface. 59 func (p *pool) Type() storage.ProviderType { 60 return storage.ProviderType(p.cfg.attrs[Type].(string)) 61 } 62 63 // Config is defined on Pool interface. 64 func (p *pool) Config() map[string]interface{} { 65 return p.cfg.values() 66 } 67 68 // NewPoolManager returns a NewPoolManager implementation using the specified state. 69 func NewPoolManager(settings SettingsManager) PoolManager { 70 return &poolManager{settings} 71 } 72 73 var _ PoolManager = (*poolManager)(nil) 74 75 type poolManager struct { 76 settings SettingsManager 77 } 78 79 const globalKeyPrefix = "pool#" 80 81 func globalKey(name string) string { 82 return globalKeyPrefix + name 83 } 84 85 // Create is defined on PoolManager interface. 86 func (pm *poolManager) Create(name string, providerType storage.ProviderType, attrs map[string]interface{}) (Pool, error) { 87 // Take a copy of the config and record name, type. 88 poolAttrs := attrs 89 poolAttrs[Name] = name 90 poolAttrs[Type] = string(providerType) 91 92 // Make sure we validate. 93 cfg := &config{poolAttrs} 94 if err := cfg.validate(); err != nil { 95 return nil, err 96 } 97 if err := pm.settings.CreateSettings(globalKey(name), poolAttrs); err != nil { 98 return nil, errors.Annotatef(err, "creating pool %q", name) 99 } 100 return &pool{cfg}, nil 101 } 102 103 // Delete is defined on PoolManager interface. 104 func (pm *poolManager) Delete(name string) error { 105 err := pm.settings.RemoveSettings(globalKey(name)) 106 if err == nil || errors.IsNotFound(err) { 107 return nil 108 } 109 return errors.Annotatef(err, "deleting pool %q", name) 110 } 111 112 // Get is defined on PoolManager interface. 113 func (pm *poolManager) Get(name string) (Pool, error) { 114 settings, err := pm.settings.ReadSettings(globalKey(name)) 115 if err != nil { 116 return nil, errors.Annotatef(err, "reading pool %q", name) 117 } 118 return &pool{&config{settings}}, nil 119 } 120 121 // List is defined on PoolManager interface. 122 func (pm *poolManager) List() ([]Pool, error) { 123 settings, err := pm.settings.ListSettings(globalKeyPrefix) 124 if err != nil { 125 return nil, errors.Annotate(err, "listing pool settings") 126 } 127 var result []Pool 128 for _, attrs := range settings { 129 result = append(result, &pool{&config{attrs}}) 130 } 131 return result, nil 132 }