@@ -39,7 +39,7 @@ func NewCmdAuth(options []crane.Option, argv ...string) *cobra.Command {
3939 Args : cobra .NoArgs ,
4040 RunE : func (cmd * cobra.Command , _ []string ) error { return cmd .Usage () },
4141 }
42- cmd .AddCommand (NewCmdAuthGet (options , argv ... ), NewCmdAuthLogin (argv ... ))
42+ cmd .AddCommand (NewCmdAuthGet (options , argv ... ), NewCmdAuthLogin (argv ... ), NewCmdAuthLogout ( argv ... ) )
4343 return cmd
4444}
4545
@@ -203,3 +203,42 @@ func login(opts loginOptions) error {
203203 log .Printf ("logged in via %s" , cf .Filename )
204204 return nil
205205}
206+
207+ // NewCmdAuthLogout creates a new `crane auth logout` command.
208+ func NewCmdAuthLogout (argv ... string ) * cobra.Command {
209+ eg := fmt .Sprintf (` # Log out of reg.example.com
210+ %s logout reg.example.com` , strings .Join (argv , " " ))
211+
212+ cmd := & cobra.Command {
213+ Use : "logout [SERVER]" ,
214+ Short : "Log out of a registry" ,
215+ Example : eg ,
216+ Args : cobra .ExactArgs (1 ),
217+ RunE : func (cmd * cobra.Command , args []string ) error {
218+ reg , err := name .NewRegistry (args [0 ])
219+ if err != nil {
220+ return err
221+ }
222+ serverAddress := reg .Name ()
223+
224+ cf , err := config .Load (os .Getenv ("DOCKER_CONFIG" ))
225+ if err != nil {
226+ return err
227+ }
228+ creds := cf .GetCredentialsStore (serverAddress )
229+ if serverAddress == name .DefaultRegistry {
230+ serverAddress = authn .DefaultAuthKey
231+ }
232+ if err := creds .Erase (serverAddress ); err != nil {
233+ return err
234+ }
235+
236+ if err := cf .Save (); err != nil {
237+ return err
238+ }
239+ log .Printf ("logged out via %s" , cf .Filename )
240+ return nil
241+ },
242+ }
243+ return cmd
244+ }
0 commit comments