Skip to content

Commit

Permalink
container: support WebSocket over HTTPS
Browse files Browse the repository at this point in the history
Signed-off-by: Soshi Katsuta <soshi.katsuta@gmail.com>
  • Loading branch information
skatsuta committed Oct 7, 2015
1 parent 9e3d15c commit 76cde5b
Show file tree
Hide file tree
Showing 2 changed files with 78 additions and 17 deletions.
85 changes: 70 additions & 15 deletions config.go
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
package codetainer

import (
"crypto/tls"
"crypto/x509"
"errors"
"fmt"
"io/ioutil"
"os"
"os/user"
"path"
Expand Down Expand Up @@ -86,6 +89,7 @@ type Config struct {
DatabasePath string
database *Database
currentDockerApiVersion string
tlsConfig *tls.Config
}

func (c *Config) Url() string {
Expand Down Expand Up @@ -133,21 +137,7 @@ func (c *Config) GetDockerClient() (*docker.Client, error) {
return docker.NewClient(endpoint)
}

certPath := c.DockerCertPath
// expand if the path starts with "~/"
if strings.HasPrefix(certPath, "~/") {
home, err := homedir.Dir()
if err != nil {
return nil, fmt.Errorf("Cannot detect home directory: %v", err)
}
certPath = filepath.Join(home, certPath[2:])
}

var (
cert = filepath.Join(certPath, "cert.pem")
key = filepath.Join(certPath, "key.pem")
ca = filepath.Join(certPath, "ca.pem")
)
cert, key, ca := c.certFilePaths()
return docker.NewTLSClient(endpoint, cert, key, ca)
}

Expand Down Expand Up @@ -220,6 +210,63 @@ and DockerPort:
return true
}

func (c *Config) certFilePaths() (cert, key, ca string) {
certPath := c.DockerCertPath
// expand if the path starts with "~"
if strings.HasPrefix(certPath, "~") {
home, err := homedir.Dir()
if err != nil {
return "", "", ""
}
certPath = filepath.Join(home, certPath[1:])
}

cert = filepath.Join(certPath, "cert.pem")
key = filepath.Join(certPath, "key.pem")
ca = filepath.Join(certPath, "ca.pem")
return cert, key, ca
}

func (c *Config) setTLSConfig() error {
cert, key, ca := c.certFilePaths()

certPEMBlock, err := ioutil.ReadFile(cert)
if err != nil {
return err
}
keyPEMBlock, err := ioutil.ReadFile(key)
if err != nil {
return err
}
caPEMCert, err := ioutil.ReadFile(ca)
if err != nil {
return err
}

if certPEMBlock == nil || keyPEMBlock == nil {
return errors.New("Both cert and key are required")
}

tlsCert, err := tls.X509KeyPair(certPEMBlock, keyPEMBlock)
if err != nil {
return err
}

tlsConfig := &tls.Config{Certificates: []tls.Certificate{tlsCert}}
if caPEMCert == nil {
tlsConfig.InsecureSkipVerify = true
} else {
caPool := x509.NewCertPool()
if !caPool.AppendCertsFromPEM(caPEMCert) {
return errors.New("Could not add RootCA pem")
}
tlsConfig.RootCAs = caPool
}

c.tlsConfig = tlsConfig
return nil
}

func NewConfig(configPath string) (*Config, error) {
var err error
if configPath == "" {
Expand Down Expand Up @@ -257,5 +304,13 @@ func NewConfig(configPath string) (*Config, error) {
if _, err := toml.DecodeFile(configPath, &config); err != nil {
return config, err
}

if config.DockerServerUseHttps {
// read certificate files and hold it
if err := config.setTLSConfig(); err != nil {
return config, err
}
}

return config, nil
}
10 changes: 8 additions & 2 deletions container.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package codetainer

import (
"bytes"
"crypto/tls"
"net"
"net/http"
"net/url"
Expand Down Expand Up @@ -120,13 +121,18 @@ func (c *ContainerConnection) openSocketToContainer() error {
return err
}

rawConn, err := net.Dial("tcp", u.Host)
var rawConn net.Conn
if GlobalConfig.DockerServerUseHttps {
rawConn, err = tls.Dial("tcp", u.Host, GlobalConfig.tlsConfig)
} else {
rawConn, err = net.Dial("tcp", u.Host)
}
if err != nil {
return err
}

wsHeaders := http.Header{
"Origin": {"http://localhost:4500"},
"Origin": {endpoint},
}

wsConn, resp, err := websocket.NewClient(rawConn, u, wsHeaders, 1024, 1024)
Expand Down

0 comments on commit 76cde5b

Please sign in to comment.