فهرست منبع

Implement HTTPS for GUI

Jakob Borg 11 سال پیش
والد
کامیت
7c8652b600
6فایلهای تغییر یافته به همراه42 افزوده شده و 13 حذف شده
  1. 0 0
      auto/gui.files.go
  2. 25 3
      cmd/syncthing/gui.go
  3. 10 5
      cmd/syncthing/main.go
  4. 5 5
      cmd/syncthing/tls.go
  5. 1 0
      config/config.go
  6. 1 0
      gui/app.js

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 0 - 0
auto/gui.files.go


+ 25 - 3
cmd/syncthing/gui.go

@@ -13,6 +13,7 @@ import (
 	"sync"
 	"time"
 
+	"crypto/tls"
 	"code.google.com/p/go.crypto/bcrypt"
 	"github.com/calmh/syncthing/config"
 	"github.com/calmh/syncthing/logger"
@@ -42,9 +43,30 @@ func init() {
 }
 
 func startGUI(cfg config.GUIConfiguration, m *model.Model) error {
-	listener, err := net.Listen("tcp", cfg.Address)
-	if err != nil {
-		return err
+	var listener net.Listener
+	var err error
+	if cfg.UseTLS {
+		cert, err := loadCert(confDir, "https-")
+		if err != nil {
+			newCertificate(confDir, "https-")
+			cert, err = loadCert(confDir, "https-")
+		}
+		if err != nil {
+			return err
+		}
+		tlsCfg := &tls.Config{
+			Certificates: []tls.Certificate{cert},
+			ServerName:   "syncthing",
+		}
+		listener, err = tls.Listen("tcp", cfg.Address, tlsCfg)
+		if err != nil {
+			return err
+		}
+	} else {
+		listener, err = net.Listen("tcp", cfg.Address)
+		if err != nil {
+			return err
+		}
 	}
 
 	router := martini.NewRouter()

+ 10 - 5
cmd/syncthing/main.go

@@ -144,10 +144,10 @@ func main() {
 	// Ensure that our home directory exists and that we have a certificate and key.
 
 	ensureDir(confDir, 0700)
-	cert, err := loadCert(confDir)
+	cert, err := loadCert(confDir, "")
 	if err != nil {
-		newCertificate(confDir)
-		cert, err = loadCert(confDir)
+		newCertificate(confDir, "")
+		cert, err = loadCert(confDir, "")
 		l.FatalErr(err)
 	}
 
@@ -272,13 +272,18 @@ func main() {
 				hostShow = hostOpen
 			}
 
-			l.Infof("Starting web GUI on http://%s:%d/", hostShow, addr.Port)
+			var proto = "http"
+			if cfg.GUI.UseTLS {
+				proto = "https"
+			}
+
+			l.Infof("Starting web GUI on %s://%s:%d/", proto, hostShow, addr.Port)
 			err := startGUI(cfg.GUI, m)
 			if err != nil {
 				l.Fatalln("Cannot start GUI:", err)
 			}
 			if cfg.Options.StartBrowser && len(os.Getenv("STRESTART")) == 0 {
-				openURL(fmt.Sprintf("http://%s:%d", hostOpen, addr.Port))
+				openURL(fmt.Sprintf("%s://%s:%d", proto, hostOpen, addr.Port))
 			}
 		}
 	}

+ 5 - 5
cmd/syncthing/tls.go

@@ -22,8 +22,8 @@ const (
 	tlsName    = "syncthing"
 )
 
-func loadCert(dir string) (tls.Certificate, error) {
-	return tls.LoadX509KeyPair(filepath.Join(dir, "cert.pem"), filepath.Join(dir, "key.pem"))
+func loadCert(dir string, prefix string) (tls.Certificate, error) {
+	return tls.LoadX509KeyPair(filepath.Join(dir, prefix+"cert.pem"), filepath.Join(dir, prefix+"key.pem"))
 }
 
 func certID(bs []byte) string {
@@ -40,7 +40,7 @@ func certSeed(bs []byte) int64 {
 	return int64(binary.BigEndian.Uint64(id))
 }
 
-func newCertificate(dir string) {
+func newCertificate(dir string, prefix string) {
 	l.Infoln("Generating RSA certificate and key...")
 
 	priv, err := rsa.GenerateKey(rand.Reader, tlsRSABits)
@@ -65,13 +65,13 @@ func newCertificate(dir string) {
 	derBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &priv.PublicKey, priv)
 	l.FatalErr(err)
 
-	certOut, err := os.Create(filepath.Join(dir, "cert.pem"))
+	certOut, err := os.Create(filepath.Join(dir, prefix+"cert.pem"))
 	l.FatalErr(err)
 	pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: derBytes})
 	certOut.Close()
 	l.Okln("Created RSA certificate file")
 
-	keyOut, err := os.OpenFile(filepath.Join(dir, "key.pem"), os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0600)
+	keyOut, err := os.OpenFile(filepath.Join(dir, prefix+"key.pem"), os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0600)
 	l.FatalErr(err)
 	pem.Encode(keyOut, &pem.Block{Type: "RSA PRIVATE KEY", Bytes: x509.MarshalPKCS1PrivateKey(priv)})
 	keyOut.Close()

+ 1 - 0
config/config.go

@@ -73,6 +73,7 @@ type GUIConfiguration struct {
 	Address  string `xml:"address" default:"127.0.0.1:8080"`
 	User     string `xml:"user,omitempty"`
 	Password string `xml:"password,omitempty"`
+	UseTLS   bool   `xml:"tls,attr"`
 }
 
 func setDefaults(data interface{}) error {

+ 1 - 0
gui/app.js

@@ -40,6 +40,7 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
     {id: 'Address', descr: 'GUI Listen Addresses', type: 'text', restart: true},
     {id: 'User', descr: 'GUI Authentication User', type: 'text', restart: true},
     {id: 'Password', descr: 'GUI Authentication Password', type: 'password', restart: true},
+    {id: 'UseTLS', descr: 'Use HTTPS for GUI', type: 'bool', restart: true},
     ];
 
     function getSucceeded() {

برخی فایل ها در این مقایسه diff نمایش داده نمی شوند زیرا تعداد فایل ها بسیار زیاد است