func (s *loopSuite) TestVolumeSource(c *gc.C) { p := s.loopProvider(c) cfg, err := storage.NewConfig("name", provider.LoopProviderType, map[string]interface{}{}) c.Assert(err, jc.ErrorIsNil) _, err = p.VolumeSource(cfg) c.Assert(err, gc.ErrorMatches, "storage directory not specified") cfg, err = storage.NewConfig("name", provider.LoopProviderType, map[string]interface{}{ "storage-dir": c.MkDir(), }) c.Assert(err, jc.ErrorIsNil) _, err = p.VolumeSource(cfg) c.Assert(err, jc.ErrorIsNil) }
func (s *tmpfsSuite) TestFilesystemSource(c *gc.C) { p := s.tmpfsProvider(c) cfg, err := storage.NewConfig("name", provider.TmpfsProviderType, map[string]interface{}{}) c.Assert(err, jc.ErrorIsNil) _, err = p.FilesystemSource(nil, cfg) c.Assert(err, gc.ErrorMatches, "storage directory not specified") cfg, err = storage.NewConfig("name", provider.TmpfsProviderType, map[string]interface{}{ "storage-dir": c.MkDir(), }) c.Assert(err, jc.ErrorIsNil) _, err = p.FilesystemSource(nil, cfg) c.Assert(err, jc.ErrorIsNil) }
func mustStorageConfig(name string, provider storage.ProviderType, attrs map[string]interface{}) *storage.Config { cfg, err := storage.NewConfig(name, provider, attrs) if err != nil { panic(err) } return cfg }
func (s *baseStorageSuite) constructPoolManager(c *gc.C) *mockPoolManager { return &mockPoolManager{ getPool: func(name string) (*jujustorage.Config, error) { if one, ok := s.pools[name]; ok { return one, nil } return nil, errors.NotFoundf("mock pool manager: get pool %v", name) }, createPool: func(name string, providerType jujustorage.ProviderType, attrs map[string]interface{}) (*jujustorage.Config, error) { pool, err := jujustorage.NewConfig(name, providerType, attrs) s.pools[name] = pool return pool, err }, deletePool: func(name string) error { delete(s.pools, name) return nil }, listPools: func() ([]*jujustorage.Config, error) { result := make([]*jujustorage.Config, len(s.pools)) i := 0 for _, v := range s.pools { result[i] = v i++ } return result, nil }, } }
// Create is defined on PoolManager interface. func (pm *poolManager) Create(name string, providerType storage.ProviderType, attrs map[string]interface{}) (*storage.Config, error) { if name == "" { return nil, MissingNameError } if providerType == "" { return nil, MissingTypeError } cfg, err := storage.NewConfig(name, providerType, attrs) if err != nil { return nil, errors.Trace(err) } p, err := registry.StorageProvider(providerType) if err != nil { return nil, errors.Trace(err) } if err := provider.ValidateConfig(p, cfg); err != nil { return nil, errors.Annotate(err, "validating storage provider config") } poolAttrs := cfg.Attrs() poolAttrs[Name] = name poolAttrs[Type] = string(providerType) if err := pm.settings.CreateSettings(globalKey(name), poolAttrs); err != nil { return nil, errors.Annotatef(err, "creating pool %q", name) } return cfg, nil }
func (s *storageSuite) TestFilesystemSource(c *gc.C) { storageConfig, err := storage.NewConfig("azure", "azure", nil) c.Assert(err, jc.ErrorIsNil) _, err = s.provider.FilesystemSource(storageConfig) c.Assert(err, gc.ErrorMatches, "filesystems not supported") c.Assert(err, jc.Satisfies, errors.IsNotSupported) }
func (*storageSuite) TestValidateConfigUnknownConfig(c *gc.C) { p := ec2.EBSProvider() cfg, err := storage.NewConfig("foo", ec2.EBS_ProviderType, map[string]interface{}{ "unknown": "config", }) c.Assert(err, jc.ErrorIsNil) err = p.ValidateConfig(cfg) c.Assert(err, jc.ErrorIsNil) // unknown attrs ignored }
func init() { ebsssdPool, _ := storage.NewConfig("ebs-ssd", EBS_ProviderType, map[string]interface{}{ EBS_VolumeType: volumeTypeSsd, }) defaultPools := []*storage.Config{ ebsssdPool, } poolmanager.RegisterDefaultStoragePools(defaultPools) }
func (s *defaultStoragePoolsSuite) TestDefaultStoragePools(c *gc.C) { p1, err := storage.NewConfig("pool1", storage.ProviderType("loop"), map[string]interface{}{"1": "2"}) p2, err := storage.NewConfig("pool2", storage.ProviderType("tmpfs"), map[string]interface{}{"3": "4"}) c.Assert(err, jc.ErrorIsNil) defaultPools := []*storage.Config{p1, p2} poolmanager.RegisterDefaultStoragePools(defaultPools) settings := state.NewStateSettings(s.State) err = poolmanager.AddDefaultStoragePools(settings) c.Assert(err, jc.ErrorIsNil) pm := poolmanager.New(settings) for _, pool := range defaultPools { p, err := pm.Get(pool.Name()) c.Assert(err, jc.ErrorIsNil) c.Assert(p.Provider(), gc.Equals, pool.Provider()) c.Assert(p.Attrs(), gc.DeepEquals, pool.Attrs()) } }
func (s *tmpfsSuite) TestValidateConfig(c *gc.C) { p := s.tmpfsProvider(c) cfg, err := storage.NewConfig("name", provider.TmpfsProviderType, map[string]interface{}{}) c.Assert(err, jc.ErrorIsNil) err = p.ValidateConfig(cfg) // The tmpfs provider does not have any user // configuration, so an empty map will pass. c.Assert(err, jc.ErrorIsNil) }
func (s *poolSuite) createPools(c *gc.C, num int) { var err error for i := 0; i < num; i++ { poolName := fmt.Sprintf("%v%v", tstName, i) s.baseStorageSuite.pools[poolName], err = storage.NewConfig(poolName, provider.LoopProviderType, nil) c.Assert(err, jc.ErrorIsNil) } }
func (*storageProviderSuite) TestValidateConfigUnknownAttribute(c *gc.C) { p := maasStorageProvider{} cfg, err := storage.NewConfig("foo", maasStorageProviderType, map[string]interface{}{ "unknown": "config", }) c.Assert(err, jc.ErrorIsNil) err = p.ValidateConfig(cfg) c.Assert(err, jc.ErrorIsNil) // unknown attributes are ignored }
func (*storageProviderSuite) TestValidateConfigInvalidConfig(c *gc.C) { p := maasStorageProvider{} cfg, err := storage.NewConfig("foo", maasStorageProviderType, map[string]interface{}{ "tags": "white space", }) c.Assert(err, jc.ErrorIsNil) err = p.ValidateConfig(cfg) c.Assert(err, gc.ErrorMatches, `tags may not contain whitespace: "white space"`) }
func (s *defaultStoragePoolsSuite) TestDefaultStoragePools(c *gc.C) { p1, err := storage.NewConfig("pool1", storage.ProviderType("whatever"), map[string]interface{}{"1": "2"}) c.Assert(err, jc.ErrorIsNil) p2, err := storage.NewConfig("pool2", storage.ProviderType("whatever"), map[string]interface{}{"3": "4"}) c.Assert(err, jc.ErrorIsNil) provider := &dummystorage.StorageProvider{ DefaultPools_: []*storage.Config{p1, p2}, } settings := poolmanager.MemSettings{make(map[string]map[string]interface{})} pm := poolmanager.New(settings, storage.StaticProviderRegistry{ map[storage.ProviderType]storage.Provider{"whatever": provider}, }) err = poolmanager.AddDefaultStoragePools(provider, pm) c.Assert(err, jc.ErrorIsNil) c.Assert(settings.Settings, jc.DeepEquals, map[string]map[string]interface{}{ "pool#pool1": map[string]interface{}{"1": "2", "name": "pool1", "type": "whatever"}, "pool#pool2": map[string]interface{}{"3": "4", "name": "pool2", "type": "whatever"}, }) }
func (s *poolSuite) TestListByTypesOr(c *gc.C) { s.createPools(c, 2) s.registerProviders(c) tstType := string(provider.TmpfsProviderType) poolName := "rayofsunshine" var err error s.baseStorageSuite.pools[poolName], err = storage.NewConfig(poolName, provider.TmpfsProviderType, nil) c.Assert(err, jc.ErrorIsNil) pools, err := s.api.ListPools(params.StoragePoolFilter{ Providers: []string{tstType, string(provider.LoopProviderType)}}) c.Assert(err, jc.ErrorIsNil) assertPoolNames(c, pools.Results, "testpool0", "testpool1", "rayofsunshine", "loop", "tmpfs") }
func (s *loopSuite) TestCreateVolumesInsideLXC(c *gc.C) { s.runningInsideLXC = true source, _ := s.loopVolumeSource(c) s.testCreateVolumesInsideLXC(c, source) p := s.loopProvider(c) cfg, err := storage.NewConfig("name", provider.LoopProviderType, map[string]interface{}{ "storage-dir": s.storageDir, }) c.Assert(err, jc.ErrorIsNil) source, err = p.VolumeSource(nil, cfg) c.Assert(err, jc.ErrorIsNil) s.testCreateVolumesInsideLXC(c, source) }
func (s *storageSuite) volumeSource(c *gc.C, attrs ...testing.Attrs) storage.VolumeSource { storageConfig, err := storage.NewConfig("azure", "azure", nil) c.Assert(err, jc.ErrorIsNil) volumeSource, err := s.provider.VolumeSource(storageConfig) c.Assert(err, jc.ErrorIsNil) // Force an explicit refresh of the access token, so it isn't done // implicitly during the tests. s.sender = azuretesting.Senders{ tokenRefreshSender(), } err = azure.ForceVolumeSourceTokenRefresh(volumeSource) c.Assert(err, jc.ErrorIsNil) return volumeSource }
func (s *poolSuite) TestListByNamesOr(c *gc.C) { s.createPools(c, 2) s.registerProviders(c) poolName := "rayofsunshine" var err error s.baseStorageSuite.pools[poolName], err = storage.NewConfig(poolName, provider.TmpfsProviderType, nil) c.Assert(err, jc.ErrorIsNil) pools, err := s.api.ListPools(params.StoragePoolFilter{ Names: []string{ fmt.Sprintf("%v%v", tstName, 1), fmt.Sprintf("%v%v", tstName, 0), }}) c.Assert(err, jc.ErrorIsNil) assertPoolNames(c, pools.Results, "testpool0", "testpool1") }
func (*storageProviderSuite) TestValidateConfigTags(c *gc.C) { p := maasStorageProvider{} validate := func(tags interface{}) { cfg, err := storage.NewConfig("foo", maasStorageProviderType, map[string]interface{}{ "tags": tags, }) c.Assert(err, jc.ErrorIsNil) err = p.ValidateConfig(cfg) c.Assert(err, jc.ErrorIsNil) } validate("singular") validate("mul,ti,ple") validate(" leading, spaces") validate("trailing ,spaces ") validate(" and,everything, in , between ") }
func sourceParams(providerType storage.ProviderType, sourceName, baseStorageDir string) (storage.Provider, *storage.Config, error) { provider, err := registry.StorageProvider(providerType) if err != nil { return nil, nil, errors.Annotate(err, "getting provider") } attrs := make(map[string]interface{}) if baseStorageDir != "" { storageDir := filepath.Join(baseStorageDir, sourceName) attrs[storage.ConfigStorageDir] = storageDir } sourceConfig, err := storage.NewConfig(sourceName, providerType, attrs) if err != nil { return nil, nil, errors.Annotate(err, "getting config") } return provider, sourceConfig, nil }
func (s *poolSuite) TestListByNameAndTypeAnd(c *gc.C) { s.createPools(c, 2) s.registerProviders(c) tstType := string(provider.TmpfsProviderType) poolName := "rayofsunshine" var err error s.baseStorageSuite.pools[poolName], err = storage.NewConfig(poolName, provider.TmpfsProviderType, nil) c.Assert(err, jc.ErrorIsNil) pools, err := s.api.ListPools(params.StoragePoolFilter{ Providers: []string{tstType}, Names: []string{poolName}}) c.Assert(err, jc.ErrorIsNil) c.Assert(pools.Results, gc.HasLen, 1) c.Assert(pools.Results[0].Provider, gc.DeepEquals, tstType) c.Assert(pools.Results[0].Name, gc.DeepEquals, poolName) }
func (s *storageSuite) volumeSource(c *gc.C, attrs ...testing.Attrs) storage.VolumeSource { storageConfig, err := storage.NewConfig("azure", "azure", nil) c.Assert(err, jc.ErrorIsNil) attrs = append([]testing.Attrs{{ "storage-account": fakeStorageAccount, "storage-account-key": fakeStorageAccountKey, }}, attrs...) cfg := makeTestModelConfig(c, attrs...) volumeSource, err := s.provider.VolumeSource(cfg, storageConfig) c.Assert(err, jc.ErrorIsNil) // Force an explicit refresh of the access token, so it isn't done // implicitly during the tests. s.sender = azuretesting.Senders{tokenRefreshSender()} err = azure.ForceVolumeSourceTokenRefresh(volumeSource) c.Assert(err, jc.ErrorIsNil) return volumeSource }
func destroyVolumes( environConfig *config.Config, storageProviderType storage.ProviderType, storageProvider storage.Provider, ) error { if !storageProvider.Supports(storage.StorageKindBlock) { return nil } storageConfig, err := storage.NewConfig( string(storageProviderType), storageProviderType, map[string]interface{}{}, ) if err != nil { return errors.Trace(err) } volumeSource, err := storageProvider.VolumeSource(environConfig, storageConfig) if err != nil { return errors.Annotate(err, "getting volume source") } volumeIds, err := volumeSource.ListVolumes() if err != nil { return errors.Annotate(err, "listing volumes") } var errStrings []string errs, err := volumeSource.DestroyVolumes(volumeIds) if err != nil { return errors.Annotate(err, "destroying volumes") } for _, err := range errs { if err != nil { errStrings = append(errStrings, err.Error()) } } if len(errStrings) > 0 { return errors.Errorf("destroying volumes: %s", strings.Join(errStrings, ", ")) } return nil }
func (s *poolCreateSuite) TestCreatePool(c *gc.C) { const ( pname = "pname" ptype = string(provider.LoopProviderType) ) expected, _ := jujustorage.NewConfig(pname, provider.LoopProviderType, nil) err := s.api.CreatePool(params.StoragePool{ Name: pname, Provider: ptype, Attrs: nil, }) c.Assert(err, jc.ErrorIsNil) pools, err := s.poolManager.List() c.Assert(err, jc.ErrorIsNil) c.Assert(pools, gc.HasLen, 1) c.Assert(pools[0], gc.DeepEquals, expected) }
func configFromSettings(settings map[string]interface{}) (*storage.Config, error) { providerType := storage.ProviderType(settings[Type].(string)) name := settings[Name].(string) // Ensure returned attributes are stripped of name and type, // as these are not user-specified attributes. delete(settings, Name) delete(settings, Type) cfg, err := storage.NewConfig(name, providerType, settings) if err != nil { return nil, errors.Trace(err) } p, err := registry.StorageProvider(providerType) if err != nil { return nil, errors.Trace(err) } if err := provider.ValidateConfig(p, cfg); err != nil { return nil, errors.Trace(err) } return cfg, nil }
// DefaultPools is defined on the Provider interface. func (e *ebsProvider) DefaultPools() []*storage.Config { ssdPool, _ := storage.NewConfig("ebs-ssd", EBS_ProviderType, map[string]interface{}{ EBS_VolumeType: volumeTypeSSD, }) return []*storage.Config{ssdPool} }