github.com/axw/juju@v0.0.0-20161005053422-4bd6544d08d4/cmd/juju/user/login_test.go (about) 1 // Copyright 2014 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package user_test 5 6 import ( 7 "strings" 8 9 "github.com/juju/cmd" 10 jc "github.com/juju/testing/checkers" 11 gc "gopkg.in/check.v1" 12 "gopkg.in/juju/names.v2" 13 14 "github.com/juju/juju/apiserver/params" 15 "github.com/juju/juju/cmd/juju/user" 16 "github.com/juju/juju/juju" 17 "github.com/juju/juju/jujuclient" 18 coretesting "github.com/juju/juju/testing" 19 ) 20 21 type LoginCommandSuite struct { 22 BaseSuite 23 mockAPI *mockLoginAPI 24 loginErr error 25 } 26 27 var _ = gc.Suite(&LoginCommandSuite{}) 28 29 func (s *LoginCommandSuite) SetUpTest(c *gc.C) { 30 s.BaseSuite.SetUpTest(c) 31 s.mockAPI = &mockLoginAPI{} 32 s.loginErr = nil 33 } 34 35 func (s *LoginCommandSuite) run(c *gc.C, stdin string, args ...string) (*cmd.Context, juju.NewAPIConnectionParams, error) { 36 var argsOut juju.NewAPIConnectionParams 37 cmd, _ := user.NewLoginCommandForTest(func(args juju.NewAPIConnectionParams) (user.LoginAPI, user.ConnectionAPI, error) { 38 argsOut = args 39 // The account details are modified in place, so take a copy. 40 accountDetails := *argsOut.AccountDetails 41 argsOut.AccountDetails = &accountDetails 42 if s.loginErr != nil { 43 err := s.loginErr 44 s.loginErr = nil 45 return nil, nil, err 46 } 47 return s.mockAPI, s.mockAPI, nil 48 }, s.store) 49 ctx := coretesting.Context(c) 50 if stdin == "" { 51 stdin = "sekrit\n" 52 } 53 ctx.Stdin = strings.NewReader(stdin) 54 err := coretesting.InitCommand(cmd, args) 55 if err != nil { 56 return nil, argsOut, err 57 } 58 err = cmd.Run(ctx) 59 return ctx, argsOut, err 60 } 61 62 func (s *LoginCommandSuite) TestInit(c *gc.C) { 63 for i, test := range []struct { 64 args []string 65 user string 66 errorString string 67 }{ 68 { 69 // no args is fine 70 }, { 71 args: []string{"foobar"}, 72 user: "foobar", 73 }, { 74 args: []string{"--foobar"}, 75 errorString: "flag provided but not defined: --foobar", 76 }, { 77 args: []string{"foobar", "extra"}, 78 errorString: `unrecognized args: \["extra"\]`, 79 }, 80 } { 81 c.Logf("test %d", i) 82 wrappedCommand, command := user.NewLoginCommandForTest(nil, s.store) 83 err := coretesting.InitCommand(wrappedCommand, test.args) 84 if test.errorString == "" { 85 c.Check(command.User, gc.Equals, test.user) 86 } else { 87 c.Check(err, gc.ErrorMatches, test.errorString) 88 } 89 } 90 } 91 92 func (s *LoginCommandSuite) TestLogin(c *gc.C) { 93 context, args, err := s.run(c, "current-user\nsekrit\n") 94 c.Assert(err, jc.ErrorIsNil) 95 c.Assert(coretesting.Stdout(context), gc.Equals, "") 96 c.Assert(coretesting.Stderr(context), gc.Equals, ` 97 username: You are now logged in to "testing" as "current-user@local". 98 `[1:], 99 ) 100 s.assertStorePassword(c, "current-user@local", "", "superuser") 101 c.Assert(args.AccountDetails, jc.DeepEquals, &jujuclient.AccountDetails{ 102 User: "current-user@local", 103 }) 104 } 105 106 func (s *LoginCommandSuite) TestLoginNewUser(c *gc.C) { 107 err := s.store.RemoveAccount("testing") 108 c.Assert(err, jc.ErrorIsNil) 109 context, args, err := s.run(c, "", "new-user") 110 c.Assert(err, jc.ErrorIsNil) 111 c.Assert(coretesting.Stdout(context), gc.Equals, "") 112 c.Assert(coretesting.Stderr(context), gc.Equals, ` 113 You are now logged in to "testing" as "new-user@local". 114 `[1:], 115 ) 116 s.assertStorePassword(c, "new-user@local", "", "superuser") 117 c.Assert(args.AccountDetails, jc.DeepEquals, &jujuclient.AccountDetails{ 118 User: "new-user@local", 119 }) 120 } 121 122 func (s *LoginCommandSuite) TestLoginAlreadyLoggedInSameUser(c *gc.C) { 123 _, _, err := s.run(c, "", "current-user") 124 c.Assert(err, jc.ErrorIsNil) 125 } 126 127 func (s *LoginCommandSuite) TestLoginAlreadyLoggedInDifferentUser(c *gc.C) { 128 _, _, err := s.run(c, "", "other-user") 129 c.Assert(err, gc.ErrorMatches, `already logged in 130 131 Run "juju logout" first before attempting to log in as a different user. 132 `) 133 } 134 135 func (s *LoginCommandSuite) TestLoginWithMacaroons(c *gc.C) { 136 err := s.store.RemoveAccount("testing") 137 c.Assert(err, jc.ErrorIsNil) 138 context, args, err := s.run(c, "") 139 c.Assert(err, jc.ErrorIsNil) 140 c.Assert(coretesting.Stdout(context), gc.Equals, "") 141 c.Assert(coretesting.Stderr(context), gc.Equals, ` 142 You are now logged in to "testing" as "user@external". 143 `[1:], 144 ) 145 c.Assert(args.AccountDetails, jc.DeepEquals, &jujuclient.AccountDetails{}) 146 } 147 148 func (s *LoginCommandSuite) TestLoginWithMacaroonsNotSupported(c *gc.C) { 149 err := s.store.RemoveAccount("testing") 150 c.Assert(err, jc.ErrorIsNil) 151 s.loginErr = ¶ms.Error{Code: params.CodeNoCreds, Message: "barf"} 152 context, _, err := s.run(c, "new-user\nsekrit\n") 153 c.Assert(err, jc.ErrorIsNil) 154 c.Assert(coretesting.Stdout(context), gc.Equals, "") 155 c.Assert(coretesting.Stderr(context), gc.Equals, ` 156 username: You are now logged in to "testing" as "new-user@local". 157 `[1:], 158 ) 159 } 160 161 type mockLoginAPI struct{} 162 163 func (*mockLoginAPI) Close() error { 164 return nil 165 } 166 167 func (*mockLoginAPI) AuthTag() names.Tag { 168 return names.NewUserTag("user@external") 169 } 170 171 func (*mockLoginAPI) ControllerAccess() string { 172 return "superuser" 173 }