Skip to content

Commit

Permalink
CLOUDP-66292: mongocli config delete (#226)
Browse files Browse the repository at this point in the history
  • Loading branch information
robcarlan-mlab authored Jul 1, 2020
1 parent 5d30aff commit a19f7c7
Show file tree
Hide file tree
Showing 6 changed files with 111 additions and 10 deletions.
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ require (
github.com/mitchellh/go-homedir v1.1.0
github.com/mitchellh/mapstructure v1.3.1 // indirect
github.com/mongodb/go-client-mongodb-atlas v0.3.0
github.com/pelletier/go-toml v1.8.0 // indirect
github.com/pelletier/go-toml v1.8.0
github.com/spf13/afero v1.2.2
github.com/spf13/cast v1.3.1 // indirect
github.com/spf13/cobra v1.0.0
Expand Down
1 change: 1 addition & 0 deletions internal/cli/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,7 @@ func Builder() *cobra.Command {
cmd.AddCommand(SetBuilder())
cmd.AddCommand(ListBuilder())
cmd.AddCommand(DescribeBuilder())
cmd.AddCommand(DeleteBuilder())

return cmd
}
61 changes: 61 additions & 0 deletions internal/cli/config/delete.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
// Copyright 2020 MongoDB Inc
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package config

import (
"fmt"

"github.com/mongodb/mongocli/internal/cli"

"github.com/mongodb/mongocli/internal/config"
"github.com/mongodb/mongocli/internal/description"
"github.com/spf13/cobra"
)

type DeleteOpts struct {
*cli.DeleteOpts
}

func (opts *DeleteOpts) Run() error {
return config.Delete()
}

func DeleteBuilder() *cobra.Command {
opts := &DeleteOpts{
DeleteOpts: cli.NewDeleteOpts("Profile '%s' deleted\n", "Profile not deleted"),
}
cmd := &cobra.Command{
Use: "delete <name>",
Aliases: []string{"rm"},
Short: description.ConfigDeleteDescription,
Args: cobra.ExactArgs(1),
PreRunE: func(cmd *cobra.Command, args []string) error {
opts.Entry = args[0]

config.SetName(&opts.Entry)
profile := config.GetConfigDescription()
if len(profile) == 0 {
return fmt.Errorf("profile %v does not exist", opts.Entry)
}

return opts.Prompt()
},
RunE: func(cmd *cobra.Command, args []string) error {
return opts.Run()
},
}

return cmd
}
3 changes: 2 additions & 1 deletion internal/cli/config/describe.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,8 @@ type ListOpts struct {
}

func (opts *ListOpts) Run() error {
configDescription := config.GetConfigDescription(opts.name)
config.SetName(&opts.name)
configDescription := config.GetConfigDescription()

if len(configDescription) == 0 {
return fmt.Errorf("no profile with name '%s'", opts.name)
Expand Down
53 changes: 45 additions & 8 deletions internal/config/profile.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,10 @@ import (
"errors"
"fmt"
"log"
"os"
"sort"

"github.com/pelletier/go-toml"
"github.com/spf13/afero"
"github.com/spf13/viper"
)
Expand Down Expand Up @@ -226,20 +228,55 @@ func (p *profile) SetOrgID(v string) {
}

// GetConfigDescription returns a map describing the configuration
func GetConfigDescription(name string) map[string]string {
redactedValue := "redacted"
func GetConfigDescription() map[string]string { return p.GetConfigDescription() }
func (p *profile) GetConfigDescription() map[string]string {
settings := viper.GetStringMapString(p.Name())
newSettings := make(map[string]string)

for k, v := range settings {
if k == privateAPIKey || k == publicAPIKey {
newSettings[k] = "redacted"
} else {
newSettings[k] = v
}
}

return newSettings
}

// Delete deletes an existing configuration. The profiles are reloaded afterwards, as
// this edits the file directly.
func Delete() error { return p.Delete() }
func (p *profile) Delete() error {
// Configuration needs to be deleted from toml, as viper doesn't support this yet.
// FIXME :: change when https://github.com/spf13/viper/pull/519 is merged.
configurationAfterDelete := viper.AllSettings()

t, err := toml.TreeFromMap(configurationAfterDelete)
if err != nil {
return err
}

// Delete from the toml manually
err = t.Delete(p.Name())
if err != nil {
return err
}

m := viper.GetStringMapString(name)
s := t.String()

if _, ok := m[privateAPIKey]; ok {
m[privateAPIKey] = redactedValue
flags := os.O_CREATE | os.O_TRUNC | os.O_WRONLY
f, err := p.fs.OpenFile(fmt.Sprintf("%s/%s.toml", p.configDir, ToolName), flags, 0600)
if err != nil {
return err
}

if _, ok := m[publicAPIKey]; ok {
m[publicAPIKey] = redactedValue
if _, err := f.WriteString(s); err != nil {
return err
}

return m
// Force reload, so that viper has the new configuration
return p.Load(true)
}

// Load loads the configuration from disk
Expand Down
1 change: 1 addition & 0 deletions internal/description/description.go
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ const (
StartUpCluster = "Start up a cluster."
ConfigDescription = "Configure a profile to store access settings for your MongoDB deployment."
ConfigSetDescription = "Configure specific properties of a profile."
ConfigDeleteDescription = "Delete a profile."
ConfigList = "List available profiles."
ConfigDescribe = "Return a specific profile"
IAM = "Organization and projects operations."
Expand Down

0 comments on commit a19f7c7

Please sign in to comment.