diff --git a/context.go b/context.go index 880735caa..c7beed9e4 100644 --- a/context.go +++ b/context.go @@ -3,15 +3,13 @@ package echo import ( "encoding/json" "encoding/xml" - "io" "net/http" + "path" "fmt" "net/url" - "os" - "golang.org/x/net/websocket" ) @@ -166,16 +164,14 @@ func (c *Context) XML(code int, i interface{}) error { return xml.NewEncoder(c.response).Encode(i) } -// File sends a file as attachment. -func (c *Context) File(name string) error { - file, err := os.Open(name) - if err != nil { - return err +// File sends a response with the content of the file. If attachment is true, the +// client is prompted to save the file. +func (c *Context) File(name string, attachment bool) error { + dir, file := path.Split(name) + if attachment { + c.response.Header().Set(ContentDisposition, "attachment; filename="+file) } - fi, _ := file.Stat() - c.response.Header().Set(ContentDisposition, "attachment; filename="+fi.Name()) - _, err = io.Copy(c.response, file) - return err + return serveFile(dir, file, c) } // NoContent sends a response with no body and a status code. diff --git a/context_test.go b/context_test.go index 21472d3ef..77e4b7d8f 100644 --- a/context_test.go +++ b/context_test.go @@ -141,12 +141,22 @@ func TestContext(t *testing.T) { // File rec = httptest.NewRecorder() c = NewContext(req, NewResponse(rec), New()) - err = c.File("test/fixture/walle.png") + err = c.File("test/fixture/walle.png", false) if assert.NoError(t, err) { assert.Equal(t, http.StatusOK, rec.Code) assert.Equal(t, 219885, rec.Body.Len()) } + // File as attachment + rec = httptest.NewRecorder() + c = NewContext(req, NewResponse(rec), New()) + err = c.File("test/fixture/walle.png", true) + if assert.NoError(t, err) { + assert.Equal(t, http.StatusOK, rec.Code) + assert.Equal(t, rec.Header().Get(ContentDisposition), "attachment; filename=walle.png") + assert.Equal(t, 219885, rec.Body.Len()) + } + // NoContent rec = httptest.NewRecorder() c = NewContext(req, NewResponse(rec), New()) diff --git a/website/docs/guide.md b/website/docs/guide.md index 669807301..281005492 100644 --- a/website/docs/guide.md +++ b/website/docs/guide.md @@ -368,6 +368,15 @@ Context.String(code int, s string) error Sends a text/plain HTTP response with status code. +### File + +```go +Context.File(name string, attachment bool) error +``` + +File sends a response with the content of the file. If attachment is true, the client +is prompted to save the file. + ### Static files `Echo.Static(path, root string)` serves static files. For example, code below serves