Experiment with eliminating allocations.
Encode png images as pngs rather than turning them into jpgs. Shorten things to eliminate bytes and boilerplate. Remove some old code.
This commit is contained in:
parent
d9cffb2c5f
commit
eb49dde076
|
@ -48,16 +48,17 @@ type DefaultAttachmentStore struct {
|
|||
}
|
||||
|
||||
func NewDefaultAttachmentStore(acc *qgen.Accumulator) (*DefaultAttachmentStore, error) {
|
||||
a := "attachments"
|
||||
return &DefaultAttachmentStore{
|
||||
get: acc.Select("attachments").Columns("originID, sectionID, uploadedBy, path, extra").Where("attachID = ?").Prepare(),
|
||||
getByObj: acc.Select("attachments").Columns("attachID, sectionID, uploadedBy, path, extra").Where("originTable = ? AND originID = ?").Prepare(),
|
||||
add: acc.Insert("attachments").Columns("sectionID, sectionTable, originID, originTable, uploadedBy, path, extra").Fields("?,?,?,?,?,?,?").Prepare(),
|
||||
count: acc.Count("attachments").Prepare(),
|
||||
countIn: acc.Count("attachments").Where("originTable = ? and originID = ?").Prepare(),
|
||||
countInPath: acc.Count("attachments").Where("path = ?").Prepare(),
|
||||
move: acc.Update("attachments").Set("sectionID = ?").Where("originID = ? AND originTable = ?").Prepare(),
|
||||
moveByExtra: acc.Update("attachments").Set("sectionID = ?").Where("originTable = ? AND extra = ?").Prepare(),
|
||||
delete: acc.Delete("attachments").Where("attachID = ?").Prepare(),
|
||||
get: acc.Select(a).Columns("originID, sectionID, uploadedBy, path, extra").Where("attachID = ?").Prepare(),
|
||||
getByObj: acc.Select(a).Columns("attachID, sectionID, uploadedBy, path, extra").Where("originTable = ? AND originID = ?").Prepare(),
|
||||
add: acc.Insert(a).Columns("sectionID, sectionTable, originID, originTable, uploadedBy, path, extra").Fields("?,?,?,?,?,?,?").Prepare(),
|
||||
count: acc.Count(a).Prepare(),
|
||||
countIn: acc.Count(a).Where("originTable = ? and originID = ?").Prepare(),
|
||||
countInPath: acc.Count(a).Where("path = ?").Prepare(),
|
||||
move: acc.Update(a).Set("sectionID = ?").Where("originID = ? AND originTable = ?").Prepare(),
|
||||
moveByExtra: acc.Update(a).Set("sectionID = ?").Where("originTable = ? AND extra = ?").Prepare(),
|
||||
delete: acc.Delete(a).Where("attachID = ?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
|
@ -93,7 +94,7 @@ func (s *DefaultAttachmentStore) BulkMiniGetList(originTable string, ids []int)
|
|||
amap = make(map[int][]*MiniAttachment)
|
||||
var buffer []*MiniAttachment
|
||||
var currentID int
|
||||
rows, err := qgen.NewAcc().Select("attachments").Columns("attachID,sectionID,originID,uploadedBy,path").Where("originTable = ?").In("originID", ids).Orderby("originID ASC").Query(originTable)
|
||||
rows, err := qgen.NewAcc().Select("attachments").Columns("attachID,sectionID,originID,uploadedBy,path").Where("originTable=?").In("originID", ids).Orderby("originID ASC").Query(originTable)
|
||||
defer rows.Close()
|
||||
for rows.Next() {
|
||||
a := &MiniAttachment{}
|
||||
|
|
|
@ -32,10 +32,11 @@ type SQLModLogStore struct {
|
|||
}
|
||||
|
||||
func NewModLogStore(acc *qgen.Accumulator) (*SQLModLogStore, error) {
|
||||
ml := "moderation_logs"
|
||||
return &SQLModLogStore{
|
||||
create: acc.Insert("moderation_logs").Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Fields("?,?,?,?,?,UTC_TIMESTAMP()").Prepare(),
|
||||
count: acc.Count("moderation_logs").Prepare(),
|
||||
getOffset: acc.Select("moderation_logs").Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Orderby("doneAt DESC").Limit("?,?").Prepare(),
|
||||
create: acc.Insert(ml).Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Fields("?,?,?,?,?,UTC_TIMESTAMP()").Prepare(),
|
||||
count: acc.Count(ml).Prepare(),
|
||||
getOffset: acc.Select(ml).Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Orderby("doneAt DESC").Limit("?,?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
|
@ -83,10 +84,11 @@ type SQLAdminLogStore struct {
|
|||
}
|
||||
|
||||
func NewAdminLogStore(acc *qgen.Accumulator) (*SQLAdminLogStore, error) {
|
||||
al := "administration_logs"
|
||||
return &SQLAdminLogStore{
|
||||
create: acc.Insert("administration_logs").Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Fields("?,?,?,?,?,UTC_TIMESTAMP()").Prepare(),
|
||||
count: acc.Count("administration_logs").Prepare(),
|
||||
getOffset: acc.Select("administration_logs").Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Orderby("doneAt DESC").Limit("?,?").Prepare(),
|
||||
create: acc.Insert(al).Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Fields("?,?,?,?,?,UTC_TIMESTAMP()").Prepare(),
|
||||
count: acc.Count(al).Prepare(),
|
||||
getOffset: acc.Select(al).Columns("action, elementID, elementType, ipaddress, actorID, doneAt").Orderby("doneAt DESC").Limit("?,?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
|
|
|
@ -30,15 +30,15 @@ func (list PluginList) Add(plugin *Plugin) {
|
|||
list[plugin.UName] = plugin
|
||||
}
|
||||
|
||||
func buildPlugin(plugin *Plugin) {
|
||||
plugin.Installable = (plugin.Install != nil)
|
||||
func buildPlugin(pl *Plugin) {
|
||||
pl.Installable = (pl.Install != nil)
|
||||
/*
|
||||
The Active field should never be altered by a plugin. It's used internally by the software to determine whether an admin has enabled a plugin or not and whether to run it. This will be overwritten by the user's preference.
|
||||
*/
|
||||
plugin.Active = false
|
||||
plugin.Installed = false
|
||||
plugin.Hooks = make(map[string]int)
|
||||
plugin.Data = nil
|
||||
pl.Active = false
|
||||
pl.Installed = false
|
||||
pl.Hooks = make(map[string]int)
|
||||
pl.Data = nil
|
||||
}
|
||||
|
||||
var hookTableBox atomic.Value
|
||||
|
@ -391,13 +391,14 @@ var extendStmts ExtendStmts
|
|||
|
||||
func init() {
|
||||
DbInits.Add(func(acc *qgen.Accumulator) error {
|
||||
pl := "plugins"
|
||||
extendStmts = ExtendStmts{
|
||||
getPlugins: acc.Select("plugins").Columns("uname, active, installed").Prepare(),
|
||||
getPlugins: acc.Select(pl).Columns("uname, active, installed").Prepare(),
|
||||
|
||||
isActive: acc.Select("plugins").Columns("active").Where("uname = ?").Prepare(),
|
||||
setActive: acc.Update("plugins").Set("active = ?").Where("uname = ?").Prepare(),
|
||||
setInstalled: acc.Update("plugins").Set("installed = ?").Where("uname = ?").Prepare(),
|
||||
add: acc.Insert("plugins").Columns("uname, active, installed").Fields("?,?,?").Prepare(),
|
||||
isActive: acc.Select(pl).Columns("active").Where("uname = ?").Prepare(),
|
||||
setActive: acc.Update(pl).Set("active = ?").Where("uname = ?").Prepare(),
|
||||
setInstalled: acc.Update(pl).Set("installed = ?").Where("uname = ?").Prepare(),
|
||||
add: acc.Insert(pl).Columns("uname, active, installed").Fields("?,?,?").Prepare(),
|
||||
}
|
||||
return acc.FirstError()
|
||||
})
|
||||
|
@ -564,8 +565,7 @@ func InitPlugins() {
|
|||
// ? - Are the following functions racey?
|
||||
func RunTaskHook(name string) error {
|
||||
for _, hook := range taskHooks[name] {
|
||||
err := hook()
|
||||
if err != nil {
|
||||
if err := hook(); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
|
|
@ -110,8 +110,8 @@ func PermmapToQuery(permmap map[string]*ForumPerms, fid int) error {
|
|||
}
|
||||
|
||||
addForumPermsToForumAdminsTx, err := qgen.Builder.SimpleInsertSelectTx(tx,
|
||||
qgen.DBInsert{"forums_permissions", "gid, fid, preset, permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid, ?, '', ?", "is_admin = 1", "", ""},
|
||||
qgen.DBInsert{"forums_permissions", "gid,fid,preset,permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid,?,'',?", "is_admin = 1", "", ""},
|
||||
)
|
||||
if err != nil {
|
||||
return err
|
||||
|
@ -127,8 +127,8 @@ func PermmapToQuery(permmap map[string]*ForumPerms, fid int) error {
|
|||
}
|
||||
|
||||
addForumPermsToForumStaffTx, err := qgen.Builder.SimpleInsertSelectTx(tx,
|
||||
qgen.DBInsert{"forums_permissions", "gid, fid, preset, permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid, ?, '', ?", "is_admin = 0 AND is_mod = 1", "", ""},
|
||||
qgen.DBInsert{"forums_permissions", "gid,fid,preset,permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid,?,'',?", "is_admin = 0 AND is_mod = 1", "", ""},
|
||||
)
|
||||
if err != nil {
|
||||
return err
|
||||
|
@ -144,8 +144,8 @@ func PermmapToQuery(permmap map[string]*ForumPerms, fid int) error {
|
|||
}
|
||||
|
||||
addForumPermsToForumMembersTx, err := qgen.Builder.SimpleInsertSelectTx(tx,
|
||||
qgen.DBInsert{"forums_permissions", "gid, fid, preset, permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid, ?, '', ?", "is_admin = 0 AND is_mod = 0 AND is_banned = 0", "", ""},
|
||||
qgen.DBInsert{"forums_permissions", "gid,fid,preset,permissions", ""},
|
||||
qgen.DBSelect{"users_groups", "gid,?,'',?", "is_admin = 0 AND is_mod = 0 AND is_banned = 0", "", ""},
|
||||
)
|
||||
if err != nil {
|
||||
return err
|
||||
|
|
|
@ -76,17 +76,18 @@ type MemoryForumStore struct {
|
|||
// NewMemoryForumStore gives you a new instance of MemoryForumStore
|
||||
func NewMemoryForumStore() (*MemoryForumStore, error) {
|
||||
acc := qgen.NewAcc()
|
||||
f := "forums"
|
||||
// TODO: Do a proper delete
|
||||
return &MemoryForumStore{
|
||||
get: acc.Select("forums").Columns("name, desc, tmpl, active, order, preset, parentID, parentType, topicCount, lastTopicID, lastReplyerID").Where("fid = ?").Prepare(),
|
||||
getAll: acc.Select("forums").Columns("fid, name, desc, tmpl, active, order, preset, parentID, parentType, topicCount, lastTopicID, lastReplyerID").Orderby("order ASC, fid ASC").Prepare(),
|
||||
delete: acc.Update("forums").Set("name= '', active = 0").Where("fid = ?").Prepare(),
|
||||
create: acc.Insert("forums").Columns("name, desc, tmpl, active, preset").Fields("?,?,'',?,?").Prepare(),
|
||||
count: acc.Count("forums").Where("name != ''").Prepare(),
|
||||
updateCache: acc.Update("forums").Set("lastTopicID = ?, lastReplyerID = ?").Where("fid = ?").Prepare(),
|
||||
addTopics: acc.Update("forums").Set("topicCount = topicCount + ?").Where("fid = ?").Prepare(),
|
||||
removeTopics: acc.Update("forums").Set("topicCount = topicCount - ?").Where("fid = ?").Prepare(),
|
||||
updateOrder: acc.Update("forums").Set("order = ?").Where("fid = ?").Prepare(),
|
||||
get: acc.Select(f).Columns("name, desc, tmpl, active, order, preset, parentID, parentType, topicCount, lastTopicID, lastReplyerID").Where("fid = ?").Prepare(),
|
||||
getAll: acc.Select(f).Columns("fid, name, desc, tmpl, active, order, preset, parentID, parentType, topicCount, lastTopicID, lastReplyerID").Orderby("order ASC, fid ASC").Prepare(),
|
||||
delete: acc.Update(f).Set("name= '', active = 0").Where("fid = ?").Prepare(),
|
||||
create: acc.Insert(f).Columns("name, desc, tmpl, active, preset").Fields("?,?,'',?,?").Prepare(),
|
||||
count: acc.Count(f).Where("name != ''").Prepare(),
|
||||
updateCache: acc.Update(f).Set("lastTopicID = ?, lastReplyerID = ?").Where("fid = ?").Prepare(),
|
||||
addTopics: acc.Update(f).Set("topicCount = topicCount + ?").Where("fid = ?").Prepare(),
|
||||
removeTopics: acc.Update(f).Set("topicCount = topicCount - ?").Where("fid = ?").Prepare(),
|
||||
updateOrder: acc.Update(f).Set("order = ?").Where("fid = ?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
|
@ -107,7 +108,7 @@ func (s *MemoryForumStore) LoadForums() error {
|
|||
}
|
||||
defer rows.Close()
|
||||
|
||||
var i = 0
|
||||
i := 0
|
||||
for ; rows.Next(); i++ {
|
||||
f := &Forum{ID: 0, Active: true, Preset: "all"}
|
||||
err = rows.Scan(&f.ID, &f.Name, &f.Desc, &f.Tmpl, &f.Active, &f.Order, &f.Preset, &f.ParentID, &f.ParentType, &f.TopicCount, &f.LastTopicID, &f.LastReplyerID)
|
||||
|
@ -254,7 +255,7 @@ func (s *MemoryForumStore) GetAllVisible() (forumView []*Forum, err error) {
|
|||
|
||||
func (s *MemoryForumStore) GetAllVisibleIDs() ([]int, error) {
|
||||
forumView := s.forumView.Load().([]*Forum)
|
||||
var ids = make([]int, len(forumView))
|
||||
ids := make([]int, len(forumView))
|
||||
for i := 0; i < len(forumView); i++ {
|
||||
ids[i] = forumView[i].ID
|
||||
}
|
||||
|
|
|
@ -44,10 +44,11 @@ var groupStmts GroupStmts
|
|||
|
||||
func init() {
|
||||
DbInits.Add(func(acc *qgen.Accumulator) error {
|
||||
ug := "users_groups"
|
||||
groupStmts = GroupStmts{
|
||||
updateGroup: acc.Update("users_groups").Set("name = ?, tag = ?").Where("gid = ?").Prepare(),
|
||||
updateGroupRank: acc.Update("users_groups").Set("is_admin = ?, is_mod = ?, is_banned = ?").Where("gid = ?").Prepare(),
|
||||
updateGroupPerms: acc.Update("users_groups").Set("permissions = ?").Where("gid = ?").Prepare(),
|
||||
updateGroup: acc.Update(ug).Set("name = ?, tag = ?").Where("gid = ?").Prepare(),
|
||||
updateGroupRank: acc.Update(ug).Set("is_admin = ?, is_mod = ?, is_banned = ?").Where("gid = ?").Prepare(),
|
||||
updateGroupPerms: acc.Update(ug).Set("permissions = ?").Where("gid = ?").Prepare(),
|
||||
}
|
||||
return acc.FirstError()
|
||||
})
|
||||
|
|
|
@ -40,7 +40,7 @@ func (s *DefaultMenuStore) Get(mid int) (*MenuListHolder, error) {
|
|||
}
|
||||
|
||||
func (s *DefaultMenuStore) Items(mid int) (mlist MenuItemList, err error) {
|
||||
err = qgen.NewAcc().Select("menu_items").Columns("miid, name, htmlID, cssClass, position, path, aria, tooltip, order, tmplName, guestOnly, memberOnly, staffOnly, adminOnly").Where("mid = " + strconv.Itoa(mid)).Orderby("order ASC").Each(func(rows *sql.Rows) error {
|
||||
err = qgen.NewAcc().Select("menu_items").Columns("miid,name,htmlID,cssClass,position,path,aria,tooltip,order,tmplName,guestOnly,memberOnly,staffOnly,adminOnly").Where("mid = " + strconv.Itoa(mid)).Orderby("order ASC").Each(func(rows *sql.Rows) error {
|
||||
i := MenuItem{MenuID: mid}
|
||||
err := rows.Scan(&i.ID, &i.Name, &i.HTMLID, &i.CSSClass, &i.Position, &i.Path, &i.Aria, &i.Tooltip, &i.Order, &i.TmplName, &i.GuestOnly, &i.MemberOnly, &i.SuperModOnly, &i.AdminOnly)
|
||||
if err != nil {
|
||||
|
|
|
@ -64,63 +64,64 @@ var menuItemStmts MenuItemStmts
|
|||
|
||||
func init() {
|
||||
DbInits.Add(func(acc *qgen.Accumulator) error {
|
||||
mi := "menu_items"
|
||||
menuItemStmts = MenuItemStmts{
|
||||
update: acc.Update("menu_items").Set("name = ?, htmlID = ?, cssClass = ?, position = ?, path = ?, aria = ?, tooltip = ?, tmplName = ?, guestOnly = ?, memberOnly = ?, staffOnly = ?, adminOnly = ?").Where("miid = ?").Prepare(),
|
||||
insert: acc.Insert("menu_items").Columns("mid, name, htmlID, cssClass, position, path, aria, tooltip, tmplName, guestOnly, memberOnly, staffOnly, adminOnly").Fields("?,?,?,?,?,?,?,?,?,?,?,?,?").Prepare(),
|
||||
delete: acc.Delete("menu_items").Where("miid = ?").Prepare(),
|
||||
updateOrder: acc.Update("menu_items").Set("order = ?").Where("miid = ?").Prepare(),
|
||||
update: acc.Update(mi).Set("name = ?, htmlID = ?, cssClass = ?, position = ?, path = ?, aria = ?, tooltip = ?, tmplName = ?, guestOnly = ?, memberOnly = ?, staffOnly = ?, adminOnly = ?").Where("miid = ?").Prepare(),
|
||||
insert: acc.Insert(mi).Columns("mid, name, htmlID, cssClass, position, path, aria, tooltip, tmplName, guestOnly, memberOnly, staffOnly, adminOnly").Fields("?,?,?,?,?,?,?,?,?,?,?,?,?").Prepare(),
|
||||
delete: acc.Delete(mi).Where("miid = ?").Prepare(),
|
||||
updateOrder: acc.Update(mi).Set("order = ?").Where("miid = ?").Prepare(),
|
||||
}
|
||||
return acc.FirstError()
|
||||
})
|
||||
}
|
||||
|
||||
func (item MenuItem) Commit() error {
|
||||
_, err := menuItemStmts.update.Exec(item.Name, item.HTMLID, item.CSSClass, item.Position, item.Path, item.Aria, item.Tooltip, item.TmplName, item.GuestOnly, item.MemberOnly, item.SuperModOnly, item.AdminOnly, item.ID)
|
||||
Menus.Load(item.MenuID)
|
||||
func (i MenuItem) Commit() error {
|
||||
_, err := menuItemStmts.update.Exec(i.Name, i.HTMLID, i.CSSClass, i.Position, i.Path, i.Aria, i.Tooltip, i.TmplName, i.GuestOnly, i.MemberOnly, i.SuperModOnly, i.AdminOnly, i.ID)
|
||||
Menus.Load(i.MenuID)
|
||||
return err
|
||||
}
|
||||
|
||||
func (item MenuItem) Create() (int, error) {
|
||||
res, err := menuItemStmts.insert.Exec(item.MenuID, item.Name, item.HTMLID, item.CSSClass, item.Position, item.Path, item.Aria, item.Tooltip, item.TmplName, item.GuestOnly, item.MemberOnly, item.SuperModOnly, item.AdminOnly)
|
||||
func (i MenuItem) Create() (int, error) {
|
||||
res, err := menuItemStmts.insert.Exec(i.MenuID, i.Name, i.HTMLID, i.CSSClass, i.Position, i.Path, i.Aria, i.Tooltip, i.TmplName, i.GuestOnly, i.MemberOnly, i.SuperModOnly, i.AdminOnly)
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
Menus.Load(item.MenuID)
|
||||
Menus.Load(i.MenuID)
|
||||
|
||||
miid64, err := res.LastInsertId()
|
||||
return int(miid64), err
|
||||
}
|
||||
|
||||
func (item MenuItem) Delete() error {
|
||||
_, err := menuItemStmts.delete.Exec(item.ID)
|
||||
Menus.Load(item.MenuID)
|
||||
func (i MenuItem) Delete() error {
|
||||
_, err := menuItemStmts.delete.Exec(i.ID)
|
||||
Menus.Load(i.MenuID)
|
||||
return err
|
||||
}
|
||||
|
||||
func (hold *MenuListHolder) LoadTmpl(name string) (menuTmpl MenuTmpl, err error) {
|
||||
func (h *MenuListHolder) LoadTmpl(name string) (menuTmpl MenuTmpl, err error) {
|
||||
data, err := ioutil.ReadFile("./templates/" + name + ".html")
|
||||
if err != nil {
|
||||
return menuTmpl, err
|
||||
}
|
||||
return hold.Parse(name, data), nil
|
||||
return h.Parse(name, data), nil
|
||||
}
|
||||
|
||||
// TODO: Make this atomic, maybe with a transaction or store the order on the menu itself?
|
||||
func (hold *MenuListHolder) UpdateOrder(updateMap map[int]int) error {
|
||||
func (h *MenuListHolder) UpdateOrder(updateMap map[int]int) error {
|
||||
for miid, order := range updateMap {
|
||||
_, err := menuItemStmts.updateOrder.Exec(order, miid)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
Menus.Load(hold.MenuID)
|
||||
Menus.Load(h.MenuID)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (hold *MenuListHolder) LoadTmpls() (tmpls map[string]MenuTmpl, err error) {
|
||||
func (h *MenuListHolder) LoadTmpls() (tmpls map[string]MenuTmpl, err error) {
|
||||
tmpls = make(map[string]MenuTmpl)
|
||||
var loadTmpl = func(name string) error {
|
||||
menuTmpl, err := hold.LoadTmpl(name)
|
||||
loadTmpl := func(name string) error {
|
||||
menuTmpl, err := h.LoadTmpl(name)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -136,32 +137,32 @@ func (hold *MenuListHolder) LoadTmpls() (tmpls map[string]MenuTmpl, err error) {
|
|||
}
|
||||
|
||||
// TODO: Run this in main, sync ticks, when the phrase file changes (need to implement the sync for that first), and when the settings are changed
|
||||
func (hold *MenuListHolder) Preparse() error {
|
||||
tmpls, err := hold.LoadTmpls()
|
||||
func (h *MenuListHolder) Preparse() error {
|
||||
tmpls, err := h.LoadTmpls()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
var addVariation = func(index int, callback func(mitem MenuItem) bool) {
|
||||
renderBuffer, variableIndices, pathList := hold.Scan(tmpls, callback)
|
||||
hold.Variations[index] = menuTmpl{renderBuffer, variableIndices, pathList}
|
||||
addVariation := func(index int, callback func(i MenuItem) bool) {
|
||||
renderBuffer, variableIndices, pathList := h.Scan(tmpls, callback)
|
||||
h.Variations[index] = menuTmpl{renderBuffer, variableIndices, pathList}
|
||||
}
|
||||
|
||||
// Guest Menu
|
||||
addVariation(0, func(mitem MenuItem) bool {
|
||||
return !mitem.MemberOnly
|
||||
addVariation(0, func(i MenuItem) bool {
|
||||
return !i.MemberOnly
|
||||
})
|
||||
// Member Menu
|
||||
addVariation(1, func(mitem MenuItem) bool {
|
||||
return !mitem.SuperModOnly && !mitem.GuestOnly
|
||||
addVariation(1, func(i MenuItem) bool {
|
||||
return !i.SuperModOnly && !i.GuestOnly
|
||||
})
|
||||
// Super Mod Menu
|
||||
addVariation(2, func(mitem MenuItem) bool {
|
||||
return !mitem.AdminOnly && !mitem.GuestOnly
|
||||
addVariation(2, func(i MenuItem) bool {
|
||||
return !i.AdminOnly && !i.GuestOnly
|
||||
})
|
||||
// Admin Menu
|
||||
addVariation(3, func(mitem MenuItem) bool {
|
||||
return !mitem.GuestOnly
|
||||
addVariation(3, func(i MenuItem) bool {
|
||||
return !i.GuestOnly
|
||||
})
|
||||
return nil
|
||||
}
|
||||
|
@ -264,13 +265,13 @@ func menuDumpSlice(outerSlice [][]byte) {
|
|||
}
|
||||
}
|
||||
|
||||
func (hold *MenuListHolder) Parse(name string, tmplData []byte) (menuTmpl MenuTmpl) {
|
||||
func (h *MenuListHolder) Parse(name string, tmplData []byte) (menuTmpl MenuTmpl) {
|
||||
var textBuffer, variableBuffer [][]byte
|
||||
var renderList []menuRenderItem
|
||||
var subBuffer []byte
|
||||
|
||||
// ? We only support simple properties on MenuItem right now
|
||||
var addVariable = func(name []byte) {
|
||||
addVariable := func(name []byte) {
|
||||
// TODO: Check if the subBuffer has any items or is empty
|
||||
textBuffer = append(textBuffer, subBuffer)
|
||||
subBuffer = nil
|
||||
|
@ -325,13 +326,13 @@ func (hold *MenuListHolder) Parse(name string, tmplData []byte) (menuTmpl MenuTm
|
|||
return MenuTmpl{name, textBuffer, variableBuffer, renderList}
|
||||
}
|
||||
|
||||
func (hold *MenuListHolder) Scan(menuTmpls map[string]MenuTmpl, showItem func(mitem MenuItem) bool) (renderBuffer [][]byte, variableIndices []int, pathList []menuPath) {
|
||||
for _, mitem := range hold.List {
|
||||
func (h *MenuListHolder) Scan(menuTmpls map[string]MenuTmpl, showItem func(i MenuItem) bool) (renderBuffer [][]byte, variableIndices []int, pathList []menuPath) {
|
||||
for _, mitem := range h.List {
|
||||
// Do we want this item in this variation of the menu?
|
||||
if !showItem(mitem) {
|
||||
continue
|
||||
}
|
||||
renderBuffer, variableIndices = hold.ScanItem(menuTmpls, mitem, renderBuffer, variableIndices)
|
||||
renderBuffer, variableIndices = h.ScanItem(menuTmpls, mitem, renderBuffer, variableIndices)
|
||||
pathList = append(pathList, menuPath{mitem.Path, len(renderBuffer) - 1})
|
||||
}
|
||||
|
||||
|
@ -340,7 +341,7 @@ func (hold *MenuListHolder) Scan(menuTmpls map[string]MenuTmpl, showItem func(mi
|
|||
}
|
||||
|
||||
// Note: This doesn't do a visibility check like hold.Scan() does
|
||||
func (hold *MenuListHolder) ScanItem(menuTmpls map[string]MenuTmpl, mitem MenuItem, renderBuffer [][]byte, variableIndices []int) ([][]byte, []int) {
|
||||
func (h *MenuListHolder) ScanItem(menuTmpls map[string]MenuTmpl, mitem MenuItem, renderBuffer [][]byte, variableIndices []int) ([][]byte, []int) {
|
||||
menuTmpl, ok := menuTmpls[mitem.TmplName]
|
||||
if !ok {
|
||||
menuTmpl = menuTmpls["menu_item"]
|
||||
|
@ -416,16 +417,16 @@ func (hold *MenuListHolder) ScanItem(menuTmpls map[string]MenuTmpl, mitem MenuIt
|
|||
}
|
||||
|
||||
// TODO: Pre-render the lang stuff
|
||||
func (hold *MenuListHolder) Build(w io.Writer, user *User, pathPrefix string) error {
|
||||
func (h *MenuListHolder) Build(w io.Writer, user *User, pathPrefix string) error {
|
||||
var mTmpl menuTmpl
|
||||
if !user.Loggedin {
|
||||
mTmpl = hold.Variations[0]
|
||||
mTmpl = h.Variations[0]
|
||||
} else if user.IsAdmin {
|
||||
mTmpl = hold.Variations[3]
|
||||
mTmpl = h.Variations[3]
|
||||
} else if user.IsSuperMod {
|
||||
mTmpl = hold.Variations[2]
|
||||
mTmpl = h.Variations[2]
|
||||
} else {
|
||||
mTmpl = hold.Variations[1]
|
||||
mTmpl = h.Variations[1]
|
||||
}
|
||||
if pathPrefix == "" {
|
||||
pathPrefix = Config.DefaultPath
|
||||
|
@ -438,7 +439,7 @@ func (hold *MenuListHolder) Build(w io.Writer, user *User, pathPrefix string) er
|
|||
return nil
|
||||
}
|
||||
|
||||
var nearIndex = 0
|
||||
nearIndex := 0
|
||||
for index, renderItem := range mTmpl.RenderBuffer {
|
||||
if index != mTmpl.VariableIndices[nearIndex] {
|
||||
w.Write(renderItem)
|
||||
|
|
|
@ -26,16 +26,17 @@ type DefaultReportStore struct {
|
|||
}
|
||||
|
||||
func NewDefaultReportStore(acc *qgen.Accumulator) (*DefaultReportStore, error) {
|
||||
t := "topics"
|
||||
return &DefaultReportStore{
|
||||
create: acc.Insert("topics").Columns("title, content, parsed_content, ipaddress, createdAt, lastReplyAt, createdBy, lastReplyBy, data, parentID, css_class").Fields("?,?,?,?,UTC_TIMESTAMP(),UTC_TIMESTAMP(),?,?,?,?,'report'").Prepare(),
|
||||
exists: acc.Count("topics").Where("data = ? AND data != '' AND parentID = ?").Prepare(),
|
||||
create: acc.Insert(t).Columns("title, content, parsed_content, ipaddress, createdAt, lastReplyAt, createdBy, lastReplyBy, data, parentID, css_class").Fields("?,?,?,?,UTC_TIMESTAMP(),UTC_TIMESTAMP(),?,?,?,?,'report'").Prepare(),
|
||||
exists: acc.Count(t).Where("data = ? AND data != '' AND parentID = ?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
// ! There's a data race in this. If two users report one item at the exact same time, then both reports will go through
|
||||
func (s *DefaultReportStore) Create(title string, content string, user *User, itemType string, itemID int) (int, error) {
|
||||
func (s *DefaultReportStore) Create(title string, content string, user *User, itemType string, itemID int) (tid int, err error) {
|
||||
var count int
|
||||
err := s.exists.QueryRow(itemType+"_"+strconv.Itoa(itemID), ReportForumID).Scan(&count)
|
||||
err = s.exists.QueryRow(itemType+"_"+strconv.Itoa(itemID), ReportForumID).Scan(&count)
|
||||
if err != nil && err != sql.ErrNoRows {
|
||||
return 0, err
|
||||
}
|
||||
|
@ -47,11 +48,10 @@ func (s *DefaultReportStore) Create(title string, content string, user *User, it
|
|||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
lastID, err := res.LastInsertId()
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
return int(lastID), Forums.AddTopic(int(lastID), user.ID, ReportForumID)
|
||||
tid = int(lastID)
|
||||
return tid, Forums.AddTopic(tid, user.ID, ReportForumID)
|
||||
}
|
||||
|
|
|
@ -41,11 +41,12 @@ var themeStmts ThemeStmts
|
|||
|
||||
func init() {
|
||||
DbInits.Add(func(acc *qgen.Accumulator) error {
|
||||
t := "themes"
|
||||
themeStmts = ThemeStmts{
|
||||
getAll: acc.Select("themes").Columns("uname, default").Prepare(),
|
||||
isDefault: acc.Select("themes").Columns("default").Where("uname = ?").Prepare(),
|
||||
update: acc.Update("themes").Set("default = ?").Where("uname = ?").Prepare(),
|
||||
add: acc.Insert("themes").Columns("uname, default").Fields("?,?").Prepare(),
|
||||
getAll: acc.Select(t).Columns("uname, default").Prepare(),
|
||||
isDefault: acc.Select(t).Columns("default").Where("uname = ?").Prepare(),
|
||||
update: acc.Update(t).Set("default = ?").Where("uname = ?").Prepare(),
|
||||
add: acc.Insert(t).Columns("uname, default").Fields("?,?").Prepare(),
|
||||
}
|
||||
return acc.FirstError()
|
||||
})
|
||||
|
@ -144,7 +145,7 @@ func NewThemeList() (themes ThemeList, err error) {
|
|||
return themes, err
|
||||
}
|
||||
if len(overrides) > 0 {
|
||||
var overCount = 0
|
||||
overCount := 0
|
||||
theme.OverridenMap = make(map[string]bool)
|
||||
for _, override := range overrides {
|
||||
if override.IsDir() {
|
||||
|
@ -180,7 +181,6 @@ func NewThemeList() (themes ThemeList, err error) {
|
|||
|
||||
themes[theme.Name] = theme
|
||||
}
|
||||
|
||||
if defaultTheme == "" {
|
||||
defaultTheme = lastTheme
|
||||
}
|
||||
|
@ -232,8 +232,7 @@ func (t ThemeList) LoadActiveStatus() error {
|
|||
|
||||
func (t ThemeList) LoadStaticFiles() error {
|
||||
for _, theme := range t {
|
||||
err := theme.LoadStaticFiles()
|
||||
if err != nil {
|
||||
if err := theme.LoadStaticFiles(); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
@ -244,7 +243,6 @@ func ResetTemplateOverrides() {
|
|||
log.Print("Resetting the template overrides")
|
||||
for name := range overridenTemplates {
|
||||
log.Print("Resetting '" + name + "' template override")
|
||||
|
||||
originPointer, ok := TmplPtrMap["o_"+name]
|
||||
if !ok {
|
||||
log.Print("The origin template doesn't exist!")
|
||||
|
@ -269,7 +267,6 @@ func ResetTemplateOverrides() {
|
|||
LogError(errors.New("The source and destination templates are incompatible"))
|
||||
return
|
||||
}
|
||||
|
||||
*dPtr = oPtr
|
||||
log.Print("The template override was reset")
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@ import (
|
|||
"image"
|
||||
"image/gif"
|
||||
"image/jpeg"
|
||||
_ "image/png"
|
||||
"image/png"
|
||||
"os"
|
||||
"strconv"
|
||||
|
||||
|
@ -66,6 +66,14 @@ func ThumbTask(thumbChan chan bool) {
|
|||
if err != nil {
|
||||
LogError(err)
|
||||
}
|
||||
|
||||
/*
|
||||
err := acc.Select("attach_image_queue").Columns("attachID").Limit("0,5").EachInt(func(attachID int) error {
|
||||
return nil
|
||||
|
||||
_, err = acc.Delete("attach_image_queue").Where("attachID = ?").Run(uid)
|
||||
}
|
||||
*/
|
||||
if err = acc.FirstError(); err != nil {
|
||||
LogError(err)
|
||||
}
|
||||
|
@ -119,6 +127,8 @@ func precodeImage(format string, inPath string, tmpPath string) error {
|
|||
// TODO: Make sure animated gifs work after being encoded
|
||||
if format == "gif" {
|
||||
return gif.Encode(outFile, img, nil)
|
||||
} else if format == "png" {
|
||||
return png.Encode(outFile, img)
|
||||
}
|
||||
return jpeg.Encode(outFile, img, nil)
|
||||
}
|
||||
|
|
|
@ -212,24 +212,25 @@ var topicStmts TopicStmts
|
|||
|
||||
func init() {
|
||||
DbInits.Add(func(acc *qgen.Accumulator) error {
|
||||
t := "topics"
|
||||
topicStmts = TopicStmts{
|
||||
getRids: acc.Select("replies").Columns("rid").Where("tid = ?").Orderby("rid ASC").Limit("?,?").Prepare(),
|
||||
getReplies: acc.SimpleLeftJoin("replies AS r", "users AS u", "r.rid, r.content, r.createdBy, r.createdAt, r.lastEdit, r.lastEditBy, u.avatar, u.name, u.group, u.url_prefix, u.url_name, u.level, r.ipaddress, r.likeCount, r.attachCount, r.actionType", "r.createdBy = u.uid", "r.tid = ?", "r.rid ASC", "?,?"),
|
||||
addReplies: acc.Update("topics").Set("postCount = postCount + ?, lastReplyBy = ?, lastReplyAt = UTC_TIMESTAMP()").Where("tid = ?").Prepare(),
|
||||
updateLastReply: acc.Update("topics").Set("lastReplyID = ?").Where("lastReplyID > ? AND tid = ?").Prepare(),
|
||||
lock: acc.Update("topics").Set("is_closed = 1").Where("tid = ?").Prepare(),
|
||||
unlock: acc.Update("topics").Set("is_closed = 0").Where("tid = ?").Prepare(),
|
||||
moveTo: acc.Update("topics").Set("parentID = ?").Where("tid = ?").Prepare(),
|
||||
stick: acc.Update("topics").Set("sticky = 1").Where("tid = ?").Prepare(),
|
||||
unstick: acc.Update("topics").Set("sticky = 0").Where("tid = ?").Prepare(),
|
||||
addReplies: acc.Update(t).Set("postCount = postCount + ?, lastReplyBy = ?, lastReplyAt = UTC_TIMESTAMP()").Where("tid = ?").Prepare(),
|
||||
updateLastReply: acc.Update(t).Set("lastReplyID = ?").Where("lastReplyID > ? AND tid = ?").Prepare(),
|
||||
lock: acc.Update(t).Set("is_closed = 1").Where("tid = ?").Prepare(),
|
||||
unlock: acc.Update(t).Set("is_closed = 0").Where("tid = ?").Prepare(),
|
||||
moveTo: acc.Update(t).Set("parentID = ?").Where("tid = ?").Prepare(),
|
||||
stick: acc.Update(t).Set("sticky = 1").Where("tid = ?").Prepare(),
|
||||
unstick: acc.Update(t).Set("sticky = 0").Where("tid = ?").Prepare(),
|
||||
hasLikedTopic: acc.Select("likes").Columns("targetItem").Where("sentBy = ? and targetItem = ? and targetType = 'topics'").Prepare(),
|
||||
createLike: acc.Insert("likes").Columns("weight, targetItem, targetType, sentBy, createdAt").Fields("?,?,?,?,UTC_TIMESTAMP()").Prepare(),
|
||||
addLikesToTopic: acc.Update("topics").Set("likeCount = likeCount + ?").Where("tid = ?").Prepare(),
|
||||
delete: acc.Delete("topics").Where("tid = ?").Prepare(),
|
||||
addLikesToTopic: acc.Update(t).Set("likeCount = likeCount + ?").Where("tid = ?").Prepare(),
|
||||
delete: acc.Delete(t).Where("tid = ?").Prepare(),
|
||||
deleteActivity: acc.Delete("activity_stream").Where("elementID = ? AND elementType = 'topic'").Prepare(),
|
||||
deleteActivitySubs: acc.Delete("activity_subscriptions").Where("targetID = ? AND targetType = 'topic'").Prepare(),
|
||||
edit: acc.Update("topics").Set("title = ?, content = ?, parsed_content = ?").Where("tid = ?").Prepare(), // TODO: Only run the content update bits on non-polls, does this matter?
|
||||
setPoll: acc.Update("topics").Set("poll = ?").Where("tid = ? AND poll = 0").Prepare(),
|
||||
edit: acc.Update(t).Set("title = ?, content = ?, parsed_content = ?").Where("tid = ?").Prepare(), // TODO: Only run the content update bits on non-polls, does this matter?
|
||||
setPoll: acc.Update(t).Set("poll = ?").Where("tid = ? AND poll = 0").Prepare(),
|
||||
createAction: acc.Insert("replies").Columns("tid, actionType, ipaddress, createdBy, createdAt, lastUpdated, content, parsed_content").Fields("?,?,?,?,UTC_TIMESTAMP(),UTC_TIMESTAMP(),'',''").Prepare(),
|
||||
|
||||
getTopicUser: acc.SimpleLeftJoin("topics AS t", "users AS u", "t.title, t.content, t.createdBy, t.createdAt, t.lastReplyAt, t.lastReplyBy, t.lastReplyID, t.is_closed, t.sticky, t.parentID, t.ipaddress, t.views, t.postCount, t.likeCount, t.attachCount,t.poll, u.name, u.avatar, u.group, u.url_prefix, u.url_name, u.level", "t.createdBy = u.uid", "tid = ?", "", ""),
|
||||
|
|
|
@ -56,12 +56,13 @@ func NewDefaultTopicStore(cache TopicCache) (*DefaultTopicStore, error) {
|
|||
if cache == nil {
|
||||
cache = NewNullTopicCache()
|
||||
}
|
||||
t := "topics"
|
||||
return &DefaultTopicStore{
|
||||
cache: cache,
|
||||
get: acc.Select("topics").Columns("title, content, createdBy, createdAt, lastReplyBy, lastReplyAt, lastReplyID, is_closed, sticky, parentID, ipaddress, views, postCount, likeCount, attachCount, poll, data").Where("tid = ?").Prepare(),
|
||||
exists: acc.Select("topics").Columns("tid").Where("tid = ?").Prepare(),
|
||||
count: acc.Count("topics").Prepare(),
|
||||
create: acc.Insert("topics").Columns("parentID, title, content, parsed_content, createdAt, lastReplyAt, lastReplyBy, ipaddress, words, createdBy").Fields("?,?,?,?,UTC_TIMESTAMP(),UTC_TIMESTAMP(),?,?,?,?").Prepare(),
|
||||
get: acc.Select(t).Columns("title, content, createdBy, createdAt, lastReplyBy, lastReplyAt, lastReplyID, is_closed, sticky, parentID, ipaddress, views, postCount, likeCount, attachCount, poll, data").Where("tid = ?").Prepare(),
|
||||
exists: acc.Exists(t,"tid").Prepare(),
|
||||
count: acc.Count(t).Prepare(),
|
||||
create: acc.Insert(t).Columns("parentID, title, content, parsed_content, createdAt, lastReplyAt, lastReplyBy, ipaddress, words, createdBy").Fields("?,?,?,?,UTC_TIMESTAMP(),UTC_TIMESTAMP(),?,?,?,?").Prepare(),
|
||||
}, acc.FirstError()
|
||||
}
|
||||
|
||||
|
@ -159,8 +160,7 @@ func (s *DefaultTopicStore) BulkGetMap(ids []int) (list map[int]*Topic, err erro
|
|||
s.cache.Set(t)
|
||||
list[t.ID] = t
|
||||
}
|
||||
err = rows.Err()
|
||||
if err != nil {
|
||||
if err = rows.Err(); err != nil {
|
||||
return list, err
|
||||
}
|
||||
|
||||
|
@ -211,19 +211,18 @@ func (s *DefaultTopicStore) Create(fid int, topicName string, content string, ui
|
|||
return 0, ErrNoBody
|
||||
}
|
||||
|
||||
wcount := WordCount(content)
|
||||
// TODO: Move this statement into the topic store
|
||||
res, err := s.create.Exec(fid, topicName, content, parsedContent, uid, ipaddress, wcount, uid)
|
||||
res, err := s.create.Exec(fid, topicName, content, parsedContent, uid, ipaddress, WordCount(content), uid)
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
lastID, err := res.LastInsertId()
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
tid = int(lastID)
|
||||
|
||||
return int(lastID), Forums.AddTopic(int(lastID), uid, fid)
|
||||
return tid, Forums.AddTopic(tid, uid, fid)
|
||||
}
|
||||
|
||||
// ? - What is this? Do we need it? Should it be in the main store interface?
|
||||
|
|
|
@ -38,12 +38,13 @@ type DefaultWordFilterStore struct {
|
|||
}
|
||||
|
||||
func NewDefaultWordFilterStore(acc *qgen.Accumulator) (*DefaultWordFilterStore, error) {
|
||||
wf := "word_filters"
|
||||
store := &DefaultWordFilterStore{
|
||||
getAll: acc.Select("word_filters").Columns("wfid, find, replacement").Prepare(),
|
||||
create: acc.Insert("word_filters").Columns("find, replacement").Fields("?,?").Prepare(),
|
||||
delete: acc.Delete("word_filters").Where("wfid = ?").Prepare(),
|
||||
update: acc.Update("word_filters").Set("find = ?, replacement = ?").Where("wfid = ?").Prepare(),
|
||||
count: acc.Count("word_filters").Prepare(),
|
||||
getAll: acc.Select(wf).Columns("wfid,find,replacement").Prepare(),
|
||||
create: acc.Insert(wf).Columns("find,replacement").Fields("?,?").Prepare(),
|
||||
delete: acc.Delete(wf).Where("wfid = ?").Prepare(),
|
||||
update: acc.Update(wf).Set("find = ?, replacement = ?").Where("wfid = ?").Prepare(),
|
||||
count: acc.Count(wf).Prepare(),
|
||||
}
|
||||
// TODO: Should we initialise this elsewhere?
|
||||
if acc.FirstError() == nil {
|
||||
|
|
|
@ -869,10 +869,6 @@ function mainInit(){
|
|||
});
|
||||
|
||||
// The time range selector for the time graphs in the Control Panel
|
||||
/*$(".timeRangeSelector").change(function(){
|
||||
console.log("Changed the time range to " + this.options[this.selectedIndex].getAttribute("val"));
|
||||
window.location = this.form.getAttribute("action")+"?timeRange=" + this.options[this.selectedIndex].getAttribute("val"); // Do a redirect as a form submission refuses to work properly
|
||||
});*/
|
||||
$(".autoSubmitRedirect").change(function(){
|
||||
let elems = this.form.elements;
|
||||
let s = "";
|
||||
|
|
Loading…
Reference in New Issue