Skip to content

Commit

Permalink
Merge pull request #71 from go-kivik/config
Browse files Browse the repository at this point in the history
Allow 'get config <url>'
  • Loading branch information
flimzy committed Apr 24, 2021
2 parents fdfe734 + 905a7ce commit b882638
Show file tree
Hide file tree
Showing 6 changed files with 93 additions and 3 deletions.
7 changes: 7 additions & 0 deletions cmd/kouchctl/cmd/get.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,13 @@ func getCmd(r *root) *cobra.Command {
}

func (g *get) RunE(cmd *cobra.Command, args []string) error {
dsn, err := g.conf.URL()
if err != nil {
return err
}
if _, _, ok := configFromDSN(dsn); ok {
return g.cf.RunE(cmd, args)
}
if g.conf.HasAttachment() {
return g.att.RunE(cmd, args)
}
Expand Down
21 changes: 19 additions & 2 deletions cmd/kouchctl/cmd/get_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
package cmd

import (
"net/url"
"strings"

"github.com/spf13/cobra"
Expand All @@ -37,23 +38,39 @@ func getConfigCmd(r *root) *cobra.Command {

pf := cmd.PersistentFlags()
pf.StringVarP(&c.node, "node", "n", "_local", "Specify the node name to query")
pf.StringVarP(&c.key, "key", "k", "", "Fetch only the specified config section, and optionally key, separated by a period")
pf.StringVarP(&c.key, "key", "k", "", "Fetch only the specified config section, and optionally key, separated by a slash")

return cmd
}

func configFromDSN(dsn *url.URL) (node, key string, ok bool) {
parts := strings.Split(dsn.Path, "/")
if len(parts) < 4 || parts[1] != "_node" || parts[3] != "_config" {
return "", "", false
}
return parts[2], strings.Join(parts[4:], "/"), true
}

func (c *getConfig) RunE(cmd *cobra.Command, _ []string) error {
client, err := c.client()
if err != nil {
return err
}
dsn, err := c.conf.URL()
if err != nil {
return err
}
c.conf.Finalize()
if node, key, ok := configFromDSN(dsn); ok {
c.node = node
c.key = key
}

return c.retry(func() error {
var conf interface{}
var err error
if c.key != "" {
if parts := strings.SplitN(c.key, ".", 2); len(parts) > 1 {
if parts := strings.SplitN(c.key, "/", 2); len(parts) > 1 {
conf, err = client.ConfigValue(cmd.Context(), c.node, parts[0], parts[1])
} else {
conf, err = client.ConfigSection(cmd.Context(), c.node, c.key)
Expand Down
41 changes: 40 additions & 1 deletion cmd/kouchctl/cmd/get_config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ package cmd
import (
"io/ioutil"
"net/http"
"net/url"
"strings"
"testing"

Expand Down Expand Up @@ -93,11 +94,49 @@ func Test_get_config_RunE(t *testing.T) {
})

return cmdTest{
args: []string{"get", "config", s.URL, "--key", "chttpd.backlog"},
args: []string{"get", "config", s.URL, "--key", "chttpd/backlog"},
}
})

tests.Run(t, func(t *testing.T, tt cmdTest) {
tt.Test(t)
})
}

func Test_configFromDSN(t *testing.T) {
type tt struct {
dsn string
node, key string
ok bool
}

tests := testy.NewTable()
tests.Add("no path", tt{
dsn: "http://foo.com/",
})
tests.Add("short path", tt{
dsn: "http://foo.com/_node/foo",
})
tests.Add("config", tt{
dsn: "http://foo.com/_node/foo/_config",
node: "foo",
ok: true,
})
tests.Add("config key", tt{
dsn: "http://foo.com/_node/foo/_config/foo/bar",
node: "foo",
key: "foo/bar",
ok: true,
})

tests.Run(t, func(t *testing.T, tt tt) {
url, err := url.Parse(tt.dsn)
if err != nil {
t.Fatal(err)
}
node, key, ok := configFromDSN(url)
if node != tt.node || key != tt.key || ok != tt.ok {
t.Errorf("Unexpected result: node:%s, key:%s, ok:%T", node, key, ok)
}
})
}
18 changes: 18 additions & 0 deletions cmd/kouchctl/cmd/get_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,24 @@ func Test_get_RunE(t *testing.T) {
args: []string{"get", s.URL + "/_all_dbs"},
}
})
tests.Add("auto config key", func(t *testing.T) interface{} {
s := testy.ServeResponseValidator(t, &http.Response{
StatusCode: http.StatusOK,
Header: http.Header{
"Content-Type": []string{"application/json"},
"ETag": []string{"1-xxx"},
},
Body: ioutil.NopCloser(strings.NewReader(`"512"`)),
}, func(t *testing.T, req *http.Request) {
if req.URL.Path != "/_node/_local/_config/chttpd/backlog" {
t.Errorf("unexpected path: %s", req.URL.Path)
}
})

return cmdTest{
args: []string{"get", s.URL + "/_node/_local/_config/chttpd/backlog"},
}
})

tests.Run(t, func(t *testing.T, tt cmdTest) {
tt.Test(t)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"512"
8 changes: 8 additions & 0 deletions cmd/kouchctl/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -223,6 +223,14 @@ func (c *Config) ClientInfo() (string, string, error) {
return scheme, dsn, nil
}

func (c *Config) URL() (*url.URL, error) {
cx, err := c.currentCx()
if err != nil {
return nil, err
}
return cx.dsn(), nil
}

func (c *Config) DSN() (string, error) {
cx, err := c.currentCx()
if err != nil {
Expand Down

0 comments on commit b882638

Please sign in to comment.