deb-simple/http.go

129 lines
3.1 KiB
Go

package main
import (
"net/http"
"io"
"os"
"path/filepath"
"log"
"encoding/json"
"fmt"
)
func uploadHandler(config Conf) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
if r.Method != "POST" {
http.Error(w, "method not supported", http.StatusMethodNotAllowed)
return
}
archType := r.URL.Query().Get("arch")
if archType == "" {
archType = "all"
}
distroName := r.URL.Query().Get("distro")
if distroName == "" {
distroName = "stable"
}
key := r.URL.Query().Get("key")
if key == "" || key != config.Key {
http.Error(w, "unauthorized", 403)
return
}
reader, err := r.MultipartReader()
if err != nil {
httpErrorf(w, "error creating multipart reader: %s", err)
return
}
for {
part, err := reader.NextPart()
if err == io.EOF {
break
}
if part.FileName() == "" {
continue
}
newPath := config.PoolPackagePath(distroName, archType, part.FileName())
if _, err := os.Stat(newPath); err != nil {
if os.IsNotExist(err) {
if err := os.MkdirAll(newPath, 0755); err != nil {
httpErrorf(w, "error creating path: %s", err)
return
}
}
}
dst, err := os.Create(filepath.Join(newPath, part.FileName()))
if err != nil {
httpErrorf(w, "error creating deb file: %s", err)
return
}
defer dst.Close()
if _, err := io.Copy(dst, part); err != nil {
httpErrorf(w, "error writing deb file: %s", err)
return
}
}
mutex.Lock()
defer mutex.Unlock()
log.Println("got lock, updating package list...")
if err := createPackagesGz(config, distroName, archType); err != nil {
httpErrorf(w, "error creating package: %s", err)
return
}
err = createRelease(config, distroName, archType)
if err != nil {
httpErrorf(w, "error creating package: %s", err)
return
}
w.WriteHeader(http.StatusOK)
})
}
func deleteHandler(config Conf) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
if r.Method != "DELETE" {
http.Error(w, "method not supported", http.StatusMethodNotAllowed)
return
}
var toDelete DeleteObj
if err := json.NewDecoder(r.Body).Decode(&toDelete); err != nil {
httpErrorf(w, "failed to decode json: %s", err)
return
}
debPath := filepath.Join(config.ArchPath(toDelete.DistroName, toDelete.Arch), toDelete.Filename)
if err := os.Remove(debPath); err != nil {
httpErrorf(w, "failed to delete: %s", err)
return
}
key := r.URL.Query().Get("key")
if key == "" || key != config.Key {
http.Error(w, "unauthorized", http.StatusForbidden)
return
}
mutex.Lock()
defer mutex.Unlock()
log.Println("got lock, updating package list...")
if err := createPackagesGz(config, toDelete.DistroName, toDelete.Arch); err != nil {
httpErrorf(w, "failed to delete package: %s", err)
return
}
if err := createRelease(config, toDelete.DistroName, toDelete.Arch); err != nil {
httpErrorf(w, "failed to delete package: %s", err)
return
}
})
}
func httpErrorf(w http.ResponseWriter, format string, a ...interface{}) {
err := fmt.Errorf(format, a...)
log.Println(err)
http.Error(w, err.Error(), http.StatusInternalServerError)
}