You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
96 lines
2.6 KiB
96 lines
2.6 KiB
|
2 months ago
|
package secretstore
|
||
|
|
|
||
|
|
import (
|
||
|
|
"bytes"
|
||
|
|
"os"
|
||
|
|
"path/filepath"
|
||
|
|
"runtime"
|
||
|
|
"testing"
|
||
|
|
)
|
||
|
|
|
||
|
|
func TestStorePersistsSecretsOutsideCallerSnapshots(t *testing.T) {
|
||
|
|
path := filepath.Join(t.TempDir(), "secrets.json")
|
||
|
|
store, err := Open(path)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
want := []byte("operation password")
|
||
|
|
if err := store.Set("port.pending.ch01.1", want); err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
reloaded, err := Open(path)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
actual, ok := reloaded.Get("port.pending.ch01.1")
|
||
|
|
if !ok || !bytes.Equal(actual, want) {
|
||
|
|
t.Fatalf("Get() = %q, %t", actual, ok)
|
||
|
|
}
|
||
|
|
if runtime.GOOS != "windows" {
|
||
|
|
info, err := os.Stat(path)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
if info.Mode().Perm() != 0o600 {
|
||
|
|
t.Fatalf("mode = %o", info.Mode().Perm())
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if err := reloaded.Copy("port.pending.ch01.1", "port.running.ch01.1"); err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
if err := reloaded.Delete("port.pending.ch01.1"); err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
if _, ok := reloaded.Get("port.pending.ch01.1"); ok {
|
||
|
|
t.Fatal("deleted secret is still present")
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
func TestStoreRejectsUnsafeKeysAndEmptyValues(t *testing.T) {
|
||
|
|
store, _ := Open("")
|
||
|
|
if err := store.Set("../escape", []byte("secret")); err == nil {
|
||
|
|
t.Fatal("unsafe key accepted")
|
||
|
|
}
|
||
|
|
if err := store.Set("safe.key", nil); err == nil {
|
||
|
|
t.Fatal("empty secret accepted")
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
func TestStoreDeletePrefixesRemovesOnlySelectedNamespaces(t *testing.T) {
|
||
|
|
path := filepath.Join(t.TempDir(), "secrets.json")
|
||
|
|
store, err := Open(path)
|
||
|
|
if err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
for key, value := range map[string]string{
|
||
|
|
"port.pending.ch01.1": "pending-port",
|
||
|
|
"config/pending/smtp/password": "pending-smtp",
|
||
|
|
"external/pending/radius/server1": "pending-radius",
|
||
|
|
"port.running.ch01.1": "running-port",
|
||
|
|
"config/persistent/smtp/password": "saved-smtp",
|
||
|
|
} {
|
||
|
|
if err := store.Set(key, []byte(value)); err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if err := store.DeletePrefixes("port.pending.", "config/pending/", "external/pending/"); err != nil {
|
||
|
|
t.Fatal(err)
|
||
|
|
}
|
||
|
|
for _, key := range []string{"port.pending.ch01.1", "config/pending/smtp/password", "external/pending/radius/server1"} {
|
||
|
|
if store.Has(key) {
|
||
|
|
t.Fatalf("pending secret %q was not removed", key)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
for _, key := range []string{"port.running.ch01.1", "config/persistent/smtp/password"} {
|
||
|
|
if !store.Has(key) {
|
||
|
|
t.Fatalf("non-pending secret %q was removed", key)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if err := store.DeletePrefixes(); err == nil {
|
||
|
|
t.Fatal("empty prefix list was accepted")
|
||
|
|
}
|
||
|
|
if err := store.DeletePrefixes("../"); err == nil {
|
||
|
|
t.Fatal("unsafe prefix was accepted")
|
||
|
|
}
|
||
|
|
}
|