Added the InternalErrorJS and LocalErrorJS error handler functions.
Hid the themes which aren't under construction yet from the Theme Manager. Fixed a bug in the BBCode parser where every post had ten spaces appended to them. Added the get_reply() internal API function for plugins to make use of. Added the bell to the theme. Fixed some bits of the Cosmo theme where the rowhead wasn't appearing. Added a "Don't have an account?" link to the login page. I began work on the alerts system, I took a little break, so it's a little further behind than you might expect, but it shouldn't take too long for me to finish it up. I haven't finished the back-end portions of it yet, so there's not much to see yet!
This commit is contained in:
parent
1d85224dbc
commit
9fce51a3d7
24
data.sql
24
data.sql
@ -112,13 +112,35 @@ CREATE TABLE `users_replies`(
|
|||||||
|
|
||||||
CREATE TABLE `likes`(
|
CREATE TABLE `likes`(
|
||||||
`weight` tinyint DEFAULT 1 not null,
|
`weight` tinyint DEFAULT 1 not null,
|
||||||
/*`type` tinyint not null, /* Regular Post = 1, Big Post = 2, Mega Post = 3, etc.*/
|
/*`type` tinyint not null, /* Regular Post: 1, Big Post: 2, Mega Post: 3, etc.*/
|
||||||
`targetItem` int not null,
|
`targetItem` int not null,
|
||||||
`targetType` varchar(50) DEFAULT 'replies' not null,
|
`targetType` varchar(50) DEFAULT 'replies' not null,
|
||||||
`sentBy` int not null,
|
`sentBy` int not null,
|
||||||
`recalc` tinyint DEFAULT 0 not null
|
`recalc` tinyint DEFAULT 0 not null
|
||||||
);
|
);
|
||||||
|
|
||||||
|
CREATE TABLE `activity_stream_matches`(
|
||||||
|
`watcher` int not null,
|
||||||
|
`asid` int not null
|
||||||
|
);
|
||||||
|
|
||||||
|
CREATE TABLE `activity_stream`(
|
||||||
|
`asid` int not null AUTO_INCREMENT,
|
||||||
|
`actor` int not null, /* the one doing the act */
|
||||||
|
`targetUser` int not null, /* the user who created the item the actor is acting on, some items like forums may lack a targetUser field */
|
||||||
|
`event` varchar(50) not null, /* mention, like, reply (as in the act of replying to an item, not the reply item type, you can "reply" to a forum by making a topic in it), friend_invite */
|
||||||
|
`elementType` varchar(50) not null, /* topic, post (calling it post here to differentiate it from the 'reply' event), forum, user */
|
||||||
|
`elementID` int not null, /* the ID of the element being acted upon */
|
||||||
|
primary key(`asid`)
|
||||||
|
);
|
||||||
|
|
||||||
|
CREATE TABLE `activity_subscriptions`(
|
||||||
|
`user` int not null,
|
||||||
|
`targetID` int not null,
|
||||||
|
`targetType` varchar(50) not null,
|
||||||
|
`level` tinyint DEFAULT 0 not null /* 0: Mentions (aka the global default for any post), 1: Replies, 2: Everyone*/
|
||||||
|
);
|
||||||
|
|
||||||
CREATE TABLE `settings`(
|
CREATE TABLE `settings`(
|
||||||
`name` varchar(200) not null,
|
`name` varchar(200) not null,
|
||||||
`content` varchar(250) not null,
|
`content` varchar(250) not null,
|
||||||
|
11
errors.go
11
errors.go
@ -41,6 +41,12 @@ func InternalErrorJSQ(err error, w http.ResponseWriter, r *http.Request, is_js s
|
|||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func InternalErrorJS(err error, w http.ResponseWriter, r *http.Request) {
|
||||||
|
w.WriteHeader(500)
|
||||||
|
w.Write([]byte(`{'errmsg': 'A problem has occured in the system.'}`))
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
func PreError(errmsg string, w http.ResponseWriter, r *http.Request) {
|
func PreError(errmsg string, w http.ResponseWriter, r *http.Request) {
|
||||||
w.WriteHeader(500)
|
w.WriteHeader(500)
|
||||||
user := User{ID:0,Group:6,Perms:GuestPerms,}
|
user := User{ID:0,Group:6,Perms:GuestPerms,}
|
||||||
@ -91,6 +97,11 @@ func LocalErrorJSQ(errmsg string, w http.ResponseWriter, r *http.Request, user U
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func LocalErrorJS(errmsg string, w http.ResponseWriter, r *http.Request) {
|
||||||
|
w.WriteHeader(500)
|
||||||
|
w.Write([]byte(`{'errmsg': '` + errmsg + `'}`))
|
||||||
|
}
|
||||||
|
|
||||||
func NoPermissions(w http.ResponseWriter, r *http.Request, user User) {
|
func NoPermissions(w http.ResponseWriter, r *http.Request, user User) {
|
||||||
w.WriteHeader(403)
|
w.WriteHeader(403)
|
||||||
pi := Page{"Local Error",user,nList,tList,"You don't have permission to do that."}
|
pi := Page{"Local Error",user,nList,tList,"You don't have permission to do that."}
|
||||||
|
@ -10,12 +10,17 @@ import "net/http"
|
|||||||
import "net/http/httptest"
|
import "net/http/httptest"
|
||||||
import "io/ioutil"
|
import "io/ioutil"
|
||||||
import "database/sql"
|
import "database/sql"
|
||||||
import _ "github.com/go-sql-driver/mysql"
|
//import _ "github.com/go-sql-driver/mysql"
|
||||||
|
//import "github.com/erikstmartin/go-testdb"
|
||||||
//import "github.com/husobee/vestigo"
|
//import "github.com/husobee/vestigo"
|
||||||
import "runtime/pprof"
|
import "runtime/pprof"
|
||||||
|
|
||||||
|
var db_test *sql.DB
|
||||||
|
var db_prod *sql.DB
|
||||||
var gloinited bool = false
|
var gloinited bool = false
|
||||||
|
|
||||||
func gloinit() {
|
func gloinit() {
|
||||||
|
var err error
|
||||||
debug = false
|
debug = false
|
||||||
nogrouplog = true
|
nogrouplog = true
|
||||||
|
|
||||||
@ -24,10 +29,15 @@ func gloinit() {
|
|||||||
//log.SetOutput(discard)
|
//log.SetOutput(discard)
|
||||||
|
|
||||||
init_themes()
|
init_themes()
|
||||||
var err error
|
|
||||||
init_database(err)
|
init_database(err)
|
||||||
|
db_prod = db
|
||||||
|
//db_test, err = sql.Open("testdb","")
|
||||||
|
//if err != nil {
|
||||||
|
// log.Fatal(err)
|
||||||
|
//}
|
||||||
|
|
||||||
init_templates()
|
init_templates()
|
||||||
db.SetMaxOpenConns(64)
|
db_prod.SetMaxOpenConns(64)
|
||||||
err = init_errors()
|
err = init_errors()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
@ -1368,6 +1378,35 @@ func TestForumGuestRoute(t *testing.T) {
|
|||||||
fmt.Println("No problems found in the forum-guest route!")
|
fmt.Println("No problems found in the forum-guest route!")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*func TestAlerts(t *testing.T) {
|
||||||
|
if !gloinited {
|
||||||
|
gloinit()
|
||||||
|
}
|
||||||
|
if !plugins_inited {
|
||||||
|
init_plugins()
|
||||||
|
}
|
||||||
|
db = db_test
|
||||||
|
alert_w := httptest.NewRecorder()
|
||||||
|
alert_req := httptest.NewRequest("get","/api/?action=get&module=alerts",bytes.NewReader(nil))
|
||||||
|
alert_handler := http.HandlerFunc(route_api)
|
||||||
|
//testdb.StubQuery()
|
||||||
|
testdb.SetQueryFunc(func(query string) (result sql.Rows, err error) {
|
||||||
|
cols := []string{"asid","actor","targetUser","event","elementType","elementID"}
|
||||||
|
rows := `1,1,0,like,post,5
|
||||||
|
1,1,0,friend_invite,user,2`
|
||||||
|
return testdb.RowsFromCSVString(cols,rows), nil
|
||||||
|
})
|
||||||
|
|
||||||
|
alert_handler.ServeHTTP(alert_w,alert_req)
|
||||||
|
fmt.Println(alert_w.Body)
|
||||||
|
if alert_w.Code != 200 {
|
||||||
|
panic("HTTP Error!")
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Println("No problems found in the alert handler!")
|
||||||
|
db = db_prod
|
||||||
|
}*/
|
||||||
|
|
||||||
/*func TestRoute(t *testing.T) {
|
/*func TestRoute(t *testing.T) {
|
||||||
|
|
||||||
}*/
|
}*/
|
4
main.go
4
main.go
@ -184,8 +184,7 @@ func main(){
|
|||||||
init_plugins()
|
init_plugins()
|
||||||
|
|
||||||
router := NewRouter()
|
router := NewRouter()
|
||||||
router.HandleFunc("/static/", route_static) // In a directory to stop it clashing with the other paths
|
router.HandleFunc("/static/", route_static)
|
||||||
|
|
||||||
fs_u := http.FileServer(http.Dir("./uploads"))
|
fs_u := http.FileServer(http.Dir("./uploads"))
|
||||||
router.Handle("/uploads/", http.StripPrefix("/uploads/",fs_u))
|
router.Handle("/uploads/", http.StripPrefix("/uploads/",fs_u))
|
||||||
|
|
||||||
@ -260,6 +259,7 @@ func main(){
|
|||||||
router.HandleFunc("/panel/users/edit/", route_panel_users_edit)
|
router.HandleFunc("/panel/users/edit/", route_panel_users_edit)
|
||||||
router.HandleFunc("/panel/users/edit/submit/", route_panel_users_edit_submit)
|
router.HandleFunc("/panel/users/edit/submit/", route_panel_users_edit_submit)
|
||||||
router.HandleFunc("/panel/groups/", route_panel_groups)
|
router.HandleFunc("/panel/groups/", route_panel_groups)
|
||||||
|
router.HandleFunc("/api/", route_api)
|
||||||
//router.HandleFunc("/exit/", route_exit)
|
//router.HandleFunc("/exit/", route_exit)
|
||||||
|
|
||||||
router.HandleFunc("/", default_route)
|
router.HandleFunc("/", default_route)
|
||||||
|
@ -1412,6 +1412,9 @@ func route_panel_themes(w http.ResponseWriter, r *http.Request){
|
|||||||
|
|
||||||
var themeList []interface{}
|
var themeList []interface{}
|
||||||
for _, theme := range themes {
|
for _, theme := range themes {
|
||||||
|
if theme.HideFromThemes {
|
||||||
|
continue
|
||||||
|
}
|
||||||
themeList = append(themeList,theme)
|
themeList = append(themeList,theme)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
31
mysql.go
31
mysql.go
@ -16,8 +16,10 @@ var get_full_user_stmt *sql.Stmt
|
|||||||
var get_topic_list_stmt *sql.Stmt
|
var get_topic_list_stmt *sql.Stmt
|
||||||
var get_topic_user_stmt *sql.Stmt
|
var get_topic_user_stmt *sql.Stmt
|
||||||
var get_topic_stmt *sql.Stmt
|
var get_topic_stmt *sql.Stmt
|
||||||
|
var get_topic_by_reply_stmt *sql.Stmt
|
||||||
var get_topic_replies_stmt *sql.Stmt
|
var get_topic_replies_stmt *sql.Stmt
|
||||||
var get_topic_replies_offset_stmt *sql.Stmt
|
var get_topic_replies_offset_stmt *sql.Stmt
|
||||||
|
var get_post_stmt *sql.Stmt
|
||||||
var get_forum_topics_stmt *sql.Stmt
|
var get_forum_topics_stmt *sql.Stmt
|
||||||
var get_forum_topics_offset_stmt *sql.Stmt
|
var get_forum_topics_offset_stmt *sql.Stmt
|
||||||
var create_topic_stmt *sql.Stmt
|
var create_topic_stmt *sql.Stmt
|
||||||
@ -37,6 +39,7 @@ var delete_reply_stmt *sql.Stmt
|
|||||||
var delete_topic_stmt *sql.Stmt
|
var delete_topic_stmt *sql.Stmt
|
||||||
var stick_topic_stmt *sql.Stmt
|
var stick_topic_stmt *sql.Stmt
|
||||||
var unstick_topic_stmt *sql.Stmt
|
var unstick_topic_stmt *sql.Stmt
|
||||||
|
var get_activity_feed_by_watcher_stmt *sql.Stmt
|
||||||
var update_last_ip_stmt *sql.Stmt
|
var update_last_ip_stmt *sql.Stmt
|
||||||
var login_stmt *sql.Stmt
|
var login_stmt *sql.Stmt
|
||||||
var update_session_stmt *sql.Stmt
|
var update_session_stmt *sql.Stmt
|
||||||
@ -133,6 +136,12 @@ func init_database(err error) {
|
|||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log.Print("Preparing get_topic_by_reply statement.")
|
||||||
|
get_topic_by_reply_stmt, err = db.Prepare("select topics.tid, topics.title, topics.content, topics.createdBy, topics.createdAt, topics.is_closed, topics.sticky, topics.parentID, topics.ipaddress, topics.postCount, topics.likeCount from replies left join topics on replies.tid = topics.tid where rid = ?")
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
log.Print("Preparing get_topic_replies statement.")
|
log.Print("Preparing get_topic_replies statement.")
|
||||||
get_topic_replies_stmt, err = db.Prepare("select replies.rid, replies.content, replies.createdBy, replies.createdAt, replies.lastEdit, replies.lastEditBy, users.avatar, users.name, users.group, users.url_prefix, users.url_name, users.level, replies.ipaddress from replies left join users ON replies.createdBy = users.uid where tid = ?")
|
get_topic_replies_stmt, err = db.Prepare("select replies.rid, replies.content, replies.createdBy, replies.createdAt, replies.lastEdit, replies.lastEditBy, users.avatar, users.name, users.group, users.url_prefix, users.url_name, users.level, replies.ipaddress from replies left join users ON replies.createdBy = users.uid where tid = ?")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -145,6 +154,12 @@ func init_database(err error) {
|
|||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log.Print("Preparing get_post statement.")
|
||||||
|
get_post_stmt, err = db.Prepare("select content, createdBy, createdAt, lastEdit, lastEditBy, ipaddress, likeCount from replies where rid = ?")
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
log.Print("Preparing get_forum_topics statement.")
|
log.Print("Preparing get_forum_topics statement.")
|
||||||
get_forum_topics_stmt, err = db.Prepare("select topics.tid, topics.title, topics.content, topics.createdBy, topics.is_closed, topics.sticky, topics.createdAt, topics.lastReplyAt, topics.parentID, users.name, users.avatar from topics left join users ON topics.createdBy = users.uid where topics.parentID = ? order by topics.sticky DESC, topics.lastReplyAt DESC, topics.createdBy desc")
|
get_forum_topics_stmt, err = db.Prepare("select topics.tid, topics.title, topics.content, topics.createdBy, topics.is_closed, topics.sticky, topics.createdAt, topics.lastReplyAt, topics.parentID, users.name, users.avatar from topics left join users ON topics.createdBy = users.uid where topics.parentID = ? order by topics.sticky DESC, topics.lastReplyAt DESC, topics.createdBy desc")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -259,6 +274,12 @@ func init_database(err error) {
|
|||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log.Print("Preparing get_activity_feed_by_watcher statement.")
|
||||||
|
get_activity_feed_by_watcher_stmt, err = db.Prepare("SELECT activity_stream_matches.asid, activity_stream.actor, activity_stream.targetUser, activity_stream.event, activity_stream.elementType, activity_stream.elementID FROM `activity_stream_matches` LEFT JOIN `activity_stream` ON activity_stream_matches.asid = activity_stream.asid WHERE `watcher` = ?")
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
log.Print("Preparing update_last_ip statement.")
|
log.Print("Preparing update_last_ip statement.")
|
||||||
update_last_ip_stmt, err = db.Prepare("UPDATE users SET last_ip = ? WHERE uid = ?")
|
update_last_ip_stmt, err = db.Prepare("UPDATE users SET last_ip = ? WHERE uid = ?")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -266,7 +287,7 @@ func init_database(err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
log.Print("Preparing login statement.")
|
log.Print("Preparing login statement.")
|
||||||
login_stmt, err = db.Prepare("SELECT `uid`, `name`, `password`, `salt` FROM `users` WHERE `name` = ?")
|
login_stmt, err = db.Prepare("SELECT `uid`,`name`,`password`,`salt` FROM `users` WHERE `name` = ?")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
@ -290,7 +311,7 @@ func init_database(err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
log.Print("Preparing get_password statement.")
|
log.Print("Preparing get_password statement.")
|
||||||
get_password_stmt, err = db.Prepare("SELECT `password`, `salt` FROM `users` WHERE `uid` = ?")
|
get_password_stmt, err = db.Prepare("SELECT `password`,`salt` FROM `users` WHERE `uid` = ?")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
@ -444,19 +465,19 @@ func init_database(err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
log.Print("Preparing add_forum_perms_to_forum_admins statement.")
|
log.Print("Preparing add_forum_perms_to_forum_admins statement.")
|
||||||
add_forum_perms_to_forum_admins_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset, ? AS permissions FROM users_groups WHERE is_admin = 1")
|
add_forum_perms_to_forum_admins_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset,? AS permissions FROM users_groups WHERE is_admin = 1")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Print("Preparing add_forum_perms_to_forum_staff statement.")
|
log.Print("Preparing add_forum_perms_to_forum_staff statement.")
|
||||||
add_forum_perms_to_forum_staff_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset, ? AS permissions FROM users_groups WHERE is_admin = 0 AND is_mod = 1")
|
add_forum_perms_to_forum_staff_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset,? AS permissions FROM users_groups WHERE is_admin = 0 AND is_mod = 1")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Print("Preparing add_forum_perms_to_forum_members statement.")
|
log.Print("Preparing add_forum_perms_to_forum_members statement.")
|
||||||
add_forum_perms_to_forum_members_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset, ? AS permissions FROM users_groups WHERE is_admin = 0 AND is_mod = 0 AND is_banned = 0")
|
add_forum_perms_to_forum_members_stmt, err = db.Prepare("INSERT INTO forums_permissions(gid,fid,preset,permissions) SELECT `gid`,? AS fid,? AS preset,? AS permissions FROM users_groups WHERE is_admin = 0 AND is_mod = 0 AND is_banned = 0")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal(err)
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
|
@ -364,21 +364,20 @@ func bbcode_full_parse(data interface{}) interface{} {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//fmt.Println(outbytes)
|
|
||||||
//fmt.Println(string(outbytes))
|
//fmt.Println(string(outbytes))
|
||||||
if lastTag != i {
|
if lastTag != i {
|
||||||
outbytes = append(outbytes, msgbytes[lastTag:len(msgbytes) - 10]...)
|
outbytes = append(outbytes, msgbytes[lastTag:]...)
|
||||||
}
|
}
|
||||||
if len(outbytes) != 0 {
|
if len(outbytes) != 0 {
|
||||||
return string(outbytes)
|
return string(outbytes[0:len(msgbytes) - 10])
|
||||||
}
|
}
|
||||||
|
|
||||||
msg = string(msgbytes)
|
msg = string(msgbytes[0:len(msgbytes) - 10])
|
||||||
//msg = bbcode_url.ReplaceAllString(msg,"<a href=\"$1$2//$3\" rel=\"nofollow\">$1$2//$3</i>")
|
//msg = bbcode_url.ReplaceAllString(msg,"<a href=\"$1$2//$3\" rel=\"nofollow\">$1$2//$3</i>")
|
||||||
msg = bbcode_url_label.ReplaceAllString(msg,"<a href=\"$1$2//$3\" rel=\"nofollow\">$4</i>")
|
msg = bbcode_url_label.ReplaceAllString(msg,"<a href=\"$1$2//$3\" rel=\"nofollow\">$4</i>")
|
||||||
// Convert [code] into class="codequotes"
|
// Convert [code] into class="codequotes"
|
||||||
} else {
|
} else {
|
||||||
msg = string(msgbytes)
|
msg = string(msgbytes[0:len(msgbytes) - 10])
|
||||||
}
|
}
|
||||||
return msg
|
return msg
|
||||||
}
|
}
|
||||||
|
23
reply.go
23
reply.go
@ -2,7 +2,7 @@
|
|||||||
package main
|
package main
|
||||||
import "html/template"
|
import "html/template"
|
||||||
|
|
||||||
type Reply struct
|
type Reply struct /* Should probably rename this to ReplyUser and rename ReplyShort to Reply */
|
||||||
{
|
{
|
||||||
ID int
|
ID int
|
||||||
ParentID int
|
ParentID int
|
||||||
@ -27,3 +27,24 @@ type Reply struct
|
|||||||
LikeCount int
|
LikeCount int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ReplyShort struct
|
||||||
|
{
|
||||||
|
ID int
|
||||||
|
ParentID int
|
||||||
|
Content string
|
||||||
|
CreatedBy int
|
||||||
|
Group int
|
||||||
|
CreatedAt string
|
||||||
|
LastEdit int
|
||||||
|
LastEditBy int
|
||||||
|
ContentLines int
|
||||||
|
IpAddress string
|
||||||
|
Liked bool
|
||||||
|
LikeCount int
|
||||||
|
}
|
||||||
|
|
||||||
|
func get_reply(id int) (*ReplyShort, error) {
|
||||||
|
reply := ReplyShort{ID:id}
|
||||||
|
err := get_post_stmt.QueryRow(id).Scan(&reply.Content, &reply.CreatedBy, &reply.CreatedAt, &reply.LastEdit, &reply.LastEditBy, &reply.IpAddress, &reply.LikeCount)
|
||||||
|
return &reply, err
|
||||||
|
}
|
||||||
|
184
routes.go
184
routes.go
@ -1605,3 +1605,187 @@ func route_register_submit(w http.ResponseWriter, r *http.Request) {
|
|||||||
http.SetCookie(w,&cookie)
|
http.SetCookie(w,&cookie)
|
||||||
http.Redirect(w,r, "/", http.StatusSeeOther)
|
http.Redirect(w,r, "/", http.StatusSeeOther)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func route_api(w http.ResponseWriter, r *http.Request) {
|
||||||
|
err := r.ParseForm()
|
||||||
|
is_js := r.PostFormValue("js")
|
||||||
|
if is_js == "" {
|
||||||
|
is_js = "0"
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
PreErrorJSQ("Bad Form",w,r,is_js)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
user, ok := SimpleSessionCheck(w,r)
|
||||||
|
if !ok {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
action := r.FormValue("action")
|
||||||
|
if action != "get" && action != "set" {
|
||||||
|
PreErrorJSQ("Invalid Action",w,r,is_js)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
module := r.FormValue("module")
|
||||||
|
switch(module) {
|
||||||
|
case "alerts": // A feed of events tailored for a specific user
|
||||||
|
w.Header().Set("Content-Type","application/json")
|
||||||
|
if !user.Loggedin {
|
||||||
|
w.Write([]byte(`{"msgs":[{"msg":"Login to see your alerts","path":"/accounts/login"}]}`))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var msglist string
|
||||||
|
var asid int
|
||||||
|
var actor_id int
|
||||||
|
var targetUser_id int
|
||||||
|
var event string
|
||||||
|
var elementType string
|
||||||
|
var elementID int
|
||||||
|
//---
|
||||||
|
var targetUser *User
|
||||||
|
|
||||||
|
rows, err := get_activity_feed_by_watcher_stmt.Query(user.ID)
|
||||||
|
if err != nil {
|
||||||
|
InternalErrorJS(err,w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
for rows.Next() {
|
||||||
|
err = rows.Scan(&asid,&actor_id,&targetUser_id,&event,&elementType,&elementID)
|
||||||
|
if err != nil {
|
||||||
|
InternalErrorJS(err,w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
actor, err := users.CascadeGet(actor_id)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the actor",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
/*if elementType != "forum" {
|
||||||
|
targetUser, err = users.CascadeGet(targetUser_id)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the target user",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}*/
|
||||||
|
|
||||||
|
if event == "friend_invite" {
|
||||||
|
msglist += `{"msg":"You received a friend invite from {0}","sub":["` + actor.Name + `"],"path":"/user/`+strconv.Itoa(actor.ID)+`"},`
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
"You received a friend invite from {user}"
|
||||||
|
"{x}{mentioned you on}{user}{'s profile}"
|
||||||
|
"{x}{mentioned you in}{topic}"
|
||||||
|
"{x}{likes}{you}"
|
||||||
|
"{x}{liked}{your topic}{topic}"
|
||||||
|
"{x}{liked}{your post on}{user}{'s profile}" todo
|
||||||
|
"{x}{liked}{your post in}{topic}"
|
||||||
|
"{x}{replied to}{your post in}{topic}" todo
|
||||||
|
"{x}{created a new topic}{topic}"
|
||||||
|
*/
|
||||||
|
|
||||||
|
var act string
|
||||||
|
var post_act string
|
||||||
|
var url string
|
||||||
|
var area string
|
||||||
|
var start_frag string
|
||||||
|
var end_frag string
|
||||||
|
switch(elementType) {
|
||||||
|
case "forum":
|
||||||
|
if event == "reply" {
|
||||||
|
act = "created a new topic"
|
||||||
|
topic, err := topics.CascadeGet(elementID)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the linked topic",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
url = build_topic_url(elementID)
|
||||||
|
area = topic.Title
|
||||||
|
// Store the forum ID in the targetUser column instead of making a new one? o.O
|
||||||
|
// Add an additional column for extra information later on when we add the ability to link directly to posts. We don't need the forum data for now..
|
||||||
|
} else {
|
||||||
|
act = "did something in a forum"
|
||||||
|
}
|
||||||
|
case "topic":
|
||||||
|
topic, err := topics.CascadeGet(elementID)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the linked topic",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
url = build_topic_url(elementID)
|
||||||
|
area = topic.Title
|
||||||
|
if targetUser_id == user.ID {
|
||||||
|
post_act = " your topic"
|
||||||
|
}
|
||||||
|
case "user":
|
||||||
|
targetUser, err = users.CascadeGet(elementID)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the target user",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
area = targetUser.Name
|
||||||
|
end_frag = "'s profile"
|
||||||
|
url = build_profile_url(elementID)
|
||||||
|
case "post":
|
||||||
|
topic, err := get_topic_by_reply(elementID)
|
||||||
|
if err != nil {
|
||||||
|
LocalErrorJS("Unable to find the target reply or parent topic",w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
url = build_topic_url(elementID)
|
||||||
|
area = topic.Title
|
||||||
|
if targetUser_id == user.ID {
|
||||||
|
post_act = " your post in"
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
LocalErrorJS("Invalid elementType",w,r)
|
||||||
|
}
|
||||||
|
|
||||||
|
if event == "like" {
|
||||||
|
if elementType == "user" {
|
||||||
|
act = "likes"
|
||||||
|
end_frag = ""
|
||||||
|
if targetUser.ID == user.ID {
|
||||||
|
area = "you"
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
act = "liked"
|
||||||
|
}
|
||||||
|
} else if event == "mention" {
|
||||||
|
if elementType == "user" {
|
||||||
|
act = "mentioned you on"
|
||||||
|
} else {
|
||||||
|
act = "mentioned you in"
|
||||||
|
post_act = ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
msglist += `{"msg":"{0} ` + start_frag + act + post_act + ` {1}` + end_frag + `","sub":["` + actor.Name + `","` + area + `"],"path":"` + url + `"},`
|
||||||
|
}
|
||||||
|
|
||||||
|
err = rows.Err()
|
||||||
|
if err != nil {
|
||||||
|
InternalErrorJS(err,w,r)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
rows.Close()
|
||||||
|
|
||||||
|
if len(msglist) != 0 {
|
||||||
|
msglist = msglist[0:len(msglist)-1]
|
||||||
|
}
|
||||||
|
w.Write([]byte(`{"msgs":[`+msglist+`]}`))
|
||||||
|
//case "topics":
|
||||||
|
//case "forums":
|
||||||
|
//case "users":
|
||||||
|
//case "pages":
|
||||||
|
default:
|
||||||
|
PreErrorJSQ("Invalid Module",w,r,is_js)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_forum_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_forum_vars.NoticeList) != 0 {
|
if len(tmpl_forum_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_forum_vars.NoticeList {
|
for _, item := range tmpl_forum_vars.NoticeList {
|
||||||
|
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_forums_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_forums_vars.NoticeList) != 0 {
|
if len(tmpl_forums_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_forums_vars.NoticeList {
|
for _, item := range tmpl_forums_vars.NoticeList {
|
||||||
|
@ -40,6 +40,9 @@ var menu_6 []byte = []byte(`
|
|||||||
<li class="menu_left menu_login"><a href="/accounts/login/">Login</a></li>
|
<li class="menu_left menu_login"><a href="/accounts/login/">Login</a></li>
|
||||||
`)
|
`)
|
||||||
var menu_7 []byte = []byte(`
|
var menu_7 []byte = []byte(`
|
||||||
|
<li class="menu_right menu_alerts">🔔︎<div class="alert_counter">`)
|
||||||
|
var menu_8 []byte = []byte(`1`)
|
||||||
|
var menu_9 []byte = []byte(`</div></li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_profile_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_profile_vars.NoticeList) != 0 {
|
if len(tmpl_profile_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_profile_vars.NoticeList {
|
for _, item := range tmpl_profile_vars.NoticeList {
|
||||||
|
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_topic_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_topic_vars.NoticeList) != 0 {
|
if len(tmpl_topic_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_topic_vars.NoticeList {
|
for _, item := range tmpl_topic_vars.NoticeList {
|
||||||
|
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_topic_alt_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_topic_alt_vars.NoticeList) != 0 {
|
if len(tmpl_topic_alt_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_topic_alt_vars.NoticeList {
|
for _, item := range tmpl_topic_alt_vars.NoticeList {
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
/* This file was automatically generated by the software. Please don't edit it as your changes may be overwritten at any moment. */
|
/* This file was automatically generated by the software. Please don't edit it as your changes may be overwritten at any moment. */
|
||||||
package main
|
package main
|
||||||
import "strconv"
|
|
||||||
import "io"
|
import "io"
|
||||||
|
import "strconv"
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
template_topics_handle = template_topics
|
template_topics_handle = template_topics
|
||||||
@ -32,6 +32,10 @@ w.Write(menu_5)
|
|||||||
w.Write(menu_6)
|
w.Write(menu_6)
|
||||||
}
|
}
|
||||||
w.Write(menu_7)
|
w.Write(menu_7)
|
||||||
|
if !tmpl_topics_vars.CurrentUser.Loggedin {
|
||||||
|
w.Write(menu_8)
|
||||||
|
}
|
||||||
|
w.Write(menu_9)
|
||||||
w.Write(header_3)
|
w.Write(header_3)
|
||||||
if len(tmpl_topics_vars.NoticeList) != 0 {
|
if len(tmpl_topics_vars.NoticeList) != 0 {
|
||||||
for _, item := range tmpl_topics_vars.NoticeList {
|
for _, item := range tmpl_topics_vars.NoticeList {
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
<div class="colblock_left">
|
<div class="colblock_left">
|
||||||
<div class="rowitem"><a>My Account</a></div>
|
<div class="rowitem rowhead"><a>My Account</a></div>
|
||||||
<div class="rowitem passive"><a href="/user/edit/avatar/">Change Avatar</a></div>
|
<div class="rowitem passive"><a href="/user/edit/avatar/">Change Avatar</a></div>
|
||||||
<div class="rowitem passive"><a href="/user/edit/username/">Change Username</a></div>
|
<div class="rowitem passive"><a href="/user/edit/username/">Change Username</a></div>
|
||||||
<div class="rowitem passive"><a href="/user/edit/critical/">Change Password</a></div>
|
<div class="rowitem passive"><a href="/user/edit/critical/">Change Password</a></div>
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
{{template "account-menu.html" . }}
|
{{template "account-menu.html" . }}
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<div class="rowitem"><a>Edit Avatar</a></div>
|
<div class="rowitem rowhead"><a>Edit Avatar</a></div>
|
||||||
</div>
|
</div>
|
||||||
{{ if .CurrentUser.Avatar }}
|
{{ if .CurrentUser.Avatar }}
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
{{template "account-menu.html" . }}
|
{{template "account-menu.html" . }}
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<div class="rowitem"><a>Emails</a></div>
|
<div class="rowitem rowhead"><a>Emails</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
{{range .ItemList}}
|
{{range .ItemList}}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
{{template "account-menu.html" . }}
|
{{template "account-menu.html" . }}
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<div class="rowitem"><a>Edit Username</a></div>
|
<div class="rowitem rowhead"><a>Edit Username</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<form action="/user/edit/username/submit/" method="post">
|
<form action="/user/edit/username/submit/" method="post">
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
{{template "account-menu.html" . }}
|
{{template "account-menu.html" . }}
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<div class="rowitem"><a>Edit Password</a></div>
|
<div class="rowitem rowhead"><a>Edit Password</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="colblock_right">
|
<div class="colblock_right">
|
||||||
<form action="/user/edit/critical/submit/" method="post">
|
<form action="/user/edit/critical/submit/" method="post">
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<div class="rowitem"><a>Create Topic</a></div>
|
<div class="rowitem rowhead"><a>Create Topic</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<form action="/topic/create/submit/" method="post">
|
<form action="/topic/create/submit/" method="post">
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<div class="rowitem"><a>Login</a></div>
|
<div class="rowitem rowhead"><a>Login</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<form action="/accounts/login/submit/" method="post">
|
<form action="/accounts/login/submit/" method="post">
|
||||||
@ -13,7 +13,8 @@
|
|||||||
<div class="formitem"><input name="password" type="password" autocomplete="current-password" placeholder="*****" /></div>
|
<div class="formitem"><input name="password" type="password" autocomplete="current-password" placeholder="*****" /></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="formrow">
|
<div class="formrow">
|
||||||
<div class="formitem"><button name="login-button" class="formbutton">Login</div></div>
|
<div class="formitem"><button name="login-button" class="formbutton">Login</div>
|
||||||
|
<div class="formitem" style="color: #505050; font-size: 12px; font-weight: normal; float: right;">Don't have an account?</div>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</div>
|
||||||
|
@ -9,12 +9,13 @@
|
|||||||
{{if .CurrentUser.Loggedin}}
|
{{if .CurrentUser.Loggedin}}
|
||||||
<li class="menu_left menu_account"><a href="/user/edit/critical/">Account</a></li>
|
<li class="menu_left menu_account"><a href="/user/edit/critical/">Account</a></li>
|
||||||
<li class="menu_left menu_profile"><a href="/user/{{.CurrentUser.ID}}">Profile</a></li>
|
<li class="menu_left menu_profile"><a href="/user/{{.CurrentUser.ID}}">Profile</a></li>
|
||||||
{{ if .CurrentUser.Is_Super_Mod}}<li class="menu_left menu_account"><a href="/panel/">Panel</a></li>{{end}}
|
{{if .CurrentUser.Is_Super_Mod}}<li class="menu_left menu_account"><a href="/panel/">Panel</a></li>{{end}}
|
||||||
<li class="menu_left menu_logout"><a href="/accounts/logout?session={{.CurrentUser.Session}}">Logout</a></li>
|
<li class="menu_left menu_logout"><a href="/accounts/logout?session={{.CurrentUser.Session}}">Logout</a></li>
|
||||||
{{else}}
|
{{else}}
|
||||||
<li class="menu_left menu_register"><a href="/accounts/create/">Register</a></li>
|
<li class="menu_left menu_register"><a href="/accounts/create/">Register</a></li>
|
||||||
<li class="menu_left menu_login"><a href="/accounts/login/">Login</a></li>
|
<li class="menu_left menu_login"><a href="/accounts/login/">Login</a></li>
|
||||||
{{end}}
|
{{end}}
|
||||||
|
<li class="menu_right menu_alerts">🔔︎<div class="alert_counter">{{if not .CurrentUser.Loggedin}}1{{end}}</div></li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
{{template "header.html" . }}
|
{{template "header.html" . }}
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<div class="rowitem"><a>Create Account</a></div>
|
<div class="rowitem rowhead"><a>Create Account</a></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="rowblock">
|
<div class="rowblock">
|
||||||
<form action="/accounts/create/submit/" method="post">
|
<form action="/accounts/create/submit/" method="post">
|
||||||
|
27
themes.go
27
themes.go
@ -26,6 +26,7 @@ type Theme struct
|
|||||||
FullImage string
|
FullImage string
|
||||||
MobileFriendly bool
|
MobileFriendly bool
|
||||||
Disabled bool
|
Disabled bool
|
||||||
|
HideFromThemes bool
|
||||||
Tag string
|
Tag string
|
||||||
Settings map[string]ThemeSetting
|
Settings map[string]ThemeSetting
|
||||||
Templates []TemplateMapping
|
Templates []TemplateMapping
|
||||||
@ -141,21 +142,7 @@ func map_theme_templates(theme Theme) {
|
|||||||
case *func(TopicPage,io.Writer):
|
case *func(TopicPage,io.Writer):
|
||||||
//overriden_templates[themeTmpl.Name] = d_tmpl_ptr
|
//overriden_templates[themeTmpl.Name] = d_tmpl_ptr
|
||||||
overriden_templates[themeTmpl.Name] = true
|
overriden_templates[themeTmpl.Name] = true
|
||||||
//log.Print("Topic Handle")
|
|
||||||
//fmt.Println(template_topic_handle)
|
|
||||||
//log.Print("Before")
|
|
||||||
//fmt.Println(d_tmpl_ptr)
|
|
||||||
//fmt.Println(*d_tmpl_ptr)
|
|
||||||
//log.Print("Source")
|
|
||||||
//fmt.Println(s_tmpl_ptr)
|
|
||||||
//fmt.Println(*s_tmpl_ptr)
|
|
||||||
*d_tmpl_ptr = *s_tmpl_ptr
|
*d_tmpl_ptr = *s_tmpl_ptr
|
||||||
//log.Print("After")
|
|
||||||
//fmt.Println(d_tmpl_ptr)
|
|
||||||
//fmt.Println(*d_tmpl_ptr)
|
|
||||||
//log.Print("Source")
|
|
||||||
//fmt.Println(s_tmpl_ptr)
|
|
||||||
//fmt.Println(*s_tmpl_ptr)
|
|
||||||
default:
|
default:
|
||||||
log.Fatal("The source and destination templates are incompatible")
|
log.Fatal("The source and destination templates are incompatible")
|
||||||
}
|
}
|
||||||
@ -236,19 +223,7 @@ func reset_template_overrides() {
|
|||||||
case func(TopicPage,io.Writer):
|
case func(TopicPage,io.Writer):
|
||||||
switch d_ptr := dest_tmpl_ptr.(type) {
|
switch d_ptr := dest_tmpl_ptr.(type) {
|
||||||
case *func(TopicPage,io.Writer):
|
case *func(TopicPage,io.Writer):
|
||||||
//log.Print("Topic Handle")
|
|
||||||
//fmt.Println(template_topic_handle)
|
|
||||||
//log.Print("Before")
|
|
||||||
//fmt.Println(d_ptr)
|
|
||||||
//fmt.Println(*d_ptr)
|
|
||||||
//log.Print("Origin")
|
|
||||||
//fmt.Println(o_ptr)
|
|
||||||
*d_ptr = o_ptr
|
*d_ptr = o_ptr
|
||||||
//log.Print("After")
|
|
||||||
//fmt.Println(d_ptr)
|
|
||||||
//fmt.Println(*d_ptr)
|
|
||||||
//log.Print("Origin")
|
|
||||||
//fmt.Println(o_ptr)
|
|
||||||
default:
|
default:
|
||||||
log.Fatal("The origin and destination templates are incompatible")
|
log.Fatal("The origin and destination templates are incompatible")
|
||||||
}
|
}
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
"Version": "Coming Soon",
|
"Version": "Coming Soon",
|
||||||
"Creator": "Azareal",
|
"Creator": "Azareal",
|
||||||
"Disabled": true,
|
"Disabled": true,
|
||||||
|
"HideFromThemes": true,
|
||||||
"Tag": "WIP",
|
"Tag": "WIP",
|
||||||
"Templates": [
|
"Templates": [
|
||||||
{
|
{
|
||||||
|
@ -50,10 +50,7 @@ li
|
|||||||
padding-left: 1px;
|
padding-left: 1px;
|
||||||
padding-right: 1px;
|
padding-right: 1px;
|
||||||
|
|
||||||
border: 1px solid #7a7a7a;
|
border-right: 1px solid #7a7a7a;
|
||||||
border-top: none;
|
|
||||||
border-bottom: none;
|
|
||||||
border-left: none;
|
|
||||||
font-weight: normal;
|
font-weight: normal;
|
||||||
color: white;
|
color: white;
|
||||||
}
|
}
|
||||||
@ -63,16 +60,10 @@ li a
|
|||||||
color: white;
|
color: white;
|
||||||
text-decoration: none;
|
text-decoration: none;
|
||||||
}
|
}
|
||||||
li:hover a, li a:hover, li a:link, li a:visited
|
|
||||||
{
|
|
||||||
color: white;
|
|
||||||
text-decoration: none;
|
|
||||||
}
|
|
||||||
li:hover
|
li:hover
|
||||||
{
|
{
|
||||||
background: rgba(10,10,10,0.5);
|
background: rgba(10,10,10,0.5);
|
||||||
font-weight: normal;
|
font-weight: normal;
|
||||||
color: white;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.menu_right
|
.menu_right
|
||||||
@ -85,17 +76,28 @@ li:hover
|
|||||||
padding-right: 10px;
|
padding-right: 10px;
|
||||||
height: 38px;
|
height: 38px;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
|
border-left: 1px solid #7a7a7a;
|
||||||
}
|
}
|
||||||
|
|
||||||
.menu_right:hover
|
.menu_alerts .alert_counter {
|
||||||
{
|
position: relative;
|
||||||
border: #282828 1px solid;
|
font-size: 9px;
|
||||||
background: #282828;
|
top: -24px;
|
||||||
padding-left: 10px;
|
background-color: rgb(140,0,0);
|
||||||
padding-right: 10px;
|
color: white;
|
||||||
height: 38px;
|
padding: 3px;
|
||||||
|
width: 14px;
|
||||||
|
left: 10px;
|
||||||
|
line-height: 8px;
|
||||||
|
border-radius: 20px;
|
||||||
|
padding-top: 2.5px;
|
||||||
|
height: 14px;
|
||||||
|
opacity: 0.8;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
|
.menu_alerts .alert_counter:empty {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
#footer
|
#footer
|
||||||
{
|
{
|
||||||
|
8
themes/shadow/theme.json
Normal file
8
themes/shadow/theme.json
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
{
|
||||||
|
"Name": "shadow",
|
||||||
|
"FriendlyName": "Shadow",
|
||||||
|
"Version": "0.0.1",
|
||||||
|
"Creator": "Azareal",
|
||||||
|
"Disabled": true,
|
||||||
|
"HideFromThemes": true
|
||||||
|
}
|
@ -57,6 +57,31 @@ li a
|
|||||||
padding-right: 10px;
|
padding-right: 10px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.menu_alerts {
|
||||||
|
padding-left: 7px;
|
||||||
|
padding-top: 2px;
|
||||||
|
color: rgb(80,80,80);
|
||||||
|
}
|
||||||
|
.menu_alerts .alert_counter {
|
||||||
|
position:relative;
|
||||||
|
font-size: 9px;
|
||||||
|
top: -24px;
|
||||||
|
background-color: rgb(140,0,0);
|
||||||
|
color: white;
|
||||||
|
padding: 3px;
|
||||||
|
width: 14px;
|
||||||
|
left: 10px;
|
||||||
|
line-height: 8px;
|
||||||
|
border-radius: 20px;
|
||||||
|
padding-top: 2.5px;
|
||||||
|
height: 14px;
|
||||||
|
opacity: 0.8;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.menu_alerts .alert_counter:empty {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
.container
|
.container
|
||||||
{
|
{
|
||||||
width: 90%;
|
width: 90%;
|
||||||
|
@ -55,6 +55,31 @@ li a
|
|||||||
padding-right: 10px;
|
padding-right: 10px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.menu_alerts {
|
||||||
|
padding-left: 7px;
|
||||||
|
padding-top: 2px;
|
||||||
|
color: rgb(80,80,80);
|
||||||
|
}
|
||||||
|
.menu_alerts .alert_counter {
|
||||||
|
position:relative;
|
||||||
|
font-size: 9px;
|
||||||
|
top: -24px;
|
||||||
|
background-color: rgb(140,0,0);
|
||||||
|
color: white;
|
||||||
|
padding: 3px;
|
||||||
|
width: 14px;
|
||||||
|
left: 10px;
|
||||||
|
line-height: 8px;
|
||||||
|
border-radius: 20px;
|
||||||
|
padding-top: 2.5px;
|
||||||
|
height: 14px;
|
||||||
|
opacity: 0.8;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.menu_alerts .alert_counter:empty {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
.container
|
.container
|
||||||
{
|
{
|
||||||
width: 90%;
|
width: 90%;
|
||||||
|
13
topic.go
13
topic.go
@ -1,6 +1,7 @@
|
|||||||
package main
|
package main
|
||||||
//import "fmt"
|
//import "fmt"
|
||||||
import "sync"
|
import "sync"
|
||||||
|
import "strconv"
|
||||||
import "html/template"
|
import "html/template"
|
||||||
import "database/sql"
|
import "database/sql"
|
||||||
|
|
||||||
@ -341,4 +342,14 @@ func copy_topic_to_topicuser(topic *Topic, user *User) (tu TopicUser) {
|
|||||||
tu.PostCount = topic.PostCount
|
tu.PostCount = topic.PostCount
|
||||||
tu.LikeCount = topic.LikeCount
|
tu.LikeCount = topic.LikeCount
|
||||||
return tu
|
return tu
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func get_topic_by_reply(rid int) (*Topic, error) {
|
||||||
|
topic := Topic{ID:0}
|
||||||
|
err := get_topic_by_reply_stmt.QueryRow(rid).Scan(&topic.ID, &topic.Title, &topic.Content, &topic.CreatedBy, &topic.CreatedAt, &topic.Is_Closed, &topic.Sticky, &topic.ParentID, &topic.IpAddress, &topic.PostCount, &topic.LikeCount)
|
||||||
|
return &topic, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func build_topic_url(tid int) string {
|
||||||
|
return "/topic/" + strconv.Itoa(tid)
|
||||||
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user