2016-12-08 08:12:18 +00:00
|
|
|
package api
|
2016-01-20 21:44:34 +00:00
|
|
|
|
|
|
|
import (
|
2016-01-23 11:19:47 +00:00
|
|
|
"bufio"
|
2016-01-20 21:44:34 +00:00
|
|
|
"crypto/sha512"
|
|
|
|
"encoding/base32"
|
|
|
|
"encoding/json"
|
|
|
|
"errors"
|
2016-12-08 11:00:53 +00:00
|
|
|
"fmt"
|
2016-01-22 16:57:50 +00:00
|
|
|
"log"
|
2016-01-20 21:44:34 +00:00
|
|
|
"net/http"
|
|
|
|
"os"
|
|
|
|
"path"
|
|
|
|
"strings"
|
|
|
|
|
|
|
|
"srs.epita.fr/fic-server/libfic"
|
|
|
|
)
|
|
|
|
|
2016-12-08 08:12:18 +00:00
|
|
|
var CloudDAVBase string
|
|
|
|
var CloudUsername string
|
|
|
|
var CloudPassword string
|
|
|
|
|
2016-12-08 11:00:53 +00:00
|
|
|
type uploadedFile struct {
|
|
|
|
URI string
|
|
|
|
Digest []byte
|
|
|
|
Path string
|
|
|
|
Parts []string
|
|
|
|
}
|
|
|
|
|
2016-12-26 00:14:46 +00:00
|
|
|
func createExerciceFile(exercice fic.Exercice, body []byte) (interface{}, error) {
|
2016-12-08 11:00:53 +00:00
|
|
|
var uf uploadedFile
|
2016-01-20 21:44:34 +00:00
|
|
|
if err := json.Unmarshal(body, &uf); err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2016-11-19 14:54:32 +00:00
|
|
|
var hash [sha512.Size]byte
|
|
|
|
var logStr string
|
|
|
|
var fromURI string
|
|
|
|
var getFile func(string) (error)
|
|
|
|
|
2016-12-08 11:00:53 +00:00
|
|
|
if uf.URI != "" {
|
|
|
|
hash = sha512.Sum512([]byte(uf.URI))
|
|
|
|
logStr = "Import file from Cloud: " + uf.URI + " =>"
|
|
|
|
fromURI = uf.URI
|
|
|
|
getFile = func(dest string) error { return getCloudFile(uf.URI, dest); }
|
|
|
|
} else if uf.Path != "" && len(uf.Parts) > 0 {
|
|
|
|
hash = sha512.Sum512([]byte(uf.Path))
|
|
|
|
logStr = fmt.Sprintf("Import file from local FS: %s =>", uf.Parts)
|
|
|
|
fromURI = uf.Path
|
|
|
|
getFile = func(dest string) error {
|
|
|
|
if fdto, err := os.Create(dest); err != nil {
|
|
|
|
return err
|
|
|
|
} else {
|
|
|
|
writer := bufio.NewWriter(fdto)
|
|
|
|
for _, partname := range uf.Parts {
|
|
|
|
if fdfrm, err := os.Open(partname); err != nil {
|
|
|
|
return err
|
|
|
|
} else {
|
|
|
|
reader := bufio.NewReader(fdfrm)
|
|
|
|
reader.WriteTo(writer)
|
|
|
|
writer.Flush()
|
|
|
|
fdfrm.Close()
|
|
|
|
}
|
|
|
|
}
|
|
|
|
fdto.Close()
|
|
|
|
}
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
} else if uf.Path != "" {
|
|
|
|
hash = sha512.Sum512([]byte(uf.Path))
|
|
|
|
logStr = "Import file from local FS: " + uf.Path + " =>"
|
|
|
|
fromURI = uf.Path
|
|
|
|
getFile = func(dest string) error { return os.Symlink(uf.Path, dest); }
|
2016-11-19 14:54:32 +00:00
|
|
|
} else {
|
|
|
|
return nil, errors.New("URI or path not filled")
|
2016-01-20 21:44:34 +00:00
|
|
|
}
|
|
|
|
|
2016-11-19 14:54:32 +00:00
|
|
|
pathname := path.Join(fic.FilesDir, strings.ToLower(base32.StdEncoding.EncodeToString(hash[:])), path.Base(fromURI))
|
2016-01-20 21:44:34 +00:00
|
|
|
|
2016-01-22 16:57:50 +00:00
|
|
|
if _, err := os.Stat(pathname); os.IsNotExist(err) {
|
2016-11-19 14:54:32 +00:00
|
|
|
log.Println(logStr, pathname)
|
2016-01-23 11:19:47 +00:00
|
|
|
if err := os.MkdirAll(path.Dir(pathname), 0777); err != nil {
|
|
|
|
return nil, err
|
2016-11-19 14:54:32 +00:00
|
|
|
} else if err := getFile(pathname); err != nil {
|
2016-01-20 21:44:34 +00:00
|
|
|
return nil, err
|
2016-01-22 16:57:50 +00:00
|
|
|
}
|
2016-01-20 21:44:34 +00:00
|
|
|
}
|
2016-01-22 16:57:50 +00:00
|
|
|
|
2016-11-19 14:54:32 +00:00
|
|
|
return exercice.ImportFile(pathname, fromURI)
|
2016-01-20 21:44:34 +00:00
|
|
|
}
|
|
|
|
|
2016-01-23 12:19:28 +00:00
|
|
|
func getCloudFile(pathname string, dest string) error {
|
2016-01-20 21:44:34 +00:00
|
|
|
client := http.Client{}
|
|
|
|
if req, err := http.NewRequest("GET", CloudDAVBase+pathname, nil); err != nil {
|
2016-01-23 11:19:47 +00:00
|
|
|
return err
|
2016-01-20 21:44:34 +00:00
|
|
|
} else {
|
|
|
|
req.SetBasicAuth(CloudUsername, CloudPassword)
|
|
|
|
if resp, err := client.Do(req); err != nil {
|
2016-01-23 11:19:47 +00:00
|
|
|
return err
|
2016-01-20 21:44:34 +00:00
|
|
|
} else {
|
|
|
|
defer resp.Body.Close()
|
2016-01-23 11:19:47 +00:00
|
|
|
|
|
|
|
if fd, err := os.Create(dest); err != nil {
|
|
|
|
return err
|
2016-01-20 21:44:34 +00:00
|
|
|
} else {
|
2016-01-23 12:19:28 +00:00
|
|
|
defer fd.Close()
|
2016-01-23 11:19:47 +00:00
|
|
|
|
|
|
|
if resp.StatusCode != http.StatusOK {
|
|
|
|
return errors.New(resp.Status)
|
|
|
|
} else {
|
|
|
|
writer := bufio.NewWriter(fd)
|
|
|
|
reader := bufio.NewReader(resp.Body)
|
|
|
|
reader.WriteTo(writer)
|
|
|
|
writer.Flush()
|
|
|
|
}
|
2016-01-20 21:44:34 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2016-01-23 11:19:47 +00:00
|
|
|
return nil
|
2016-01-20 21:44:34 +00:00
|
|
|
}
|