|
|
|
@ -318,71 +318,69 @@ func (s *Server) postHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var b bytes.Buffer
|
|
|
|
|
file, err := ioutil.TempFile(s.tempPath, "transfer-")
|
|
|
|
|
defer s.cleanTmpFile(file)
|
|
|
|
|
|
|
|
|
|
n, err := io.CopyN(&b, f, _24K+1)
|
|
|
|
|
if err != nil && err != io.EOF {
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
n, err := io.Copy(file, f)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var file *os.File
|
|
|
|
|
var reader io.Reader
|
|
|
|
|
|
|
|
|
|
if n > _24K {
|
|
|
|
|
file, err = ioutil.TempFile(s.tempPath, "transfer-")
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Fatal(err)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
n, err = io.Copy(file, io.MultiReader(&b, f))
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.cleanTmpFile(file)
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
reader, err = os.Open(file.Name())
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
reader = bytes.NewReader(b.Bytes())
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
contentLength := n
|
|
|
|
|
|
|
|
|
|
_, err = file.Seek(0, io.SeekStart)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if s.maxUploadSize > 0 && contentLength > s.maxUploadSize {
|
|
|
|
|
s.logger.Print("Entity too large")
|
|
|
|
|
http.Error(w, http.StatusText(http.StatusRequestEntityTooLarge), http.StatusRequestEntityTooLarge)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if s.performClamavPrescan {
|
|
|
|
|
status, err := s.performScan(file.Name())
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not perform prescan", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if status != clamavScanStatusOK {
|
|
|
|
|
s.logger.Printf("prescan positive: %s", status)
|
|
|
|
|
http.Error(w, "Clamav prescan found a virus", http.StatusPreconditionFailed)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
metadata := metadataForRequest(contentType, s.randomTokenLength, r)
|
|
|
|
|
|
|
|
|
|
buffer := &bytes.Buffer{}
|
|
|
|
|
if err := json.NewEncoder(buffer).Encode(metadata); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, errors.New("Could not encode metadata").Error(), 500)
|
|
|
|
|
http.Error(w, "Could not encode metadata", 500)
|
|
|
|
|
|
|
|
|
|
s.cleanTmpFile(file)
|
|
|
|
|
return
|
|
|
|
|
} else if err := s.storage.Put(token, fmt.Sprintf("%s.metadata", filename), buffer, "text/json", uint64(buffer.Len())); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, errors.New("Could not save metadata").Error(), 500)
|
|
|
|
|
http.Error(w, "Could not save metadata", 500)
|
|
|
|
|
|
|
|
|
|
s.cleanTmpFile(file)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("Uploading %s %s %d %s", token, filename, contentLength, contentType)
|
|
|
|
|
|
|
|
|
|
if err = s.storage.Put(token, filename, reader, contentType, uint64(contentLength)); err != nil {
|
|
|
|
|
if err = s.storage.Put(token, filename, file, contentType, uint64(contentLength)); err != nil {
|
|
|
|
|
s.logger.Printf("Backend storage error: %s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
@ -392,8 +390,6 @@ func (s *Server) postHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
filename = url.PathEscape(filename)
|
|
|
|
|
relativeURL, _ := url.Parse(path.Join(s.proxyPath, token, filename))
|
|
|
|
|
fmt.Fprintln(w, getURL(r, s.proxyPort).ResolveReference(relativeURL).String())
|
|
|
|
|
|
|
|
|
|
s.cleanTmpFile(file)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -458,57 +454,35 @@ func (s *Server) putHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
|
|
|
|
|
contentLength := r.ContentLength
|
|
|
|
|
|
|
|
|
|
var reader io.Reader
|
|
|
|
|
|
|
|
|
|
reader = r.Body
|
|
|
|
|
|
|
|
|
|
defer r.Body.Close()
|
|
|
|
|
|
|
|
|
|
if contentLength == -1 {
|
|
|
|
|
// queue file to disk, because s3 needs content length
|
|
|
|
|
var err error
|
|
|
|
|
var f io.Reader
|
|
|
|
|
file, err := ioutil.TempFile(s.tempPath, "transfer-")
|
|
|
|
|
defer s.cleanTmpFile(file)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
f = reader
|
|
|
|
|
// queue file to disk, because s3 needs content length
|
|
|
|
|
// and clamav prescan scans a file
|
|
|
|
|
n, err := io.Copy(file, r.Body)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
|
|
|
|
|
var b bytes.Buffer
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
n, err := io.CopyN(&b, f, _24K+1)
|
|
|
|
|
if err != nil && err != io.EOF {
|
|
|
|
|
s.logger.Printf("Error putting new file: %s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
_, err = file.Seek(0, io.SeekStart)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Cannot reset cache file", http.StatusInternalServerError)
|
|
|
|
|
|
|
|
|
|
var file *os.File
|
|
|
|
|
|
|
|
|
|
if n > _24K {
|
|
|
|
|
file, err = ioutil.TempFile(s.tempPath, "transfer-")
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
defer s.cleanTmpFile(file)
|
|
|
|
|
|
|
|
|
|
n, err = io.Copy(file, io.MultiReader(&b, f))
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
reader, err = os.Open(file.Name())
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, err.Error(), 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
reader = bytes.NewReader(b.Bytes())
|
|
|
|
|
}
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if contentLength < 1 {
|
|
|
|
|
contentLength = n
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -520,10 +494,25 @@ func (s *Server) putHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
|
|
|
|
|
if contentLength == 0 {
|
|
|
|
|
s.logger.Print("Empty content-length")
|
|
|
|
|
http.Error(w, errors.New("Could not upload empty file").Error(), 400)
|
|
|
|
|
http.Error(w, "Could not upload empty file", http.StatusBadRequest)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if s.performClamavPrescan {
|
|
|
|
|
status, err := s.performScan(file.Name())
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not perform prescan", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if status != clamavScanStatusOK {
|
|
|
|
|
s.logger.Printf("prescan positive: %s", status)
|
|
|
|
|
http.Error(w, "Clamav prescan found a virus", http.StatusPreconditionFailed)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
contentType := mime.TypeByExtension(filepath.Ext(vars["filename"]))
|
|
|
|
|
|
|
|
|
|
token := token(s.randomTokenLength)
|
|
|
|
@ -533,25 +522,23 @@ func (s *Server) putHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
buffer := &bytes.Buffer{}
|
|
|
|
|
if err := json.NewEncoder(buffer).Encode(metadata); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, errors.New("Could not encode metadata").Error(), 500)
|
|
|
|
|
http.Error(w, "Could not encode metadata", 500)
|
|
|
|
|
return
|
|
|
|
|
} else if !metadata.MaxDate.IsZero() && time.Now().After(metadata.MaxDate) {
|
|
|
|
|
s.logger.Print("Invalid MaxDate")
|
|
|
|
|
http.Error(w, errors.New("Invalid MaxDate, make sure Max-Days is smaller than 290 years").Error(), 400)
|
|
|
|
|
http.Error(w, "Invalid MaxDate, make sure Max-Days is smaller than 290 years", http.StatusBadRequest)
|
|
|
|
|
return
|
|
|
|
|
} else if err := s.storage.Put(token, fmt.Sprintf("%s.metadata", filename), buffer, "text/json", uint64(buffer.Len())); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, errors.New("Could not save metadata").Error(), 500)
|
|
|
|
|
http.Error(w, "Could not save metadata", 500)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("Uploading %s %s %d %s", token, filename, contentLength, contentType)
|
|
|
|
|
|
|
|
|
|
var err error
|
|
|
|
|
|
|
|
|
|
if err = s.storage.Put(token, filename, reader, contentType, uint64(contentLength)); err != nil {
|
|
|
|
|
if err = s.storage.Put(token, filename, file, contentType, uint64(contentLength)); err != nil {
|
|
|
|
|
s.logger.Printf("Error putting new file: %s", err.Error())
|
|
|
|
|
http.Error(w, errors.New("Could not save file").Error(), 500)
|
|
|
|
|
http.Error(w, "Could not save file", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -718,9 +705,9 @@ func (s *Server) checkMetadata(token, filename string, increaseDownload bool) (m
|
|
|
|
|
|
|
|
|
|
buffer := &bytes.Buffer{}
|
|
|
|
|
if err := json.NewEncoder(buffer).Encode(metadata); err != nil {
|
|
|
|
|
return metadata, errors.New("Could not encode metadata")
|
|
|
|
|
return metadata, errors.New("could not encode metadata")
|
|
|
|
|
} else if err := s.storage.Put(token, fmt.Sprintf("%s.metadata", filename), buffer, "text/json", uint64(buffer.Len())); err != nil {
|
|
|
|
|
return metadata, errors.New("Could not save metadata")
|
|
|
|
|
return metadata, errors.New("could not save metadata")
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -783,7 +770,7 @@ func (s *Server) deleteHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
return
|
|
|
|
|
} else if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not delete file.", 500)
|
|
|
|
|
http.Error(w, "Could not delete file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -821,7 +808,7 @@ func (s *Server) zipHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not retrieve file.", 500)
|
|
|
|
|
http.Error(w, "Could not retrieve file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -838,20 +825,20 @@ func (s *Server) zipHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if _, err = io.Copy(fw, reader); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if err := zw.Close(); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -892,7 +879,7 @@ func (s *Server) tarGzHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not retrieve file.", 500)
|
|
|
|
|
http.Error(w, "Could not retrieve file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -906,13 +893,13 @@ func (s *Server) tarGzHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
err = zw.WriteHeader(header)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if _, err = io.Copy(zw, reader); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -951,7 +938,7 @@ func (s *Server) tarHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not retrieve file.", 500)
|
|
|
|
|
http.Error(w, "Could not retrieve file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -965,13 +952,13 @@ func (s *Server) tarHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
err = zw.WriteHeader(header)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if _, err = io.Copy(zw, reader); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Internal server error.", 500)
|
|
|
|
|
http.Error(w, "Internal server error.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -998,7 +985,7 @@ func (s *Server) headHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
return
|
|
|
|
|
} else if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not retrieve file.", 500)
|
|
|
|
|
http.Error(w, "Could not retrieve file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1033,7 +1020,7 @@ func (s *Server) getHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
return
|
|
|
|
|
} else if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Could not retrieve file.", 500)
|
|
|
|
|
http.Error(w, "Could not retrieve file.", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1064,7 +1051,7 @@ func (s *Server) getHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
file, err := ioutil.TempFile(s.tempPath, "range-")
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", 500)
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1073,7 +1060,7 @@ func (s *Server) getHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
_, err = io.Copy(file, reader)
|
|
|
|
|
if err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", 500)
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1083,7 +1070,7 @@ func (s *Server) getHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
|
|
|
|
|
if _, err = io.Copy(w, reader); err != nil {
|
|
|
|
|
s.logger.Printf("%s", err.Error())
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", 500)
|
|
|
|
|
http.Error(w, "Error occurred copying to output stream", http.StatusInternalServerError)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|