瀏覽代碼

Enable gzip encoding static files for webgui

Sergey Mishin 10 年之前
父節點
當前提交
77882e6086
共有 5 個文件被更改,包括 62 次插入24 次删除
  1. 19 12
      cmd/genassets/main.go
  2. 12 2
      cmd/syncthing/gui.go
  3. 7 0
      internal/auto/auto_test.go
  4. 4 6
      internal/auto/gui.files.go
  5. 20 4
      test/http_test.go

+ 19 - 12
cmd/genassets/main.go

@@ -15,33 +15,32 @@ import (
 	"flag"
 	"go/format"
 	"io"
+	"net/http"
 	"os"
 	"path/filepath"
 	"strings"
 	"text/template"
+	"time"
 )
 
 var tpl = template.Must(template.New("assets").Parse(`package auto
 
 import (
-	"bytes"
-	"compress/gzip"
 	"encoding/base64"
-	"io/ioutil"
+)
+
+const (
+	AssetsBuildDate = "{{.BuildDate}}"
 )
 
 func Assets() map[string][]byte {
-	var assets = make(map[string][]byte, {{.assets | len}})
-	var bs []byte
-	var gr *gzip.Reader
-{{range $asset := .assets}}
-	bs, _ = base64.StdEncoding.DecodeString("{{$asset.Data}}")
-	gr, _ = gzip.NewReader(bytes.NewReader(bs))
-	bs, _ = ioutil.ReadAll(gr)
-	assets["{{$asset.Name}}"] = bs
+	var assets = make(map[string][]byte, {{.Assets | len}})
+{{range $asset := .Assets}}
+	assets["{{$asset.Name}}"], _ = base64.StdEncoding.DecodeString("{{$asset.Data}}")
 {{end}}
 	return assets
 }
+
 `))
 
 type asset struct {
@@ -86,12 +85,20 @@ func walkerFor(basePath string) filepath.WalkFunc {
 	}
 }
 
+type templateVars struct {
+	Assets    []asset
+	BuildDate string
+}
+
 func main() {
 	flag.Parse()
 
 	filepath.Walk(flag.Arg(0), walkerFor(flag.Arg(0)))
 	var buf bytes.Buffer
-	tpl.Execute(&buf, map[string][]asset{"assets": assets})
+	tpl.Execute(&buf, templateVars{
+		Assets:    assets,
+		BuildDate: time.Now().UTC().Format(http.TimeFormat),
+	})
 	bs, err := format.Source(buf.Bytes())
 	if err != nil {
 		panic(err)

+ 12 - 2
cmd/syncthing/gui.go

@@ -7,6 +7,8 @@
 package main
 
 import (
+	"bytes"
+	"compress/gzip"
 	"crypto/tls"
 	"encoding/json"
 	"fmt"
@@ -45,7 +47,6 @@ var (
 	configInSync = true
 	guiErrors    = []guiError{}
 	guiErrorsMut sync.Mutex
-	modt         = time.Now().UTC().Format(http.TimeFormat)
 	eventSub     *events.BufferedSubscription
 )
 
@@ -832,8 +833,17 @@ func embeddedStatic(assetDir string) http.Handler {
 		if len(mtype) != 0 {
 			w.Header().Set("Content-Type", mtype)
 		}
+		if strings.Contains(r.Header.Get("Accept-Encoding"), "gzip") {
+			w.Header().Set("Content-Encoding", "gzip")
+		} else {
+			// ungzip if browser not send gzip accepted header
+			var gr *gzip.Reader
+			gr, _ = gzip.NewReader(bytes.NewReader(bs))
+			bs, _ = ioutil.ReadAll(gr)
+			gr.Close()
+		}
 		w.Header().Set("Content-Length", fmt.Sprintf("%d", len(bs)))
-		w.Header().Set("Last-Modified", modt)
+		w.Header().Set("Last-Modified", auto.AssetsBuildDate)
 
 		w.Write(bs)
 	})

+ 7 - 0
internal/auto/auto_test.go

@@ -8,6 +8,8 @@ package auto_test
 
 import (
 	"bytes"
+	"compress/gzip"
+	"io/ioutil"
 	"testing"
 
 	"github.com/syncthing/syncthing/internal/auto"
@@ -19,6 +21,11 @@ func TestAssets(t *testing.T) {
 	if !ok {
 		t.Fatal("No index.html in compiled in assets")
 	}
+
+	var gr *gzip.Reader
+	gr, _ = gzip.NewReader(bytes.NewReader(idx))
+	idx, _ = ioutil.ReadAll(gr)
+
 	if !bytes.Contains(idx, []byte("<html")) {
 		t.Fatal("No html in index.html")
 	}

File diff suppressed because it is too large
+ 4 - 6
internal/auto/gui.files.go


+ 20 - 4
test/http_test.go

@@ -9,7 +9,9 @@
 package integration
 
 import (
+	"bytes"
 	"encoding/json"
+	"io/ioutil"
 	"net/http"
 	"strings"
 	"testing"
@@ -49,8 +51,15 @@ func TestGetIndex(t *testing.T) {
 	if res.StatusCode != 200 {
 		t.Errorf("Status %d != 200", res.StatusCode)
 	}
-	if res.ContentLength < 1024 {
-		t.Errorf("Length %d < 1024", res.ContentLength)
+	bs, err := ioutil.ReadAll(res.Body)
+	if err != nil {
+		t.Fatal(err)
+	}
+	if len(bs) < 1024 {
+		t.Errorf("Length %d < 1024", len(bs))
+	}
+	if !bytes.Contains(bs, []byte("</html>")) {
+		t.Error("Incorrect response")
 	}
 	if res.Header.Get("Set-Cookie") == "" {
 		t.Error("No set-cookie header")
@@ -64,8 +73,15 @@ func TestGetIndex(t *testing.T) {
 	if res.StatusCode != 200 {
 		t.Errorf("Status %d != 200", res.StatusCode)
 	}
-	if res.ContentLength < 1024 {
-		t.Errorf("Length %d < 1024", res.ContentLength)
+	bs, err = ioutil.ReadAll(res.Body)
+	if err != nil {
+		t.Fatal(err)
+	}
+	if len(bs) < 1024 {
+		t.Errorf("Length %d < 1024", len(bs))
+	}
+	if !bytes.Contains(bs, []byte("</html>")) {
+		t.Error("Incorrect response")
 	}
 	if res.Header.Get("Set-Cookie") == "" {
 		t.Error("No set-cookie header")

Some files were not shown because too many files changed in this diff