You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
bit4sat/api/handlers.go

183 lines
3.7 KiB
Go

package api
import (
"fmt"
"log"
"net/http"
"git.sp4ke.com/sp4ke/bit4sat/db"
"git.sp4ke.com/sp4ke/bit4sat/ln"
"git.sp4ke.com/sp4ke/bit4sat/storage"
"git.sp4ke.com/sp4ke/bit4sat/utils"
"github.com/gin-gonic/gin"
"github.com/mediocregopher/radix/v3"
)
func upSessionHandler(c *gin.Context) {
upSession, err := SessionStore.Get(c.Request, UpSessionKey)
if err != nil {
utils.JSONErrPriv(c, http.StatusInternalServerError, err)
return
}
lastUp, exists := upSession.Values["lastUp"]
if exists {
err = upSession.Save(c.Request, c.Writer)
if err != nil {
utils.JSONErrPriv(c, http.StatusInternalServerError, err)
return
}
// Get upload status
uId := lastUp.([]string)[0]
key := fmt.Sprintf("upload_status_%s", uId)
var upStatus storage.UpStatus
err := db.DB.Redis.Do(radix.FlatCmd(&upStatus, "GET", key))
if err != nil {
utils.JSONErrPriv(c, http.StatusInternalServerError,
fmt.Errorf("error finding upload status %s", lastUp))
fmt.Println(err)
return
}
invoice, err := storage.GetUploadInvoice(lastUp.(string))
if err != nil {
utils.JSONErrPriv(c, http.StatusInternalServerError, err)
return
}
// if invoice is not empty
c.JSON(http.StatusOK, gin.H{
"uploadId": lastUp,
"status": upStatus,
"invoice": invoice,
})
return
}
c.JSON(http.StatusOK, gin.H{
"uploadId": 0,
})
return
}
func pollInvoice(c *gin.Context) {
invoiceId := c.Param("rhash")
// First check if already paid
// Get the invoice from invoice_id
invoiceKey := fmt.Sprintf("invoice_%s", invoiceId)
invoice := ln.Invoice{}
err := db.DB.Redis.Do(radix.FlatCmd(&invoice, "GET", invoiceKey))
if err != nil {
utils.JSONErrPriv(c, http.StatusInternalServerError, err)
return
}
// If paid return ok
if invoice.Settled {
c.JSON(http.StatusOK, gin.H{
"invoice": invoice,
})
// Poll
} else {
invoiceChan := make(chan *ln.Invoice)
errorChan := make(chan error)
log.Printf("starting invoice poll for %s", invoice.RHash)
// If waiting payment, wait until invoice is paid
go ln.PollPaidInvoice(invoice.RHash, invoiceChan, errorChan)
select {
case invoice := <-invoiceChan:
// if expired return with expired response
if invoice.Expired {
c.JSON(http.StatusGone, gin.H{
"invoice": invoice,
})
return
}
////////////////
///// Invoice was paid
////////////////
//
log.Println("POLL: invoice was paid")
c.JSON(http.StatusOK, gin.H{
"invoice": invoice,
})
return
case err := <-errorChan:
utils.JSONErrPriv(c, http.StatusInternalServerError, err)
return
}
// We stopped waiting for the invoice, it must have expired
c.JSON(http.StatusGone, gin.H{
"invoice": invoice,
})
return
}
}
// Was used by ln-charge
func invoiceCbHandler(c *gin.Context) {
invoice := ln.Invoice{}
//dec := json.Decoder(c.Request.Body)
if err := c.ShouldBindJSON(&invoice); err != nil {
log.Println(err)
utils.JSONErr(c, http.StatusNotAcceptable,
"callback: could not parse request from charge api")
return
}
log.Printf("received invoice paid from ln charge\n%s", invoice)
c.Status(http.StatusOK)
// get upload id related to invoice
var uploadId string
invoiceUploadKey := fmt.Sprintf("invoice_%s_upload_id", invoice.RHash)
err := db.DB.Redis.Do(radix.FlatCmd(&uploadId, "GET", invoiceUploadKey))
if err != nil {
panic(err)
}
if uploadId == "" {
log.Printf("cannot find uploadId for invoice %s", invoice)
return
}
// Invoice paid !!!!
// Set upload status to paid
err = storage.SetUploadStatus(uploadId, storage.UpPaid)
if err != nil {
panic(err)
}
//
// Update Upload Invoice
err = storage.SetUploadInvoice(uploadId, &invoice)
if err != nil {
panic(err)
}
return
}