Allow for marked up file thumbnails to be shown and uploaded.
This commit is contained in:
parent
bebc161256
commit
563de29fcf
@ -5,6 +5,7 @@ import (
|
||||
"image"
|
||||
"image/png"
|
||||
"io"
|
||||
"log"
|
||||
"os"
|
||||
|
||||
"github.com/tardisx/discord-auto-upload/upload"
|
||||
@ -16,8 +17,18 @@ const (
|
||||
thumbnailMaxY = 128
|
||||
)
|
||||
|
||||
func (ip *Processor) ThumbPNG(ul *upload.Upload, w io.Writer) error {
|
||||
file, err := os.Open(ul.OriginalFilename)
|
||||
func (ip *Processor) ThumbPNG(ul *upload.Upload, which string, w io.Writer) error {
|
||||
|
||||
var filename string
|
||||
if which == "orig" {
|
||||
filename = ul.OriginalFilename
|
||||
} else if which == "markedup" {
|
||||
filename = ul.MarkedUpFilename
|
||||
} else {
|
||||
log.Fatal("was passed incorrect 'which' arg")
|
||||
}
|
||||
|
||||
file, err := os.Open(filename)
|
||||
if err != nil {
|
||||
return fmt.Errorf("could not open file: %s", err)
|
||||
}
|
||||
|
@ -14,7 +14,6 @@ import (
|
||||
"mime/multipart"
|
||||
"net/http"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"sync/atomic"
|
||||
"time"
|
||||
|
||||
@ -49,9 +48,8 @@ type Upload struct {
|
||||
Id int32 `json:"id"`
|
||||
UploadedAt time.Time `json:"uploaded_at"`
|
||||
|
||||
OriginalFilename string `json:"original_file"` // path on the local disk
|
||||
MarkedUpFilename string `json:"markedup_file"` // a temporary file, if the user did some markup
|
||||
TemporaryFileToUpload string // post-watermark, or just original if unwatermarked
|
||||
OriginalFilename string `json:"original_file"` // path on the local disk
|
||||
MarkedUpFilename string `json:"markedup_file"` // a temporary file, if the user did some markup
|
||||
|
||||
webhookURL string
|
||||
|
||||
@ -121,13 +119,6 @@ func (u *Upload) processUpload() error {
|
||||
return errors.New("webhook url not configured")
|
||||
}
|
||||
|
||||
if u.watermark {
|
||||
daulog.SendLog("Watermarking image", daulog.LogTypeInfo)
|
||||
u.applyWatermark()
|
||||
} else {
|
||||
u.TemporaryFileToUpload = u.OriginalFilename
|
||||
}
|
||||
|
||||
extraParams := map[string]string{}
|
||||
|
||||
if u.usernameOverride != "" {
|
||||
@ -152,7 +143,42 @@ func (u *Upload) processUpload() error {
|
||||
var retriesRemaining = 5
|
||||
for retriesRemaining > 0 {
|
||||
|
||||
request, err := newfileUploadRequest(u.webhookURL, extraParams, "file", u.TemporaryFileToUpload)
|
||||
// open an io.ReadCloser for the file we intend to upload
|
||||
var filedata *os.File
|
||||
var err error
|
||||
if len(u.MarkedUpFilename) > 0 {
|
||||
filedata, err = os.Open(u.MarkedUpFilename)
|
||||
if err != nil {
|
||||
log.Print("Error opening marked up file:", err)
|
||||
retriesRemaining--
|
||||
sleepForRetries(retriesRemaining)
|
||||
continue
|
||||
}
|
||||
} else {
|
||||
filedata, err = os.Open(u.OriginalFilename)
|
||||
if err != nil {
|
||||
log.Print("Error opening original file:", err)
|
||||
retriesRemaining--
|
||||
sleepForRetries(retriesRemaining)
|
||||
continue
|
||||
}
|
||||
}
|
||||
|
||||
var imageData io.Reader
|
||||
if u.watermark {
|
||||
daulog.SendLog("Watermarking image", daulog.LogTypeInfo)
|
||||
imageData, err = u.applyWatermark(filedata)
|
||||
if err != nil {
|
||||
log.Print("Error watermarking:", err)
|
||||
retriesRemaining--
|
||||
sleepForRetries(retriesRemaining)
|
||||
continue
|
||||
}
|
||||
} else {
|
||||
imageData = filedata
|
||||
}
|
||||
|
||||
request, err := newfileUploadRequest(u.webhookURL, extraParams, "file", "pikachu.png", imageData)
|
||||
if err != nil {
|
||||
log.Printf("error creating upload request: %s", err)
|
||||
return fmt.Errorf("could not create upload request: %s", err)
|
||||
@ -237,9 +263,9 @@ func (u *Upload) processUpload() error {
|
||||
}
|
||||
}
|
||||
|
||||
if u.watermark {
|
||||
daulog.SendLog(fmt.Sprintf("Removing temporary file: %s", u.TemporaryFileToUpload), daulog.LogTypeDebug)
|
||||
os.Remove(u.TemporaryFileToUpload)
|
||||
// remove any marked up file
|
||||
if len(u.MarkedUpFilename) > 0 {
|
||||
os.Remove(u.MarkedUpFilename)
|
||||
}
|
||||
|
||||
if retriesRemaining == 0 {
|
||||
@ -247,23 +273,19 @@ func (u *Upload) processUpload() error {
|
||||
u.State = StateFailed
|
||||
return errors.New("could not upload after all retries")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func newfileUploadRequest(uri string, params map[string]string, paramName, path string) (*http.Request, error) {
|
||||
file, err := os.Open(path)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("could not open file '%s': %s", path, err)
|
||||
}
|
||||
defer file.Close()
|
||||
func newfileUploadRequest(uri string, params map[string]string, paramName string, filename string, filedata io.Reader) (*http.Request, error) {
|
||||
|
||||
body := &bytes.Buffer{}
|
||||
writer := multipart.NewWriter(body)
|
||||
part, err := writer.CreateFormFile(paramName, filepath.Base(path))
|
||||
part, err := writer.CreateFormFile(paramName, filename)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
_, err = io.Copy(part, file)
|
||||
_, err = io.Copy(part, filedata)
|
||||
if err != nil {
|
||||
log.Fatal("Could not copy: ", err)
|
||||
}
|
||||
@ -281,20 +303,15 @@ func newfileUploadRequest(uri string, params map[string]string, paramName, path
|
||||
return req, err
|
||||
}
|
||||
|
||||
func (u *Upload) applyWatermark() {
|
||||
// applyWatermark applies the watermark to the image
|
||||
func (u *Upload) applyWatermark(in *os.File) (io.Reader, error) {
|
||||
|
||||
reader, err := os.Open(u.OriginalFilename)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
defer reader.Close()
|
||||
defer in.Close()
|
||||
|
||||
im, _, err := image.Decode(reader)
|
||||
im, _, err := image.Decode(in)
|
||||
if err != nil {
|
||||
daulog.SendLog(fmt.Sprintf("Cannot decode image: %v - skipping watermarking", err), daulog.LogTypeError)
|
||||
u.watermark = false
|
||||
u.TemporaryFileToUpload = u.OriginalFilename
|
||||
return
|
||||
return nil, errors.New("cannot decode image")
|
||||
}
|
||||
bounds := im.Bounds()
|
||||
// var S float64 = float64(bounds.Max.X)
|
||||
@ -315,16 +332,9 @@ func (u *Upload) applyWatermark() {
|
||||
|
||||
dc.DrawString("github.com/tardisx/discord-auto-upload", 5.0, float64(bounds.Max.Y)-5.0)
|
||||
|
||||
tempfile, err := ioutil.TempFile("", "dau")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
tempfile.Close()
|
||||
os.Remove(tempfile.Name())
|
||||
actualName := tempfile.Name() + ".png"
|
||||
|
||||
dc.SavePNG(actualName)
|
||||
u.TemporaryFileToUpload = actualName
|
||||
b := bytes.Buffer{}
|
||||
dc.EncodePNG(&b)
|
||||
return &b, nil
|
||||
}
|
||||
|
||||
func sleepForRetries(retry int) {
|
||||
|
5
web/data/alpine.js
Normal file
5
web/data/alpine.js
Normal file
File diff suppressed because one or more lines are too long
@ -23,7 +23,8 @@
|
||||
<button @click="skip_upload(ul.id)" type="button" class="btn btn-primary">reject</button>
|
||||
</td>
|
||||
<td>
|
||||
<td><a x-bind:href="'/editor.html?id='+ul.id"><img x-bind:src="'/rest/image/'+ul.id+'/thumb'"></a></td>
|
||||
<a x-bind:href="'/editor.html?id='+ul.id"><img x-bind:src="'/rest/image/'+ul.id+'/thumb'"></a>
|
||||
<a x-show="ul.markedup_file" x-bind:href="'/editor.html?id='+ul.id"><img x-bind:src="'/rest/image/'+ul.id+'/markedup_thumb'"></a>
|
||||
</td>
|
||||
</tr>
|
||||
</template>
|
||||
|
@ -7,7 +7,7 @@
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||
|
||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@4.6.0/dist/css/bootstrap.min.css" integrity="sha384-B0vP5xmATw1+K9KRQjQERJvTumQW0nPEzvF6L/Z6nronJ3oUOFUFpCjEUQouq2+l" crossorigin="anonymous">
|
||||
<script src="//unpkg.com/alpinejs" defer></script>
|
||||
<script src="/alpine.js" defer></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/fabric@4.6.0/dist/fabric.min.js"></script>
|
||||
|
||||
<style>
|
||||
|
@ -189,7 +189,31 @@ func (ws *WebService) imageThumb(w http.ResponseWriter, r *http.Request) {
|
||||
returnJSONError(w, "bad id")
|
||||
return
|
||||
}
|
||||
err = processor.ThumbPNG(ul, w)
|
||||
err = processor.ThumbPNG(ul, "orig", w)
|
||||
if err != nil {
|
||||
returnJSONError(w, "could not create thumb")
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
func (ws *WebService) imageMarkedupThumb(w http.ResponseWriter, r *http.Request) {
|
||||
|
||||
w.Header().Set("Content-Type", "image/png")
|
||||
processor := imageprocess.Processor{}
|
||||
|
||||
vars := mux.Vars(r)
|
||||
id, err := strconv.ParseInt(vars["id"], 10, 32)
|
||||
if err != nil {
|
||||
returnJSONError(w, "bad id")
|
||||
return
|
||||
}
|
||||
|
||||
ul := ws.Uploader.UploadById(int32(id))
|
||||
if ul == nil {
|
||||
returnJSONError(w, "bad id")
|
||||
return
|
||||
}
|
||||
err = processor.ThumbPNG(ul, "markedup", w)
|
||||
if err != nil {
|
||||
returnJSONError(w, "could not create thumb")
|
||||
return
|
||||
@ -268,7 +292,22 @@ func (ws *WebService) modifyUpload(w http.ResponseWriter, r *http.Request) {
|
||||
returnJSONError(w, err.Error())
|
||||
return
|
||||
}
|
||||
fmt.Printf("YAY %v", b)
|
||||
|
||||
// write to a temporary file
|
||||
tempfile, err := ioutil.TempFile("", "dau_markup")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
n, err := tempfile.Write(b)
|
||||
if n != len(b) {
|
||||
log.Fatalf("only wrote %d bytes??", n)
|
||||
}
|
||||
if err != nil {
|
||||
log.Fatalf("Could not write temp file: %v", err)
|
||||
}
|
||||
|
||||
tempfile.Close()
|
||||
anUpload.MarkedUpFilename = tempfile.Name()
|
||||
|
||||
} else {
|
||||
returnJSONError(w, "bad change type")
|
||||
@ -294,6 +333,8 @@ func (ws *WebService) StartWebServer() {
|
||||
r.HandleFunc("/rest/upload/{id:[0-9]+}/{change}", ws.modifyUpload)
|
||||
|
||||
r.HandleFunc("/rest/image/{id:[0-9]+}/thumb", ws.imageThumb)
|
||||
r.HandleFunc("/rest/image/{id:[0-9]+}/markedup_thumb", ws.imageMarkedupThumb)
|
||||
|
||||
r.HandleFunc("/rest/image/{id:[0-9]+}", ws.image)
|
||||
|
||||
r.HandleFunc("/rest/config", ws.handleConfig)
|
||||
|
Loading…
x
Reference in New Issue
Block a user