From 5e01570ad49c2d6e677dcbcf97f12c3dd9c41bb5 Mon Sep 17 00:00:00 2001 From: Ivan Kozlovic Date: Thu, 2 May 2019 15:49:56 -0600 Subject: [PATCH] Fixed failed configuration reload due to present of leafnode with TLS We don't support reload of leafnode config yet, but we need to make sure it does not fail the reload process if nothing has been changed. (it would fail because TLSConfig internally do change in some cases) Signed-off-by: Ivan Kozlovic --- server/reload.go | 12 ++++++++ server/reload_test.go | 64 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 76 insertions(+) diff --git a/server/reload.go b/server/reload.go index d0d96f3737..223d57b949 100644 --- a/server/reload.go +++ b/server/reload.go @@ -723,6 +723,18 @@ func (s *Server) diffOptions(newOpts *Options) ([]option, error) { return nil, fmt.Errorf("config reload not supported for %s: old=%v, new=%v", field.Name, oldValue, newValue) } + case "leafnode": + // Similar to gateways + tmpOld := oldValue.(LeafNodeOpts) + tmpNew := newValue.(LeafNodeOpts) + tmpOld.TLSConfig = nil + tmpNew.TLSConfig = nil + // If there is really a change prevents reload. + if !reflect.DeepEqual(tmpOld, tmpNew) { + // See TODO(ik) note below about printing old/new values. + return nil, fmt.Errorf("config reload not supported for %s: old=%v, new=%v", + field.Name, oldValue, newValue) + } case "nolog", "nosigs": // Ignore NoLog and NoSigs options since they are not parsed and only used in // testing. diff --git a/server/reload_test.go b/server/reload_test.go index ec68f45e32..ddfaaa3584 100644 --- a/server/reload_test.go +++ b/server/reload_test.go @@ -21,6 +21,7 @@ import ( "fmt" "io/ioutil" "net" + "net/url" "os" "path/filepath" "reflect" @@ -3695,3 +3696,66 @@ func TestConfigReloadLeafNodeRandomPort(t *testing.T) { t.Fatalf("Expected leafnodes listen port to be same, was %v is now %v", lnPortBefore, lnPortAfter) } } + +func TestConfigReloadLeafNodeWithTLS(t *testing.T) { + template := ` + port: -1 + %s + leaf { + listen: "127.0.0.1:-1" + tls: { + ca_file: "../test/configs/certs/tlsauth/ca.pem" + cert_file: "../test/configs/certs/tlsauth/server.pem" + key_file: "../test/configs/certs/tlsauth/server-key.pem" + timeout: 3 + } + } + ` + conf1 := createConfFile(t, []byte(fmt.Sprintf(template, ""))) + defer os.Remove(conf1) + s1, o1 := RunServerWithConfig(conf1) + defer s1.Shutdown() + + u, err := url.Parse(fmt.Sprintf("nats://localhost:%d", o1.LeafNode.Port)) + if err != nil { + t.Fatalf("Error creating url: %v", err) + } + conf2 := createConfFile(t, []byte(fmt.Sprintf(` + port: -1 + leaf { + remotes [ + { + url: "%s" + tls { + ca_file: "../test/configs/certs/tlsauth/ca.pem" + cert_file: "../test/configs/certs/tlsauth/client.pem" + key_file: "../test/configs/certs/tlsauth/client-key.pem" + timeout: 2 + } + } + ] + } + `, u.String()))) + defer os.Remove(conf2) + o2, err := ProcessConfigFile(conf2) + if err != nil { + t.Fatalf("Error processing config file: %v", err) + } + o2.NoLog, o2.NoSigs = true, true + o2.LeafNode.resolver = &testLoopbackResolver{} + s2 := RunServer(o2) + defer s2.Shutdown() + + checkFor(t, 3*time.Second, 15*time.Millisecond, func() error { + if n := s1.NumLeafNodes(); n != 1 { + return fmt.Errorf("Expected 1 leaf node, got %v", n) + } + return nil + }) + + changeCurrentConfigContentWithNewContent(t, conf1, []byte(fmt.Sprintf(template, "debug: false"))) + + if err := s1.Reload(); err != nil { + t.Fatalf("Error during reload: %v", err) + } +}