diff options
author | Christian Pointner <equinox@helsinki.at> | 2016-07-22 16:42:07 (GMT) |
---|---|---|
committer | Christian Pointner <equinox@helsinki.at> | 2016-07-22 16:42:07 (GMT) |
commit | a4588ab0c505b79caf8858cac06a9b8fb58ac81c (patch) | |
tree | 6768091dfef1537b8d99646c66c11741c9514981 /src/rhimportd/uploadWeb.go | |
parent | 34d536887eeb88e7b3d407a31332a13bb0bff5f5 (diff) |
new uploadWeb mostly done
Diffstat (limited to 'src/rhimportd/uploadWeb.go')
-rw-r--r-- | src/rhimportd/uploadWeb.go | 72 |
1 files changed, 54 insertions, 18 deletions
diff --git a/src/rhimportd/uploadWeb.go b/src/rhimportd/uploadWeb.go index 412df12..224e91d 100644 --- a/src/rhimportd/uploadWeb.go +++ b/src/rhimportd/uploadWeb.go @@ -27,9 +27,7 @@ package main import ( "bytes" "encoding/json" - "fmt" "io" - "io/ioutil" "mime/multipart" "net/http" @@ -62,7 +60,7 @@ const ( webUploadMaxRequestSize = (2 << 30) - 1 // 2GB, (2 << 30) overflows int on 32-bit systems therefore we use 2GB - 1 Byte ) -func webUploadParseForm(w http.ResponseWriter, r *http.Request) (username, sessionid, srcfile string, src *multipart.Part, ok bool) { +func webUploadParseForm(w http.ResponseWriter, r *http.Request) (username, sessionid, srcfile string, src *multipart.Part) { mpr, err := r.MultipartReader() if err != nil { rhl.Printf("WebUploadHandler: error while parsing multipart-form: %v", err) @@ -72,6 +70,9 @@ func webUploadParseForm(w http.ResponseWriter, r *http.Request) (username, sessi for { p, err := mpr.NextPart() + if err == io.EOF { + return + } if err != nil { rhl.Printf("WebUploadHandler: error while parsing multipart-form: %v", err) webUploadErrorResponse(w, http.StatusBadRequest, err.Error()) @@ -86,12 +87,10 @@ func webUploadParseForm(w http.ResponseWriter, r *http.Request) (username, sessi case "FILENAME": srcfile = p.FileName() src = p - ok = true - return + return // don't read any fileds beyond this point because we would need to load the whole file in order to continue parsing default: - rhl.Printf("WebUploadHandler: unknown form field: '%s'", p.FormName()) - webUploadErrorResponse(w, http.StatusBadRequest, fmt.Sprintf("unknown field %s", p.FormName())) - return + rhdl.Printf("WebUploadHandler: ingoring unknown form field: '%s'", p.FormName()) + continue } var buf bytes.Buffer @@ -125,10 +124,7 @@ func webUploadHandler(conf *rhimport.Config, db *rddb.DBChan, sessions *rhimport } r.Body = http.MaxBytesReader(w, r.Body, webUploadMaxRequestSize) - username, sessionid, srcfile, src, ok := webUploadParseForm(w, r) - if !ok { - return - } + username, sessionid, srcfile, src := webUploadParseForm(w, r) if username == "" { webUploadErrorResponse(w, http.StatusBadRequest, "missing field LOGIN_NAME") return @@ -137,13 +133,53 @@ func webUploadHandler(conf *rhimport.Config, db *rddb.DBChan, sessions *rhimport webUploadErrorResponse(w, http.StatusBadRequest, "missing field SESSION_ID") return } + if srcfile == "" || src == nil { + webUploadErrorResponse(w, http.StatusBadRequest, "missing field FILENAME") + return + } + + s, _, code, _ := sessions.Get(username, sessionid) + if code != http.StatusOK { + webUploadErrorResponse(w, http.StatusUnauthorized, "session not found") + return + } + + cancel, attachmentChan := s.AttachUploader() + if attachmentChan == nil || cancel == nil { + webUploadErrorResponse(w, http.StatusForbidden, "upload already in progress") + return + } + defer close(attachmentChan) - // TODO: get session->attachmentChan from store -> 401 if not found - // TODO: take session -> 403 if already taken + rhl.Printf("WebUploadHandler: starting upload for file '%s'", srcfile) + for { + chunk := rhimport.AttachmentChunk{} + + var data [128 * 1024]byte + n, err := src.Read(data[:]) + if n > 0 { + chunk.Data = data[:n] + if err == io.EOF { + err = nil + } + } + chunk.Error = err + if err == io.EOF { + webUploadSuccessResponse(w) + return + } - // TODO: fetch file (src) in chunks and send it to attachmentChan && check for canceled - rhl.Printf("WebUploadHandler: fetching file from '%s' (%v)", srcfile, src) - io.Copy(ioutil.Discard, src) + select { + case <-cancel: + rhl.Printf("WebUploadHandler: upload for file '%s' got canceld", srcfile) + webUploadErrorResponse(w, http.StatusNoContent, "canceled") + return + case attachmentChan <- chunk: + } - webUploadSuccessResponse(w) + if err != nil { + webUploadErrorResponse(w, http.StatusInternalServerError, err.Error()) + return + } + } } |