mirror of
				https://github.com/optim-enterprises-bv/vault.git
				synced 2025-10-31 02:28:09 +00:00 
			
		
		
		
	Dockerize Postgres secret backend acceptance tests
Additionally enable them on all unit test runs.
This commit is contained in:
		| @@ -6,14 +6,68 @@ import ( | ||||
| 	"log" | ||||
| 	"os" | ||||
| 	"reflect" | ||||
| 	"sync" | ||||
| 	"testing" | ||||
| 	"time" | ||||
|  | ||||
| 	"github.com/hashicorp/vault/logical" | ||||
| 	logicaltest "github.com/hashicorp/vault/logical/testing" | ||||
| 	"github.com/lib/pq" | ||||
| 	"github.com/mitchellh/mapstructure" | ||||
| 	"github.com/ory-am/dockertest" | ||||
| ) | ||||
|  | ||||
| var ( | ||||
| 	testImagePull sync.Once | ||||
| ) | ||||
|  | ||||
| func prepareTestContainer(t *testing.T, s logical.Storage, b logical.Backend) (cid dockertest.ContainerID, retURL string) { | ||||
| 	if os.Getenv("PG_URL") != "" { | ||||
| 		return "", os.Getenv("PG_URL") | ||||
| 	} | ||||
|  | ||||
| 	dockertest.BindDockerToLocalhost = "yep" | ||||
|  | ||||
| 	testImagePull.Do(func() { | ||||
| 		dockertest.Pull("postgres") | ||||
| 	}) | ||||
|  | ||||
| 	cid, connErr := dockertest.ConnectToPostgreSQL(60, 500*time.Millisecond, func(connURL string) bool { | ||||
| 		// This will cause a validation to run | ||||
| 		resp, err := b.HandleRequest(&logical.Request{ | ||||
| 			Storage:   s, | ||||
| 			Operation: logical.UpdateOperation, | ||||
| 			Path:      "config/connection", | ||||
| 			Data: map[string]interface{}{ | ||||
| 				"connection_url": connURL, | ||||
| 			}, | ||||
| 		}) | ||||
| 		if err != nil || (resp != nil && resp.IsError()) { | ||||
| 			// It's likely not up and running yet, so return false and try again | ||||
| 			return false | ||||
| 		} | ||||
| 		if resp == nil { | ||||
| 			t.Fatal("expected warning") | ||||
| 		} | ||||
|  | ||||
| 		retURL = connURL | ||||
| 		return true | ||||
| 	}) | ||||
|  | ||||
| 	if connErr != nil { | ||||
| 		t.Fatalf("could not connect to database: %v", connErr) | ||||
| 	} | ||||
|  | ||||
| 	return | ||||
| } | ||||
|  | ||||
| func cleanupTestContainer(t *testing.T, cid dockertest.ContainerID) { | ||||
| 	err := cid.KillRemove() | ||||
| 	if err != nil { | ||||
| 		t.Fatal(err) | ||||
| 	} | ||||
| } | ||||
|  | ||||
| func TestBackend_config_connection(t *testing.T) { | ||||
| 	var resp *logical.Response | ||||
| 	var err error | ||||
| @@ -55,43 +109,51 @@ func TestBackend_config_connection(t *testing.T) { | ||||
| } | ||||
|  | ||||
| func TestBackend_basic(t *testing.T) { | ||||
| 	b, _ := Factory(logical.TestBackendConfig()) | ||||
|  | ||||
| 	d1 := map[string]interface{}{ | ||||
| 		"connection_url": os.Getenv("PG_URL"), | ||||
| 	config := logical.TestBackendConfig() | ||||
| 	config.StorageView = &logical.InmemStorage{} | ||||
| 	b, err := Factory(config) | ||||
| 	if err != nil { | ||||
| 		t.Fatal(err) | ||||
| 	} | ||||
| 	d2 := map[string]interface{}{ | ||||
| 		"value": os.Getenv("PG_URL"), | ||||
|  | ||||
| 	cid, connURL := prepareTestContainer(t, config.StorageView, b) | ||||
| 	if cid != "" { | ||||
| 		defer cleanupTestContainer(t, cid) | ||||
| 	} | ||||
| 	connData := map[string]interface{}{ | ||||
| 		"connection_url": connURL, | ||||
| 	} | ||||
|  | ||||
| 	logicaltest.Test(t, logicaltest.TestCase{ | ||||
| 		AcceptanceTest: true, | ||||
| 		PreCheck:       func() { testAccPreCheck(t) }, | ||||
| 		Backend:        b, | ||||
| 		Backend: b, | ||||
| 		Steps: []logicaltest.TestStep{ | ||||
| 			testAccStepConfig(t, d1, false), | ||||
| 			testAccStepConfig(t, connData, false), | ||||
| 			testAccStepRole(t), | ||||
| 			testAccStepReadCreds(t, b, "web"), | ||||
| 			testAccStepConfig(t, d2, false), | ||||
| 			testAccStepRole(t), | ||||
| 			testAccStepReadCreds(t, b, "web"), | ||||
| 			testAccStepReadCreds(t, b, "web", connURL), | ||||
| 		}, | ||||
| 	}) | ||||
|  | ||||
| } | ||||
|  | ||||
| func TestBackend_roleCrud(t *testing.T) { | ||||
| 	b, _ := Factory(logical.TestBackendConfig()) | ||||
| 	d := map[string]interface{}{ | ||||
| 		"connection_url": os.Getenv("PG_URL"), | ||||
| 	config := logical.TestBackendConfig() | ||||
| 	config.StorageView = &logical.InmemStorage{} | ||||
| 	b, err := Factory(config) | ||||
| 	if err != nil { | ||||
| 		t.Fatal(err) | ||||
| 	} | ||||
|  | ||||
| 	cid, connURL := prepareTestContainer(t, config.StorageView, b) | ||||
| 	if cid != "" { | ||||
| 		defer cleanupTestContainer(t, cid) | ||||
| 	} | ||||
| 	connData := map[string]interface{}{ | ||||
| 		"connection_url": connURL, | ||||
| 	} | ||||
|  | ||||
| 	logicaltest.Test(t, logicaltest.TestCase{ | ||||
| 		AcceptanceTest: true, | ||||
| 		PreCheck:       func() { testAccPreCheck(t) }, | ||||
| 		Backend:        b, | ||||
| 		Backend: b, | ||||
| 		Steps: []logicaltest.TestStep{ | ||||
| 			testAccStepConfig(t, d, false), | ||||
| 			testAccStepConfig(t, connData, false), | ||||
| 			testAccStepRole(t), | ||||
| 			testAccStepReadRole(t, "web", testRole), | ||||
| 			testAccStepDeleteRole(t, "web"), | ||||
| @@ -100,39 +162,6 @@ func TestBackend_roleCrud(t *testing.T) { | ||||
| 	}) | ||||
| } | ||||
|  | ||||
| func TestBackend_configConnection(t *testing.T) { | ||||
| 	b, _ := Factory(logical.TestBackendConfig()) | ||||
| 	d1 := map[string]interface{}{ | ||||
| 		"value": os.Getenv("PG_URL"), | ||||
| 	} | ||||
| 	d2 := map[string]interface{}{ | ||||
| 		"connection_url": os.Getenv("PG_URL"), | ||||
| 	} | ||||
| 	d3 := map[string]interface{}{ | ||||
| 		"value":          os.Getenv("PG_URL"), | ||||
| 		"connection_url": os.Getenv("PG_URL"), | ||||
| 	} | ||||
| 	d4 := map[string]interface{}{} | ||||
|  | ||||
| 	logicaltest.Test(t, logicaltest.TestCase{ | ||||
| 		AcceptanceTest: true, | ||||
| 		PreCheck:       func() { testAccPreCheck(t) }, | ||||
| 		Backend:        b, | ||||
| 		Steps: []logicaltest.TestStep{ | ||||
| 			testAccStepConfig(t, d1, false), | ||||
| 			testAccStepConfig(t, d2, false), | ||||
| 			testAccStepConfig(t, d3, false), | ||||
| 			testAccStepConfig(t, d4, true), | ||||
| 		}, | ||||
| 	}) | ||||
| } | ||||
|  | ||||
| func testAccPreCheck(t *testing.T) { | ||||
| 	if v := os.Getenv("PG_URL"); v == "" { | ||||
| 		t.Fatal("PG_URL must be set for acceptance tests") | ||||
| 	} | ||||
| } | ||||
|  | ||||
| func testAccStepConfig(t *testing.T, d map[string]interface{}, expectError bool) logicaltest.TestStep { | ||||
| 	return logicaltest.TestStep{ | ||||
| 		Operation: logical.UpdateOperation, | ||||
| @@ -154,8 +183,8 @@ func testAccStepConfig(t *testing.T, d map[string]interface{}, expectError bool) | ||||
| 					return fmt.Errorf("expected error, but write succeeded.") | ||||
| 				} | ||||
| 				return nil | ||||
| 			} else if resp != nil { | ||||
| 				return fmt.Errorf("response should be nil") | ||||
| 			} else if resp != nil && resp.IsError() { | ||||
| 				return fmt.Errorf("got an error response: %v", resp.Error()) | ||||
| 			} | ||||
| 			return nil | ||||
| 		}, | ||||
| @@ -179,7 +208,7 @@ func testAccStepDeleteRole(t *testing.T, n string) logicaltest.TestStep { | ||||
| 	} | ||||
| } | ||||
|  | ||||
| func testAccStepReadCreds(t *testing.T, b logical.Backend, name string) logicaltest.TestStep { | ||||
| func testAccStepReadCreds(t *testing.T, b logical.Backend, name string, connURL string) logicaltest.TestStep { | ||||
| 	return logicaltest.TestStep{ | ||||
| 		Operation: logical.ReadOperation, | ||||
| 		Path:      "creds/" + name, | ||||
| @@ -193,7 +222,7 @@ func testAccStepReadCreds(t *testing.T, b logical.Backend, name string) logicalt | ||||
| 			} | ||||
| 			log.Printf("[WARN] Generated credentials: %v", d) | ||||
|  | ||||
| 			conn, err := pq.ParseURL(os.Getenv("PG_URL")) | ||||
| 			conn, err := pq.ParseURL(connURL) | ||||
| 			if err != nil { | ||||
| 				t.Fatal(err) | ||||
| 			} | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Jeff Mitchell
					Jeff Mitchell