summaryrefslogtreecommitdiff
path: root/vendor/github.com/jackc/pgconn/config.go
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/github.com/jackc/pgconn/config.go')
-rw-r--r--vendor/github.com/jackc/pgconn/config.go90
1 files changed, 72 insertions, 18 deletions
diff --git a/vendor/github.com/jackc/pgconn/config.go b/vendor/github.com/jackc/pgconn/config.go
index 172e7478b..0eab23af9 100644
--- a/vendor/github.com/jackc/pgconn/config.go
+++ b/vendor/github.com/jackc/pgconn/config.go
@@ -248,21 +248,21 @@ func ParseConfig(connString string) (*Config, error) {
config.LookupFunc = makeDefaultResolver().LookupHost
notRuntimeParams := map[string]struct{}{
- "host": struct{}{},
- "port": struct{}{},
- "database": struct{}{},
- "user": struct{}{},
- "password": struct{}{},
- "passfile": struct{}{},
- "connect_timeout": struct{}{},
- "sslmode": struct{}{},
- "sslkey": struct{}{},
- "sslcert": struct{}{},
- "sslrootcert": struct{}{},
- "target_session_attrs": struct{}{},
- "min_read_buffer_size": struct{}{},
- "service": struct{}{},
- "servicefile": struct{}{},
+ "host": {},
+ "port": {},
+ "database": {},
+ "user": {},
+ "password": {},
+ "passfile": {},
+ "connect_timeout": {},
+ "sslmode": {},
+ "sslkey": {},
+ "sslcert": {},
+ "sslrootcert": {},
+ "target_session_attrs": {},
+ "min_read_buffer_size": {},
+ "service": {},
+ "servicefile": {},
}
for k, v := range settings {
@@ -329,10 +329,19 @@ func ParseConfig(connString string) (*Config, error) {
}
}
- if settings["target_session_attrs"] == "read-write" {
+ switch tsa := settings["target_session_attrs"]; tsa {
+ case "read-write":
config.ValidateConnect = ValidateConnectTargetSessionAttrsReadWrite
- } else if settings["target_session_attrs"] != "any" {
- return nil, &parseConfigError{connString: connString, msg: fmt.Sprintf("unknown target_session_attrs value: %v", settings["target_session_attrs"])}
+ case "read-only":
+ config.ValidateConnect = ValidateConnectTargetSessionAttrsReadOnly
+ case "primary":
+ config.ValidateConnect = ValidateConnectTargetSessionAttrsPrimary
+ case "standby":
+ config.ValidateConnect = ValidateConnectTargetSessionAttrsStandby
+ case "any", "prefer-standby":
+ // do nothing
+ default:
+ return nil, &parseConfigError{connString: connString, msg: fmt.Sprintf("unknown target_session_attrs value: %v", tsa)}
}
return config, nil
@@ -727,3 +736,48 @@ func ValidateConnectTargetSessionAttrsReadWrite(ctx context.Context, pgConn *PgC
return nil
}
+
+// ValidateConnectTargetSessionAttrsReadOnly is an ValidateConnectFunc that implements libpq compatible
+// target_session_attrs=read-only.
+func ValidateConnectTargetSessionAttrsReadOnly(ctx context.Context, pgConn *PgConn) error {
+ result := pgConn.ExecParams(ctx, "show transaction_read_only", nil, nil, nil, nil).Read()
+ if result.Err != nil {
+ return result.Err
+ }
+
+ if string(result.Rows[0][0]) != "on" {
+ return errors.New("connection is not read only")
+ }
+
+ return nil
+}
+
+// ValidateConnectTargetSessionAttrsStandby is an ValidateConnectFunc that implements libpq compatible
+// target_session_attrs=standby.
+func ValidateConnectTargetSessionAttrsStandby(ctx context.Context, pgConn *PgConn) error {
+ result := pgConn.ExecParams(ctx, "select pg_is_in_recovery()", nil, nil, nil, nil).Read()
+ if result.Err != nil {
+ return result.Err
+ }
+
+ if string(result.Rows[0][0]) != "t" {
+ return errors.New("server is not in hot standby mode")
+ }
+
+ return nil
+}
+
+// ValidateConnectTargetSessionAttrsPrimary is an ValidateConnectFunc that implements libpq compatible
+// target_session_attrs=primary.
+func ValidateConnectTargetSessionAttrsPrimary(ctx context.Context, pgConn *PgConn) error {
+ result := pgConn.ExecParams(ctx, "select pg_is_in_recovery()", nil, nil, nil, nil).Read()
+ if result.Err != nil {
+ return result.Err
+ }
+
+ if string(result.Rows[0][0]) == "t" {
+ return errors.New("server is in standby mode")
+ }
+
+ return nil
+}