github.com/anuvu/tyk@v2.9.0-beta9-dl-apic+incompatible/gateway/cert_test.go (about)

     1  package gateway
     2  
     3  import (
     4  	"bytes"
     5  	"crypto/rand"
     6  	"crypto/rsa"
     7  	"crypto/tls"
     8  	"crypto/x509"
     9  	"encoding/pem"
    10  	"fmt"
    11  	"io/ioutil"
    12  	"math/big"
    13  	"net"
    14  	"net/http"
    15  	"net/http/httptest"
    16  	"os"
    17  	"path/filepath"
    18  	"testing"
    19  	"time"
    20  
    21  	"github.com/TykTechnologies/tyk/apidef"
    22  	"github.com/TykTechnologies/tyk/certs"
    23  	"github.com/TykTechnologies/tyk/config"
    24  	"github.com/TykTechnologies/tyk/test"
    25  	"github.com/TykTechnologies/tyk/user"
    26  )
    27  
    28  func getTLSClient(cert *tls.Certificate, caCert []byte) *http.Client {
    29  	// Setup HTTPS client
    30  	tlsConfig := &tls.Config{}
    31  
    32  	if cert != nil {
    33  		tlsConfig.Certificates = []tls.Certificate{*cert}
    34  	}
    35  
    36  	if len(caCert) > 0 {
    37  		caCertPool := x509.NewCertPool()
    38  		caCertPool.AppendCertsFromPEM(caCert)
    39  		tlsConfig.RootCAs = caCertPool
    40  		tlsConfig.BuildNameToCertificate()
    41  	} else {
    42  		tlsConfig.InsecureSkipVerify = true
    43  	}
    44  
    45  	transport := &http.Transport{TLSClientConfig: tlsConfig}
    46  
    47  	return &http.Client{Transport: transport}
    48  }
    49  
    50  func genCertificate(template *x509.Certificate) ([]byte, []byte, []byte, tls.Certificate) {
    51  	priv, _ := rsa.GenerateKey(rand.Reader, 512)
    52  
    53  	serialNumberLimit := new(big.Int).Lsh(big.NewInt(1), 128)
    54  	serialNumber, _ := rand.Int(rand.Reader, serialNumberLimit)
    55  	template.SerialNumber = serialNumber
    56  	template.BasicConstraintsValid = true
    57  	template.NotBefore = time.Now()
    58  	template.NotAfter = template.NotBefore.Add(time.Hour)
    59  
    60  	derBytes, _ := x509.CreateCertificate(rand.Reader, template, template, &priv.PublicKey, priv)
    61  
    62  	var certPem, keyPem bytes.Buffer
    63  	pem.Encode(&certPem, &pem.Block{Type: "CERTIFICATE", Bytes: derBytes})
    64  	pem.Encode(&keyPem, &pem.Block{Type: "RSA PRIVATE KEY", Bytes: x509.MarshalPKCS1PrivateKey(priv)})
    65  
    66  	clientCert, _ := tls.X509KeyPair(certPem.Bytes(), keyPem.Bytes())
    67  
    68  	combinedPEM := bytes.Join([][]byte{certPem.Bytes(), keyPem.Bytes()}, []byte("\n"))
    69  
    70  	return certPem.Bytes(), keyPem.Bytes(), combinedPEM, clientCert
    71  }
    72  
    73  func genServerCertificate() ([]byte, []byte, []byte, tls.Certificate) {
    74  	certPem, privPem, combinedPEM, cert := genCertificate(&x509.Certificate{
    75  		DNSNames:    []string{"localhost"},
    76  		IPAddresses: []net.IP{net.ParseIP("127.0.0.1"), net.ParseIP("::")},
    77  	})
    78  
    79  	return certPem, privPem, combinedPEM, cert
    80  }
    81  
    82  const (
    83  	internalTLSErr = "tls: internal error"
    84  	badcertErr     = "tls: bad certificate"
    85  )
    86  
    87  func TestGatewayTLS(t *testing.T) {
    88  	// Configure server
    89  	serverCertPem, serverPrivPem, combinedPEM, _ := genServerCertificate()
    90  
    91  	dir, _ := ioutil.TempDir("", "certs")
    92  	defer os.RemoveAll(dir)
    93  
    94  	client := getTLSClient(nil, nil)
    95  
    96  	t.Run("Without certificates", func(t *testing.T) {
    97  		globalConf := config.Global()
    98  		globalConf.HttpServerOptions.UseSSL = true
    99  		config.SetGlobal(globalConf)
   100  		defer ResetTestConfig()
   101  
   102  		ts := StartTest()
   103  		defer ts.Close()
   104  
   105  		BuildAndLoadAPI(func(spec *APISpec) {
   106  			spec.Proxy.ListenPath = "/"
   107  		})
   108  
   109  		ts.Run(t, test.TestCase{ErrorMatch: internalTLSErr, Client: client})
   110  	})
   111  
   112  	t.Run("Legacy TLS certificate path", func(t *testing.T) {
   113  		certFilePath := filepath.Join(dir, "server.crt")
   114  		ioutil.WriteFile(certFilePath, serverCertPem, 0666)
   115  
   116  		certKeyPath := filepath.Join(dir, "server.key")
   117  		ioutil.WriteFile(certKeyPath, serverPrivPem, 0666)
   118  
   119  		globalConf := config.Global()
   120  		globalConf.HttpServerOptions.Certificates = []config.CertData{{
   121  			Name:     "localhost",
   122  			CertFile: certFilePath,
   123  			KeyFile:  certKeyPath,
   124  		}}
   125  		globalConf.HttpServerOptions.UseSSL = true
   126  		config.SetGlobal(globalConf)
   127  		defer ResetTestConfig()
   128  
   129  		ts := StartTest()
   130  		defer ts.Close()
   131  
   132  		BuildAndLoadAPI(func(spec *APISpec) {
   133  			spec.Proxy.ListenPath = "/"
   134  		})
   135  
   136  		ts.Run(t, test.TestCase{Code: 200, Client: client})
   137  
   138  		CertificateManager.FlushCache()
   139  	})
   140  
   141  	t.Run("File certificate path", func(t *testing.T) {
   142  		certPath := filepath.Join(dir, "server.pem")
   143  		ioutil.WriteFile(certPath, combinedPEM, 0666)
   144  
   145  		globalConf := config.Global()
   146  		globalConf.HttpServerOptions.SSLCertificates = []string{certPath}
   147  		globalConf.HttpServerOptions.UseSSL = true
   148  		config.SetGlobal(globalConf)
   149  		defer ResetTestConfig()
   150  
   151  		ts := StartTest()
   152  		defer ts.Close()
   153  
   154  		BuildAndLoadAPI(func(spec *APISpec) {
   155  			spec.Proxy.ListenPath = "/"
   156  		})
   157  
   158  		ts.Run(t, test.TestCase{Code: 200, Client: client})
   159  
   160  		CertificateManager.FlushCache()
   161  	})
   162  
   163  	t.Run("Redis certificate", func(t *testing.T) {
   164  		certID, err := CertificateManager.Add(combinedPEM, "")
   165  		if err != nil {
   166  			t.Fatal(err)
   167  		}
   168  		defer CertificateManager.Delete(certID)
   169  
   170  		globalConf := config.Global()
   171  		globalConf.HttpServerOptions.SSLCertificates = []string{certID}
   172  		globalConf.HttpServerOptions.UseSSL = true
   173  		config.SetGlobal(globalConf)
   174  		defer ResetTestConfig()
   175  
   176  		ts := StartTest()
   177  		defer ts.Close()
   178  
   179  		BuildAndLoadAPI(func(spec *APISpec) {
   180  			spec.Proxy.ListenPath = "/"
   181  		})
   182  
   183  		ts.Run(t, test.TestCase{Code: 200, Client: client})
   184  
   185  		CertificateManager.FlushCache()
   186  	})
   187  }
   188  
   189  func TestGatewayControlAPIMutualTLS(t *testing.T) {
   190  	// Configure server
   191  	serverCertPem, _, combinedPEM, _ := genServerCertificate()
   192  
   193  	globalConf := config.Global()
   194  	globalConf.HttpServerOptions.UseSSL = true
   195  	globalConf.Security.ControlAPIUseMutualTLS = true
   196  	config.SetGlobal(globalConf)
   197  	defer ResetTestConfig()
   198  
   199  	dir, _ := ioutil.TempDir("", "certs")
   200  
   201  	defer func() {
   202  		os.RemoveAll(dir)
   203  		CertificateManager.FlushCache()
   204  	}()
   205  
   206  	clientCertPem, _, _, clientCert := genCertificate(&x509.Certificate{})
   207  	clientWithCert := getTLSClient(&clientCert, serverCertPem)
   208  
   209  	clientWithoutCert := getTLSClient(nil, nil)
   210  
   211  	t.Run("Separate domain", func(t *testing.T) {
   212  		certID, _ := CertificateManager.Add(combinedPEM, "")
   213  		defer CertificateManager.Delete(certID)
   214  
   215  		globalConf := config.Global()
   216  		globalConf.ControlAPIHostname = "localhost"
   217  		globalConf.HttpServerOptions.SSLCertificates = []string{certID}
   218  		config.SetGlobal(globalConf)
   219  
   220  		ts := StartTest()
   221  		defer ts.Close()
   222  
   223  		defer func() {
   224  			CertificateManager.FlushCache()
   225  			globalConf := config.Global()
   226  			globalConf.HttpServerOptions.SSLCertificates = nil
   227  			globalConf.Security.Certificates.ControlAPI = nil
   228  			config.SetGlobal(globalConf)
   229  		}()
   230  
   231  		unknownErr := "x509: certificate signed by unknown authority"
   232  		badcertErr := "tls: bad certificate"
   233  
   234  		ts.Run(t, []test.TestCase{
   235  			// Should acess tyk without client certificates
   236  			{Client: clientWithoutCert},
   237  			// Should raise error for ControlAPI without certificate
   238  			{ControlRequest: true, ErrorMatch: unknownErr},
   239  			// Should raise error for for unknown certificate
   240  			{ControlRequest: true, ErrorMatch: badcertErr, Client: clientWithCert},
   241  		}...)
   242  
   243  		clientCertID, _ := CertificateManager.Add(clientCertPem, "")
   244  		defer CertificateManager.Delete(clientCertID)
   245  
   246  		globalConf = config.Global()
   247  		globalConf.Security.Certificates.ControlAPI = []string{clientCertID}
   248  		config.SetGlobal(globalConf)
   249  
   250  		// Should pass request with valid client cert
   251  		ts.Run(t, test.TestCase{
   252  			Path: "/tyk/certs", Code: 200, ControlRequest: true, AdminAuth: true, Client: clientWithCert,
   253  		})
   254  	})
   255  }
   256  
   257  func TestAPIMutualTLS(t *testing.T) {
   258  	// Configure server
   259  	serverCertPem, _, combinedPEM, _ := genServerCertificate()
   260  	certID, _ := CertificateManager.Add(combinedPEM, "")
   261  	defer CertificateManager.Delete(certID)
   262  
   263  	globalConf := config.Global()
   264  	globalConf.EnableCustomDomains = true
   265  	globalConf.HttpServerOptions.UseSSL = true
   266  	globalConf.ListenPort = 0
   267  	globalConf.HttpServerOptions.SSLCertificates = []string{certID}
   268  	config.SetGlobal(globalConf)
   269  	defer ResetTestConfig()
   270  
   271  	ts := StartTest()
   272  	defer ts.Close()
   273  
   274  	// Initialize client certificates
   275  	clientCertPem, _, _, clientCert := genCertificate(&x509.Certificate{})
   276  
   277  	t.Run("SNI and domain per API", func(t *testing.T) {
   278  		t.Run("API without mutual TLS", func(t *testing.T) {
   279  			client := getTLSClient(&clientCert, serverCertPem)
   280  
   281  			BuildAndLoadAPI(func(spec *APISpec) {
   282  				spec.Domain = "localhost"
   283  				spec.Proxy.ListenPath = "/"
   284  			})
   285  
   286  			ts.Run(t, test.TestCase{Path: "/", Code: 200, Client: client, Domain: "localhost"})
   287  		})
   288  
   289  		t.Run("MutualTLSCertificate not set", func(t *testing.T) {
   290  			client := getTLSClient(nil, nil)
   291  
   292  			BuildAndLoadAPI(func(spec *APISpec) {
   293  				spec.Domain = "localhost"
   294  				spec.Proxy.ListenPath = "/"
   295  				spec.UseMutualTLSAuth = true
   296  			})
   297  
   298  			ts.Run(t, test.TestCase{
   299  				ErrorMatch: badcertErr,
   300  				Client:     client,
   301  				Domain:     "localhost",
   302  			})
   303  		})
   304  
   305  		t.Run("Client certificate match", func(t *testing.T) {
   306  			client := getTLSClient(&clientCert, serverCertPem)
   307  			clientCertID, _ := CertificateManager.Add(clientCertPem, "")
   308  
   309  			BuildAndLoadAPI(func(spec *APISpec) {
   310  				spec.Domain = "localhost"
   311  				spec.Proxy.ListenPath = "/"
   312  				spec.UseMutualTLSAuth = true
   313  				spec.ClientCertificates = []string{clientCertID}
   314  			})
   315  
   316  			ts.Run(t, test.TestCase{
   317  				Code: 200, Client: client, Domain: "localhost",
   318  			})
   319  
   320  			CertificateManager.Delete(clientCertID)
   321  			CertificateManager.FlushCache()
   322  
   323  			client = getTLSClient(&clientCert, serverCertPem)
   324  			ts.Run(t, test.TestCase{
   325  				Client: client, Domain: "localhost", ErrorMatch: badcertErr,
   326  			})
   327  		})
   328  
   329  		t.Run("Client certificate differ", func(t *testing.T) {
   330  			client := getTLSClient(&clientCert, serverCertPem)
   331  
   332  			clientCertPem2, _, _, _ := genCertificate(&x509.Certificate{})
   333  			clientCertID2, _ := CertificateManager.Add(clientCertPem2, "")
   334  			defer CertificateManager.Delete(clientCertID2)
   335  
   336  			BuildAndLoadAPI(func(spec *APISpec) {
   337  				spec.Domain = "localhost"
   338  				spec.Proxy.ListenPath = "/"
   339  				spec.UseMutualTLSAuth = true
   340  				spec.ClientCertificates = []string{clientCertID2}
   341  			})
   342  
   343  			ts.Run(t, test.TestCase{
   344  				Client: client, ErrorMatch: badcertErr, Domain: "localhost",
   345  			})
   346  		})
   347  	})
   348  
   349  	t.Run("Multiple APIs on same domain", func(t *testing.T) {
   350  		clientCertID, _ := CertificateManager.Add(clientCertPem, "")
   351  		defer CertificateManager.Delete(clientCertID)
   352  
   353  		loadAPIS := func(certs ...string) {
   354  			BuildAndLoadAPI(
   355  				func(spec *APISpec) {
   356  					spec.Proxy.ListenPath = "/with_mutual"
   357  					spec.UseMutualTLSAuth = true
   358  					spec.ClientCertificates = certs
   359  				},
   360  				func(spec *APISpec) {
   361  					spec.Proxy.ListenPath = "/without_mutual"
   362  				},
   363  			)
   364  		}
   365  
   366  		t.Run("Without certificate", func(t *testing.T) {
   367  			clientWithoutCert := getTLSClient(nil, nil)
   368  
   369  			loadAPIS()
   370  
   371  			certNotMatchErr := "Client TLS certificate is required"
   372  			ts.Run(t, []test.TestCase{
   373  				{
   374  					Path:      "/with_mutual",
   375  					Client:    clientWithoutCert,
   376  					Code:      403,
   377  					BodyMatch: `"error": "` + certNotMatchErr,
   378  				},
   379  				{
   380  					Path:   "/without_mutual",
   381  					Client: clientWithoutCert,
   382  					Code:   200,
   383  				},
   384  			}...)
   385  		})
   386  
   387  		t.Run("Client certificate not match", func(t *testing.T) {
   388  			client := getTLSClient(&clientCert, serverCertPem)
   389  
   390  			loadAPIS()
   391  
   392  			certNotAllowedErr := `Certificate with SHA256 ` + certs.HexSHA256(clientCert.Certificate[0]) + ` not allowed`
   393  
   394  			ts.Run(t, test.TestCase{
   395  				Path:      "/with_mutual",
   396  				Client:    client,
   397  				Code:      403,
   398  				BodyMatch: `"error": "` + certNotAllowedErr,
   399  			})
   400  		})
   401  
   402  		t.Run("Client certificate match", func(t *testing.T) {
   403  			loadAPIS(clientCertID)
   404  			client := getTLSClient(&clientCert, serverCertPem)
   405  
   406  			ts.Run(t, test.TestCase{
   407  				Path:   "/with_mutual",
   408  				Client: client,
   409  				Code:   200,
   410  			})
   411  		})
   412  	})
   413  }
   414  
   415  func TestUpstreamMutualTLS(t *testing.T) {
   416  	_, _, combinedClientPEM, clientCert := genCertificate(&x509.Certificate{})
   417  	clientCert.Leaf, _ = x509.ParseCertificate(clientCert.Certificate[0])
   418  
   419  	upstream := httptest.NewUnstartedServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
   420  	}))
   421  
   422  	// Mutual TLS protected upstream
   423  	pool := x509.NewCertPool()
   424  	upstream.TLS = &tls.Config{
   425  		ClientAuth:         tls.RequireAndVerifyClientCert,
   426  		ClientCAs:          pool,
   427  		InsecureSkipVerify: true,
   428  	}
   429  
   430  	upstream.StartTLS()
   431  	defer upstream.Close()
   432  
   433  	t.Run("Without API", func(t *testing.T) {
   434  		client := getTLSClient(&clientCert, nil)
   435  
   436  		if _, err := client.Get(upstream.URL); err == nil {
   437  			t.Error("Should reject without certificate")
   438  		}
   439  
   440  		pool.AddCert(clientCert.Leaf)
   441  
   442  		if _, err := client.Get(upstream.URL); err != nil {
   443  			t.Error("Should pass with valid certificate")
   444  		}
   445  	})
   446  
   447  	t.Run("Upstream API", func(t *testing.T) {
   448  		globalConf := config.Global()
   449  		globalConf.ProxySSLInsecureSkipVerify = true
   450  		config.SetGlobal(globalConf)
   451  		defer ResetTestConfig()
   452  
   453  		ts := StartTest()
   454  		defer ts.Close()
   455  
   456  		clientCertID, _ := CertificateManager.Add(combinedClientPEM, "")
   457  		defer CertificateManager.Delete(clientCertID)
   458  
   459  		pool.AddCert(clientCert.Leaf)
   460  
   461  		BuildAndLoadAPI(func(spec *APISpec) {
   462  			spec.Proxy.ListenPath = "/"
   463  			spec.Proxy.TargetURL = upstream.URL
   464  			spec.UpstreamCertificates = map[string]string{
   465  				"*": clientCertID,
   466  			}
   467  		})
   468  
   469  		// Should pass with valid upstream certificate
   470  		ts.Run(t, test.TestCase{Code: 200})
   471  	})
   472  }
   473  
   474  func TestKeyWithCertificateTLS(t *testing.T) {
   475  	_, _, combinedPEM, _ := genServerCertificate()
   476  	serverCertID, _ := CertificateManager.Add(combinedPEM, "")
   477  	defer CertificateManager.Delete(serverCertID)
   478  
   479  	_, _, _, clientCert := genCertificate(&x509.Certificate{})
   480  	clientCertID := certs.HexSHA256(clientCert.Certificate[0])
   481  
   482  	globalConf := config.Global()
   483  	globalConf.HttpServerOptions.UseSSL = true
   484  	globalConf.HttpServerOptions.SSLCertificates = []string{serverCertID}
   485  	config.SetGlobal(globalConf)
   486  	defer ResetTestConfig()
   487  
   488  	ts := StartTest()
   489  	defer ts.Close()
   490  
   491  	BuildAndLoadAPI(func(spec *APISpec) {
   492  		spec.UseKeylessAccess = false
   493  		spec.BaseIdentityProvidedBy = apidef.AuthToken
   494  		spec.Auth.UseCertificate = true
   495  		spec.Proxy.ListenPath = "/"
   496  	})
   497  
   498  	client := getTLSClient(&clientCert, nil)
   499  
   500  	t.Run("Cert unknown", func(t *testing.T) {
   501  		ts.Run(t, test.TestCase{Code: 403, Client: client})
   502  	})
   503  
   504  	t.Run("Cert known", func(t *testing.T) {
   505  		CreateSession(func(s *user.SessionState) {
   506  			s.Certificate = clientCertID
   507  			s.AccessRights = map[string]user.AccessDefinition{"test": {
   508  				APIID: "test", Versions: []string{"v1"},
   509  			}}
   510  		})
   511  
   512  		ts.Run(t, test.TestCase{Path: "/", Code: 200, Client: client})
   513  	})
   514  }
   515  
   516  func TestAPICertificate(t *testing.T) {
   517  	_, _, combinedPEM, _ := genServerCertificate()
   518  	serverCertID, _ := CertificateManager.Add(combinedPEM, "")
   519  	defer CertificateManager.Delete(serverCertID)
   520  
   521  	globalConf := config.Global()
   522  	globalConf.HttpServerOptions.UseSSL = true
   523  	globalConf.HttpServerOptions.SSLCertificates = []string{}
   524  	config.SetGlobal(globalConf)
   525  	defer ResetTestConfig()
   526  
   527  	ts := StartTest()
   528  	defer ts.Close()
   529  
   530  	client := &http.Client{Transport: &http.Transport{TLSClientConfig: &tls.Config{
   531  		InsecureSkipVerify: true,
   532  	}}}
   533  
   534  	t.Run("Cert set via API", func(t *testing.T) {
   535  		BuildAndLoadAPI(func(spec *APISpec) {
   536  			spec.Certificates = []string{serverCertID}
   537  			spec.UseKeylessAccess = true
   538  			spec.Proxy.ListenPath = "/"
   539  		})
   540  
   541  		ts.Run(t, test.TestCase{Code: 200, Client: client})
   542  	})
   543  
   544  	t.Run("Cert unknown", func(t *testing.T) {
   545  		BuildAndLoadAPI(func(spec *APISpec) {
   546  			spec.UseKeylessAccess = true
   547  			spec.Proxy.ListenPath = "/"
   548  		})
   549  
   550  		ts.Run(t, test.TestCase{ErrorMatch: "tls: internal error"})
   551  	})
   552  }
   553  
   554  func TestCertificateHandlerTLS(t *testing.T) {
   555  	_, _, combinedServerPEM, serverCert := genServerCertificate()
   556  	serverCertID := certs.HexSHA256(serverCert.Certificate[0])
   557  
   558  	clientPEM, _, _, clientCert := genCertificate(&x509.Certificate{})
   559  	clientCertID := certs.HexSHA256(clientCert.Certificate[0])
   560  
   561  	ts := StartTest()
   562  	defer ts.Close()
   563  
   564  	t.Run("List certificates, empty", func(t *testing.T) {
   565  		ts.Run(t, test.TestCase{
   566  			Path: "/tyk/certs", Code: 200, AdminAuth: true, BodyMatch: `{"certs":null}`,
   567  		})
   568  	})
   569  
   570  	t.Run("Should add certificates with and without private keys", func(t *testing.T) {
   571  		ts.Run(t, []test.TestCase{
   572  			// Public Certificate
   573  			{Method: "POST", Path: "/tyk/certs", Data: string(clientPEM), AdminAuth: true, Code: 200, BodyMatch: `"id":"` + clientCertID},
   574  			// Public + Private
   575  			{Method: "POST", Path: "/tyk/certs", Data: string(combinedServerPEM), AdminAuth: true, Code: 200, BodyMatch: `"id":"` + serverCertID},
   576  		}...)
   577  	})
   578  
   579  	t.Run("List certificates, non empty", func(t *testing.T) {
   580  		ts.Run(t, []test.TestCase{
   581  			{Method: "GET", Path: "/tyk/certs", AdminAuth: true, Code: 200, BodyMatch: clientCertID},
   582  			{Method: "GET", Path: "/tyk/certs", AdminAuth: true, Code: 200, BodyMatch: serverCertID},
   583  		}...)
   584  	})
   585  
   586  	certMetaTemplate := `{"id":"%s","fingerprint":"%s","has_private":%s`
   587  
   588  	t.Run("Certificate meta info", func(t *testing.T) {
   589  		clientCertMeta := fmt.Sprintf(certMetaTemplate, clientCertID, clientCertID, "false")
   590  		serverCertMeta := fmt.Sprintf(certMetaTemplate, serverCertID, serverCertID, "true")
   591  
   592  		ts.Run(t, []test.TestCase{
   593  			{Method: "GET", Path: "/tyk/certs/" + clientCertID, AdminAuth: true, Code: 200, BodyMatch: clientCertMeta},
   594  			{Method: "GET", Path: "/tyk/certs/" + serverCertID, AdminAuth: true, Code: 200, BodyMatch: serverCertMeta},
   595  			{Method: "GET", Path: "/tyk/certs/" + serverCertID + "," + clientCertID, AdminAuth: true, Code: 200, BodyMatch: "[" + serverCertMeta},
   596  			{Method: "GET", Path: "/tyk/certs/" + serverCertID + "," + clientCertID, AdminAuth: true, Code: 200, BodyMatch: clientCertMeta},
   597  		}...)
   598  	})
   599  
   600  	t.Run("Certificate removal", func(t *testing.T) {
   601  		ts.Run(t, []test.TestCase{
   602  			{Method: "DELETE", Path: "/tyk/certs/" + serverCertID, AdminAuth: true, Code: 200},
   603  			{Method: "DELETE", Path: "/tyk/certs/" + clientCertID, AdminAuth: true, Code: 200},
   604  			{Method: "GET", Path: "/tyk/certs", AdminAuth: true, Code: 200, BodyMatch: `{"certs":null}`},
   605  		}...)
   606  	})
   607  }
   608  
   609  func TestCipherSuites(t *testing.T) {
   610  	//configure server so we can useSSL and utilize the logic, but skip verification in the clients
   611  	_, _, combinedPEM, _ := genServerCertificate()
   612  	serverCertID, _ := CertificateManager.Add(combinedPEM, "")
   613  	defer CertificateManager.Delete(serverCertID)
   614  
   615  	globalConf := config.Global()
   616  	globalConf.HttpServerOptions.UseSSL = true
   617  	globalConf.HttpServerOptions.Ciphers = []string{"TLS_RSA_WITH_RC4_128_SHA", "TLS_RSA_WITH_3DES_EDE_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA"}
   618  	globalConf.HttpServerOptions.SSLCertificates = []string{serverCertID}
   619  	config.SetGlobal(globalConf)
   620  	defer ResetTestConfig()
   621  
   622  	ts := StartTest()
   623  	defer ts.Close()
   624  
   625  	BuildAndLoadAPI(func(spec *APISpec) {
   626  		spec.Proxy.ListenPath = "/"
   627  	})
   628  
   629  	//matching ciphers
   630  	t.Run("Cipher match", func(t *testing.T) {
   631  
   632  		client := &http.Client{Transport: &http.Transport{TLSClientConfig: &tls.Config{
   633  			CipherSuites:       getCipherAliases([]string{"TLS_RSA_WITH_RC4_128_SHA", "TLS_RSA_WITH_3DES_EDE_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA"}),
   634  			InsecureSkipVerify: true,
   635  		}}}
   636  
   637  		// If there is an internal TLS error it will fail test
   638  		ts.Run(t, test.TestCase{Client: client, Path: "/"})
   639  	})
   640  
   641  	t.Run("Cipher non-match", func(t *testing.T) {
   642  
   643  		client := &http.Client{Transport: &http.Transport{TLSClientConfig: &tls.Config{
   644  			CipherSuites:       getCipherAliases([]string{"TLS_RSA_WITH_AES_256_CBC_SHA"}), // not matching ciphers
   645  			InsecureSkipVerify: true,
   646  		}}}
   647  
   648  		ts.Run(t, test.TestCase{Client: client, Path: "/", ErrorMatch: "tls: handshake failure"})
   649  	})
   650  }