mirror of
https://github.com/oauth2-proxy/oauth2-proxy.git
synced 2025-02-11 13:53:07 +02:00
Initalize TLS.Config when connecting to Redis with TLS (#1296)
* init TLS.Config when connecting to Redis with TLS * don't overwrite TLS config if it exists * add tests for Redis with TLS * remove hardcoded certs * add GenerateCert func * use GenerateCert util func * fix issue reported by go fmt * limit return statements in GenerateCert
This commit is contained in:
parent
ea261ca014
commit
b49e62f9b2
@ -47,6 +47,7 @@
|
||||
- [#1357](https://github.com/oauth2-proxy/oauth2-proxy/pull/1357) Fix unsafe access to session variable (@harzallah)
|
||||
- [#997](https://github.com/oauth2-proxy/oauth2-proxy/pull/997) Allow passing the raw url path when proxying upstream requests - e.g. /%2F/ (@FStelzer)
|
||||
- [#1147](https://github.com/oauth2-proxy/oauth2-proxy/pull/1147) Multiarch support for docker image (@goshlanguage)
|
||||
- [#1296](https://github.com/oauth2-proxy/oauth2-proxy/pull/1296) Fixed `panic` when connecting to Redis with TLS (@mstrzele)
|
||||
|
||||
# V7.1.3
|
||||
|
||||
|
@ -2,20 +2,15 @@ package http
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto/rand"
|
||||
"crypto/rsa"
|
||||
"crypto/tls"
|
||||
"crypto/x509"
|
||||
"crypto/x509/pkix"
|
||||
"encoding/pem"
|
||||
"math/big"
|
||||
"net"
|
||||
"net/http"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/apis/options"
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/logger"
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/util"
|
||||
. "github.com/onsi/ginkgo"
|
||||
. "github.com/onsi/gomega"
|
||||
)
|
||||
@ -34,38 +29,16 @@ func TestHTTPSuite(t *testing.T) {
|
||||
|
||||
var _ = BeforeSuite(func() {
|
||||
By("Generating a self-signed cert for TLS tests", func() {
|
||||
priv, err := rsa.GenerateKey(rand.Reader, 2048)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
keyOut := bytes.NewBuffer(nil)
|
||||
privBytes, err := x509.MarshalPKCS8PrivateKey(priv)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(pem.Encode(keyOut, &pem.Block{Type: "PRIVATE KEY", Bytes: privBytes})).To(Succeed())
|
||||
keyDataSource.Value = keyOut.Bytes()
|
||||
|
||||
serialNumberLimit := new(big.Int).Lsh(big.NewInt(1), 128)
|
||||
serialNumber, err := rand.Int(rand.Reader, serialNumberLimit)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
template := x509.Certificate{
|
||||
SerialNumber: serialNumber,
|
||||
Subject: pkix.Name{
|
||||
Organization: []string{"OAuth2 Proxy Test Suite"},
|
||||
},
|
||||
NotBefore: time.Now(),
|
||||
NotAfter: time.Now().Add(time.Hour),
|
||||
IPAddresses: []net.IP{net.ParseIP("127.0.0.1")},
|
||||
KeyUsage: x509.KeyUsageDigitalSignature | x509.KeyUsageKeyEncipherment,
|
||||
ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
|
||||
}
|
||||
|
||||
certBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &priv.PublicKey, priv)
|
||||
certBytes, keyBytes, err := util.GenerateCert()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
certData = certBytes
|
||||
|
||||
certOut := bytes.NewBuffer(nil)
|
||||
certOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: certBytes})).To(Succeed())
|
||||
certDataSource.Value = certOut.Bytes()
|
||||
keyOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(keyOut, &pem.Block{Type: "PRIVATE KEY", Bytes: keyBytes})).To(Succeed())
|
||||
keyDataSource.Value = keyOut.Bytes()
|
||||
})
|
||||
|
||||
By("Setting up a http client", func() {
|
||||
|
@ -2,6 +2,7 @@ package redis
|
||||
|
||||
import (
|
||||
"context"
|
||||
"crypto/tls"
|
||||
"crypto/x509"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
@ -127,6 +128,11 @@ func buildStandaloneClient(opts options.RedisStoreOptions) (Client, error) {
|
||||
}
|
||||
|
||||
if opts.InsecureSkipTLSVerify {
|
||||
if opt.TLSConfig == nil {
|
||||
/* #nosec */
|
||||
opt.TLSConfig = &tls.Config{}
|
||||
}
|
||||
|
||||
opt.TLSConfig.InsecureSkipVerify = true
|
||||
}
|
||||
|
||||
@ -148,6 +154,11 @@ func buildStandaloneClient(opts options.RedisStoreOptions) (Client, error) {
|
||||
logger.Errorf("no certs appended, using system certs only")
|
||||
}
|
||||
|
||||
if opt.TLSConfig == nil {
|
||||
/* #nosec */
|
||||
opt.TLSConfig = &tls.Config{}
|
||||
}
|
||||
|
||||
opt.TLSConfig.RootCAs = rootCAs
|
||||
}
|
||||
|
||||
|
@ -1,7 +1,10 @@
|
||||
package redis
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"crypto/tls"
|
||||
"encoding/pem"
|
||||
"log"
|
||||
"os"
|
||||
"testing"
|
||||
@ -15,6 +18,7 @@ import (
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/logger"
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/sessions/persistence"
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/sessions/tests"
|
||||
"github.com/oauth2-proxy/oauth2-proxy/v7/pkg/util"
|
||||
. "github.com/onsi/ginkgo"
|
||||
. "github.com/onsi/gomega"
|
||||
)
|
||||
@ -224,4 +228,104 @@ var _ = Describe("Redis SessionStore Tests", func() {
|
||||
)
|
||||
})
|
||||
})
|
||||
|
||||
Context("with custom CA path", func() {
|
||||
var caPath string
|
||||
|
||||
BeforeEach(func() {
|
||||
certBytes, keyBytes, err := util.GenerateCert()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
certOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: certBytes})).To(Succeed())
|
||||
certData := certOut.Bytes()
|
||||
keyOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(keyOut, &pem.Block{Type: "PRIVATE KEY", Bytes: keyBytes})).To(Succeed())
|
||||
cert, err := tls.X509KeyPair(certData, keyOut.Bytes())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
certFile, err := os.CreateTemp("", "cert.*.pem")
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
caPath = certFile.Name()
|
||||
_, err = certFile.Write(certData)
|
||||
defer certFile.Close()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
mr.Close()
|
||||
|
||||
mr, err = miniredis.RunTLS(&tls.Config{Certificates: []tls.Certificate{cert}})
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
AfterEach(func() {
|
||||
Expect(os.Remove(caPath)).ToNot(HaveOccurred())
|
||||
|
||||
mr.Close()
|
||||
|
||||
var err error
|
||||
mr, err = miniredis.Run()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
tests.RunSessionStoreTests(
|
||||
func(opts *options.SessionOptions, cookieOpts *options.Cookie) (sessionsapi.SessionStore, error) {
|
||||
// Set the connection URL
|
||||
opts.Type = options.RedisSessionStoreType
|
||||
opts.Redis.ConnectionURL = "redis://" + mr.Addr()
|
||||
opts.Redis.CAPath = caPath
|
||||
|
||||
// Capture the session store so that we can close the client
|
||||
var err error
|
||||
ss, err = NewRedisSessionStore(opts, cookieOpts)
|
||||
return ss, err
|
||||
},
|
||||
func(d time.Duration) error {
|
||||
mr.FastForward(d)
|
||||
return nil
|
||||
},
|
||||
)
|
||||
})
|
||||
|
||||
Context("with insecure TLS connection", func() {
|
||||
BeforeEach(func() {
|
||||
certBytes, keyBytes, err := util.GenerateCert()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
certOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: certBytes})).To(Succeed())
|
||||
keyOut := new(bytes.Buffer)
|
||||
Expect(pem.Encode(keyOut, &pem.Block{Type: "PRIVATE KEY", Bytes: keyBytes})).To(Succeed())
|
||||
cert, err := tls.X509KeyPair(certOut.Bytes(), keyOut.Bytes())
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
mr.Close()
|
||||
|
||||
mr, err = miniredis.RunTLS(&tls.Config{Certificates: []tls.Certificate{cert}})
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
AfterEach(func() {
|
||||
mr.Close()
|
||||
|
||||
var err error
|
||||
mr, err = miniredis.Run()
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
tests.RunSessionStoreTests(
|
||||
func(opts *options.SessionOptions, cookieOpts *options.Cookie) (sessionsapi.SessionStore, error) {
|
||||
// Set the connection URL
|
||||
opts.Type = options.RedisSessionStoreType
|
||||
opts.Redis.ConnectionURL = "redis://127.0.0.1:" + mr.Port() // func (*Miniredis) StartTLS listens on 127.0.0.1
|
||||
opts.Redis.InsecureSkipTLSVerify = true
|
||||
|
||||
// Capture the session store so that we can close the client
|
||||
var err error
|
||||
ss, err = NewRedisSessionStore(opts, cookieOpts)
|
||||
return ss, err
|
||||
},
|
||||
func(d time.Duration) error {
|
||||
mr.FastForward(d)
|
||||
return nil
|
||||
},
|
||||
)
|
||||
})
|
||||
})
|
||||
|
@ -1,9 +1,15 @@
|
||||
package util
|
||||
|
||||
import (
|
||||
"crypto/rand"
|
||||
"crypto/rsa"
|
||||
"crypto/x509"
|
||||
"crypto/x509/pkix"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"math/big"
|
||||
"net"
|
||||
"time"
|
||||
)
|
||||
|
||||
func GetCertPool(paths []string) (*x509.CertPool, error) {
|
||||
@ -23,3 +29,40 @@ func GetCertPool(paths []string) (*x509.CertPool, error) {
|
||||
}
|
||||
return pool, nil
|
||||
}
|
||||
|
||||
// https://golang.org/src/crypto/tls/generate_cert.go as a function
|
||||
func GenerateCert() ([]byte, []byte, error) {
|
||||
var err error
|
||||
|
||||
priv, err := rsa.GenerateKey(rand.Reader, 2048)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
keyBytes, err := x509.MarshalPKCS8PrivateKey(priv)
|
||||
if err != nil {
|
||||
return nil, keyBytes, err
|
||||
}
|
||||
|
||||
serialNumber, err := rand.Int(rand.Reader, new(big.Int).Lsh(big.NewInt(1), 128))
|
||||
if err != nil {
|
||||
return nil, keyBytes, err
|
||||
}
|
||||
|
||||
notBefore := time.Now()
|
||||
template := x509.Certificate{
|
||||
SerialNumber: serialNumber,
|
||||
Subject: pkix.Name{
|
||||
Organization: []string{"OAuth2 Proxy Test Suite"},
|
||||
},
|
||||
NotBefore: notBefore,
|
||||
NotAfter: notBefore.Add(time.Hour),
|
||||
KeyUsage: x509.KeyUsageDigitalSignature | x509.KeyUsageKeyEncipherment,
|
||||
|
||||
ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
|
||||
|
||||
IPAddresses: []net.IP{net.ParseIP("127.0.0.1")},
|
||||
}
|
||||
certBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &priv.PublicKey, priv)
|
||||
return certBytes, keyBytes, err
|
||||
}
|
||||
|
@ -1,3 +1,4 @@
|
||||
//go:build go1.3 && !plan9 && !solaris
|
||||
// +build go1.3,!plan9,!solaris
|
||||
|
||||
package main
|
||||
|
@ -1,3 +1,4 @@
|
||||
//go:build !go1.3 || plan9 || solaris
|
||||
// +build !go1.3 plan9 solaris
|
||||
|
||||
package main
|
||||
|
Loading…
x
Reference in New Issue
Block a user