Skip to content

Commit c45d9e9

Browse files
author
Jake Sanders
committed
Implement client.List, change list API
[]string, []string -> map[string]string because the other APIs assume a 1:1 correspondence Signed-off-by: Jake Sanders <[email protected]>
1 parent 80833ad commit c45d9e9

File tree

11 files changed

+71
-75
lines changed

11 files changed

+71
-75
lines changed

client/client.go

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -68,14 +68,20 @@ func Erase(program ProgramFunc, serverURL string) error {
6868
return nil
6969
}
7070

71-
// List executes a program to remove the server credentials from the native store.
72-
func List(program ProgramFunc) error {
71+
// List executes a program to list server credentials in the native store.
72+
func List(program ProgramFunc) (map[string]string, error) {
7373
cmd := program("list")
74-
cmd.Input(strings.NewReader("garbage"))
74+
cmd.Input(strings.NewReader("unused"))
7575
out, err := cmd.Output()
7676
if err != nil {
7777
t := strings.TrimSpace(string(out))
78-
return fmt.Errorf("error listing credentials - err: %v, out: `%s`", err, t)
78+
return nil, fmt.Errorf("error listing credentials - err: %v, out: `%s`", err, t)
7979
}
80-
return nil
80+
81+
var resp map[string]string
82+
if err = json.NewDecoder(bytes.NewReader(out)).Decode(&resp); err != nil {
83+
return nil, err
84+
}
85+
86+
return resp, nil
8187
}

client/client_test.go

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313

1414
const (
1515
validServerAddress = "https://index.docker.io/v1"
16+
validUsername = "linus"
1617
validServerAddress2 = "https://example.com:5002"
1718
invalidServerAddress = "https://foobar.example.com"
1819
missingCredsAddress = "https://missing.docker.io/v1"
@@ -71,7 +72,7 @@ func (m *mockProgram) Output() ([]byte, error) {
7172
return []byte("error storing credentials"), errProgramExited
7273
}
7374
case "list":
74-
return []byte(`{"Path":"e237574ae22fd53ddb9490dc1f72139946fd5372d42ba54d1eeb3ae5068fd22b","Username":"http://example.com/collections\u003cnotary_key\u003eSnapshot"}`), nil
75+
return []byte(fmt.Sprintf(`{"%s": "%s"}`, validServerAddress, validUsername)), nil
7576

7677
}
7778

@@ -195,7 +196,12 @@ func TestErase(t *testing.T) {
195196
}
196197

197198
func TestList(t *testing.T) {
198-
if err := List(mockProgramFn); err != nil {
199+
auths, err := List(mockProgramFn)
200+
if err != nil {
199201
t.Fatal(err)
200202
}
203+
204+
if username, exists := auths[validServerAddress]; !exists || username != validUsername {
205+
t.Fatalf("auths[%s] returned %s, %t; expected %s, %t", validServerAddress, username, exists, validUsername, true)
206+
}
201207
}

credentials/credentials.go

Lines changed: 2 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,6 @@ type Credentials struct {
1717
Secret string
1818
}
1919

20-
type KeyData struct {
21-
Path string
22-
Username string
23-
}
24-
2520
// Serve initializes the credentials helper and parses the action argument.
2621
// This function is designed to be called from a command line interface.
2722
// It uses os.Args[1] as the key for the action.
@@ -138,22 +133,9 @@ func Erase(helper Helper, reader io.Reader) error {
138133
//List returns all the serverURLs of keys in
139134
//the OS store as a list of strings
140135
func List(helper Helper, writer io.Writer) error {
141-
paths, accts, err := helper.List()
136+
accts, err := helper.List()
142137
if err != nil {
143138
return err
144139
}
145-
keyDataList := []KeyData{}
146-
for index := 0; index < len(paths); index++ {
147-
keyDataObj := KeyData{
148-
Path: paths[index],
149-
Username: accts[index],
150-
}
151-
keyDataList = append([]KeyData{keyDataObj}, keyDataList...)
152-
}
153-
buffer := new(bytes.Buffer)
154-
if err := json.NewEncoder(buffer).Encode(keyDataList); err != nil {
155-
return err
156-
}
157-
fmt.Fprint(writer, buffer.String())
158-
return nil
140+
return json.NewEncoder(writer).Encode(accts)
159141
}

credentials/credentials_test.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,9 +36,9 @@ func (m *memoryStore) Get(serverURL string) (string, string, error) {
3636
return c.Username, c.Secret, nil
3737
}
3838

39-
func (m *memoryStore) List() ([]string, []string, error) {
39+
func (m *memoryStore) List() (map[string]string, error) {
4040
//Simply a placeholder to let memoryStore be a valid implementation of Helper interface
41-
return nil, nil, nil
41+
return nil, nil
4242
}
4343

4444
func TestStore(t *testing.T) {

credentials/helper.go

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,6 @@ type Helper interface {
99
// Get retrieves credentials from the store.
1010
// It returns username and secret as strings.
1111
Get(serverURL string) (string, string, error)
12-
// List returns the serverURLs of keys and their
13-
// associated usernames from the OS store as a
14-
// list of strings
15-
List() ([]string, []string, error)
12+
// List returns the stored serverURLs and their associated usernames.
13+
List() (map[string]string, error)
1614
}

osxkeychain/osxkeychain_darwin.go

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,8 @@ func (h Osxkeychain) Get(serverURL string) (string, string, error) {
9494
return user, pass, nil
9595
}
9696

97-
func (h Osxkeychain) List() ([]string, []string, error) {
97+
// List returns the stored URLs and corresponding usernames.
98+
func (h Osxkeychain) List() (map[string]string, error) {
9899
var pathsC **C.char
99100
defer C.free(unsafe.Pointer(pathsC))
100101
var acctsC **C.char
@@ -104,29 +105,25 @@ func (h Osxkeychain) List() ([]string, []string, error) {
104105
if errMsg != nil {
105106
defer C.free(unsafe.Pointer(errMsg))
106107
goMsg := C.GoString(errMsg)
107-
return nil, nil, errors.New(goMsg)
108+
return nil, errors.New(goMsg)
108109
}
110+
111+
defer C.freeListData(&pathsC, listLenC)
112+
defer C.freeListData(&acctsC, listLenC)
113+
109114
var listLen int
110115
listLen = int(listLenC)
111116
pathTmp := (*[1 << 30]*C.char)(unsafe.Pointer(pathsC))[:listLen:listLen]
112117
acctTmp := (*[1 << 30]*C.char)(unsafe.Pointer(acctsC))[:listLen:listLen]
113118
//taking the array of c strings into go while ignoring all the stuff irrelevant to credentials-helper
114-
paths := make([]string, listLen)
115-
accts := make([]string, listLen)
116-
at := 0
119+
resp := make(map[string]string)
117120
for i := 0; i < listLen; i++ {
118121
if C.GoString(pathTmp[i]) == "0" {
119122
continue
120123
}
121-
paths[at] = C.GoString(pathTmp[i])
122-
accts[at] = C.GoString(acctTmp[i])
123-
at = at + 1
124+
resp[C.GoString(pathTmp[i])] = C.GoString(acctTmp[i])
124125
}
125-
paths = paths[:at]
126-
accts = accts[:at]
127-
C.freeListData(&pathsC, listLenC)
128-
C.freeListData(&acctsC, listLenC)
129-
return paths, accts, nil
126+
return resp, nil
130127
}
131128

132129
func splitServer(serverURL string) (*C.struct_Server, error) {

osxkeychain/osxkeychain_darwin_test.go

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -34,19 +34,19 @@ func TestOSXKeychainHelper(t *testing.T) {
3434
t.Fatalf("expected %s, got %s\n", "foobarbaz", secret)
3535
}
3636

37-
paths, accts, err := helper.List()
38-
if err != nil || len(paths) == 0 || len(accts) == 0 {
37+
auths, err := helper.List()
38+
if err != nil || len(auths) == 0 {
3939
t.Fatal(err)
4040
}
4141

4242
helper.Add(creds1)
4343
defer helper.Delete(creds1.ServerURL)
44-
newpaths, newaccts, err := helper.List()
45-
if len(newpaths)-len(paths) != 1 || len(newaccts)-len(accts) != 1 {
44+
newauths, err := helper.List()
45+
if len(newauths)-len(auths) != 1 {
4646
if err == nil {
47-
t.Fatalf("Error: len(newpaths): %d, len(paths): %d\n len(newaccts): %d, len(accts): %d\n Error= %s", len(newpaths), len(paths), len(newaccts), len(accts), "")
47+
t.Fatalf("Error: len(newauths): %d, len(auths): %d", len(newauths), len(auths))
4848
}
49-
t.Fatalf("Error: len(newpaths): %d, len(paths): %d\n len(newaccts): %d, len(accts): %d\n Error= %s", len(newpaths), len(paths), len(newaccts), len(accts), err.Error())
49+
t.Fatalf("Error: len(newauths): %d, len(auths): %d\n Error= %v", len(newauths), len(auths), err)
5050
}
5151

5252
if err := helper.Delete(creds.ServerURL); err != nil {

secretservice/secretservice_linux.go

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,8 @@ func (h Secretservice) Get(serverURL string) (string, string, error) {
7979
return user, pass, nil
8080
}
8181

82-
func (h Secretservice) List() ([]string, []string, error) {
82+
// List returns the stored URLs and corresponding usernames.
83+
func (h Secretservice) List() (map[string]string, error) {
8384
var pathsC **C.char
8485
defer C.free(unsafe.Pointer(pathsC))
8586
var acctsC **C.char
@@ -88,18 +89,18 @@ func (h Secretservice) List() ([]string, []string, error) {
8889
err := C.list(&pathsC, &acctsC, &listLenC)
8990
if err != nil {
9091
defer C.free(unsafe.Pointer(err))
91-
return nil, nil, errors.New("Error from list function in secretservice_linux.c likely due to error in secretservice library")
92+
return nil, errors.New("Error from list function in secretservice_linux.c likely due to error in secretservice library")
9293
}
94+
defer C.freeListData(&pathsC, listLenC)
95+
defer C.freeListData(&acctsC, listLenC)
96+
9397
listLen := int(listLenC)
9498
pathTmp := (*[1 << 30]*C.char)(unsafe.Pointer(pathsC))[:listLen:listLen]
9599
acctTmp := (*[1 << 30]*C.char)(unsafe.Pointer(acctsC))[:listLen:listLen]
96-
paths := make([]string, listLen)
97-
accts := make([]string, listLen)
100+
resp := make(map[string]string)
98101
for i := 0; i < listLen; i++ {
99-
paths[i] = C.GoString(pathTmp[i])
100-
accts[i] = C.GoString(acctTmp[i])
102+
resp[C.GoString(pathTmp[i])] = C.GoString(acctTmp[i])
101103
}
102-
C.freeListData(&pathsC, listLenC)
103-
C.freeListData(&acctsC, listLenC)
104-
return paths, accts, nil
104+
105+
return resp, nil
105106
}

secretservice/secretservice_linux_test.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,12 +36,12 @@ func TestSecretServiceHelper(t *testing.T) {
3636
if err := helper.Delete(creds.ServerURL); err != nil {
3737
t.Fatal(err)
3838
}
39-
paths, accts, err := helper.List()
40-
if err != nil || len(paths) == 0 || len(accts) == 0 {
39+
auths, err := helper.List()
40+
if err != nil || len(auths) == 0 {
4141
t.Fatal(err)
4242
}
4343
helper.Add(creds)
44-
if newpaths, newaccts, err := helper.List(); (len(newpaths)-len(paths)) != 1 || (len(newaccts)-len(accts)) != 1 {
44+
if newauths, err := helper.List(); (len(newauths) - len(auths)) != 1 {
4545
t.Fatal(err)
4646
}
4747
}

wincred/wincred_windows.go

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -38,16 +38,18 @@ func (h Wincred) Get(serverURL string) (string, string, error) {
3838
return g.UserName, string(g.CredentialBlob), nil
3939
}
4040

41-
func (h Wincred) List() ([]string, []string, error) {
41+
// List returns the stored URLs and corresponding usernames.
42+
func (h Wincred) List() (map[string]string, error) {
4243
creds, err := winc.List()
4344
paths := make([]string, len(creds))
4445
accts := make([]string, len(creds))
4546
if err != nil {
46-
return nil, nil, err
47+
return nil, err
4748
}
49+
50+
resp := make(map[string]string)
4851
for i := range creds {
49-
paths[i] = creds[i].TargetName
50-
accts[i] = creds[i].UserName
52+
resp[creds[i].TargetName] = creds[i].UserName
5153
}
52-
return paths, accts, nil
54+
return resp, nil
5355
}

0 commit comments

Comments
 (0)