Avoid nginx reloads
This commit is contained in:
parent
5a8e090736
commit
42b58e957c
4 changed files with 20 additions and 26 deletions
|
@ -105,22 +105,18 @@ func (n NGINXController) Start() {
|
||||||
|
|
||||||
// Reload checks if the running configuration file is different
|
// Reload checks if the running configuration file is different
|
||||||
// to the specified and reload nginx if required
|
// to the specified and reload nginx if required
|
||||||
func (n NGINXController) Reload(data []byte) ([]byte, error) {
|
func (n NGINXController) Reload(data []byte) ([]byte, bool, error) {
|
||||||
if !n.isReloadRequired(data) {
|
if !n.isReloadRequired(data) {
|
||||||
return nil, fmt.Errorf("Reload not required")
|
return []byte("Reload not required"), false, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
err := ioutil.WriteFile(cfgPath, data, 0644)
|
err := ioutil.WriteFile(cfgPath, data, 0644)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return exec.Command(n.binary, "-s", "reload").CombinedOutput()
|
o, e := exec.Command(n.binary, "-s", "reload").CombinedOutput()
|
||||||
}
|
return o, true, e
|
||||||
|
|
||||||
// Test checks is a file contains a valid NGINX configuration
|
|
||||||
func (n NGINXController) Test(file string) *exec.Cmd {
|
|
||||||
return exec.Command(n.binary, "-t", "-c", file)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// BackendDefaults returns the nginx defaults
|
// BackendDefaults returns the nginx defaults
|
||||||
|
@ -188,7 +184,7 @@ func (n NGINXController) testTemplate(cfg []byte) error {
|
||||||
}
|
}
|
||||||
defer tmpfile.Close()
|
defer tmpfile.Close()
|
||||||
ioutil.WriteFile(tmpfile.Name(), cfg, 0644)
|
ioutil.WriteFile(tmpfile.Name(), cfg, 0644)
|
||||||
out, err := n.Test(tmpfile.Name()).CombinedOutput()
|
out, err := exec.Command(n.binary, "-t", "-c", tmpfile.Name()).CombinedOutput()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// this error is different from the rest because it must be clear why nginx is not working
|
// this error is different from the rest because it must be clear why nginx is not working
|
||||||
oe := fmt.Sprintf(`
|
oe := fmt.Sprintf(`
|
||||||
|
|
|
@ -89,9 +89,11 @@ func (ic *GenericController) syncSecret(k interface{}) error {
|
||||||
// create certificates and add or update the item in the store
|
// create certificates and add or update the item in the store
|
||||||
_, exists = ic.sslCertTracker.Get(key)
|
_, exists = ic.sslCertTracker.Get(key)
|
||||||
if exists {
|
if exists {
|
||||||
|
glog.V(3).Infof("updating secret %v/%v in the store ", sec.Namespace, sec.Name)
|
||||||
ic.sslCertTracker.Update(key, cert)
|
ic.sslCertTracker.Update(key, cert)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
glog.V(3).Infof("adding secret %v/%v to the store ", sec.Namespace, sec.Name)
|
||||||
ic.sslCertTracker.Add(key, cert)
|
ic.sslCertTracker.Add(key, cert)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
@ -99,7 +101,7 @@ func (ic *GenericController) syncSecret(k interface{}) error {
|
||||||
func (ic *GenericController) getPemCertificate(secretName string) (*ingress.SSLCert, error) {
|
func (ic *GenericController) getPemCertificate(secretName string) (*ingress.SSLCert, error) {
|
||||||
secretInterface, exists, err := ic.secrLister.Store.GetByKey(secretName)
|
secretInterface, exists, err := ic.secrLister.Store.GetByKey(secretName)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, fmt.Errorf("Error retriveing secret %v: %v", secretName, err)
|
return nil, fmt.Errorf("error retriveing secret %v: %v", secretName, err)
|
||||||
}
|
}
|
||||||
if !exists {
|
if !exists {
|
||||||
return nil, fmt.Errorf("secret named %v does not exists", secretName)
|
return nil, fmt.Errorf("secret named %v does not exists", secretName)
|
||||||
|
|
|
@ -386,14 +386,16 @@ func (ic *GenericController) sync(key interface{}) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
out, err := ic.cfg.Backend.Reload(data)
|
out, reloaded, err := ic.cfg.Backend.Reload(data)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
incReloadErrorCount()
|
incReloadErrorCount()
|
||||||
glog.Errorf("unexpected failure restarting the backend: \n%v", string(out))
|
glog.Errorf("unexpected failure restarting the backend: \n%v", string(out))
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
if reloaded {
|
||||||
glog.Infof("ingress backend successfully reloaded...")
|
glog.Infof("ingress backend successfully reloaded...")
|
||||||
incReloadCount()
|
incReloadCount()
|
||||||
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -686,7 +688,6 @@ func (ic *GenericController) getBackendServers() ([]*ingress.Backend, []*ingress
|
||||||
loc.BasicDigestAuth = *nginxAuth
|
loc.BasicDigestAuth = *nginxAuth
|
||||||
loc.RateLimit = *rl
|
loc.RateLimit = *rl
|
||||||
loc.Redirect = *locRew
|
loc.Redirect = *locRew
|
||||||
//loc.SecureUpstream = secUpstream
|
|
||||||
loc.Whitelist = *wl
|
loc.Whitelist = *wl
|
||||||
loc.Backend = ups.Name
|
loc.Backend = ups.Name
|
||||||
loc.EnableCORS = eCORS
|
loc.EnableCORS = eCORS
|
||||||
|
@ -706,7 +707,6 @@ func (ic *GenericController) getBackendServers() ([]*ingress.Backend, []*ingress
|
||||||
BasicDigestAuth: *nginxAuth,
|
BasicDigestAuth: *nginxAuth,
|
||||||
RateLimit: *rl,
|
RateLimit: *rl,
|
||||||
Redirect: *locRew,
|
Redirect: *locRew,
|
||||||
//SecureUpstream: secUpstream,
|
|
||||||
Whitelist: *wl,
|
Whitelist: *wl,
|
||||||
EnableCORS: eCORS,
|
EnableCORS: eCORS,
|
||||||
ExternalAuth: ra,
|
ExternalAuth: ra,
|
||||||
|
@ -921,7 +921,7 @@ func (ic *GenericController) createServers(data []interface{}, upstreams map[str
|
||||||
host = defServerName
|
host = defServerName
|
||||||
}
|
}
|
||||||
|
|
||||||
// only add certificate if the server does not have one previously configured
|
// only add a certificate if the server does not have one previously configured
|
||||||
if len(ing.Spec.TLS) > 0 && servers[host].SSLCertificate != "" {
|
if len(ing.Spec.TLS) > 0 && servers[host].SSLCertificate != "" {
|
||||||
key := fmt.Sprintf("%v/%v", ing.Namespace, ing.Spec.TLS[0].SecretName)
|
key := fmt.Sprintf("%v/%v", ing.Namespace, ing.Spec.TLS[0].SecretName)
|
||||||
bc, exists := ic.sslCertTracker.Get(key)
|
bc, exists := ic.sslCertTracker.Get(key)
|
||||||
|
@ -1048,8 +1048,8 @@ func (ic GenericController) Start() {
|
||||||
go ic.secrController.Run(ic.stopCh)
|
go ic.secrController.Run(ic.stopCh)
|
||||||
go ic.mapController.Run(ic.stopCh)
|
go ic.mapController.Run(ic.stopCh)
|
||||||
|
|
||||||
go ic.secretQueue.Run(time.Second, ic.stopCh)
|
go ic.secretQueue.Run(5*time.Second, ic.stopCh)
|
||||||
go ic.syncQueue.Run(time.Second, ic.stopCh)
|
go ic.syncQueue.Run(5*time.Second, ic.stopCh)
|
||||||
|
|
||||||
go ic.syncStatus.Run(ic.stopCh)
|
go ic.syncStatus.Run(ic.stopCh)
|
||||||
|
|
||||||
|
|
|
@ -17,8 +17,6 @@ limitations under the License.
|
||||||
package ingress
|
package ingress
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"os/exec"
|
|
||||||
|
|
||||||
"k8s.io/kubernetes/pkg/api"
|
"k8s.io/kubernetes/pkg/api"
|
||||||
|
|
||||||
"k8s.io/ingress/core/pkg/ingress/annotations/auth"
|
"k8s.io/ingress/core/pkg/ingress/annotations/auth"
|
||||||
|
@ -43,15 +41,13 @@ var (
|
||||||
// TODO (#18): Make sure this is sufficiently supportive of other backends.
|
// TODO (#18): Make sure this is sufficiently supportive of other backends.
|
||||||
type Controller interface {
|
type Controller interface {
|
||||||
// Reload takes a byte array representing the new loadbalancer configuration,
|
// Reload takes a byte array representing the new loadbalancer configuration,
|
||||||
// and returns a byte array containing any output/errors from the backend.
|
// and returns a byte array containing any output/errors from the backend and
|
||||||
|
// if a reload was required.
|
||||||
// Before returning the backend must load the configuration in the given array
|
// Before returning the backend must load the configuration in the given array
|
||||||
// into the loadbalancer and restart it, or fail with an error and message string.
|
// into the loadbalancer and restart it, or fail with an error and message string.
|
||||||
// If reloading fails, there should be not change in the running configuration or
|
// If reloading fails, there should be not change in the running configuration or
|
||||||
// the given byte array.
|
// the given byte array.
|
||||||
Reload(data []byte) ([]byte, error)
|
Reload(data []byte) ([]byte, bool, error)
|
||||||
// Tests returns the commands to execute that verifies if the configuration file is valid
|
|
||||||
// Example: nginx -t -c <file>
|
|
||||||
Test(file string) *exec.Cmd
|
|
||||||
// OnUpdate callback invoked from the sync queue https://k8s.io/ingress/core/blob/master/pkg/ingress/controller/controller.go#L387
|
// OnUpdate callback invoked from the sync queue https://k8s.io/ingress/core/blob/master/pkg/ingress/controller/controller.go#L387
|
||||||
// when an update occurs. This is executed frequently because Ingress
|
// when an update occurs. This is executed frequently because Ingress
|
||||||
// controllers watches changes in:
|
// controllers watches changes in:
|
||||||
|
|
Loading…
Reference in a new issue