✨ Count post views
This commit is contained in:
parent
14c17eded8
commit
269e79ca58
@ -15,6 +15,7 @@ var AutoMaintainRange = []any{
|
|||||||
&models.Poll{},
|
&models.Poll{},
|
||||||
&models.PollAnswer{},
|
&models.PollAnswer{},
|
||||||
&models.PostFlag{},
|
&models.PostFlag{},
|
||||||
|
&models.PostView{},
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunMigration(source *gorm.DB) error {
|
func RunMigration(source *gorm.DB) error {
|
||||||
|
@ -2,13 +2,14 @@ package api
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"time"
|
||||||
|
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/models"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/models"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/services"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/services"
|
||||||
vocab "github.com/go-ap/activitypub"
|
vocab "github.com/go-ap/activitypub"
|
||||||
"github.com/gofiber/fiber/v2"
|
"github.com/gofiber/fiber/v2"
|
||||||
"github.com/samber/lo"
|
"github.com/samber/lo"
|
||||||
"time"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func apGetPublisher(c *fiber.Ctx) error {
|
func apGetPublisher(c *fiber.Ctx) error {
|
||||||
@ -42,7 +43,7 @@ func apGetPost(c *fiber.Ctx) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "published_at DESC")
|
items, err := services.ListPost(tx, take, offset, "published_at DESC", nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -2,13 +2,14 @@ package api
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
|
||||||
"git.solsynth.dev/hypernet/nexus/pkg/nex/cruda"
|
"git.solsynth.dev/hypernet/nexus/pkg/nex/cruda"
|
||||||
"git.solsynth.dev/hypernet/nexus/pkg/nex/sec"
|
"git.solsynth.dev/hypernet/nexus/pkg/nex/sec"
|
||||||
"git.solsynth.dev/hypernet/passport/pkg/authkit"
|
"git.solsynth.dev/hypernet/passport/pkg/authkit"
|
||||||
authm "git.solsynth.dev/hypernet/passport/pkg/authkit/models"
|
authm "git.solsynth.dev/hypernet/passport/pkg/authkit/models"
|
||||||
"gorm.io/gorm"
|
"gorm.io/gorm"
|
||||||
"strconv"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/gap"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/gap"
|
||||||
@ -114,13 +115,18 @@ func searchPost(c *fiber.Ctx) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
countTx := tx
|
countTx := tx
|
||||||
count, err := services.CountPost(countTx)
|
count, err := services.CountPost(countTx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "published_at DESC")
|
items, err := services.ListPost(tx, take, offset, "published_at DESC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
@ -150,13 +156,18 @@ func listPost(c *fiber.Ctx) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
countTx := tx
|
countTx := tx
|
||||||
count, err := services.CountPost(countTx)
|
count, err := services.CountPost(countTx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "published_at DESC")
|
items, err := services.ListPost(tx, take, offset, "published_at DESC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
@ -222,12 +233,17 @@ func listDraftPost(c *fiber.Ctx) error {
|
|||||||
|
|
||||||
tx := services.FilterPostWithAuthorDraft(database.C, user.ID)
|
tx := services.FilterPostWithAuthorDraft(database.C, user.ID)
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
count, err := services.CountPost(tx)
|
count, err := services.CountPost(tx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "created_at DESC", true)
|
items, err := services.ListPost(tx, take, offset, "created_at DESC", userId, true)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -28,7 +28,12 @@ func listPinnedPost(c *fiber.Ctx) error {
|
|||||||
tx = tx.Where("publisher_id = ?", user.ID)
|
tx = tx.Where("publisher_id = ?", user.ID)
|
||||||
tx = tx.Where("pinned_at IS NOT NULL")
|
tx = tx.Where("pinned_at IS NOT NULL")
|
||||||
|
|
||||||
items, err := services.ListPost(tx, 100, 0, "published_at DESC")
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
|
items, err := services.ListPost(tx, 100, 0, "published_at DESC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -25,8 +25,13 @@ func listRecommendation(c *fiber.Ctx) error {
|
|||||||
return item.ID
|
return item.ID
|
||||||
})
|
})
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
tx := database.C.Where("id IN ?", postIdx)
|
tx := database.C.Where("id IN ?", postIdx)
|
||||||
newPosts, err := services.ListPost(tx, featuredMax, 0, "id ASC")
|
newPosts, err := services.ListPost(tx, featuredMax, 0, "id ASC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
@ -65,6 +70,11 @@ func listRecommendationFriends(c *fiber.Ctx) error {
|
|||||||
|
|
||||||
tx = tx.Where("publisher_id IN ?", friendList)
|
tx = tx.Where("publisher_id IN ?", friendList)
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
countTx := tx
|
countTx := tx
|
||||||
count, err := services.CountPost(countTx)
|
count, err := services.CountPost(countTx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -76,7 +86,7 @@ func listRecommendationFriends(c *fiber.Ctx) error {
|
|||||||
order = "published_at DESC, (COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC"
|
order = "published_at DESC, (COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC"
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, order)
|
items, err := services.ListPost(tx, take, offset, order, userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
@ -106,13 +116,18 @@ func listRecommendationShuffle(c *fiber.Ctx) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
countTx := tx
|
countTx := tx
|
||||||
count, err := services.CountPost(countTx)
|
count, err := services.CountPost(countTx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "RANDOM()")
|
items, err := services.ListPost(tx, take, offset, "RANDOM()", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -2,9 +2,11 @@ package api
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/models"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/models"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/services"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/services"
|
||||||
|
authm "git.solsynth.dev/hypernet/passport/pkg/authkit/models"
|
||||||
"github.com/gofiber/fiber/v2"
|
"github.com/gofiber/fiber/v2"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -35,12 +37,17 @@ func listPostReplies(c *fiber.Ctx) error {
|
|||||||
tx = services.FilterPostWithTag(tx, c.Query("tag"))
|
tx = services.FilterPostWithTag(tx, c.Query("tag"))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
count, err := services.CountPost(tx)
|
count, err := services.CountPost(tx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, offset, "published_at DESC")
|
items, err := services.ListPost(tx, take, offset, "published_at DESC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
@ -55,6 +62,11 @@ func listPostFeaturedReply(c *fiber.Ctx) error {
|
|||||||
take := c.QueryInt("take", 0)
|
take := c.QueryInt("take", 0)
|
||||||
take = max(1, min(take, 3))
|
take = max(1, min(take, 3))
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
tx := database.C
|
tx := database.C
|
||||||
var post models.Post
|
var post models.Post
|
||||||
if err := database.C.Where("id = ?", c.Params("postId")).First(&post).Error; err != nil {
|
if err := database.C.Where("id = ?", c.Params("postId")).First(&post).Error; err != nil {
|
||||||
@ -78,7 +90,7 @@ func listPostFeaturedReply(c *fiber.Ctx) error {
|
|||||||
tx = services.FilterPostWithTag(tx, c.Query("tag"))
|
tx = services.FilterPostWithTag(tx, c.Query("tag"))
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, take, 0, "(COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC, published_at DESC")
|
items, err := services.ListPost(tx, take, 0, "(COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC, published_at DESC", userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -24,6 +24,11 @@ func getWhatsNew(c *fiber.Ctx) error {
|
|||||||
|
|
||||||
tx = tx.Where("id > ?", pivot)
|
tx = tx.Where("id > ?", pivot)
|
||||||
|
|
||||||
|
var userId *uint
|
||||||
|
if user, authenticated := c.Locals("user").(authm.Account); authenticated {
|
||||||
|
userId = &user.ID
|
||||||
|
}
|
||||||
|
|
||||||
countTx := tx
|
countTx := tx
|
||||||
count, err := services.CountPost(countTx)
|
count, err := services.CountPost(countTx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -35,7 +40,7 @@ func getWhatsNew(c *fiber.Ctx) error {
|
|||||||
order = "published_at DESC, (COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC"
|
order = "published_at DESC, (COALESCE(total_upvote, 0) - COALESCE(total_downvote, 0)) DESC"
|
||||||
}
|
}
|
||||||
|
|
||||||
items, err := services.ListPost(tx, 10, 0, order)
|
items, err := services.ListPost(tx, 10, 0, order, userId)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
return fiber.NewError(fiber.StatusBadRequest, err.Error())
|
||||||
}
|
}
|
||||||
|
@ -56,8 +56,10 @@ type Post struct {
|
|||||||
PublishedAt *time.Time `json:"published_at"`
|
PublishedAt *time.Time `json:"published_at"`
|
||||||
PublishedUntil *time.Time `json:"published_until"`
|
PublishedUntil *time.Time `json:"published_until"`
|
||||||
|
|
||||||
TotalUpvote int `json:"total_upvote"`
|
TotalUpvote int `json:"total_upvote"`
|
||||||
TotalDownvote int `json:"total_downvote"`
|
TotalDownvote int `json:"total_downvote"`
|
||||||
|
TotalViews int64 `json:"total_views"`
|
||||||
|
TotalAggressiveViews int64 `json:"total_aggressive_views"`
|
||||||
|
|
||||||
PollID *uint `json:"poll_id"`
|
PollID *uint `json:"poll_id"`
|
||||||
Poll *Poll `json:"poll"`
|
Poll *Poll `json:"poll"`
|
||||||
@ -111,3 +113,10 @@ type PostInsight struct {
|
|||||||
Post Post `json:"post"`
|
Post Post `json:"post"`
|
||||||
PostID uint `json:"post_id"`
|
PostID uint `json:"post_id"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type PostView struct {
|
||||||
|
AccountID uint `json:"account_id" gorm:"primaryKey"`
|
||||||
|
PostID uint `json:"post_id" gorm:"primaryKey"`
|
||||||
|
CreatedAt time.Time `json:"created_at"`
|
||||||
|
UpdatedAt time.Time `json:"updated_at"`
|
||||||
|
}
|
||||||
|
49
pkg/internal/services/post_views.go
Normal file
49
pkg/internal/services/post_views.go
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
package services
|
||||||
|
|
||||||
|
import (
|
||||||
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
||||||
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/models"
|
||||||
|
"gorm.io/gorm"
|
||||||
|
)
|
||||||
|
|
||||||
|
var postViewQueue []models.PostView
|
||||||
|
|
||||||
|
func AddPostView(post models.Post, account uint) {
|
||||||
|
postViewQueue = append(postViewQueue, models.PostView{
|
||||||
|
AccountID: account,
|
||||||
|
PostID: post.ID,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func AddPostViews(posts []models.Post, account uint) {
|
||||||
|
for _, post := range posts {
|
||||||
|
postViewQueue = append(postViewQueue, models.PostView{
|
||||||
|
AccountID: account,
|
||||||
|
PostID: post.ID,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func FlushPostViews() {
|
||||||
|
if len(postViewQueue) == 0 {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
workingQueue := make([]models.PostView, len(postViewQueue))
|
||||||
|
copy(workingQueue, postViewQueue)
|
||||||
|
clear(postViewQueue)
|
||||||
|
updateRequiredPost := make(map[uint]bool)
|
||||||
|
for _, item := range workingQueue {
|
||||||
|
updateRequiredPost[item.PostID] = true
|
||||||
|
}
|
||||||
|
_ = database.C.CreateInBatches(workingQueue, 1000).Error
|
||||||
|
for k := range updateRequiredPost {
|
||||||
|
var count int64
|
||||||
|
if err := database.C.Model(&models.PostView{}).Where("post_id = ?", k).Count(&count).Error; err != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
database.C.Model(&models.Post{}).Where("id = ?", k).Updates(map[string]any{
|
||||||
|
"total_views": count,
|
||||||
|
"total_aggressive_views": gorm.Expr("total_aggressive_views + ?", count),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
@ -262,7 +262,7 @@ func CountPostReactions(id uint) int64 {
|
|||||||
return count
|
return count
|
||||||
}
|
}
|
||||||
|
|
||||||
func ListPost(tx *gorm.DB, take int, offset int, order any, noReact ...bool) ([]*models.Post, error) {
|
func ListPost(tx *gorm.DB, take int, offset int, order any, user *uint, noReact ...bool) ([]*models.Post, error) {
|
||||||
if take > 100 {
|
if take > 100 {
|
||||||
take = 100
|
take = 100
|
||||||
}
|
}
|
||||||
@ -332,6 +332,12 @@ func ListPost(tx *gorm.DB, take int, offset int, order any, noReact ...bool) ([]
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if user != nil {
|
||||||
|
AddPostViews(lo.Map(items, func(item *models.Post, index int) models.Post {
|
||||||
|
return *item
|
||||||
|
}), *user)
|
||||||
|
}
|
||||||
|
|
||||||
return items, nil
|
return items, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,14 +2,15 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"os/signal"
|
||||||
|
"syscall"
|
||||||
|
|
||||||
pkg "git.solsynth.dev/hypernet/interactive/pkg/internal"
|
pkg "git.solsynth.dev/hypernet/interactive/pkg/internal"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/cache"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/cache"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/gap"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/gap"
|
||||||
"git.solsynth.dev/hypernet/nexus/pkg/nex/sec"
|
"git.solsynth.dev/hypernet/nexus/pkg/nex/sec"
|
||||||
"github.com/fatih/color"
|
"github.com/fatih/color"
|
||||||
"os"
|
|
||||||
"os/signal"
|
|
||||||
"syscall"
|
|
||||||
|
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/database"
|
||||||
"git.solsynth.dev/hypernet/interactive/pkg/internal/grpc"
|
"git.solsynth.dev/hypernet/interactive/pkg/internal/grpc"
|
||||||
@ -67,6 +68,7 @@ func main() {
|
|||||||
// Configure timed tasks
|
// Configure timed tasks
|
||||||
quartz := cron.New(cron.WithLogger(cron.VerbosePrintfLogger(&log.Logger)))
|
quartz := cron.New(cron.WithLogger(cron.VerbosePrintfLogger(&log.Logger)))
|
||||||
quartz.AddFunc("@every 60m", services.DoAutoDatabaseCleanup)
|
quartz.AddFunc("@every 60m", services.DoAutoDatabaseCleanup)
|
||||||
|
quartz.AddFunc("@every 1m", services.FlushPostViews)
|
||||||
quartz.Start()
|
quartz.Start()
|
||||||
|
|
||||||
// Initialize cache
|
// Initialize cache
|
||||||
|
Loading…
x
Reference in New Issue
Block a user