diff --git a/azure/aci.go b/azure/aci.go index 9d2cf58fd..20aef8412 100644 --- a/azure/aci.go +++ b/azure/aci.go @@ -268,28 +268,33 @@ func getSubscriptionsClient() (subscription.SubscriptionsClient, error) { return subc, nil } -// GetGroupsClient ... -func GetGroupsClient(subscriptionID string) resources.GroupsClient { +func getGroupsClient(subscriptionID string) resources.GroupsClient { groupsClient := resources.NewGroupsClient(subscriptionID) authorizer, _ := login.NewAuthorizerFromLogin() groupsClient.Authorizer = authorizer return groupsClient } -// GetSubscriptionID ... -func GetSubscriptionID(ctx context.Context) (string, error) { +func getSubscriptionIDs(ctx context.Context) ([]subscription.Model, error) { c, err := getSubscriptionsClient() if err != nil { - return "", err + return nil, err } res, err := c.List(ctx) if err != nil { - return "", err + return nil, err } subs := res.Values() + if len(subs) == 0 { - return "", errors.New("no subscriptions found") + return nil, errors.New("no subscriptions found") } - sub := subs[0] - return *sub.SubscriptionID, nil + for res.NotDone() { + err = res.NextWithContext(ctx) + if err != nil { + return nil, err + } + subs = append(subs, res.Values()...) + } + return subs, nil } diff --git a/azure/backend.go b/azure/backend.go index 99e34a888..073120e19 100644 --- a/azure/backend.go +++ b/azure/backend.go @@ -282,3 +282,7 @@ type aciCloudService struct { func (cs *aciCloudService) Login(ctx context.Context, params map[string]string) error { return cs.loginService.Login(ctx) } + +func (cs *aciCloudService) CreateContextData(ctx context.Context, params map[string]string) (interface{}, string, error) { + return createContextData(ctx, params, cliUserSelector{}) +} diff --git a/azure/context.go b/azure/context.go new file mode 100644 index 000000000..640b77b22 --- /dev/null +++ b/azure/context.go @@ -0,0 +1,175 @@ +/* + Copyright (c) 2020 Docker Inc. + + Permission is hereby granted, free of charge, to any person + obtaining a copy of this software and associated documentation + files (the "Software"), to deal in the Software without + restriction, including without limitation the rights to use, copy, + modify, merge, publish, distribute, sublicense, and/or sell copies + of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be + included in all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, + INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + HOLDERS BE LIABLE FOR ANY CLAIM, + DAMAGES OR OTHER LIABILITY, + WHETHER IN AN ACTION OF CONTRACT, + TORT OR OTHERWISE, + ARISING FROM, OUT OF OR IN CONNECTION WITH + THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +package azure + +import ( + "context" + "fmt" + + "github.com/Azure/azure-sdk-for-go/profiles/preview/preview/subscription/mgmt/subscription" + "github.com/Azure/azure-sdk-for-go/services/resources/mgmt/2018-05-01/resources" + + "os" + + "github.com/AlecAivazis/survey/v2" + + "github.com/docker/api/context/store" + + "github.com/google/uuid" + "github.com/pkg/errors" + "github.com/tj/survey/terminal" +) + +func createContextData(ctx context.Context, opts map[string]string, selector userSelector) (interface{}, string, error) { + var subscriptionID string + if opts["aciSubscriptionID"] != "" { + subscriptionID = opts["aciSubscriptionID"] + } else { + subs, err := getSubscriptionIDs(ctx) + if err != nil { + return nil, "", err + } + subscriptionID, err = chooseSub(subs, selector) + if err != nil { + return nil, "", err + } + } + + gc := getGroupsClient(subscriptionID) + var group resources.Group + var err error + + if opts["aciResourceGroup"] != "" { + group, err = gc.Get(ctx, opts["aciResourceGroup"]) + if err != nil { + return nil, "", errors.Wrapf(err, "Could not find resource group %q", opts["aciResourceGroup"]) + } + } else { + groupResponse, err := gc.List(ctx, "", nil) + if err != nil { + return nil, "", err + } + + groups := groupResponse.Values() + group, err = chooseGroup(ctx, gc, opts, groups, selector) + if err != nil { + return nil, "", err + } + } + + location := opts["aciLocation"] + if location == "" { + location = *group.Location + } + + description := fmt.Sprintf("%s@%s", *group.Name, location) + if opts["description"] != "" { + description = fmt.Sprintf("%s (%s)", opts["description"], description) + } + + return store.AciContext{ + SubscriptionID: subscriptionID, + Location: location, + ResourceGroup: *group.Name, + }, description, nil +} + +func createGroup(ctx context.Context, gc resources.GroupsClient, location string) (resources.Group, error) { + if location == "" { + location = "eastus" + } + gid := uuid.New().String() + g, err := gc.CreateOrUpdate(ctx, gid, resources.Group{ + Location: &location, + }) + if err != nil { + return resources.Group{}, err + } + + fmt.Printf("Resource group %q (%s) created\n", *g.Name, *g.Location) + + return g, nil +} + +func chooseGroup(ctx context.Context, gc resources.GroupsClient, opts map[string]string, groups []resources.Group, selector userSelector) (resources.Group, error) { + groupNames := []string{"create a new resource group"} + for _, g := range groups { + groupNames = append(groupNames, fmt.Sprintf("%s (%s)", *g.Name, *g.Location)) + } + + group, err := selector.userSelect("Choose a resource group", groupNames) + if err != nil { + if err == terminal.InterruptErr { + os.Exit(0) + } + + return resources.Group{}, err + } + + if group == 0 { + return createGroup(ctx, gc, opts["aciLocation"]) + } + + return groups[group-1], nil +} + +func chooseSub(subs []subscription.Model, selector userSelector) (string, error) { + if len(subs) == 1 { + sub := subs[0] + fmt.Println("Using only available subscription : " + *sub.DisplayName + "(" + *sub.SubscriptionID + ")") + return *sub.SubscriptionID, nil + } + var options []string + for _, sub := range subs { + options = append(options, *sub.DisplayName+"("+*sub.SubscriptionID+")") + } + selected, err := selector.userSelect("Select a subscription ID", options) + if err != nil { + if err == terminal.InterruptErr { + os.Exit(0) + } + return "", err + } + return *subs[selected].SubscriptionID, nil +} + +type userSelector interface { + userSelect(message string, options []string) (int, error) +} + +type cliUserSelector struct{} + +func (us cliUserSelector) userSelect(message string, options []string) (int, error) { + qs := &survey.Select{ + Message: message, + Options: options, + } + var selected int + err := survey.AskOne(qs, &selected, nil) + return selected, err +} diff --git a/cli/cmd/context/create.go b/cli/cmd/context/create.go index 25ffd56c2..c04ecf9e8 100644 --- a/cli/cmd/context/create.go +++ b/cli/cmd/context/create.go @@ -30,12 +30,17 @@ package context import ( "context" + "github.com/pkg/errors" + + "github.com/docker/api/client" + "github.com/spf13/cobra" "github.com/docker/api/context/store" ) -type createOpts struct { +// AciCreateOpts Options for ACI context create +type AciCreateOpts struct { description string aciLocation string aciSubscriptionID string @@ -43,7 +48,7 @@ type createOpts struct { } func createCommand() *cobra.Command { - var opts createOpts + var opts AciCreateOpts cmd := &cobra.Command{ Use: "create CONTEXT BACKEND [OPTIONS]", Short: "Create a context", @@ -61,13 +66,36 @@ func createCommand() *cobra.Command { return cmd } -func runCreate(ctx context.Context, opts createOpts, name string, contextType string) error { +func runCreate(ctx context.Context, opts AciCreateOpts, name string, contextType string) error { + var description string + var contextData interface{} + switch contextType { case "aci": - return createACIContext(ctx, name, opts) - default: - s := store.ContextStore(ctx) - // TODO: we need to implement different contexts for known backends - return s.Create(name, contextType, opts.description, store.ExampleContext{}) + cs, err := client.GetCloudService(ctx, "aci") + if err != nil { + return errors.Wrap(err, "cannot connect to backend") + } + params := map[string]string{ + "aciSubscriptionId": opts.aciSubscriptionID, + "aciResourceGroup": opts.aciResourceGroup, + "aciLocation": opts.aciLocation, + "description": opts.description, + } + contextData, description, err = cs.CreateContextData(ctx, params) + if err != nil { + return errors.Wrap(err, "cannot create context") + } + default: // TODO: we need to implement different contexts for known backends + description = opts.description + contextData = store.ExampleContext{} } + + s := store.ContextStore(ctx) + return s.Create( + name, + contextType, + description, + contextData, + ) } diff --git a/cli/cmd/context/createaci.go b/cli/cmd/context/createaci.go deleted file mode 100644 index ceb23f3c6..000000000 --- a/cli/cmd/context/createaci.go +++ /dev/null @@ -1,55 +0,0 @@ -/* - Copyright (c) 2020 Docker Inc. - - Permission is hereby granted, free of charge, to any person - obtaining a copy of this software and associated documentation - files (the "Software"), to deal in the Software without - restriction, including without limitation the rights to use, copy, - modify, merge, publish, distribute, sublicense, and/or sell copies - of the Software, and to permit persons to whom the Software is - furnished to do so, subject to the following conditions: - - The above copyright notice and this permission notice shall be - included in all copies or substantial portions of the Software. - - THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, - EXPRESS OR IMPLIED, - INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. - IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT - HOLDERS BE LIABLE FOR ANY CLAIM, - DAMAGES OR OTHER LIABILITY, - WHETHER IN AN ACTION OF CONTRACT, - TORT OR OTHERWISE, - ARISING FROM, OUT OF OR IN CONNECTION WITH - THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -*/ - -package context - -import ( - "context" - "fmt" - - "github.com/docker/api/context/store" -) - -func createACIContext(ctx context.Context, name string, opts createOpts) error { - s := store.ContextStore(ctx) - - description := fmt.Sprintf("%s@%s", opts.aciResourceGroup, opts.aciLocation) - if opts.description != "" { - description = fmt.Sprintf("%s (%s)", opts.description, description) - } - - return s.Create( - name, - store.AciContextType, - description, - store.AciContext{ - SubscriptionID: opts.aciSubscriptionID, - Location: opts.aciLocation, - ResourceGroup: opts.aciResourceGroup, - }, - ) -} diff --git a/context/cloud/api.go b/context/cloud/api.go index a00d3db7a..cae625d2f 100644 --- a/context/cloud/api.go +++ b/context/cloud/api.go @@ -10,6 +10,8 @@ import ( type Service interface { // Login login to cloud provider Login(ctx context.Context, params map[string]string) error + // Login login to cloud provider + CreateContextData(ctx context.Context, params map[string]string) (contextData interface{}, description string, err error) } // NotImplementedCloudService to use for backend that don't provide cloud services @@ -23,3 +25,7 @@ type notImplementedCloudService struct { func (cs notImplementedCloudService) Login(ctx context.Context, params map[string]string) error { return errdefs.ErrNotImplemented } + +func (cs notImplementedCloudService) CreateContextData(ctx context.Context, params map[string]string) (interface{}, string, error) { + return nil, "", errdefs.ErrNotImplemented +} diff --git a/go.mod b/go.mod index 3f7c826b9..6fe82548c 100644 --- a/go.mod +++ b/go.mod @@ -3,6 +3,7 @@ module github.com/docker/api go 1.14 require ( + github.com/AlecAivazis/survey/v2 v2.0.7 github.com/Azure/azure-sdk-for-go v42.0.0+incompatible github.com/Azure/azure-storage-file-go v0.7.0 github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78 // indirect @@ -24,6 +25,7 @@ require ( github.com/gobwas/pool v0.2.0 // indirect github.com/gobwas/ws v1.0.3 github.com/golang/protobuf v1.4.1 + github.com/google/uuid v1.1.1 github.com/gorilla/mux v1.7.4 // indirect github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 github.com/hashicorp/go-multierror v1.1.0 @@ -38,6 +40,7 @@ require ( github.com/spf13/cobra v1.0.0 github.com/spf13/pflag v1.0.5 github.com/stretchr/testify v1.5.1 + github.com/tj/survey v2.0.6+incompatible golang.org/x/net v0.0.0-20200425230154-ff2c4b7c35a0 golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be golang.org/x/sys v0.0.0-20200519105757-fe76b779f299 // indirect diff --git a/go.sum b/go.sum index ea77a4a4b..1465ba723 100644 --- a/go.sum +++ b/go.sum @@ -1,4 +1,6 @@ cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= +github.com/AlecAivazis/survey/v2 v2.0.7 h1:+f825XHLse/hWd2tE/V5df04WFGimk34Eyg/z35w/rc= +github.com/AlecAivazis/survey/v2 v2.0.7/go.mod h1:mlizQTaPjnR4jcpwRSaSlkbsRfYFEyKgLQvYTzxxiHA= github.com/Azure/azure-pipeline-go v0.2.1 h1:OLBdZJ3yvOn2MezlWvbrBMTEUQC72zAftRZOMdj5HYo= github.com/Azure/azure-pipeline-go v0.2.1/go.mod h1:UGSo8XybXnIGZ3epmeBw7Jdz+HiUVpqIlpz/HKHylF4= github.com/Azure/azure-sdk-for-go v42.0.0+incompatible h1:yz6sFf5bHZ+gEOQVuK5JhPqTTAmv+OvSLSaqgzqaCwY= @@ -34,6 +36,8 @@ github.com/Azure/go-autorest/tracing v0.5.0/go.mod h1:r/s2XiOKccPW3HrqB+W0TQzfbt github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/Microsoft/go-winio v0.4.14 h1:+hMXMk01us9KgxGb7ftKQt2Xpf5hH/yky+TDA+qxleU= github.com/Microsoft/go-winio v0.4.14/go.mod h1:qXqCSQ3Xa7+6tgxaGTIe4Kpcdsi+P8jBhyzoq1bpyYA= +github.com/Netflix/go-expect v0.0.0-20180615182759-c93bf25de8e8 h1:xzYJEypr/85nBpB11F9br+3HUrpgb+fcm5iADzXXYEw= +github.com/Netflix/go-expect v0.0.0-20180615182759-c93bf25de8e8/go.mod h1:oX5x61PbNXchhh0oikYAH+4Pcfw5LKv21+Jnpr6r6Pc= github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751 h1:JYp7IbQjafoB+tBA3gMyHYHrpOtNuDiK/uB5uXxq5wM= @@ -126,6 +130,8 @@ github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMyw github.com/google/go-cmp v0.4.0 h1:xsAVV57WRhGj6kEIi8ReJzQlHHqcBYCElAvkovg3B/4= github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/google/uuid v1.1.1 h1:Gkbcsh/GbpXz7lPftLA3P6TYMwjCLYm83jiFQZF/3gY= +github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/gorilla/mux v1.7.4 h1:VuZ8uybHlWmqV03+zRzdwKL4tUnIp1MAQtp1mIFE1bc= github.com/gorilla/mux v1.7.4/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So= github.com/gorilla/websocket v1.4.0/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= @@ -138,6 +144,8 @@ github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brv github.com/hashicorp/go-multierror v1.1.0 h1:B9UzwGQJehnUY1yNrnwREHc3fGbC2xefo8g4TbElacI= github.com/hashicorp/go-multierror v1.1.0/go.mod h1:spPvp8C1qA32ftKqdAHm4hHTbPw+vmowP0z+KUhOZdA= github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= +github.com/hinshun/vt10x v0.0.0-20180616224451-1954e6464174 h1:WlZsjVhE8Af9IcZDGgJGQpNflI3+MJSBhsgT5PCtzBQ= +github.com/hinshun/vt10x v0.0.0-20180616224451-1954e6464174/go.mod h1:DqJ97dSdRW1W22yXSB90986pcOyQ7r45iio1KN2ez1A= github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/imdario/mergo v0.3.8 h1:CGgOkSJeqMRmt0D9XLWExdT4m4F1vd3FV3VPt+0VxkQ= @@ -148,6 +156,8 @@ github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22 github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= github.com/json-iterator/go v1.1.9/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 h1:Z9n2FFNUXsshfwJMBgNA0RU6/i7WVaAegv3PtuIHPMs= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51/go.mod h1:CzGEWj7cYgsdH8dAjBGEr58BoE7ScuLd+fwFZ44+/x8= github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/konsorten/go-windows-terminal-sequences v1.0.1 h1:mweAR1A6xJ3oS2pRaGiHgQ4OO8tzTaLawm8vnODuwDk= @@ -158,16 +168,24 @@ github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFB github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/pty v1.1.4/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/pty v1.1.5 h1:hyz3dwM5QLc1Rfoz4FuWJQG5BN7tc6K1MndAUnGpQr4= github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA= github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/mattn/go-colorable v0.1.2 h1:/bC9yWikZXAL9uJdulbSfyVNIR3n3trXl+v8+1sx8mU= +github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= github.com/mattn/go-ieproxy v0.0.0-20190610004146-91bb50d98149 h1:HfxbT6/JcvIljmERptWhwa8XzP7H3T+Z2N26gTsaDaA= github.com/mattn/go-ieproxy v0.0.0-20190610004146-91bb50d98149/go.mod h1:31jz6HNzdxOmlERGGEc4v/dMssOfmp2p5bT/okiKFFc= +github.com/mattn/go-isatty v0.0.8 h1:HLtExJ+uU2HOZ+wI0Tt5DtUDrx8yhUqDcp7fYERX4CE= +github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-shellwords v1.0.10 h1:Y7Xqm8piKOO3v10Thp7Z36h4FYFjt5xB//6XvOrs2Gw= github.com/mattn/go-shellwords v1.0.10/go.mod h1:EZzvwXDESEeg03EKmM+RmDnNOPKG4lLtQsUlTZDWQ8Y= github.com/matttproud/golang_protobuf_extensions v1.0.1 h1:4hp9jkHxhMHkqkrB3Ix0jegS5sx/RkqARlsWZ6pIwiU= github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0= +github.com/mgutz/ansi v0.0.0-20170206155736-9520e82c474b h1:j7+1HpAFS1zy5+Q4qx1fWh90gTKwiN4QCGoY9TWyyO4= +github.com/mgutz/ansi v0.0.0-20170206155736-9520e82c474b/go.mod h1:01TrycV0kFyexm33Z7vhZRXopbI8J3TDReVlkTgMUxE= github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= @@ -245,11 +263,14 @@ github.com/spf13/viper v1.4.0/go.mod h1:PTJ7Z/lr49W6bUbkmS1V3by4uWynFiR9p7+dSq/y github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1 h1:2vfRuCMp5sSVIDSqO8oNnWJq7mPa6KVP3iPIwFBuy8A= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.2.1/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/tj/survey v2.0.6+incompatible h1:tVgc1+kmYX9R0CEoHaTczapjdc4GaJla0VAB7O+w1So= +github.com/tj/survey v2.0.6+incompatible/go.mod h1:vLPzQYAOKWgXqr5jV9luQXJuoXKHOg0ltn5FEw1Nz0c= github.com/tmc/grpc-websocket-proxy v0.0.0-20190109142713-0ad062ec5ee5/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= github.com/ugorji/go v1.1.4/go.mod h1:uQMGLiO92mf5W77hV/PUCpI3pbzQx3CRekS0kk+RGrc= github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f h1:J9EGpcZtP0E/raorCMxlFGSTBrsSlaDGf3jU/qvAE2c= @@ -266,6 +287,7 @@ go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/ go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20190530122614-20be4c3c3ed5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20191206172530-e9b2fee46413 h1:ULYEB3JvPRE/IfO+9uO7vKV/xzVTO7XPAwm8xbf4w2g= golang.org/x/crypto v0.0.0-20191206172530-e9b2fee46413/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -298,9 +320,11 @@ golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5h golang.org/x/sys v0.0.0-20181107165924-66b7b1311ac8/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190530182044-ad28b68e88f1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190626221950-04f50cda93cb/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200122134326-e047566fdf82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= diff --git a/tests/aci-e2e/e2e-aci_test.go b/tests/aci-e2e/e2e-aci_test.go index 8e217ab7e..c0678e28e 100644 --- a/tests/aci-e2e/e2e-aci_test.go +++ b/tests/aci-e2e/e2e-aci_test.go @@ -15,7 +15,6 @@ import ( log "github.com/sirupsen/logrus" "github.com/stretchr/testify/suite" - "github.com/docker/api/azure" "github.com/docker/api/context/store" "github.com/docker/api/tests/aci-e2e/storage" . "github.com/docker/api/tests/framework" @@ -64,9 +63,9 @@ func (s *E2eACISuite) TestContextDefault() { func (s *E2eACISuite) TestACIBackend() { It("creates a new aci context for tests", func() { setupTestResourceGroup(resourceGroupName) - var err error - subscriptionID, err = azure.GetSubscriptionID(context.TODO()) + models, err := azure.getSubscriptionIDs(context.TODO()) Expect(err).To(BeNil()) + subscriptionID = *models[0].SubscriptionID s.NewDockerCommand("context", "create", contextName, "aci", "--aci-subscription-id", subscriptionID, "--aci-resource-group", resourceGroupName, "--aci-location", location).ExecOrDie() // Expect(output).To(ContainSubstring("ACI context acitest created")) @@ -228,9 +227,9 @@ func TestE2eACI(t *testing.T) { func setupTestResourceGroup(groupName string) { log.Println("Creating resource group " + resourceGroupName) ctx := context.TODO() - subscriptionID, err := azure.GetSubscriptionID(ctx) + models, err := azure.getSubscriptionIDs(ctx) Expect(err).To(BeNil()) - gc := azure.GetGroupsClient(subscriptionID) + gc := azure.getGroupsClient(*models[0].SubscriptionID) _, err = gc.CreateOrUpdate(ctx, groupName, resources.Group{ Location: to.StringPtr(location), }) @@ -240,9 +239,9 @@ func setupTestResourceGroup(groupName string) { func deleteResourceGroup(groupName string) { log.Println("Deleting resource group " + resourceGroupName) ctx := context.TODO() - subscriptionID, err := azure.GetSubscriptionID(ctx) + models, err := azure.getSubscriptionIDs(ctx) Expect(err).To(BeNil()) - gc := azure.GetGroupsClient(subscriptionID) + gc := azure.getGroupsClient(*models[0].SubscriptionID) _, err = gc.Delete(ctx, groupName) Expect(err).To(BeNil()) }