physical/posgresql: add ability to prefer VAULT_PG_CONNECTION_URL envar over config file (#7937)

* physical/posgresql: add ability to use CONNECTION_URL environment variable instead of requiring it to be configured in the Vault config file.

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* storage/postgresql: update configuration documentation for postgresql storage backend to include connection_url configuration via the PG_CONNECTION_URL environment variable

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: add a configuration file and tests for getting the connection_url from the config file or environment

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: update postgresql backend to pull the required connection_url from the PG_CONNECTION_URL environment variable if it exists, otherwise, fallback to using the config file

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: remove configure*.go files and prefer the postgresql*.go files

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: move and simplify connectionURL function

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: update connectionURL test to use an unordered map instead of slice to avoid test flakiness

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* physical/postgresql: update config env to be prefixed with VAULT_ - VAULT_PG_CONNECTION_URL

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>

* docs/web: update postgresql backend docs to use updated, VAULT_ prefixed config env

Signed-off-by: Colton McCurdy <mccurdyc22@gmail.com>
This commit is contained in:
Colton J. McCurdy
2019-12-03 16:48:38 -05:00
committed by Clint
parent 15d3186380
commit 82786f8278
3 changed files with 79 additions and 3 deletions

View File

@@ -4,6 +4,7 @@ import (
"context"
"database/sql"
"fmt"
"os"
"strconv"
"strings"
"sync"
@@ -88,8 +89,8 @@ type PostgreSQLLock struct {
// API client, server address, credentials, and database.
func NewPostgreSQLBackend(conf map[string]string, logger log.Logger) (physical.Backend, error) {
// Get the PostgreSQL credentials to perform read/write operations.
connURL, ok := conf["connection_url"]
if !ok || connURL == "" {
connURL := connectionURL(conf)
if connURL == "" {
return nil, fmt.Errorf("missing connection_url")
}
@@ -197,6 +198,19 @@ func NewPostgreSQLBackend(conf map[string]string, logger log.Logger) (physical.B
return m, nil
}
// connectionURL first check the environment variables for a connection URL. If
// no connection URL exists in the environment variable, the Vault config file is
// checked. If neither the environment variables or the config file set the connection
// URL for the Postgres backend, because it is a required field, an error is returned.
func connectionURL(conf map[string]string) string {
connURL := conf["connection_url"]
if envURL := os.Getenv("VAULT_PG_CONNECTION_URL"); envURL != "" {
connURL = envURL
}
return connURL
}
// splitKey is a helper to split a full path key into individual
// parts: parentPath, path, key
func (m *PostgreSQLBackend) splitKey(fullPath string) (string, string, string) {

View File

@@ -114,6 +114,67 @@ func TestPostgreSQLBackendMaxIdleConnectionsParameter(t *testing.T) {
}
}
func TestConnectionURL(t *testing.T) {
type input struct {
envar string
conf map[string]string
}
var cases = map[string]struct {
want string
input input
}{
"environment_variable_not_set_use_config_value": {
want: "abc",
input: input{
envar: "",
conf: map[string]string{"connection_url": "abc"},
},
},
"no_value_connection_url_set_key_exists": {
want: "",
input: input{
envar: "",
conf: map[string]string{"connection_url": ""},
},
},
"no_value_connection_url_set_key_doesnt_exist": {
want: "",
input: input{
envar: "",
conf: map[string]string{},
},
},
"environment_variable_set": {
want: "abc",
input: input{
envar: "abc",
conf: map[string]string{"connection_url": "def"},
},
},
}
for name, tt := range cases {
t.Run(name, func(t *testing.T) {
// This is necessary to avoid always testing the branch where the env is set.
// As long the the env is set --- even if the value is "" --- `ok` returns true.
if tt.input.envar != "" {
os.Setenv("VAULT_PG_CONNECTION_URL", tt.input.envar)
defer os.Unsetenv("VAULT_PG_CONNECTION_URL")
}
got := connectionURL(tt.input.conf)
if got != tt.want {
t.Errorf("connectionURL(%s): want '%s', got '%s'", tt.input, tt.want, got)
}
})
}
}
// Similar to testHABackend, but using internal implementation details to
// trigger the lock failure scenario by setting the lock renew period for one
// of the locks to a higher value than the lock TTL.