Skip to content
Permalink
Branch: master
Find file Copy path
Find file Copy path
Fetching contributors…
Cannot retrieve contributors at this time
127 lines (108 sloc) 3.65 KB
package rdsutils
import (
"fmt"
"net/url"
"github.com/aws/aws-sdk-go/aws/awserr"
"github.com/aws/aws-sdk-go/aws/credentials"
)
// ConnectionFormat is the type of connection that will be
// used to connect to the database
type ConnectionFormat string
// ConnectionFormat enums
const (
NoConnectionFormat ConnectionFormat = ""
TCPFormat ConnectionFormat = "tcp"
)
// ErrNoConnectionFormat will be returned during build if no format had been
// specified
var ErrNoConnectionFormat = awserr.New("NoConnectionFormat", "No connection format was specified", nil)
// ConnectionStringBuilder is a builder that will construct a connection
// string with the provided parameters. params field is required to have
// a tls specification and allowCleartextPasswords must be set to true.
type ConnectionStringBuilder struct {
dbName string
endpoint string
region string
user string
creds *credentials.Credentials
connectFormat ConnectionFormat
params url.Values
}
// NewConnectionStringBuilder will return an ConnectionStringBuilder
func NewConnectionStringBuilder(endpoint, region, dbUser, dbName string, creds *credentials.Credentials) ConnectionStringBuilder {
return ConnectionStringBuilder{
dbName: dbName,
endpoint: endpoint,
region: region,
user: dbUser,
creds: creds,
}
}
// WithEndpoint will return a builder with the given endpoint
func (b ConnectionStringBuilder) WithEndpoint(endpoint string) ConnectionStringBuilder {
b.endpoint = endpoint
return b
}
// WithRegion will return a builder with the given region
func (b ConnectionStringBuilder) WithRegion(region string) ConnectionStringBuilder {
b.region = region
return b
}
// WithUser will return a builder with the given user
func (b ConnectionStringBuilder) WithUser(user string) ConnectionStringBuilder {
b.user = user
return b
}
// WithDBName will return a builder with the given database name
func (b ConnectionStringBuilder) WithDBName(dbName string) ConnectionStringBuilder {
b.dbName = dbName
return b
}
// WithParams will return a builder with the given params. The parameters
// will be included in the connection query string
//
// Example:
// v := url.Values{}
// v.Add("tls", "rds")
// b := rdsutils.NewConnectionBuilder(endpoint, region, user, dbname, creds)
// connectStr, err := b.WithParams(v).WithTCPFormat().Build()
func (b ConnectionStringBuilder) WithParams(params url.Values) ConnectionStringBuilder {
b.params = params
return b
}
// WithFormat will return a builder with the given connection format
func (b ConnectionStringBuilder) WithFormat(f ConnectionFormat) ConnectionStringBuilder {
b.connectFormat = f
return b
}
// WithTCPFormat will set the format to TCP and return the modified builder
func (b ConnectionStringBuilder) WithTCPFormat() ConnectionStringBuilder {
return b.WithFormat(TCPFormat)
}
// Build will return a new connection string that can be used to open a connection
// to the desired database.
//
// Example:
// b := rdsutils.NewConnectionStringBuilder(endpoint, region, user, dbname, creds)
// connectStr, err := b.WithTCPFormat().Build()
// if err != nil {
// panic(err)
// }
// const dbType = "mysql"
// db, err := sql.Open(dbType, connectStr)
func (b ConnectionStringBuilder) Build() (string, error) {
if b.connectFormat == NoConnectionFormat {
return "", ErrNoConnectionFormat
}
authToken, err := BuildAuthToken(b.endpoint, b.region, b.user, b.creds)
if err != nil {
return "", err
}
connectionStr := fmt.Sprintf("%s:%s@%s(%s)/%s",
b.user, authToken, string(b.connectFormat), b.endpoint, b.dbName,
)
if len(b.params) > 0 {
connectionStr = fmt.Sprintf("%s?%s", connectionStr, b.params.Encode())
}
return connectionStr, nil
}
You can’t perform that action at this time.