From 0417e8d3851ac95e2f271e19dda20faf45d64408 Mon Sep 17 00:00:00 2001 From: Richard van der Hoff Date: Tue, 18 Apr 2017 15:47:45 +0100 Subject: [PATCH] Support for compressed logfiles (#13) Allow apps to upload gzipped log files --- README.md | 5 +++++ src/github.com/matrix-org/rageshake/submit.go | 17 +++++++++++++-- .../matrix-org/rageshake/submit_test.go | 21 ++++++++++++++++--- 3 files changed, 38 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 540df23..a3d4012 100644 --- a/README.md +++ b/README.md @@ -59,6 +59,11 @@ logs.) * `id`: textual identifier for the logs. Currently ignored. * `lines`: log data. Newlines should be encoded as `\n`, as normal in JSON). +* `compressed-log`: a gzipped logfile. Decompressed and then treated the same as + `log`. + + Compressed logs are not supported for the JSON upload encoding. + * Any other form field names are interpreted as arbitrary name/value strings to include in the `details.log.gz` file. diff --git a/src/github.com/matrix-org/rageshake/submit.go b/src/github.com/matrix-org/rageshake/submit.go index 46b3f2e..0076ebe 100644 --- a/src/github.com/matrix-org/rageshake/submit.go +++ b/src/github.com/matrix-org/rageshake/submit.go @@ -207,7 +207,20 @@ func parseFormPart(part *multipart.Part, p *payload) error { defer part.Close() field := part.FormName() - b, err := ioutil.ReadAll(part) + var partReader io.Reader + if field == "compressed-log" { + // decompress logs as we read them + zrdr, err := gzip.NewReader(part) + if err != nil { + return err + } + defer zrdr.Close() + partReader = zrdr + } else { + // read the field data directly from the multipart part + partReader = part + } + b, err := ioutil.ReadAll(partReader) if err != nil { return err } @@ -221,7 +234,7 @@ func parseFormPart(part *multipart.Part, p *payload) error { p.Version = data } else if field == "user_agent" { p.UserAgent = data - } else if field == "log" { + } else if field == "log" || field == "compressed-log" { p.Logs = append(p.Logs, logEntry{ ID: part.FileName(), Lines: data, diff --git a/src/github.com/matrix-org/rageshake/submit_test.go b/src/github.com/matrix-org/rageshake/submit_test.go index d5a5ebe..2d2037d 100644 --- a/src/github.com/matrix-org/rageshake/submit_test.go +++ b/src/github.com/matrix-org/rageshake/submit_test.go @@ -111,15 +111,26 @@ Content-Disposition: form-data; name="log"; filename="instance-0.067644760733513 Content-Type: text/plain log -------WebKitFormBoundarySsdgl8Nq9voFyhdO-- ` + + body += `------WebKitFormBoundarySsdgl8Nq9voFyhdO +Content-Disposition: form-data; name="compressed-log"; filename="instance-0.0109372050779190651492004373866" +Content-Type: application/octet-stream + +` + body += string([]byte{ + 0x1f, 0x8b, 0x08, 0x00, 0xbf, 0xd8, 0xf5, 0x58, 0x00, 0x03, + 0x2b, 0x49, 0x2d, 0x2e, 0xe1, 0x02, 0x00, + 0xc6, 0x35, 0xb9, 0x3b, 0x05, 0x00, 0x00, 0x00}) + body += "\n------WebKitFormBoundarySsdgl8Nq9voFyhdO--\n" + p := testParsePayload(t, body, "multipart/form-data; boundary=----WebKitFormBoundarySsdgl8Nq9voFyhdO") wanted := "test words." if p.Text != wanted { t.Errorf("User text: got %s, want %s", p.Text, wanted) } - if len(p.Logs) != 2 { - t.Errorf("Log length: got %d, want 2", len(p.Logs)) + if len(p.Logs) != 3 { + t.Errorf("Log length: got %d, want 3", len(p.Logs)) } if len(p.Data) != 1 { t.Errorf("Data length: got %d, want 1", len(p.Data)) @@ -144,4 +155,8 @@ log if p.Logs[1].ID != wanted { t.Errorf("Log 1 ID: got %s, want %s", p.Logs[1].ID, wanted) } + wanted = "test\n" + if p.Logs[2].Lines != wanted { + t.Errorf("Log 2: got %s, want %s", p.Logs[2].Lines, wanted) + } }