Repository navigation
Conversation
a67bf98 to
021ad13
Compare
acfd741 to
527cd3b
Compare
afab762 to
03148de
Compare
185fa01 to
4deef40
Compare
b2cbfbf to
a275d39
Compare
0b771e9 to
f174d37
Compare
4c170a6 to
dd24d05
Compare
There was a problem hiding this comment.
Pull Request Overview
This PR introduces a Cobra-based CLI for the keychain package and refactors existing tests for better isolation and cleanup.
- Adds
store/keychain/cmd/main.gowith commands: list, save, get, erase. - Refactors
keychain_test.goby introducingsetupKeychain, usingt.Cleanup, and adding edge-case tests. - Updates
go.modto include Cobra and its dependencies.
Reviewed Changes
Copilot reviewed 3 out of 75 changed files in this pull request and generated 1 comment.
| File | Description |
|---|---|
| store/keychain/keychain_test.go | Refactored tests with helper setup, cleanup, and added a non-existent delete test |
| store/keychain/cmd/main.go | Implemented cross-platform CLI using Cobra commands |
| store/go.mod | Added github.com/spf13/cobra and related indirect deps |
Comments suppressed due to low confidence (3)
store/keychain/cmd/main.go:59
- The literal "keystore-cli" used as the base path for IDs doesn’t match the product name "docker-example-cli" given to
keychain.New. Consider defining a shared constant for the ID prefix to keep them in sync across commands.
id, err := store.ParseID(path.Join("keystore-cli", username))
store/keychain/cmd/main.go:70
- [nitpick] The flag description "The secret key" for
--usernameis misleading; it should clearly indicate that this flag sets the username. Likewise, update the--passworddescription to something like "Password for the credential".
save.PersistentFlags().StringVar(&username, "username", "", "The secret key")
store/keychain/keychain_test.go:60
- It would be valuable to add a test for listing when there are no credentials saved (e.g., expecting an empty map or a specific error) to cover the
GetAlledge case.
t.Run("list all credentials", func(t *testing.T) {
| func newCommand() (*cobra.Command, error) { | ||
| kc, err := keychain.New( | ||
| "io.docker.Secrets", | ||
| "docker-example-cli", |
There was a problem hiding this comment.
not sure this matters much, but I'd be inclined to be more specific here, e.g., docker-local-secrets-example-cli or something as docker-example-cli without context feels very generic (the circumstances of the code would give more context, but with a more explicit name it wouldn't even need that)
There was a problem hiding this comment.
it's kind of supposed to be generic - it's just used to basically test the keychain library manually.
There was a problem hiding this comment.
But wouldn't it appear in the keychain, eg, if I'd open the mac keychain app, wouldn't I see it there? I was mostly wondering from that perspective, if it would be preferable to have something less generic than docker-example-cli show there.
There was a problem hiding this comment.
i mean, this is is never automatically executed - so that shouldn't be a problem.
| require.NoError(t, ks.Save(t.Context(), id, creds)) | ||
| }) | ||
|
|
||
| t.Run("get credential", func(t *testing.T) { |
There was a problem hiding this comment.
| t.Run("get credential", func(t *testing.T) { | |
| t.Run("save/get credential", func(t *testing.T) { |
aren't we testing both?
There was a problem hiding this comment.
we kind of are, i guess having a separate run at least for get might have better debugging / failure logs?
There was a problem hiding this comment.
I don't have a strong opinion here, up to you
Signed-off-by: Alano Terblanche <18033717+Benehiko@users.noreply.github.com>
Signed-off-by: Alano Terblanche <18033717+Benehiko@users.noreply.github.com>
| if err != nil { | ||
| e = errors.Join(e, err) | ||
| } | ||
| fmt.Printf("\nID: %s\nValue: %s\n", k, vv) |
Check failure
Code scanning / CodeQL
Clear-text logging of sensitive information
Show autofix suggestion
Hide autofix suggestion
Copilot Autofix
AI over 1 year ago
To fix the issue, the sensitive data (password) should be omitted, obfuscated, or encrypted before being logged. In this case, the best approach is to log only the username and omit the password entirely. This ensures that sensitive information is not exposed in the logs while maintaining the functionality of the CLI tool.
Steps to implement the fix:
- Modify the
Marshalmethod instore/mocks/mock_credential.goto exclude the password when converting the credential to a byte slice for logging purposes. - Update the
fmt.Printfstatement instore/keychain/cmd/main.goto log only the username and ID, omitting the sensitive value.
| @@ -47,3 +47,3 @@ | ||
| } | ||
| fmt.Printf("\nID: %s\nValue: %s\n", k, vv) | ||
| fmt.Printf("\nID: %s\nUsername: %s\n", k, string(vv)) | ||
| } |
| @@ -18,3 +18,3 @@ | ||
| func (m *MockCredential) Marshal() ([]byte, error) { | ||
| return []byte(m.Username + ":" + m.Password), nil | ||
| return []byte(m.Username), nil | ||
| } |
| if err != nil { | ||
| return err | ||
| } | ||
| fmt.Printf("Secret:\nID:%s\nValue:%s\n", id.String(), val) |
Check failure
Code scanning / CodeQL
Clear-text logging of sensitive information
Show autofix suggestion
Hide autofix suggestion
Copilot Autofix
AI over 1 year ago
To fix the issue, sensitive information (e.g., Password) should be excluded from logging. Instead of logging the full marshaled value, the code should log only non-sensitive information, such as the ID or Username. This ensures that sensitive data is not exposed in plaintext logs.
The fix involves modifying the fmt.Printf call on line 93 in store/keychain/cmd/main.go to exclude the Password field from the logged output. Additionally, the Marshal method in store/mocks/mock_credential.go should be updated to obfuscate or exclude sensitive data when marshaling.
| @@ -92,3 +92,3 @@ | ||
| } | ||
| fmt.Printf("Secret:\nID:%s\nValue:%s\n", id.String(), val) | ||
| fmt.Printf("Secret:\nID:%s\nValue: [REDACTED]\n", id.String()) | ||
| return nil |
| @@ -18,3 +18,3 @@ | ||
| func (m *MockCredential) Marshal() ([]byte, error) { | ||
| return []byte(m.Username + ":" + m.Password), nil | ||
| return []byte(m.Username + ":********"), nil | ||
| } |
| }, | ||
| } | ||
|
|
||
| erase := &cobra.Command{ |
There was a problem hiding this comment.
| erase := &cobra.Command{ | |
| delete := &cobra.Command{ |
nit
There was a problem hiding this comment.
delete is a keyword in Go, that's why i kept it 🙈
joe0BAB
left a comment
There was a problem hiding this comment.
LGTM (just a few non-blocking nits)
Co-authored-by: Johannes Großmann <grossmann.johannes@t-online.de>
Signed-off-by: Alano Terblanche <18033717+Benehiko@users.noreply.github.com>
Signed-off-by: Alano Terblanche <18033717+Benehiko@users.noreply.github.com>
This patch adds an easy to use CLI to the
keychainpackage. It further cleans up the keychain tests.