1
0
mirror of https://github.com/mgerb/go-discord-bot synced 2026-01-10 09:02:49 +00:00

back end done for video archiving

This commit is contained in:
2018-08-20 23:37:58 -05:00
parent e593472c84
commit 5a542e0ffb
16 changed files with 272 additions and 125 deletions

View File

@@ -7,17 +7,21 @@ import (
_ "github.com/jinzhu/gorm/dialects/sqlite" _ "github.com/jinzhu/gorm/dialects/sqlite"
) )
// Conn - database connection var conn *gorm.DB
var Conn *gorm.DB
// Init - initialize database // Init - initialize database
func Init() { func Init(migrations ...interface{}) {
var err error var err error
Conn, err = gorm.Open("sqlite3", "data.db") conn, err = gorm.Open("sqlite3", "data.db")
if err != nil { if err != nil {
panic("failed to connect database") panic("failed to connect database")
} }
conn.DB().SetMaxIdleConns(1)
Conn.DB().SetMaxIdleConns(1) conn.AutoMigrate(migrations...)
}
// GetConn - get db connection
func GetConn() *gorm.DB {
return conn
} }

View File

@@ -26,7 +26,7 @@ type Message struct {
// Save - // Save -
func (m *Message) Save() error { func (m *Message) Save() error {
return db.Conn.Save(m).Error return db.GetConn().Save(m).Error
} }
// Attachment - discord message attachment // Attachment - discord message attachment
@@ -55,5 +55,5 @@ type User struct {
// Save - // Save -
func (u *User) Save() error { func (u *User) Save() error {
return db.Conn.Save(u).Error return db.GetConn().Save(u).Error
} }

View File

@@ -15,7 +15,7 @@ var linkedPostsCache map[string]int
// GetMessages - returns all messages - must use paging // GetMessages - returns all messages - must use paging
func GetMessages(page int) ([]Message, error) { func GetMessages(page int) ([]Message, error) {
messages := []Message{} messages := []Message{}
err := db.Conn.Offset(page*100).Limit(100).Order("timestamp desc", true).Preload("User").Find(&messages).Error err := db.GetConn().Offset(page*100).Limit(100).Order("timestamp desc", true).Preload("User").Find(&messages).Error
return messages, err return messages, err
} }
@@ -28,7 +28,7 @@ func GetLinkedMessages() (map[string]int, error) {
} }
result := []map[string]interface{}{} result := []map[string]interface{}{}
rows, err := db.Conn.Table("messages"). rows, err := db.GetConn().Table("messages").
Select("users.username, messages.content"). Select("users.username, messages.content").
Joins("join users on messages.user_id = users.id"). Joins("join users on messages.user_id = users.id").
Rows() Rows()

View File

@@ -8,6 +8,7 @@ import (
"github.com/mgerb/go-discord-bot/server/db" "github.com/mgerb/go-discord-bot/server/db"
"github.com/mgerb/go-discord-bot/server/logger" "github.com/mgerb/go-discord-bot/server/logger"
"github.com/mgerb/go-discord-bot/server/webserver" "github.com/mgerb/go-discord-bot/server/webserver"
"github.com/mgerb/go-discord-bot/server/webserver/model"
log "github.com/sirupsen/logrus" log "github.com/sirupsen/logrus"
) )
@@ -20,8 +21,13 @@ func init() {
config.Init() config.Init()
if config.Config.Logger { if config.Config.Logger {
db.Init() migrations := []interface{}{
db.Conn.AutoMigrate(&logger.Message{}, &logger.Attachment{}, &logger.User{}) &logger.Message{},
&logger.Attachment{},
&logger.User{},
&model.VideoArchive{},
}
db.Init(migrations...)
} }
} }

View File

@@ -1,10 +0,0 @@
package handlers
import (
"github.com/gin-gonic/gin"
"github.com/mgerb/go-discord-bot/server/config"
)
func GetClientID(c *gin.Context) {
c.JSON(200, map[string]string{"id": config.Config.ClientID})
}

View File

@@ -0,0 +1,39 @@
package model
import (
"time"
"github.com/jinzhu/gorm"
)
// VideoArchive -
type VideoArchive struct {
ID uint `gorm:"primary_key" json:"id"`
CreatedAt time.Time `json:"created_at"`
UpdatedAt time.Time `json:"updated_at"`
YoutubeID string `gorm:"column:youtube_id" json:"youtube_id"`
URL string `gorm:"column:url" json:"url"`
Title string `json:"title"`
Description string `json:"description"`
DatePublished time.Time `json:"date_published"`
Author string `json:"author"`
Duration int `json:"duration"`
UploadedBy string `json:"uploaded_by"`
}
// VideoArchiveSave -
func VideoArchiveSave(conn *gorm.DB, v *VideoArchive) error {
return conn.Save(v).Error
}
// VideoArchiveDelete -
func VideoArchiveDelete(conn *gorm.DB, id string) error {
return conn.Unscoped().Delete(VideoArchive{}, "id = ?", id).Error
}
// VideoArchiveList - return list of all video archives
func VideoArchiveList(conn *gorm.DB) ([]VideoArchive, error) {
v := []VideoArchive{}
err := conn.Find(&v).Error
return v, err
}

View File

@@ -1,67 +0,0 @@
package pubg
/**
* DEPRECATED
* I no longer have a use for this so I'm ripping it out
*/
import (
"sync"
"time"
"github.com/gin-gonic/gin"
pubgClient "github.com/mgerb/go-pubg"
log "github.com/sirupsen/logrus"
)
var (
apiKey string
stats = map[string]*pubgClient.Player{}
mut = &sync.Mutex{}
)
// Start -
func Start(key string, players []string) {
apiKey = key
log.Debug("Gathering pubg data...")
go fetchStats(players)
}
func fetchStats(players []string) {
api, err := pubgClient.New(apiKey)
if err != nil {
log.Fatal(err)
}
// fetch new stats every 30 seconds
for {
for _, player := range players {
newStats, err := api.GetPlayer(player)
if err != nil {
log.Error(err)
continue
}
mut.Lock()
stats[player] = newStats
mut.Unlock()
time.Sleep(time.Second * 2)
}
time.Sleep(time.Second * 30)
}
}
// Handler - returns the pubg stats
func Handler(c *gin.Context) {
c.JSON(200, stats)
}

View File

@@ -0,0 +1,32 @@
package response
import (
"net/http"
"github.com/gin-gonic/gin"
log "github.com/sirupsen/logrus"
)
// BadRequest -
func BadRequest(c *gin.Context, message string) {
dataMap := map[string]string{
"data": message,
}
c.JSON(http.StatusBadRequest, dataMap)
}
// TODO: don't return the error on production
// InternalError -
func InternalError(c *gin.Context, err error) {
log.Error(err)
c.JSON(http.StatusInternalServerError, err)
}
// Success -
func Success(c *gin.Context, data interface{}) {
dataMap := map[string]interface{}{
"data": data,
}
c.JSON(http.StatusOK, dataMap)
}

View File

@@ -0,0 +1,15 @@
package routes
import (
"github.com/gin-gonic/gin"
"github.com/mgerb/go-discord-bot/server/config"
)
// AddConfigRoutes -
func AddConfigRoutes(group *gin.RouterGroup) {
group.GET("/config/client_id", getClientIDHandler)
}
func getClientIDHandler(c *gin.Context) {
c.JSON(200, map[string]string{"id": config.Config.ClientID})
}

View File

@@ -1,4 +1,4 @@
package handlers package routes
import ( import (
"bytes" "bytes"
@@ -11,8 +11,12 @@ import (
log "github.com/sirupsen/logrus" log "github.com/sirupsen/logrus"
) )
// Downloader - // AddDownloaderRoutes -
func Downloader(c *gin.Context) { func AddDownloaderRoutes(group *gin.RouterGroup) {
group.GET("/ytdownloader", downloaderHandler)
}
func downloaderHandler(c *gin.Context) {
url := c.Query("url") url := c.Query("url")
fileType := c.Query("fileType") fileType := c.Query("fileType")

View File

@@ -1,4 +1,4 @@
package handlers package routes
import ( import (
"strconv" "strconv"
@@ -7,8 +7,13 @@ import (
"github.com/mgerb/go-discord-bot/server/logger" "github.com/mgerb/go-discord-bot/server/logger"
) )
// GetMessages - get all messages // AddLoggerRoutes -
func GetMessages(c *gin.Context) { func AddLoggerRoutes(group *gin.RouterGroup) {
group.GET("/logger/messages", getMessagesHandler)
group.GET("/logger/linkedmessages", getLinkedMessagesHandler)
}
func getMessagesHandler(c *gin.Context) {
page, err := strconv.Atoi(c.Query("page")) page, err := strconv.Atoi(c.Query("page"))
if err != nil { if err != nil {
@@ -25,8 +30,7 @@ func GetMessages(c *gin.Context) {
c.JSON(200, messages) c.JSON(200, messages)
} }
// GetLinkedMessages - func getLinkedMessagesHandler(c *gin.Context) {
func GetLinkedMessages(c *gin.Context) {
posts, err := logger.GetLinkedMessages() posts, err := logger.GetLinkedMessages()
if err != nil { if err != nil {

View File

@@ -1,4 +1,4 @@
package handlers package routes
import ( import (
"github.com/gin-gonic/gin" "github.com/gin-gonic/gin"
@@ -13,8 +13,12 @@ type oauthReq struct {
Code string `json:"code"` Code string `json:"code"`
} }
// Oauth - // AddOauthRoutes -
func Oauth(c *gin.Context) { func AddOauthRoutes(group *gin.RouterGroup) {
group.POST("/oauth", oauthHandler)
}
func oauthHandler(c *gin.Context) {
var json oauthReq var json oauthReq

View File

@@ -1,4 +1,4 @@
package handlers package routes
import ( import (
"io/ioutil" "io/ioutil"
@@ -17,8 +17,13 @@ type sound struct {
Extension string `json:"extension"` Extension string `json:"extension"`
} }
// SoundList - // AddSoundListRoutes -
func SoundList(c *gin.Context) { func AddSoundListRoutes(group *gin.RouterGroup) {
group.GET("/soundlist", soundListHandler)
group.GET("/cliplist", clipListHandler)
}
func soundListHandler(c *gin.Context) {
soundList, err := readSoundsDir(config.Config.SoundsPath) soundList, err := readSoundsDir(config.Config.SoundsPath)
@@ -31,8 +36,7 @@ func SoundList(c *gin.Context) {
c.JSON(200, soundList) c.JSON(200, soundList)
} }
// ClipList - func clipListHandler(c *gin.Context) {
func ClipList(c *gin.Context) {
clipList, err := readSoundsDir(config.Config.ClipsPath) clipList, err := readSoundsDir(config.Config.ClipsPath)

View File

@@ -1,4 +1,4 @@
package handlers package routes
import ( import (
"os" "os"
@@ -8,11 +8,16 @@ import (
"github.com/gin-gonic/gin" "github.com/gin-gonic/gin"
"github.com/mgerb/go-discord-bot/server/config" "github.com/mgerb/go-discord-bot/server/config"
"github.com/mgerb/go-discord-bot/server/webserver/middleware"
log "github.com/sirupsen/logrus" log "github.com/sirupsen/logrus"
) )
// FileUpload - // AddUploadRoutes - add file upload routes
func FileUpload(c *gin.Context) { func AddUploadRoutes(group *gin.RouterGroup) {
group.POST("/upload", middleware.AuthorizedJWT(), fileUploadHandler)
}
func fileUploadHandler(c *gin.Context) {
// originalClaims, _ := c.Get("claims") // originalClaims, _ := c.Get("claims")
// claims, _ := originalClaims.(*middleware.CustomClaims) // claims, _ := originalClaims.(*middleware.CustomClaims)

View File

@@ -0,0 +1,104 @@
package routes
import (
"errors"
"github.com/gin-gonic/gin"
"github.com/mgerb/go-discord-bot/server/db"
"github.com/mgerb/go-discord-bot/server/webserver/middleware"
"github.com/mgerb/go-discord-bot/server/webserver/model"
"github.com/mgerb/go-discord-bot/server/webserver/response"
"github.com/rylio/ytdl"
)
// AddVideoArchiveRoutes -
func AddVideoArchiveRoutes(group *gin.RouterGroup) {
group.GET("/video-archives", listVideoArchivesHandler)
authGroup := group.Group("", middleware.AuthorizedJWT())
authGroup.POST("/video-archives", middleware.AuthPermissions(middleware.PermMod), postVideoArchivesHandler)
authGroup.DELETE("/video-archives/:id", middleware.AuthPermissions(middleware.PermAdmin), deleteVideoArchivesHandler)
}
func listVideoArchivesHandler(c *gin.Context) {
archives, err := model.VideoArchiveList(db.GetConn())
if err != nil {
response.InternalError(c, err)
return
}
response.Success(c, archives)
}
func deleteVideoArchivesHandler(c *gin.Context) {
id := c.Param("id")
if id == "" {
response.BadRequest(c, "Invalid ID")
return
}
err := model.VideoArchiveDelete(db.GetConn(), id)
if err != nil {
response.InternalError(c, err)
return
}
response.Success(c, "deleted")
}
func postVideoArchivesHandler(c *gin.Context) {
params := struct {
URL string `json:"url"`
}{}
c.BindJSON(&params)
if params.URL == "" {
response.BadRequest(c, "URL Required")
return
}
cl, _ := c.Get("claims")
claims, ok := cl.(*middleware.CustomClaims)
if !ok {
response.InternalError(c, errors.New("Claims error"))
return
}
info, err := ytdl.GetVideoInfo(params.URL)
if err != nil {
response.InternalError(c, err)
return
}
// if title and author are blank
if info.Title == "" && info.Author == "" {
response.BadRequest(c, "Invalid URL")
return
}
videoArchive := model.VideoArchive{
Author: info.Author,
DatePublished: info.DatePublished,
Description: info.Description,
Duration: int(info.Duration.Seconds()),
Title: info.Title,
URL: params.URL,
YoutubeID: info.ID,
UploadedBy: claims.Username,
}
err = model.VideoArchiveSave(db.GetConn(), &videoArchive)
if err != nil {
response.InternalError(c, err)
return
}
response.Success(c, "saved")
}

View File

@@ -1,12 +1,14 @@
package webserver package webserver
import ( import (
"strings"
"github.com/gobuffalo/packr" "github.com/gobuffalo/packr"
"github.com/mgerb/go-discord-bot/server/webserver/response"
"github.com/gin-gonic/gin" "github.com/gin-gonic/gin"
"github.com/mgerb/go-discord-bot/server/config" "github.com/mgerb/go-discord-bot/server/config"
"github.com/mgerb/go-discord-bot/server/webserver/handlers" "github.com/mgerb/go-discord-bot/server/webserver/routes"
"github.com/mgerb/go-discord-bot/server/webserver/middleware"
) )
func getRouter() *gin.Engine { func getRouter() *gin.Engine {
@@ -19,29 +21,30 @@ func getRouter() *gin.Engine {
router.Static("/public/youtube", config.Config.YoutubePath) router.Static("/public/youtube", config.Config.YoutubePath)
router.Static("/public/clips", config.Config.ClipsPath) router.Static("/public/clips", config.Config.ClipsPath)
router.NoRoute(func(c *gin.Context) {
c.Data(200, "text/html", box.Bytes("index.html"))
})
api := router.Group("/api") api := router.Group("/api")
api.GET("/ytdownloader", handlers.Downloader)
api.GET("/soundlist", handlers.SoundList)
api.GET("/cliplist", handlers.ClipList)
api.POST("/oauth", handlers.Oauth)
api.GET("/logger/messages", handlers.GetMessages)
api.GET("/logger/linkedmessages", handlers.GetLinkedMessages)
api.GET("/config/client_id", handlers.GetClientID)
authorizedAPI := router.Group("/api") // add api routes
authorizedAPI.Use(middleware.AuthorizedJWT()) routes.AddSoundListRoutes(api)
authorizedAPI.POST("/upload", handlers.FileUpload) routes.AddOauthRoutes(api)
routes.AddLoggerRoutes(api)
routes.AddDownloaderRoutes(api)
routes.AddConfigRoutes(api)
routes.AddUploadRoutes(api)
routes.AddVideoArchiveRoutes(api)
router.NoRoute(func(c *gin.Context) {
if strings.HasPrefix(c.Request.URL.String(), "/api/") {
response.BadRequest(c, "404 Not Found")
} else {
c.Data(200, "text/html", box.Bytes("index.html"))
}
})
return router return router
} }
// Start - // Start -
func Start() { func Start() {
router := getRouter() router := getRouter()
router.Run(config.Config.ServerAddr) router.Run(config.Config.ServerAddr)
} }