diff --git a/createdb.sql b/createdb.sql index 50f018a..6f09ddf 100644 --- a/createdb.sql +++ b/createdb.sql @@ -129,3 +129,14 @@ CREATE TABLE visits ( ); CREATE INDEX CONCURRENTLY visits_downloads_idx on visits(downloads DESC NULLS LAST); CREATE INDEX CONCURRENTLY visits_views_idx on visits(views DESC NULLS LAST); + + +CREATE TABLE submissions ( + id serial unique, + submission_id varchar(16), + filename text, + status text, + book_id varchar(16) unique REFERENCES books(id) ON DELETE SET NULL +); +CREATE INDEX CONCURRENTLY submissions_id_idx on submissions(submission_id); +CREATE INDEX CONCURRENTLY submissions_book_idx on submissions(book_id); diff --git a/lib/admin.go b/lib/admin.go index 510122a..c996d3f 100644 --- a/lib/admin.go +++ b/lib/admin.go @@ -34,6 +34,10 @@ func deleteHandler(h handler) { h.sess.Notify("Book not found!", "The book with id '"+id+"' is not there", "error") continue } + err = h.db.UpdateSubmissionByBook(id, "Rejected", nil) + if err != nil { + log.Error("There was a problem updating the submission: ", err) + } h.store.Delete(id) h.db.DeleteBook(id) @@ -216,6 +220,12 @@ func storeHandler(h handler) { log.Error("Error storing book '", book.Title, "': ", err.Error()) continue } + + err = h.db.UpdateSubmissionByBook(id, "Included in the library", &book) + if err != nil { + log.Error("There was a problem updating the submission: ", err) + } + titles = append(titles, book.Title) } if titles != nil { diff --git a/lib/database/database.go b/lib/database/database.go index c27655d..89fe83b 100644 --- a/lib/database/database.go +++ b/lib/database/database.go @@ -27,6 +27,10 @@ type DB interface { IncViews(ID string) error IncDownloads(ID string) error GetFrontPage() FrontPage + AddSubmission(submission Submission) (id int, err error) + UpdateSubmission(id int, status string, book *Book) error + UpdateSubmissionByBook(bookID string, status string, book *Book) error + GetSubmission(submissionID string) (submission []Submission, err error) } const ( diff --git a/lib/database/ro.go b/lib/database/ro.go index e195d12..00d4be4 100644 --- a/lib/database/ro.go +++ b/lib/database/ro.go @@ -88,3 +88,19 @@ func (db *roDB) IncDownloads(ID string) error { func (db *roDB) GetFrontPage() FrontPage { return db.db.GetFrontPage() } + +func (db *roDB) AddSubmission(submission Submission) (id int, err error) { + return 0, errors.New("RO database") +} + +func (db *roDB) UpdateSubmission(id int, status string, book *Book) error { + return errors.New("RO database") +} + +func (db *roDB) UpdateSubmissionByBook(bookID string, status string, book *Book) error { + return errors.New("RO database") +} + +func (db *roDB) GetSubmission(submissionID string) (submission []Submission, err error) { + return db.db.GetSubmission(submissionID) +} diff --git a/lib/database/submissions.go b/lib/database/submissions.go new file mode 100644 index 0000000..3fa3405 --- /dev/null +++ b/lib/database/submissions.go @@ -0,0 +1,48 @@ +package database + +type Submission struct { + ID int + SubmissionID string + Filename string + Status string + BookID string + Book *Book +} + +func (db *pgDB) AddSubmission(submission Submission) (id int, err error) { + err = db.sql.Insert(&submission) + return submission.ID, err +} + +func (db *pgDB) UpdateSubmission(id int, status string, book *Book) error { + _, err := db.sql.Model(&Submission{}). + Set("status = ?", status). + Set("book_id = ?", extractID(book)). + Where("id = ?", id). + Update() + return err +} + +func (db *pgDB) UpdateSubmissionByBook(bookID string, status string, book *Book) error { + _, err := db.sql.Model(&Submission{}). + Set("status = ?", status). + Set("book_id = ?", extractID(book)). + Where("book_id = ?", bookID). + Update() + return err +} + +func (db *pgDB) GetSubmission(submissionID string) (submission []Submission, err error) { + err = db.sql.Model(&submission). + Column("Book"). + Where("submission_id = ?", submissionID). + Select() + return +} + +func extractID(book *Book) interface{} { + if book == nil { + return nil + } + return book.ID +} diff --git a/lib/template.go b/lib/template.go index f7e5992..d1a7801 100644 --- a/lib/template.go +++ b/lib/template.go @@ -65,6 +65,7 @@ func InitTemplate(assetsPath string) *Template { path.Join(templatePath, "book.html"), path.Join(templatePath, "search.html"), path.Join(templatePath, "upload.html"), + path.Join(templatePath, "submission.html"), path.Join(templatePath, "login.html"), path.Join(templatePath, "new.html"), path.Join(templatePath, "read.html"), diff --git a/lib/trantor.go b/lib/trantor.go index 6e21896..84bb6f1 100644 --- a/lib/trantor.go +++ b/lib/trantor.go @@ -169,6 +169,7 @@ func InitRouter(db database.DB, sg *StatsGatherer, assetsPath string) http.Handl r.HandleFunc("/search/", sg.Gather(searchHandler)) r.HandleFunc("/upload/", sg.Gather(uploadHandler)).Methods("GET") r.HandleFunc("/upload/", sg.Gather(uploadPostHandler)).Methods("POST") + r.HandleFunc("/submission/{id:"+idPattern+"}", sg.Gather(submissionHandler)) r.HandleFunc("/read/{id:"+idPattern+"}", sg.Gather(readStartHandler)) r.HandleFunc("/read/{id:"+idPattern+"}/{file:.*}", sg.Gather(readHandler)) r.HandleFunc("/content/{id:"+idPattern+"}/{file:.*}", sg.Gather(contentHandler)) diff --git a/lib/upload.go b/lib/upload.go index 4bf368b..72e33f3 100644 --- a/lib/upload.go +++ b/lib/upload.go @@ -9,6 +9,7 @@ import ( "io/ioutil" "mime/multipart" + "github.com/gorilla/mux" "github.com/meskio/epubgo" "gitlab.com/trantor/trantor/lib/database" "gitlab.com/trantor/trantor/lib/parser" @@ -29,6 +30,7 @@ var uploadChannel chan uploadRequest type uploadRequest struct { file multipart.File filename string + id int } func uploadWorker(database database.DB, store storage.Store) { @@ -43,6 +45,7 @@ func processFile(req uploadRequest, db database.DB, store storage.Store) { epub, err := openMultipartEpub(req.file) if err != nil { log.Warn("Not valid epub uploaded file ", req.filename, ": ", err) + db.UpdateSubmission(req.id, "It is not a valid epub file", nil) return } defer epub.Close() @@ -54,6 +57,7 @@ func processFile(req uploadRequest, db database.DB, store storage.Store) { size, err := store.Store(book.ID, req.file, epubFile) if err != nil { log.Error("Error storing book (", book.ID, "): ", err) + db.UpdateSubmission(req.id, "There was a problem in our server", nil) return } @@ -63,9 +67,11 @@ func processFile(req uploadRequest, db database.DB, store storage.Store) { err = db.AddBook(book) if err != nil { log.Error("Error storing metadata (", book.ID, "): ", err) + db.UpdateSubmission(req.id, "There was a problem in our server", nil) return } log.Info("File uploaded: ", req.filename) + db.UpdateSubmission(req.id, "Waiting for moderation", &book) } func uploadPostHandler(h handler) { @@ -75,33 +81,41 @@ func uploadPostHandler(h handler) { return } - problem := false - h.r.ParseMultipartForm(20000000) filesForm := h.r.MultipartForm.File["epub"] + submissionID := genID() for _, f := range filesForm { + submission := database.Submission{ + SubmissionID: submissionID, + Filename: f.Filename, + Status: "Waiting to be processed", + } + file, err := f.Open() if err != nil { log.Error("Can not open uploaded file ", f.Filename, ": ", err) h.sess.Notify("Upload problem!", "There was a problem with book "+f.Filename, "error") - problem = true + submission.Status = "It was not possible to read the book" + h.db.AddSubmission(submission) continue } - uploadChannel <- uploadRequest{file, f.Filename} - } - if !problem { - if len(filesForm) > 0 { - h.sess.Notify("Upload successful!", "Thank you for your contribution", "success") - } else { - h.sess.Notify("Upload problem!", "No books where uploaded.", "error") + id, err := h.db.AddSubmission(submission) + if err != nil { + log.Error("Can add submission to db for ", f.Filename, ": ", err) } + uploadChannel <- uploadRequest{file, f.Filename, id} } - uploadHandler(h) + _uploadHandler(h, submissionID) } func uploadHandler(h handler) { + _uploadHandler(h, "") +} + +func _uploadHandler(h handler, submissionID string) { var data uploadData + data.SubmissionID = submissionID data.S = GetStatus(h) data.S.Title = "Upload -- " + data.S.Title data.S.Upload = true @@ -109,7 +123,27 @@ func uploadHandler(h handler) { } type uploadData struct { - S Status + S Status + SubmissionID string +} + +func submissionHandler(h handler) { + var data submissionData + var err error + + submissionID := mux.Vars(h.r)["id"] + data.Submissions, err = h.db.GetSubmission(submissionID) + if err != nil { + log.Error("Can get submission ", submissionID, ": ", err) + } + data.S = GetStatus(h) + data.S.Title = "Submission -- " + data.S.Title + h.load("submission", data) +} + +type submissionData struct { + S Status + Submissions []database.Submission } func openMultipartEpub(file multipart.File) (*epubgo.Epub, error) { diff --git a/templates/book.html b/templates/book.html index 4c92128..c788b8a 100644 --- a/templates/book.html +++ b/templates/book.html @@ -19,7 +19,11 @@ function delBook(){
-

{{.Title}}

+

{{.Title}} + {{if not .Active}} + waiting for moderation + {{end}} +

diff --git a/templates/read.html b/templates/read.html index 62abfe0..504083d 100644 --- a/templates/read.html +++ b/templates/read.html @@ -6,9 +6,13 @@ ← Prev {{end}} +{{if .Book.Active}}
  • Back
  • +{{else}} + waiting for moderation +{{end}} {{if .Next}}