cleanup docker.New to overload, so to speak

This commit is contained in:
Brad Rydzewski 2014-10-21 00:38:19 -07:00
parent 505ebe7024
commit 7dfc67113d

View file

@ -34,53 +34,52 @@ var Logging = true
// New creates an instance of the Docker Client // New creates an instance of the Docker Client
func New() *Client { func New() *Client {
c := &Client{} return NewHost("")
c.setHost(DEFAULTUNIXSOCKET)
c.Images = &ImageService{c}
c.Containers = &ContainerService{c}
return c
} }
func NewHost(address string) *Client { func NewHost(address string) *Client {
c := &Client{} var cli, _ = NewClient(address, "", "")
return cli
// parse the address and split
pieces := strings.Split(address, "://")
if len(pieces) == 2 {
c.proto = pieces[0]
c.addr = pieces[1]
} else if len(pieces) == 1 {
c.addr = pieces[0]
}
c.Images = &ImageService{c}
c.Containers = &ContainerService{c}
return c
} }
func NewClient(addr, cert, key string) (*Client, error) { func NewClient(uri, cert, key string) (*Client, error) {
// generate a new Client var host = GetHost(uri)
var cli = NewHost(addr) var proto, addr = GetProtoAddr(host)
cli.tls = new(tls.Config)
// this is required in order for Docker to connect var cli = new(Client)
// to a certificate generated for an IP address and cli.proto = proto
// not a Domain name cli.addr = addr
cli.tls.InsecureSkipVerify = true cli.scheme = "http"
cli.Images = &ImageService{cli}
cli.Containers = &ContainerService{cli}
// loads the keyvalue pair and stores the // if no certificate is provided returns the
// cert (pem) in a certificate store (array) // client with no TLS configured.
if len(cert) == 0 || len(key) == 0 {
return cli, nil
}
// loads the key value pair in pem format
pem, err := tls.LoadX509KeyPair(cert, key) pem, err := tls.LoadX509KeyPair(cert, key)
if err != nil { if err != nil {
return nil, err return nil, err
} }
// setup the client TLS and store the certificate.
// also skip verification since we are (typically)
// going to be using certs for IP addresses.
cli.scheme = "https"
cli.tls = new(tls.Config)
cli.tls.InsecureSkipVerify = true
cli.tls.Certificates = []tls.Certificate{pem} cli.tls.Certificates = []tls.Certificate{pem}
// creates a transport that uses the custom tls // disable compression for local socket communication.
// configuration to securely connect to remote if cli.proto == DEFAULTPROTOCOL {
// Docker clients. cli.trans.DisableCompression = true
}
// creates a transport that uses the custom tls configuration
// to securely connect to remote Docker clients.
cli.trans = &http.Transport{ cli.trans = &http.Transport{
TLSClientConfig: cli.tls, TLSClientConfig: cli.tls,
Dial: func(dial_network, dial_addr string) (net.Conn, error) { Dial: func(dial_network, dial_addr string) (net.Conn, error) {
@ -88,19 +87,15 @@ func NewClient(addr, cert, key string) (*Client, error) {
}, },
} }
if cli.proto == "unix" {
// no need in compressing for local communications
cli.trans.DisableCompression = true
}
return cli, nil return cli, nil
} }
type Client struct { type Client struct {
tls *tls.Config tls *tls.Config
trans *http.Transport trans *http.Transport
proto string scheme string
addr string proto string
addr string
Images *ImageService Images *ImageService
Containers *ContainerService Containers *ContainerService
@ -149,6 +144,48 @@ func (c *Client) setHost(defaultUnixSocket string) {
} }
} }
// GetHost returns the Docker Host address in order to
// connect to the Docker Daemon. It implements a very
// simple set of fallthrough logic to determine which
// address to use.
func GetHost(host string) string {
// if a default value was provided this
// shoudl be used
if len(host) != 0 {
return host
}
// else attempt to use the DOCKER_HOST
// environment variable
var env = os.Getenv("DOCKER_HOST")
if len(env) != 0 {
return env
}
// else check to see if the default unix
// socket exists and return
_, err := os.Stat(DEFAULTUNIXSOCKET)
if err == nil {
return fmt.Sprintf("%s://%s", DEFAULTPROTOCOL, DEFAULTUNIXSOCKET)
}
// else return the standard TCP address
return fmt.Sprintf("tcp://0.0.0.0:%d", DEFAULTHTTPPORT)
}
// GetProtoAddr is a helper function that splits
// a host into Protocol and Address.
func GetProtoAddr(host string) (string, string) {
var parts = strings.Split(host, "://")
var proto, addr string
switch {
case len(parts) == 2:
proto = parts[0]
addr = parts[1]
default:
proto = "tcp"
addr = parts[0]
}
return proto, addr
}
// helper function used to make HTTP requests to the Docker daemon. // helper function used to make HTTP requests to the Docker daemon.
func (c *Client) do(method, path string, in, out interface{}) error { func (c *Client) do(method, path string, in, out interface{}) error {
// if data input is provided, serialize to JSON // if data input is provided, serialize to JSON