Added the ability to compile templates down to Pure Go code.
I'm slowly rolling this feature out to the various routes and doing tests. Added the notice system. Added the "You are banned" notice. Added the Sendmail experimental plugin for sending emails without needing a SMTP server. Added the debug flag for tuning down the amount of noise in the console. Converted a system notice over to the notice system. Changed the Activation Function signature to allow it to return errors which abort the process of plugin activation. Plugins can now set tags. These will be visible in the Plugin Manager at a later date to specify a small snippet of additional information. Variadic hooks are now first class citizens of the Plugin API rather than just an experiment. SessionCheck() and the new SimpleSessionCheck() can now halt further processing of a route. Deleted plugins are no longer shown on the Plugin Manager. The registration form no longer allows users with blank names, emails or passwords to register. The registration form now blocks some extremely common passwords. Added the new status CSS to the /forum/ route. Simplified some of the range loops in the templates.
This commit is contained in:
parent
086239f88c
commit
7b1f27bf41
|
@ -15,6 +15,12 @@ var default_route = route_topics
|
|||
var default_group = 3
|
||||
var staff_css = " background-color: #ffeaff;"
|
||||
var uncategorised_forum_visible = true
|
||||
var enable_emails = false
|
||||
var site_email = ""
|
||||
var smtp_server = ""
|
||||
var siteurl = "localhost:8080"
|
||||
var noavatar = "https://api.adorable.io/avatars/285/{id}@" + siteurl + ".png"
|
||||
var items_per_page = 50
|
||||
|
||||
// Developer flag
|
||||
var debug = true
|
1
data.sql
1
data.sql
|
@ -86,6 +86,7 @@ CREATE TABLE `settings`(
|
|||
`name` varchar(200) not null,
|
||||
`content` varchar(250) not null,
|
||||
`type` varchar(50) not null,
|
||||
`constraints` varchar(200) DEFAULT '' not null,
|
||||
unique(`name`)
|
||||
);
|
||||
|
||||
|
|
26
errors.go
26
errors.go
|
@ -6,7 +6,7 @@ import "net/http"
|
|||
|
||||
func InternalError(err error, w http.ResponseWriter, r *http.Request, user User) {
|
||||
log.Fatal(err)
|
||||
pi := Page{"Internal Server Error","error",user,tList,"A problem has occured in the system."}
|
||||
pi := Page{"Internal Server Error","error",user,nList,tList,"A problem has occured in the system."}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -18,7 +18,7 @@ func InternalErrorJSQ(err error, w http.ResponseWriter, r *http.Request, user Us
|
|||
log.Fatal(err)
|
||||
errmsg := "A problem has occured in the system."
|
||||
if is_js == "0" {
|
||||
pi := Page{"Internal Server Error","error",user,tList,errmsg}
|
||||
pi := Page{"Internal Server Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -30,7 +30,7 @@ func InternalErrorJSQ(err error, w http.ResponseWriter, r *http.Request, user Us
|
|||
}
|
||||
|
||||
func LocalError(errmsg string, w http.ResponseWriter, r *http.Request, user User) {
|
||||
pi := Page{"Local Error","error",user,tList,errmsg}
|
||||
pi := Page{"Local Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -39,7 +39,7 @@ func LocalError(errmsg string, w http.ResponseWriter, r *http.Request, user User
|
|||
}
|
||||
|
||||
func LoginRequired(w http.ResponseWriter, r *http.Request, user User) {
|
||||
pi := Page{"Local Error","error",user,tList,"You need to login to do that."}
|
||||
pi := Page{"Local Error","error",user,nList,tList,"You need to login to do that."}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -50,7 +50,7 @@ func LoginRequired(w http.ResponseWriter, r *http.Request, user User) {
|
|||
|
||||
func LocalErrorJSQ(errmsg string, w http.ResponseWriter, r *http.Request, user User, is_js string) {
|
||||
if is_js == "0" {
|
||||
pi := Page{"Local Error","error",user,tList,errmsg}
|
||||
pi := Page{"Local Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -63,7 +63,7 @@ func LocalErrorJSQ(errmsg string, w http.ResponseWriter, r *http.Request, user U
|
|||
|
||||
func NoPermissions(w http.ResponseWriter, r *http.Request, user User) {
|
||||
errmsg := "You don't have permission to do that."
|
||||
pi := Page{"Local Error","error",user,tList,errmsg}
|
||||
pi := Page{"Local Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -74,7 +74,7 @@ func NoPermissions(w http.ResponseWriter, r *http.Request, user User) {
|
|||
func NoPermissionsJSQ(w http.ResponseWriter, r *http.Request, user User, is_js string) {
|
||||
errmsg := "You don't have permission to do that."
|
||||
if is_js == "0" {
|
||||
pi := Page{"Local Error","error",user,tList,errmsg}
|
||||
pi := Page{"Local Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -86,7 +86,7 @@ func NoPermissionsJSQ(w http.ResponseWriter, r *http.Request, user User, is_js s
|
|||
}
|
||||
|
||||
func Banned(w http.ResponseWriter, r *http.Request, user User) {
|
||||
pi := Page{"Banned","error",user,tList,"You have been banned from this site."}
|
||||
pi := Page{"Banned","error",user,nList,tList,"You have been banned from this site."}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -96,7 +96,7 @@ func Banned(w http.ResponseWriter, r *http.Request, user User) {
|
|||
|
||||
func BannedJSQ(w http.ResponseWriter, r *http.Request, user User, is_js string) {
|
||||
if is_js == "0" {
|
||||
pi := Page{"Banned","error",user,tList,"You have been banned from this site."}
|
||||
pi := Page{"Banned","error",user,nList,tList,"You have been banned from this site."}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -109,7 +109,7 @@ func BannedJSQ(w http.ResponseWriter, r *http.Request, user User, is_js string)
|
|||
|
||||
func LoginRequiredJSQ(w http.ResponseWriter, r *http.Request, user User, is_js string) {
|
||||
if is_js == "0" {
|
||||
pi := Page{"Local Error","error",user,tList,"You need to login to do that."}
|
||||
pi := Page{"Local Error","error",user,nList,tList,"You need to login to do that."}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -122,7 +122,7 @@ func LoginRequiredJSQ(w http.ResponseWriter, r *http.Request, user User, is_js s
|
|||
|
||||
func SecurityError(w http.ResponseWriter, r *http.Request, user User) {
|
||||
errmsg := "There was a security issue with your request."
|
||||
pi := Page{"Security Error","error",user,tList,errmsg}
|
||||
pi := Page{"Security Error","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -132,7 +132,7 @@ func SecurityError(w http.ResponseWriter, r *http.Request, user User) {
|
|||
|
||||
func NotFound(w http.ResponseWriter, r *http.Request, user User) {
|
||||
errmsg := "The requested page doesn't exist."
|
||||
pi := Page{"Not Found","error",user,tList,errmsg}
|
||||
pi := Page{"Not Found","error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
@ -142,7 +142,7 @@ func NotFound(w http.ResponseWriter, r *http.Request, user User) {
|
|||
|
||||
func CustomErrorJSQ(errmsg string, errcode int, errtitle string, w http.ResponseWriter, r *http.Request, user User, is_js string) {
|
||||
if is_js == "0" {
|
||||
pi := Page{errtitle,"error",user,tList,errmsg}
|
||||
pi := Page{errtitle,"error",user,nList,tList,errmsg}
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
errpage := b.String()
|
||||
|
|
|
@ -0,0 +1,67 @@
|
|||
package main
|
||||
|
||||
import "io"
|
||||
import "os/exec"
|
||||
import "errors"
|
||||
import "runtime"
|
||||
|
||||
/*
|
||||
Sending emails in a way you really shouldn't be sending them.
|
||||
This method doesn't require a SMTP server, but has higher chances of an email being rejected or being seen as spam. Use at your own risk. Only for Linux as Windows doesn't have Sendmail.
|
||||
*/
|
||||
func init() {
|
||||
plugins["sendmail"] = Plugin{"sendmail","Sendmail","Azareal","http://github.com/Azareal","",false,"Linux Only","",init_sendmail,activate_sendmail,deactivate_sendmail}
|
||||
}
|
||||
|
||||
func init_sendmail() {
|
||||
add_vhook("email_send_intercept", send_sendmail)
|
||||
}
|
||||
|
||||
// Sendmail is only available on Linux
|
||||
func activate_sendmail() error {
|
||||
if !enable_emails {
|
||||
return errors.New("You have emails disabled in your configuration file")
|
||||
}
|
||||
if runtime.GOOS != "linux" {
|
||||
return errors.New("This plugin only supports Linux")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func deactivate_sendmail() {
|
||||
remove_vhook("email_send_intercept")
|
||||
}
|
||||
|
||||
func send_sendmail(data ...interface{}) interface{} {
|
||||
to := data[0].(string)
|
||||
subject := data[1].(string)
|
||||
body := data[2].(string)
|
||||
|
||||
msg := "From: " + site_email + "\n"
|
||||
msg += "To: " + to + "\n"
|
||||
msg += "Subject: " + subject + "\n\n"
|
||||
msg += body + "\n"
|
||||
|
||||
sendmail := exec.Command("/usr/sbin/sendmail","-t","-i")
|
||||
stdin, err := sendmail.StdinPipe()
|
||||
if err != nil {
|
||||
return false // Possibly disable the plugin and show an error to the admin on the dashboard? Plugin log file?
|
||||
}
|
||||
|
||||
err = sendmail.Start()
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
io.WriteString(stdin, msg)
|
||||
|
||||
err = stdin.Close()
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
|
||||
err = sendmail.Wait()
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
19
extend.go
19
extend.go
|
@ -13,9 +13,10 @@ type Plugin struct
|
|||
URL string
|
||||
Settings string
|
||||
Active bool
|
||||
Tag string
|
||||
Type string
|
||||
Init func()
|
||||
Activate func()
|
||||
Activate func()error
|
||||
Deactivate func()
|
||||
}
|
||||
|
||||
|
@ -31,6 +32,18 @@ func run_hook(name string, data interface{}) interface{} {
|
|||
return hooks[name](data)
|
||||
}
|
||||
|
||||
func run_hook_v(name string, data ...interface{}) {
|
||||
vhooks[name](data...)
|
||||
func add_vhook(name string, handler func(...interface{}) interface{}) {
|
||||
vhooks[name] = handler
|
||||
}
|
||||
|
||||
func remove_vhook(name string) {
|
||||
delete(vhooks, name)
|
||||
}
|
||||
|
||||
func run_vhook(name string, data ...interface{}) interface{} {
|
||||
return vhooks[name](data...)
|
||||
}
|
||||
|
||||
func run_vhook_noreturn(name string, data ...interface{}) {
|
||||
_ = vhooks[name](data...)
|
||||
}
|
BIN
gosora.exe
BIN
gosora.exe
Binary file not shown.
Binary file not shown.
After Width: | Height: | Size: 9.9 KiB |
47
main.go
47
main.go
|
@ -23,7 +23,7 @@ const saltLength int = 32
|
|||
const sessionLength int = 80
|
||||
|
||||
var templates = template.Must(template.ParseGlob("templates/*"))
|
||||
var custom_pages = template.Must(template.ParseGlob("pages/*"))
|
||||
//var custom_pages = template.Must(template.ParseGlob("pages/*"))
|
||||
var no_css_tmpl = template.CSS("")
|
||||
var staff_css_tmpl = template.CSS(staff_css)
|
||||
var settings map[string]interface{} = make(map[string]interface{})
|
||||
|
@ -31,9 +31,52 @@ var external_sites map[string]string = make(map[string]string)
|
|||
var groups map[int]Group = make(map[int]Group)
|
||||
var forums map[int]Forum = make(map[int]Forum)
|
||||
var static_files map[string]SFile = make(map[string]SFile)
|
||||
var ctemplates map[string]func(Page)string = make(map[string]func(Page)string)
|
||||
|
||||
func compile_templates() {
|
||||
var c CTemplateSet
|
||||
user := User{0,"",0,false,false,false,false,false,false,"",false,"","","","",""}
|
||||
var noticeList map[int]string = make(map[int]string)
|
||||
noticeList[0] = "test"
|
||||
|
||||
log.Print("Compiling the templates")
|
||||
|
||||
topic := TopicUser{0,"",template.HTML(""),0,false,false,"",0,"","","",no_css_tmpl,0,"","","",""}
|
||||
var replyList map[int]interface{} = make(map[int]interface{})
|
||||
replyList[0] = Reply{0,0,"",template.HTML(""),0,"","",0,0,"",no_css_tmpl,0,"","","",""}
|
||||
var varList map[string]VarItem = make(map[string]VarItem)
|
||||
varList["extra_data"] = VarItem{"extra_data","tmpl_topic_vars.Something.(TopicUser)","TopicUser"}
|
||||
|
||||
pi := Page{"Title","name",user,noticeList,replyList,topic}
|
||||
topic_id := c.compile_template("topic.html","templates/","Page", pi, varList)
|
||||
|
||||
varList = make(map[string]VarItem)
|
||||
varList["extra_data"] = VarItem{"extra_data","tmpl_profile_vars.Something.(User)","User"}
|
||||
pi = Page{"Title","name",user,noticeList,replyList,user}
|
||||
profile := c.compile_template("profile.html","templates/","Page", pi, varList)
|
||||
|
||||
log.Print("Writing the templates")
|
||||
write_template("topic", topic_id)
|
||||
write_template("profile", profile)
|
||||
}
|
||||
|
||||
func write_template(name string, content string) {
|
||||
f, err := os.Create("./template_" + name + ".go")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
_, err = f.WriteString(content)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
f.Sync()
|
||||
f.Close()
|
||||
}
|
||||
|
||||
func main(){
|
||||
var err error
|
||||
compile_templates()
|
||||
init_database(err);
|
||||
|
||||
log.Print("Loading the static files.")
|
||||
|
@ -60,7 +103,7 @@ func main(){
|
|||
external_sites["YT"] = "https://www.youtube.com/"
|
||||
hooks["trow_assign"] = nil
|
||||
hooks["rrow_assign"] = nil
|
||||
//fmt.Println(plugins)
|
||||
templates.ParseGlob("pages/*")
|
||||
|
||||
for name, body := range plugins {
|
||||
log.Print("Added plugin " + name)
|
||||
|
|
168
mod_routes.go
168
mod_routes.go
|
@ -10,7 +10,11 @@ import "database/sql"
|
|||
import _ "github.com/go-sql-driver/mysql"
|
||||
|
||||
func route_edit_topic(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -62,7 +66,11 @@ func route_edit_topic(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_delete_topic(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -88,13 +96,17 @@ func route_delete_topic(w http.ResponseWriter, r *http.Request) {
|
|||
InternalError(err,w,r,user)
|
||||
return
|
||||
}
|
||||
log.Print("The topic '" + strconv.Itoa(tid) + "' was deleted by User ID #" + strconv.Itoa(user.ID) + ".")
|
||||
|
||||
log.Print("The topic '" + strconv.Itoa(tid) + "' was deleted by User ID #" + strconv.Itoa(user.ID) + ".")
|
||||
http.Redirect(w, r, "/", http.StatusSeeOther)
|
||||
}
|
||||
|
||||
func route_stick_topic(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -116,7 +128,11 @@ func route_stick_topic(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_unstick_topic(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -138,7 +154,11 @@ func route_unstick_topic(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_reply_edit_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -184,7 +204,11 @@ func route_reply_edit_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_reply_delete_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -232,7 +256,11 @@ func route_reply_delete_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_profile_reply_edit_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -278,7 +306,11 @@ func route_profile_reply_edit_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_profile_reply_delete_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -326,7 +358,11 @@ func route_profile_reply_delete_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_ban(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -351,12 +387,16 @@ func route_ban(w http.ResponseWriter, r *http.Request) {
|
|||
confirm_msg := "Are you sure you want to ban '" + uname + "'?"
|
||||
yousure := AreYouSure{"/users/ban/submit/" + strconv.Itoa(uid),confirm_msg}
|
||||
|
||||
pi := Page{"Ban User","ban-user",user,tList,yousure}
|
||||
pi := Page{"Ban User","ban-user",user,noticeList,tList,yousure}
|
||||
templates.ExecuteTemplate(w,"areyousure.html", pi)
|
||||
}
|
||||
|
||||
func route_ban_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -410,7 +450,11 @@ func route_ban_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_unban(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Mod && !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -447,7 +491,11 @@ func route_unban(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_panel_forums(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -463,12 +511,16 @@ func route_panel_forums(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
}
|
||||
|
||||
pi := Page{"Forum Manager","panel-forums",user,forumList,0}
|
||||
pi := Page{"Forum Manager","panel-forums",user,noticeList,forumList,0}
|
||||
templates.ExecuteTemplate(w,"panel-forums.html", pi)
|
||||
}
|
||||
|
||||
func route_panel_forums_create_submit(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -502,7 +554,11 @@ func route_panel_forums_create_submit(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_panel_forums_delete(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -517,7 +573,7 @@ func route_panel_forums_delete(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
_, ok := forums[fid];
|
||||
_, ok = forums[fid];
|
||||
if !ok {
|
||||
LocalError("The forum you're trying to delete doesn't exist.",w,r,user)
|
||||
return
|
||||
|
@ -526,12 +582,16 @@ func route_panel_forums_delete(w http.ResponseWriter, r *http.Request){
|
|||
confirm_msg := "Are you sure you want to delete the '" + forums[fid].Name + "' forum?"
|
||||
yousure := AreYouSure{"/panel/forums/delete/submit/" + strconv.Itoa(fid),confirm_msg}
|
||||
|
||||
pi := Page{"Delete Forum","panel-forums-delete",user,tList,yousure}
|
||||
pi := Page{"Delete Forum","panel-forums-delete",user,noticeList,tList,yousure}
|
||||
templates.ExecuteTemplate(w,"areyousure.html", pi)
|
||||
}
|
||||
|
||||
func route_panel_forums_delete_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -547,7 +607,7 @@ func route_panel_forums_delete_submit(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
_, ok := forums[fid];
|
||||
_, ok = forums[fid];
|
||||
if !ok {
|
||||
LocalError("The forum you're trying to delete doesn't exist.",w,r,user)
|
||||
return
|
||||
|
@ -565,7 +625,11 @@ func route_panel_forums_delete_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_panel_forums_edit_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -607,7 +671,11 @@ func route_panel_forums_edit_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_panel_settings(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -618,12 +686,16 @@ func route_panel_settings(w http.ResponseWriter, r *http.Request){
|
|||
settingList[name] = content
|
||||
}
|
||||
|
||||
pi := Page{"Setting Manager","panel-settings",user,tList,settingList}
|
||||
pi := Page{"Setting Manager","panel-settings",user, noticeList,tList,settingList}
|
||||
templates.ExecuteTemplate(w,"panel-settings.html", pi)
|
||||
}
|
||||
|
||||
func route_panel_setting(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -641,12 +713,16 @@ func route_panel_setting(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Edit Setting","panel-setting",user,tList,setting}
|
||||
pi := Page{"Edit Setting","panel-setting",user,noticeList,tList,setting}
|
||||
templates.ExecuteTemplate(w,"panel-setting.html", pi)
|
||||
}
|
||||
|
||||
func route_panel_setting_edit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -698,7 +774,11 @@ func route_panel_setting_edit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_panel_plugins(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -712,12 +792,16 @@ func route_panel_plugins(w http.ResponseWriter, r *http.Request){
|
|||
currentID++
|
||||
}
|
||||
|
||||
pi := Page{"Plugin Manager","panel-plugins",user,pluginList,0}
|
||||
pi := Page{"Plugin Manager","panel-plugins",user,noticeList,pluginList,0}
|
||||
templates.ExecuteTemplate(w,"panel-plugins.html", pi)
|
||||
}
|
||||
|
||||
func route_panel_plugins_activate(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -737,6 +821,14 @@ func route_panel_plugins_activate(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
if plugins[uname].Activate != nil {
|
||||
err = plugins[uname].Activate()
|
||||
if err != nil {
|
||||
LocalError(err.Error(),w,r,user)
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
has_plugin := err != sql.ErrNoRows
|
||||
if has_plugin {
|
||||
if active {
|
||||
|
@ -756,15 +848,19 @@ func route_panel_plugins_activate(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
}
|
||||
|
||||
log.Print("Activating plugin '" + plugin.Name + "'")
|
||||
plugin.Active = true
|
||||
plugins[uname] = plugin
|
||||
plugins[uname].Init()
|
||||
|
||||
http.Redirect(w,r,"/panel/plugins/",http.StatusSeeOther)
|
||||
}
|
||||
|
||||
func route_panel_plugins_deactivate(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -805,7 +901,11 @@ func route_panel_plugins_deactivate(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_panel_users(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Is_Admin {
|
||||
NoPermissions(w,r,user)
|
||||
return
|
||||
|
@ -860,7 +960,7 @@ func route_panel_users(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"User Manager","panel-users",user,userList,0}
|
||||
pi := Page{"User Manager","panel-users",user,noticeList,userList,0}
|
||||
err = templates.ExecuteTemplate(w,"panel-users.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
|
10
mysql.go
10
mysql.go
|
@ -166,7 +166,7 @@ func init_database(err error) {
|
|||
// create_account_stmt, err = db.Prepare("INSERT INTO
|
||||
|
||||
log.Print("Preparing register statement.")
|
||||
register_stmt, err = db.Prepare("INSERT INTO users(`name`,`password`,`salt`,`group`,`is_super_admin`,`session`,`message`) VALUES(?,?,?," + strconv.Itoa(default_group) + ",0,?,'')")
|
||||
register_stmt, err = db.Prepare("INSERT INTO users(`name`,`email`,`password`,`salt`,`group`,`is_super_admin`,`session`,`message`) VALUES(?,?,?,?," + strconv.Itoa(default_group) + ",0,?,'')")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
@ -332,7 +332,13 @@ func init_database(err error) {
|
|||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
plugin := plugins[uname]
|
||||
|
||||
// Was the plugin deleted at some point?
|
||||
plugin, ok := plugins[uname]
|
||||
if !ok {
|
||||
continue
|
||||
}
|
||||
|
||||
plugin.Active = active
|
||||
plugins[uname] = plugin
|
||||
}
|
||||
|
|
1
pages.go
1
pages.go
|
@ -7,6 +7,7 @@ type Page struct
|
|||
Title string
|
||||
Name string
|
||||
CurrentUser User
|
||||
NoticeList map[int]string
|
||||
ItemList map[int]interface{}
|
||||
Something interface{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
{{template "header.html" . }}
|
||||
<div class="rowblock">
|
||||
<div class="rowitem">Test Page</div>
|
||||
</div>
|
||||
<div class="rowblock">
|
||||
<div class="rowitem passive">Testing</div>
|
||||
</div>
|
||||
{{template "footer.html" . }}
|
|
@ -1,6 +0,0 @@
|
|||
{{template "header.html" . }}
|
||||
<div class="rowblock">
|
||||
<div class="rowitem">{{.Title}}</div>
|
||||
</div>
|
||||
<div class="rowblock">Testing</div>
|
||||
{{template "footer.html" . }}
|
|
@ -2,7 +2,7 @@ package main
|
|||
import "html/template"
|
||||
|
||||
func init() {
|
||||
plugins["helloworld"] = Plugin{"helloworld","Hello World","Azareal","http://github.com/Azareal","",false,"",init_helloworld,nil,deactivate_helloworld}
|
||||
plugins["helloworld"] = Plugin{"helloworld","Hello World","Azareal","http://github.com/Azareal","",false,"","",init_helloworld,nil,deactivate_helloworld}
|
||||
}
|
||||
|
||||
// init_helloworld is separate from init() as we don't want the plugin to run if the plugin is disabled
|
||||
|
|
|
@ -7,7 +7,7 @@ var bold *regexp.Regexp
|
|||
var italic *regexp.Regexp
|
||||
|
||||
func init() {
|
||||
plugins["markdown"] = Plugin{"markdown","Markdown","Azareal","http://github.com/Azareal","",false,"",init_markdown,nil,deactivate_markdown}
|
||||
plugins["markdown"] = Plugin{"markdown","Markdown","Azareal","http://github.com/Azareal","",false,"","",init_markdown,nil,deactivate_markdown}
|
||||
}
|
||||
|
||||
func init_markdown() {
|
||||
|
|
|
@ -14,6 +14,8 @@ func init() {
|
|||
|
||||
The Active field should always be set to false in the init() function of 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.
|
||||
|
||||
The Tag field is for providing a tiny snippet of information separate from the description.
|
||||
|
||||
The Type field is for the type of the plugin. This gets changed to "go" automatically and we would suggest leaving "".
|
||||
|
||||
The Init field is for the initialisation handler which is called by the software to run this plugin. This expects a function. You should add your hooks, init logic, initial queries, etc. in said function.
|
||||
|
@ -22,9 +24,12 @@ func init() {
|
|||
|
||||
The Deactivate field is for the handler which is called by the software when the admin hits the Deactivate button in the control panel. You should clean-up any resources you have allocated, remove any hooks, close any statements, etc. within this handler.
|
||||
*/
|
||||
plugins["skeleton"] = Plugin{"skeleton","Skeleton","Azareal","","",false,"",init_skeleton, activate_skeleton, deactivate_skeleton}
|
||||
plugins["skeleton"] = Plugin{"skeleton","Skeleton","Azareal","","",false,"","",init_skeleton, activate_skeleton, deactivate_skeleton}
|
||||
}
|
||||
|
||||
func init_skeleton() {}
|
||||
func activate_skeleton() {}
|
||||
|
||||
/* Any errors encountered while trying to activate the plugin are reported back to the admin and the activation is aborted */
|
||||
func activate_skeleton() error { return nil; }
|
||||
|
||||
func deactivate_skeleton() {}
|
265
routes.go
265
routes.go
|
@ -20,6 +20,7 @@ import "golang.org/x/crypto/bcrypt"
|
|||
|
||||
// A blank list to fill out that parameter in Page for routes which don't use it
|
||||
var tList map[int]interface{}
|
||||
var nList map[int]string
|
||||
|
||||
// GET functions
|
||||
func route_static(w http.ResponseWriter, r *http.Request){
|
||||
|
@ -43,8 +44,12 @@ func route_fstatic(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_overview(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
pi := Page{"Overview","overview",user,tList,0}
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
pi := Page{"Overview","overview",user,noticeList,tList,0}
|
||||
err := templates.ExecuteTemplate(w,"overview.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
@ -52,21 +57,28 @@ func route_overview(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_custom_page(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
name := r.URL.Path[len("/pages/"):]
|
||||
if custom_pages.Lookup(name) == nil {
|
||||
if templates.Lookup("page_" + name) == nil {
|
||||
NotFound(w,r,user)
|
||||
}
|
||||
pi := Page{"Page","page",user,tList,0}
|
||||
err := custom_pages.ExecuteTemplate(w,name,pi)
|
||||
pi := Page{"Page","page",user,noticeList,tList,0}
|
||||
err := templates.ExecuteTemplate(w,"page_" + name,pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
}
|
||||
}
|
||||
|
||||
func route_topics(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
var(
|
||||
topicList map[int]interface{}
|
||||
currentID int
|
||||
|
@ -133,7 +145,7 @@ func route_topics(w http.ResponseWriter, r *http.Request){
|
|||
msg = ""
|
||||
}
|
||||
|
||||
pi := Page{"Topic List","topics",user,topicList,msg}
|
||||
pi := Page{"Topic List","topics",user,noticeList,topicList,msg}
|
||||
err = templates.ExecuteTemplate(w,"topics.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
@ -141,7 +153,11 @@ func route_topics(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_forum(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
var(
|
||||
topicList map[int]interface{}
|
||||
currentID int
|
||||
|
@ -167,7 +183,7 @@ func route_forum(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
_, ok := forums[fid]
|
||||
_, ok = forums[fid]
|
||||
if !ok {
|
||||
NotFound(w,r,user)
|
||||
return
|
||||
|
@ -220,7 +236,7 @@ func route_forum(w http.ResponseWriter, r *http.Request){
|
|||
msg = ""
|
||||
}
|
||||
|
||||
pi := Page{forums[fid].Name,"forum",user,topicList,msg}
|
||||
pi := Page{forums[fid].Name,"forum",user,noticeList,topicList,msg}
|
||||
err = templates.ExecuteTemplate(w,"forum.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
@ -228,7 +244,11 @@ func route_forum(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_forums(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
var forumList map[int]interface{} = make(map[int]interface{})
|
||||
currentID := 0
|
||||
|
||||
|
@ -244,7 +264,7 @@ func route_forums(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Forum List","forums",user,forumList,0}
|
||||
pi := Page{"Forum List","forums",user,noticeList,forumList,0}
|
||||
err := templates.ExecuteTemplate(w,"forums.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
@ -252,10 +272,13 @@ func route_forums(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_topic_id(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
var(
|
||||
err error
|
||||
ok bool
|
||||
rid int
|
||||
content string
|
||||
replyContent string
|
||||
|
@ -388,15 +411,23 @@ func route_topic_id(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{topic.Title,"topic",user,replyList,topic}
|
||||
err = templates.ExecuteTemplate(w,"topic.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
}
|
||||
pi := Page{topic.Title,"topic",user,noticeList,replyList,topic}
|
||||
if ctemplates["topic"] != nil {
|
||||
w.Write([]byte(ctemplates["topic"](pi)))
|
||||
} else {
|
||||
err = templates.ExecuteTemplate(w,"topic.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func route_profile(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
var(
|
||||
err error
|
||||
rid int
|
||||
|
@ -508,7 +539,8 @@ func route_profile(w http.ResponseWriter, r *http.Request){
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{puser.Name + "'s Profile","profile",user,replyList,puser}
|
||||
pi := Page{puser.Name + "'s Profile","profile",user,noticeList,replyList,puser}
|
||||
//w.Write([]byte(template_profile(pi)))
|
||||
err = templates.ExecuteTemplate(w,"profile.html", pi)
|
||||
if err != nil {
|
||||
InternalError(err, w, r, user)
|
||||
|
@ -516,19 +548,27 @@ func route_profile(w http.ResponseWriter, r *http.Request){
|
|||
}
|
||||
|
||||
func route_topic_create(w http.ResponseWriter, r *http.Request){
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if user.Is_Banned {
|
||||
Banned(w,r,user)
|
||||
return
|
||||
}
|
||||
|
||||
pi := Page{"Create Topic","create-topic",user,tList,0}
|
||||
pi := Page{"Create Topic","create-topic",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"create-topic.html", pi)
|
||||
}
|
||||
|
||||
// POST functions. Authorised users only.
|
||||
func route_create_topic(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
LoginRequired(w,r,user)
|
||||
return
|
||||
|
@ -566,7 +606,7 @@ func route_create_topic(w http.ResponseWriter, r *http.Request) {
|
|||
|
||||
if success != 1 {
|
||||
errmsg := "Unable to create the topic"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -579,7 +619,11 @@ func route_create_topic(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_create_reply(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
LoginRequired(w,r,user)
|
||||
return
|
||||
|
@ -602,7 +646,7 @@ func route_create_reply(w http.ResponseWriter, r *http.Request) {
|
|||
success = 0
|
||||
|
||||
errmsg := "Unable to create the reply"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -638,7 +682,7 @@ func route_create_reply(w http.ResponseWriter, r *http.Request) {
|
|||
|
||||
if success != 1 {
|
||||
errmsg := "Unable to create the reply"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -651,7 +695,11 @@ func route_create_reply(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_profile_reply_create(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
LoginRequired(w,r,user)
|
||||
return
|
||||
|
@ -674,7 +722,7 @@ func route_profile_reply_create(w http.ResponseWriter, r *http.Request) {
|
|||
success = 0
|
||||
|
||||
errmsg := "Unable to create the reply"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -702,7 +750,7 @@ func route_profile_reply_create(w http.ResponseWriter, r *http.Request) {
|
|||
|
||||
if success != 1 {
|
||||
errmsg := "Unable to create the reply"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -715,7 +763,11 @@ func route_profile_reply_create(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
LoginRequired(w,r,user)
|
||||
return
|
||||
|
@ -798,7 +850,7 @@ func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
|||
content = content + "<br><br>Original Post: <a href='/topic/" + strconv.Itoa(item_id) + "'>" + title + "</a>"
|
||||
} else {
|
||||
if vhooks["report_preassign"] != nil {
|
||||
run_hook_v("report_preassign", &item_id, &item_type)
|
||||
run_vhook_noreturn("report_preassign", &item_id, &item_type)
|
||||
return
|
||||
}
|
||||
|
||||
|
@ -813,6 +865,7 @@ func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
|||
InternalError(err,w,r,user)
|
||||
return
|
||||
}
|
||||
|
||||
for rows.Next() {
|
||||
err = rows.Scan(&count)
|
||||
if err != nil {
|
||||
|
@ -820,7 +873,6 @@ func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
}
|
||||
|
||||
if count != 0 {
|
||||
LocalError("Someone has already reported this!", w, r, user)
|
||||
return
|
||||
|
@ -847,7 +899,7 @@ func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
|||
|
||||
if success != 1 {
|
||||
errmsg := "Unable to create the report"
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -860,10 +912,14 @@ func route_report_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_account_own_edit_critical(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -873,15 +929,19 @@ func route_account_own_edit_critical(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Edit Password","account-own-edit",user,tList,0}
|
||||
pi := Page{"Edit Password","account-own-edit",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"account-own-edit.html", pi)
|
||||
}
|
||||
|
||||
func route_account_own_edit_critical_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -905,7 +965,7 @@ func route_account_own_edit_critical_submit(w http.ResponseWriter, r *http.Reque
|
|||
|
||||
err = get_password_stmt.QueryRow(user.ID).Scan(&real_password, &salt)
|
||||
if err == sql.ErrNoRows {
|
||||
pi := Page{"Error","error",user,tList,"Your account doesn't exist."}
|
||||
pi := Page{"Error","error",user,nList,tList,"Your account doesn't exist."}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -921,7 +981,7 @@ func route_account_own_edit_critical_submit(w http.ResponseWriter, r *http.Reque
|
|||
current_password = current_password + salt
|
||||
err = bcrypt.CompareHashAndPassword([]byte(real_password), []byte(current_password))
|
||||
if err == bcrypt.ErrMismatchedHashAndPassword {
|
||||
pi := Page{"Error","error",user,tList,"That's not the correct password."}
|
||||
pi := Page{"Error","error",user,nList,tList,"That's not the correct password."}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -934,7 +994,7 @@ func route_account_own_edit_critical_submit(w http.ResponseWriter, r *http.Reque
|
|||
return
|
||||
}
|
||||
if new_password != confirm_password {
|
||||
pi := Page{"Error","error",user,tList,"The two passwords don't match."}
|
||||
pi := Page{"Error","error",user,nList,tList,"The two passwords don't match."}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -952,15 +1012,19 @@ func route_account_own_edit_critical_submit(w http.ResponseWriter, r *http.Reque
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Edit Password","account-own-edit-success",user,tList,0}
|
||||
pi := Page{"Edit Password","account-own-edit-success",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-success.html", pi)
|
||||
}
|
||||
|
||||
func route_account_own_edit_avatar(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -970,7 +1034,7 @@ func route_account_own_edit_avatar(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Edit Avatar","account-own-edit-avatar",user,tList,0}
|
||||
pi := Page{"Edit Avatar","account-own-edit-avatar",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-avatar.html", pi)
|
||||
}
|
||||
|
||||
|
@ -981,10 +1045,13 @@ func route_account_own_edit_avatar_submit(w http.ResponseWriter, r *http.Request
|
|||
}
|
||||
r.Body = http.MaxBytesReader(w, r.Body, int64(max_request_size))
|
||||
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1061,16 +1128,21 @@ func route_account_own_edit_avatar_submit(w http.ResponseWriter, r *http.Request
|
|||
}
|
||||
|
||||
user.Avatar = "/uploads/avatar_" + strconv.Itoa(user.ID) + "." + ext
|
||||
noticeList[len(noticeList)] = "Your avatar was successfully updated"
|
||||
|
||||
pi := Page{"Edit Avatar","account-own-edit-avatar-success",user,tList,0}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-avatar-success.html", pi)
|
||||
pi := Page{"Edit Avatar","account-own-edit-avatar",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-avatar.html", pi)
|
||||
}
|
||||
|
||||
func route_account_own_edit_username(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1080,15 +1152,19 @@ func route_account_own_edit_username(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Edit Username","account-own-edit-username",user,tList,user.Name}
|
||||
pi := Page{"Edit Username","account-own-edit-username",user,noticeList,tList,user.Name}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-username.html", pi)
|
||||
}
|
||||
|
||||
func route_account_own_edit_username_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You need to login to edit your own account."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1112,15 +1188,19 @@ func route_account_own_edit_username_submit(w http.ResponseWriter, r *http.Reque
|
|||
}
|
||||
user.Name = new_username
|
||||
|
||||
pi := Page{"Edit Username","account-own-edit-username",user,tList,user.Name}
|
||||
pi := Page{"Edit Username","account-own-edit-username",user,noticeList,tList,user.Name}
|
||||
templates.ExecuteTemplate(w,"account-own-edit-username.html", pi)
|
||||
}
|
||||
|
||||
func route_logout(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if !user.Loggedin {
|
||||
errmsg := "You can't logout without logging in first."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1139,10 +1219,14 @@ func route_logout(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_login(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if user.Loggedin {
|
||||
errmsg := "You're already logged in."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1152,15 +1236,19 @@ func route_login(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Login","login",user,tList,0}
|
||||
pi := Page{"Login","login",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"login.html", pi)
|
||||
}
|
||||
|
||||
func route_login_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if user.Loggedin {
|
||||
errmsg := "You're already logged in."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1186,7 +1274,7 @@ func route_login_submit(w http.ResponseWriter, r *http.Request) {
|
|||
err = login_stmt.QueryRow(username).Scan(&uid, &username, &real_password, &salt)
|
||||
if err == sql.ErrNoRows {
|
||||
errmsg := "That username doesn't exist."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1203,7 +1291,7 @@ func route_login_submit(w http.ResponseWriter, r *http.Request) {
|
|||
if salt == "" {
|
||||
if password != real_password {
|
||||
errmsg := "That's not the correct password."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1225,7 +1313,7 @@ func route_login_submit(w http.ResponseWriter, r *http.Request) {
|
|||
err := bcrypt.CompareHashAndPassword([]byte(real_password), []byte(password))
|
||||
if err == bcrypt.ErrMismatchedHashAndPassword {
|
||||
errmsg := "That's not the correct password."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1259,10 +1347,14 @@ func route_login_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
func route_register(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, noticeList, ok := SessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
if user.Loggedin {
|
||||
errmsg := "You're already logged in."
|
||||
pi := Page{"Error","error",user,tList,errmsg}
|
||||
pi := Page{"Error","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1272,12 +1364,16 @@ func route_register(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
pi := Page{"Registration","register",user,tList,0}
|
||||
pi := Page{"Registration","register",user,noticeList,tList,0}
|
||||
templates.ExecuteTemplate(w,"register.html", pi)
|
||||
}
|
||||
|
||||
func route_register_submit(w http.ResponseWriter, r *http.Request) {
|
||||
user := SessionCheck(w,r)
|
||||
user, ok := SimpleSessionCheck(w,r)
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
|
||||
err := r.ParseForm()
|
||||
if err != nil {
|
||||
LocalError("Bad Form", w, r, user)
|
||||
|
@ -1285,14 +1381,33 @@ func route_register_submit(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
|
||||
username := html.EscapeString(r.PostFormValue("username"))
|
||||
if username == "" {
|
||||
LocalError("You didn't put in a username.", w, r, user)
|
||||
return
|
||||
}
|
||||
|
||||
email := html.EscapeString(r.PostFormValue("email"))
|
||||
if email == "" {
|
||||
LocalError("You didn't put in an email.", w, r, user)
|
||||
return
|
||||
}
|
||||
password := r.PostFormValue("password")
|
||||
if password == "" {
|
||||
LocalError("You didn't put in a password.", w, r, user)
|
||||
return
|
||||
}
|
||||
if password == "test" || password == "123456" || password == "123" || password == "password" {
|
||||
LocalError("Your password is too weak.", w, r, user)
|
||||
return
|
||||
}
|
||||
|
||||
confirm_password := r.PostFormValue("confirm_password")
|
||||
log.Print("Registration Attempt! Username: " + username)
|
||||
|
||||
// Do the two inputted passwords match..?
|
||||
if password != confirm_password {
|
||||
errmsg := "The two passwords don't match."
|
||||
pi := Page{"Password Mismatch","error",user,tList,errmsg}
|
||||
pi := Page{"Password Mismatch","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1309,7 +1424,7 @@ func route_register_submit(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
} else if err != sql.ErrNoRows {
|
||||
errmsg := "This username isn't available. Try another."
|
||||
pi := Page{"Username Taken","error",user,tList,errmsg}
|
||||
pi := Page{"Username Taken","error",user,nList,tList,errmsg}
|
||||
|
||||
var b bytes.Buffer
|
||||
templates.ExecuteTemplate(&b,"error.html", pi)
|
||||
|
@ -1338,7 +1453,7 @@ func route_register_submit(w http.ResponseWriter, r *http.Request) {
|
|||
return
|
||||
}
|
||||
|
||||
res, err := register_stmt.Exec(username,string(hashed_password),salt,session)
|
||||
res, err := register_stmt.Exec(username,email,string(hashed_password),salt,session)
|
||||
if err != nil {
|
||||
InternalError(err,w,r,user)
|
||||
return
|
||||
|
|
|
@ -0,0 +1,191 @@
|
|||
package main
|
||||
import "strconv"
|
||||
|
||||
func init() {
|
||||
ctemplates["profile"] = template_profile
|
||||
}
|
||||
|
||||
func template_profile(tmpl_profile_vars Page) (tmpl string) {
|
||||
var extra_data User = tmpl_profile_vars.Something.(User)
|
||||
tmpl += `<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>`
|
||||
tmpl += tmpl_profile_vars.Title
|
||||
tmpl += `</title>
|
||||
<link href="/static/main.css" rel="stylesheet" type="text/css">
|
||||
<script type="text/javascript" src="/static/jquery-1.12.3.min.js"></script>
|
||||
<script type="text/javascript">
|
||||
var session = "`
|
||||
tmpl += tmpl_profile_vars.CurrentUser.Session
|
||||
tmpl += `";
|
||||
</script>
|
||||
<script type="text/javascript" src="/static/global.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<div class="container">
|
||||
`
|
||||
tmpl += `<div class="nav">
|
||||
<ul>
|
||||
<li class="menu_overview"><a href="/">Overview</a></li>
|
||||
<li class="menu_forums"><a href="/forums/">Forums</a></li>
|
||||
<li class="menu_topics"><a href="/">Topics</a></li>
|
||||
<li class="menu_create_topic"><a href="/topics/create/">Create Topic</a></li>
|
||||
`
|
||||
if tmpl_profile_vars.CurrentUser.Loggedin {
|
||||
tmpl += `
|
||||
<li class="menu_account"><a href="/user/edit/critical/">Account</a></li>
|
||||
<li class="menu_account"><a href="/user/`
|
||||
tmpl += strconv.Itoa(tmpl_profile_vars.CurrentUser.ID)
|
||||
tmpl += `">Profile</a></li>
|
||||
`
|
||||
if tmpl_profile_vars.CurrentUser.Is_Super_Mod {
|
||||
tmpl += `<li class="menu_account"><a href="/panel/forums/">Panel</a></li>`
|
||||
}
|
||||
tmpl += `
|
||||
<li class="menu_logout"><a href="/accounts/logout?session=`
|
||||
tmpl += tmpl_profile_vars.CurrentUser.Session
|
||||
tmpl += `">Logout</a></li>
|
||||
`
|
||||
} else {
|
||||
tmpl += `
|
||||
<li class="menu_register"><a href="/accounts/create/">Register</a></li>
|
||||
<li class="menu_login"><a href="/accounts/login/">Login</a></li>
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
</ul>
|
||||
</div>`
|
||||
tmpl += `
|
||||
`
|
||||
if len(tmpl_profile_vars.NoticeList) != 0 {
|
||||
for _, item := range tmpl_profile_vars.NoticeList {
|
||||
tmpl += `<div class="alert">`
|
||||
tmpl += item
|
||||
tmpl += `</div>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
<div class="colblock_left" style="max-width: 220px;">
|
||||
<div class="rowitem" style="padding: 0;"><img src="`
|
||||
tmpl += extra_data.Avatar
|
||||
tmpl += `" style="max-width: 100%;margin: 0;"/></div>
|
||||
<div class="rowitem" style="text-transform: capitalize;">
|
||||
<span style="font-size: 18px;">`
|
||||
tmpl += extra_data.Name
|
||||
tmpl += `</span>`
|
||||
if extra_data.Tag != "" {
|
||||
tmpl += `<span class="username" style="float: right;">`
|
||||
tmpl += extra_data.Tag
|
||||
tmpl += `</span>`
|
||||
}
|
||||
tmpl += `
|
||||
</div>
|
||||
<div class="rowitem passive">
|
||||
<a class="username">Add Friend</a>
|
||||
`
|
||||
if tmpl_profile_vars.CurrentUser.Is_Super_Mod && !extra_data.Is_Super_Mod {
|
||||
tmpl += `
|
||||
`
|
||||
if extra_data.Is_Banned {
|
||||
tmpl += `<a href="/users/unban/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `" class="username">Unban</a>`
|
||||
} else {
|
||||
tmpl += `<a href="/users/ban/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `" class="username">Ban</a>`
|
||||
}
|
||||
tmpl += `
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
<a href="/report/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `?session=`
|
||||
tmpl += tmpl_profile_vars.CurrentUser.Session
|
||||
tmpl += `&type=user" class="username report_item">Report</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="colblock_right">
|
||||
<div class="rowitem"><a>Comments</a></div>
|
||||
</div>
|
||||
<div class="colblock_right" style="overflow: hidden;">
|
||||
`
|
||||
if len(tmpl_profile_vars.ItemList) != 0 {
|
||||
for _, item := range tmpl_profile_vars.ItemList {
|
||||
tmpl += `
|
||||
<div class="rowitem passive deletable_block editable_parent" style="`
|
||||
if item.(Reply).Avatar != "" {
|
||||
tmpl += `background-image: url(`
|
||||
tmpl += item.(Reply).Avatar
|
||||
tmpl += `), url(/static/white-dot.jpg);background-position: 0px `
|
||||
if item.(Reply).ContentLines <= 5 {
|
||||
tmpl += `-1`
|
||||
}
|
||||
tmpl += `0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;`
|
||||
tmpl += string(item.(Reply).Css)
|
||||
}
|
||||
tmpl += `">
|
||||
<span class="editable_block user_content">`
|
||||
tmpl += string(item.(Reply).ContentHtml)
|
||||
tmpl += `</span>
|
||||
<br /><br />
|
||||
<a href="/user/`
|
||||
tmpl += strconv.Itoa(item.(Reply).CreatedBy)
|
||||
tmpl += `" class="username">`
|
||||
tmpl += item.(Reply).CreatedByName
|
||||
tmpl += `</a>
|
||||
`
|
||||
if tmpl_profile_vars.CurrentUser.Is_Mod {
|
||||
tmpl += `<a href="/profile/reply/edit/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/profile/reply/delete/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `"><button class="username delete_item">Delete</button></a>`
|
||||
}
|
||||
tmpl += `
|
||||
<a href="/report/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `?session=`
|
||||
tmpl += tmpl_profile_vars.CurrentUser.Session
|
||||
tmpl += `&type=user-reply"><button class="username report_item">Report</button></a>
|
||||
`
|
||||
if item.(Reply).Tag != "" {
|
||||
tmpl += `<a class="username" style="float: right;">`
|
||||
tmpl += item.(Reply).Tag
|
||||
tmpl += `</a>`
|
||||
}
|
||||
tmpl += `
|
||||
</div>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
</div>
|
||||
`
|
||||
if !tmpl_profile_vars.CurrentUser.Is_Banned {
|
||||
tmpl += `
|
||||
<div class="colblock_right">
|
||||
<form action="/profile/reply/create/" method="post">
|
||||
<input name="uid" value='`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' type="hidden" />
|
||||
<div class="formrow">
|
||||
<div class="formitem"><textarea name="reply-content" placeholder="Insert reply here"></textarea></div>
|
||||
</div>
|
||||
<div class="formrow">
|
||||
<div class="formitem"><button name="reply-button" class="formbutton">Create Reply</button></div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
`
|
||||
tmpl += ` <!--<link rel="stylesheet" href="https://use.fontawesome.com/8670aa03ca.css">-->
|
||||
</div>
|
||||
</body>
|
||||
</html>`
|
||||
return tmpl
|
||||
}
|
|
@ -0,0 +1,261 @@
|
|||
package main
|
||||
import "strconv"
|
||||
|
||||
func init() {
|
||||
ctemplates["topic"] = template_topic
|
||||
}
|
||||
|
||||
func template_topic(tmpl_topic_vars Page) (tmpl string) {
|
||||
var extra_data TopicUser = tmpl_topic_vars.Something.(TopicUser)
|
||||
tmpl += `<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>`
|
||||
tmpl += tmpl_topic_vars.Title
|
||||
tmpl += `</title>
|
||||
<link href="/static/main.css" rel="stylesheet" type="text/css">
|
||||
<script type="text/javascript" src="/static/jquery-1.12.3.min.js"></script>
|
||||
<script type="text/javascript">
|
||||
var session = "`
|
||||
tmpl += tmpl_topic_vars.CurrentUser.Session
|
||||
tmpl += `";
|
||||
</script>
|
||||
<script type="text/javascript" src="/static/global.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<div class="container">
|
||||
`
|
||||
tmpl += `<div class="nav">
|
||||
<ul>
|
||||
<li class="menu_overview"><a href="/">Overview</a></li>
|
||||
<li class="menu_forums"><a href="/forums/">Forums</a></li>
|
||||
<li class="menu_topics"><a href="/">Topics</a></li>
|
||||
<li class="menu_create_topic"><a href="/topics/create/">Create Topic</a></li>
|
||||
`
|
||||
if tmpl_topic_vars.CurrentUser.Loggedin {
|
||||
tmpl += `
|
||||
<li class="menu_account"><a href="/user/edit/critical/">Account</a></li>
|
||||
<li class="menu_account"><a href="/user/`
|
||||
tmpl += strconv.Itoa(tmpl_topic_vars.CurrentUser.ID)
|
||||
tmpl += `">Profile</a></li>
|
||||
`
|
||||
if tmpl_topic_vars.CurrentUser.Is_Super_Mod {
|
||||
tmpl += `<li class="menu_account"><a href="/panel/forums/">Panel</a></li>`
|
||||
}
|
||||
tmpl += `
|
||||
<li class="menu_logout"><a href="/accounts/logout?session=`
|
||||
tmpl += tmpl_topic_vars.CurrentUser.Session
|
||||
tmpl += `">Logout</a></li>
|
||||
`
|
||||
} else {
|
||||
tmpl += `
|
||||
<li class="menu_register"><a href="/accounts/create/">Register</a></li>
|
||||
<li class="menu_login"><a href="/accounts/login/">Login</a></li>
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
</ul>
|
||||
</div>`
|
||||
tmpl += `
|
||||
`
|
||||
if len(tmpl_topic_vars.NoticeList) != 0 {
|
||||
for _, item := range tmpl_topic_vars.NoticeList {
|
||||
tmpl += `<div class="alert">`
|
||||
tmpl += item
|
||||
tmpl += `</div>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
<div class="rowblock">
|
||||
<form action='/topic/edit/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' method="post">
|
||||
<div class="rowitem"`
|
||||
if extra_data.Sticky {
|
||||
tmpl += ` style="background-color: #FFFFEA;"`
|
||||
}
|
||||
tmpl += `>
|
||||
<a class='topic_name hide_on_edit'>`
|
||||
tmpl += extra_data.Title
|
||||
tmpl += `</a>
|
||||
<span class='username topic_status_e topic_status_`
|
||||
tmpl += extra_data.Status
|
||||
tmpl += ` hide_on_edit' style="font-weight:normal;float: right;">`
|
||||
tmpl += extra_data.Status
|
||||
tmpl += `</span>
|
||||
<span class="username" style="border-right: 0;font-weight: normal;float: right;">Status</span>
|
||||
`
|
||||
if tmpl_topic_vars.CurrentUser.Is_Mod {
|
||||
tmpl += `
|
||||
<a href='/topic/edit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' class="username hide_on_edit open_edit" style="font-weight: normal;margin-left: 6px;">Edit</a>
|
||||
<a href='/topic/delete/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' class="username" style="font-weight: normal;">Delete</a>
|
||||
`
|
||||
if extra_data.Sticky {
|
||||
tmpl += `<a href='/topic/unstick/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' class="username" style="font-weight: normal;">Unpin</a>`
|
||||
} else {
|
||||
tmpl += `<a href='/topic/stick/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' class="username" style="font-weight: normal;">Pin</a>`
|
||||
}
|
||||
tmpl += `
|
||||
|
||||
<input class='show_on_edit topic_name_input' name="topic_name" value='`
|
||||
tmpl += extra_data.Title
|
||||
tmpl += `' type="text" />
|
||||
<select name="topic_status" class='show_on_edit topic_status_input' style='float: right;'>
|
||||
<option>open</option>
|
||||
<option>closed</option>
|
||||
</select>
|
||||
<button name="topic-button" class="formbutton show_on_edit submit_edit">Update</button>
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
<a href="/report/submit/`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `?session=`
|
||||
tmpl += tmpl_topic_vars.CurrentUser.Session
|
||||
tmpl += `&type=topic" class="username report_item" style="font-weight: normal;">Report</a>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
<div class="rowblock">
|
||||
<div class="rowitem passive editable_parent" style="border-bottom: none;`
|
||||
if extra_data.Avatar != "" {
|
||||
tmpl += `background-image: url(`
|
||||
tmpl += extra_data.Avatar
|
||||
tmpl += `), url(/static/white-dot.jpg);background-position: 0px `
|
||||
if extra_data.ContentLines <= 5 {
|
||||
tmpl += `-1`
|
||||
}
|
||||
tmpl += `0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;`
|
||||
tmpl += string(extra_data.Css)
|
||||
}
|
||||
tmpl += `">
|
||||
<span class="hide_on_edit topic_content user_content">`
|
||||
tmpl += string(tmpl_topic_varsstring(.Something.(TopicUser).Content))
|
||||
tmpl += `</span>
|
||||
<textarea name="topic_content" class="show_on_edit topic_content_input">`
|
||||
tmpl += string(tmpl_topic_varsstring(.Something.(TopicUser).Content))
|
||||
tmpl += `</textarea>
|
||||
<br /><br />
|
||||
<a href="/user/`
|
||||
tmpl += strconv.Itoa(extra_data.CreatedBy)
|
||||
tmpl += `" class="username">`
|
||||
tmpl += extra_data.CreatedByName
|
||||
tmpl += `</a>
|
||||
`
|
||||
if extra_data.Tag != "" {
|
||||
tmpl += `<a class="username" style="float: right;">`
|
||||
tmpl += extra_data.Tag
|
||||
tmpl += `</a>`
|
||||
} else {
|
||||
if extra_data.URLName != "" {
|
||||
tmpl += `<a href="`
|
||||
tmpl += extra_data.URL
|
||||
tmpl += `" class="username" style="color: #505050;float: right;">`
|
||||
tmpl += extra_data.URLName
|
||||
tmpl += `</a>
|
||||
<a class="username" style="color: #505050;float: right;border-right: 0;">`
|
||||
tmpl += extra_data.URLPrefix
|
||||
tmpl += `</a>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
</div>
|
||||
</div><br />
|
||||
<div class="rowblock" style="overflow: hidden;">
|
||||
`
|
||||
if len(tmpl_topic_vars.ItemList) != 0 {
|
||||
for _, item := range tmpl_topic_vars.ItemList {
|
||||
tmpl += `
|
||||
<div class="rowitem passive deletable_block editable_parent" style="`
|
||||
if item.(Reply).Avatar != "" {
|
||||
tmpl += `background-image: url(`
|
||||
tmpl += item.(Reply).Avatar
|
||||
tmpl += `), url(/static/white-dot.jpg);background-position: 0px `
|
||||
if item.(Reply).ContentLines <= 5 {
|
||||
tmpl += `-1`
|
||||
}
|
||||
tmpl += `0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;`
|
||||
tmpl += string(item.(Reply).Css)
|
||||
}
|
||||
tmpl += `">
|
||||
<span class="editable_block user_content">`
|
||||
tmpl += string(item.(Reply).ContentHtml)
|
||||
tmpl += `</span>
|
||||
<br /><br />
|
||||
<a href="/user/`
|
||||
tmpl += strconv.Itoa(item.(Reply).CreatedBy)
|
||||
tmpl += `" class="username">`
|
||||
tmpl += item.(Reply).CreatedByName
|
||||
tmpl += `</a>
|
||||
`
|
||||
if tmpl_topic_vars.CurrentUser.Is_Mod {
|
||||
tmpl += `<a href="/reply/edit/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/reply/delete/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `"><button class="username delete_item">Delete</button></a>`
|
||||
}
|
||||
tmpl += `
|
||||
<a href="/report/submit/`
|
||||
tmpl += strconv.Itoa(item.(Reply).ID)
|
||||
tmpl += `?session=`
|
||||
tmpl += tmpl_topic_vars.CurrentUser.Session
|
||||
tmpl += `&type=reply"><button class="username report_item">Report</button></a>
|
||||
`
|
||||
if item.(Reply).Tag != "" {
|
||||
tmpl += `<a class="username" style="float: right;">`
|
||||
tmpl += item.(Reply).Tag
|
||||
tmpl += `</a>`
|
||||
} else {
|
||||
if item.(Reply).URLName != "" {
|
||||
tmpl += `<a href="`
|
||||
tmpl += item.(Reply).URL
|
||||
tmpl += `" class="username" style="color: #505050;float: right;" rel="nofollow">`
|
||||
tmpl += item.(Reply).URLName
|
||||
tmpl += `</a>
|
||||
<a class="username" style="color: #505050;float: right;border-right: 0;">`
|
||||
tmpl += item.(Reply).URLPrefix
|
||||
tmpl += `</a>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
</div>`
|
||||
}
|
||||
}
|
||||
tmpl += `
|
||||
</div>
|
||||
`
|
||||
if !tmpl_topic_vars.CurrentUser.Is_Banned {
|
||||
tmpl += `
|
||||
<div class="rowblock">
|
||||
<form action="/reply/create/" method="post">
|
||||
<input name="tid" value='`
|
||||
tmpl += strconv.Itoa(extra_data.ID)
|
||||
tmpl += `' type="hidden" />
|
||||
<div class="formrow">
|
||||
<div class="formitem"><textarea name="reply-content" placeholder="Insert reply here"></textarea></div>
|
||||
</div>
|
||||
<div class="formrow">
|
||||
<div class="formitem"><button name="reply-button" class="formbutton">Create Reply</button></div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
`
|
||||
}
|
||||
tmpl += `
|
||||
`
|
||||
tmpl += ` <!--<link rel="stylesheet" href="https://use.fontawesome.com/8670aa03ca.css">-->
|
||||
</div>
|
||||
</body>
|
||||
</html>`
|
||||
return tmpl
|
||||
}
|
|
@ -0,0 +1,665 @@
|
|||
package main
|
||||
import "log"
|
||||
import "fmt"
|
||||
import "strings"
|
||||
import "reflect"
|
||||
import "path/filepath"
|
||||
import "io/ioutil"
|
||||
import "text/template/parse"
|
||||
|
||||
type VarItem struct
|
||||
{
|
||||
Name string
|
||||
Destination string
|
||||
Type string
|
||||
}
|
||||
|
||||
type VarItemReflect struct
|
||||
{
|
||||
Name string
|
||||
Destination string
|
||||
Value reflect.Value
|
||||
}
|
||||
|
||||
type CTemplateSet struct
|
||||
{
|
||||
tlist map[string]*parse.Tree
|
||||
dir string
|
||||
funcMap map[string]interface{}
|
||||
importMap map[string]string
|
||||
varList map[string]VarItem
|
||||
localVars map[string]map[string]VarItemReflect
|
||||
//tempVars map[string]string
|
||||
doImports bool
|
||||
expectsInt interface{}
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_template(name string, dir string, expects string, expectsInt interface{}, varList map[string]VarItem) (out string) {
|
||||
c.dir = dir
|
||||
c.doImports = true
|
||||
c.funcMap = make(map[string]interface{})
|
||||
c.funcMap["and"] = "&&"
|
||||
c.funcMap["not"] = "!"
|
||||
c.funcMap["or"] = "||"
|
||||
c.funcMap["eq"] = true
|
||||
c.funcMap["ge"] = true
|
||||
c.funcMap["gt"] = true
|
||||
c.funcMap["le"] = true
|
||||
c.funcMap["lt"] = true
|
||||
c.funcMap["ne"] = true
|
||||
c.importMap = make(map[string]string)
|
||||
c.importMap["strconv"] = "strconv"
|
||||
c.varList = varList
|
||||
c.expectsInt = expectsInt
|
||||
holdreflect := reflect.ValueOf(expectsInt)
|
||||
|
||||
res, err := ioutil.ReadFile(dir + name)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
content := string(res)
|
||||
|
||||
tree := parse.New(name, c.funcMap)
|
||||
var treeSet map[string]*parse.Tree = make(map[string]*parse.Tree)
|
||||
tree, err = tree.Parse(content,"{{","}}", treeSet, c.funcMap)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
if debug {
|
||||
fmt.Println(name)
|
||||
}
|
||||
|
||||
out = ""
|
||||
fname := strings.TrimSuffix(name, filepath.Ext(name))
|
||||
c.tlist = make(map[string]*parse.Tree)
|
||||
c.tlist[fname] = tree
|
||||
varholder := "tmpl_" + fname + "_vars"
|
||||
|
||||
if debug {
|
||||
fmt.Println(c.tlist)
|
||||
}
|
||||
|
||||
c.localVars = make(map[string]map[string]VarItemReflect)
|
||||
c.localVars[fname] = make(map[string]VarItemReflect)
|
||||
c.localVars[fname]["."] = VarItemReflect{".",varholder,holdreflect}
|
||||
|
||||
subtree := c.tlist[fname]
|
||||
if debug {
|
||||
fmt.Println(subtree.Root)
|
||||
}
|
||||
|
||||
for _, node := range subtree.Root.Nodes {
|
||||
if debug {
|
||||
fmt.Println("Node: " + node.String())
|
||||
}
|
||||
out += c.compile_switch(varholder, holdreflect, fname, node)
|
||||
}
|
||||
|
||||
var importList string
|
||||
if c.doImports {
|
||||
for _, item := range c.importMap {
|
||||
importList += "import \"" + item + "\"\n"
|
||||
}
|
||||
}
|
||||
|
||||
var varString string
|
||||
for _, varItem := range c.varList {
|
||||
varString += "var " + varItem.Name + " " + varItem.Type + " = " + varItem.Destination + "\n"
|
||||
}
|
||||
|
||||
out = "package main\n" + importList + "\nfunc init() {\nctemplates[\"" + fname + "\"] = template_" + fname + "\n}\n\nfunc template_" + fname + "(tmpl_" + fname + "_vars " + expects + ") (tmpl string) {\n" + varString + out + "return tmpl\n}\n"
|
||||
if debug {
|
||||
fmt.Println("Output!")
|
||||
fmt.Println(out)
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_switch(varholder string, holdreflect reflect.Value, template_name string, node interface{}) (out string) {
|
||||
switch node := node.(type) {
|
||||
case *parse.ActionNode:
|
||||
if debug {
|
||||
fmt.Println("Action Node")
|
||||
}
|
||||
|
||||
if node.Pipe == nil {
|
||||
break
|
||||
}
|
||||
for _, cmd := range node.Pipe.Cmds {
|
||||
out += c.compile_subswitch(varholder, holdreflect, template_name, cmd)
|
||||
}
|
||||
return out
|
||||
case *parse.IfNode:
|
||||
if debug {
|
||||
fmt.Println("If Node: ")
|
||||
fmt.Println(node.Pipe)
|
||||
}
|
||||
|
||||
var expr string
|
||||
for _, cmd := range node.Pipe.Cmds {
|
||||
if debug {
|
||||
fmt.Println("If Node Bit: ")
|
||||
fmt.Println(cmd)
|
||||
fmt.Println(reflect.ValueOf(cmd).Type().Name())
|
||||
}
|
||||
expr += c.compile_varswitch(varholder, holdreflect, template_name, cmd)
|
||||
}
|
||||
|
||||
if node.ElseList == nil {
|
||||
if debug {
|
||||
fmt.Println("Branch 1")
|
||||
}
|
||||
return "if " + expr + " {\n" + c.compile_switch(varholder, holdreflect, template_name, node.List) + "}\n"
|
||||
} else {
|
||||
if debug {
|
||||
fmt.Println("Branch 2")
|
||||
}
|
||||
return "if " + expr + " {\n" + c.compile_switch(varholder, holdreflect, template_name, node.List) + "} else {\n" + c.compile_switch(varholder, holdreflect, template_name, node.ElseList) + "}\n"
|
||||
}
|
||||
case *parse.ListNode:
|
||||
if debug {
|
||||
fmt.Println("List Node")
|
||||
}
|
||||
for _, subnode := range node.Nodes {
|
||||
out += c.compile_switch(varholder, holdreflect, template_name, subnode)
|
||||
}
|
||||
return out
|
||||
case *parse.RangeNode:
|
||||
if debug {
|
||||
fmt.Println("Range Node!")
|
||||
fmt.Println(node.Pipe)
|
||||
}
|
||||
|
||||
var outVal reflect.Value
|
||||
for _, cmd := range node.Pipe.Cmds {
|
||||
if debug {
|
||||
fmt.Println("Range Bit: ")
|
||||
fmt.Println(cmd)
|
||||
}
|
||||
out, outVal = c.compile_reflectswitch(varholder, holdreflect, template_name, cmd)
|
||||
}
|
||||
|
||||
if debug {
|
||||
fmt.Println("Returned: ")
|
||||
fmt.Println(out)
|
||||
fmt.Println("Range Kind Switch!")
|
||||
}
|
||||
|
||||
switch outVal.Kind() {
|
||||
case reflect.Map:
|
||||
var item reflect.Value
|
||||
for _, key := range outVal.MapKeys() {
|
||||
item = outVal.MapIndex(key)
|
||||
}
|
||||
|
||||
out = "if len(" + out + ") != 0 {\nfor _, item := range " + out + " {\n" + c.compile_switch("item", item, template_name, node.List) + "}\n}"
|
||||
case reflect.Invalid:
|
||||
return ""
|
||||
}
|
||||
|
||||
if node.ElseList != nil {
|
||||
out += " else {\n" + c.compile_switch(varholder, holdreflect, template_name, node.ElseList) + "}\n"
|
||||
} else {
|
||||
out += "\n"
|
||||
}
|
||||
return out
|
||||
case *parse.TemplateNode:
|
||||
if debug {
|
||||
fmt.Println("Template Node")
|
||||
}
|
||||
return c.compile_subtemplate(varholder, holdreflect, node)
|
||||
case *parse.TextNode:
|
||||
return "tmpl += `" + string(node.Text) + "`\n"
|
||||
default:
|
||||
panic("Unknown Node in main switch")
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_subswitch(varholder string, holdreflect reflect.Value, template_name string, node *parse.CommandNode) (out string) {
|
||||
firstWord := node.Args[0]
|
||||
switch n := firstWord.(type) {
|
||||
case *parse.FieldNode:
|
||||
if debug {
|
||||
fmt.Println("Field Node: ")
|
||||
fmt.Println(n.Ident)
|
||||
}
|
||||
|
||||
/* Use reflect to determine if the field is for a method, otherwise assume it's a variable. Coming Soon. */
|
||||
cur := holdreflect
|
||||
|
||||
var varbit string
|
||||
if cur.Kind() == reflect.Interface {
|
||||
cur = cur.Elem()
|
||||
varbit += ".(" + cur.Type().Name() + ")"
|
||||
}
|
||||
|
||||
for _, id := range n.Ident {
|
||||
if debug {
|
||||
fmt.Println("Data Kind: ")
|
||||
fmt.Println(cur.Kind().String())
|
||||
fmt.Println("Field Bit: ")
|
||||
fmt.Println(id)
|
||||
}
|
||||
|
||||
cur = cur.FieldByName(id)
|
||||
if cur.Kind() == reflect.Interface {
|
||||
cur = cur.Elem()
|
||||
if cur.Kind() == reflect.String && cur.Type().Name() != "string" {
|
||||
varbit = "string(" + varbit + "." + id + ")"
|
||||
} else {
|
||||
varbit += "." + id + ".(" + cur.Type().Name() + ")"
|
||||
}
|
||||
} else {
|
||||
varbit += "." + id
|
||||
}
|
||||
|
||||
if debug {
|
||||
fmt.Println("End Cycle")
|
||||
}
|
||||
}
|
||||
out = c.compile_varsub(varholder + varbit, cur)
|
||||
|
||||
for _, varItem := range c.varList {
|
||||
if strings.HasPrefix(out, varItem.Destination) {
|
||||
out = strings.Replace(out, varItem.Destination, varItem.Name, 1)
|
||||
}
|
||||
}
|
||||
return out
|
||||
case *parse.DotNode:
|
||||
if debug {
|
||||
fmt.Println("Dot Node")
|
||||
fmt.Println(node.String())
|
||||
}
|
||||
return c.compile_varsub(varholder, holdreflect)
|
||||
case *parse.NilNode:
|
||||
panic("Nil is not a command x.x")
|
||||
case *parse.VariableNode:
|
||||
if debug {
|
||||
fmt.Println("Variable Node")
|
||||
fmt.Println(n.String())
|
||||
fmt.Println(n.Ident)
|
||||
}
|
||||
|
||||
out, _ = c.compile_if_varsub(n.String(), varholder, template_name, holdreflect)
|
||||
return "tmpl += " + out + "\n"
|
||||
case *parse.StringNode:
|
||||
return n.Quoted
|
||||
default:
|
||||
fmt.Println("Unknown Kind: ")
|
||||
fmt.Println(reflect.ValueOf(firstWord).Elem().Kind())
|
||||
fmt.Println("Unknown Type: ")
|
||||
fmt.Println(reflect.ValueOf(firstWord).Elem().Type().Name())
|
||||
panic("I don't know what node this is")
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_varswitch(varholder string, holdreflect reflect.Value, template_name string, node *parse.CommandNode) (out string) {
|
||||
firstWord := node.Args[0]
|
||||
switch n := firstWord.(type) {
|
||||
case *parse.FieldNode:
|
||||
if debug {
|
||||
fmt.Println("Field Node: ")
|
||||
fmt.Println(n.Ident)
|
||||
|
||||
for _, id := range n.Ident {
|
||||
fmt.Println("Field Bit: ")
|
||||
fmt.Println(id)
|
||||
}
|
||||
}
|
||||
|
||||
/* Use reflect to determine if the field is for a method, otherwise assume it's a variable. Coming Soon. */
|
||||
return c.compile_boolsub(n.String(), varholder, template_name, holdreflect)
|
||||
case *parse.ChainNode:
|
||||
if debug {
|
||||
fmt.Println("Chain Node: ")
|
||||
fmt.Println(n.Node)
|
||||
fmt.Println(node.Args)
|
||||
}
|
||||
break
|
||||
case *parse.IdentifierNode:
|
||||
if debug {
|
||||
fmt.Println("Identifier Node: ")
|
||||
fmt.Println(node)
|
||||
fmt.Println(node.Args)
|
||||
}
|
||||
return c.compile_identswitch(varholder, holdreflect, template_name, node)
|
||||
case *parse.DotNode:
|
||||
return varholder
|
||||
case *parse.VariableNode:
|
||||
if debug {
|
||||
fmt.Println("Variable Node")
|
||||
fmt.Println(n.String())
|
||||
fmt.Println(n.Ident)
|
||||
}
|
||||
|
||||
out, _ = c.compile_if_varsub(n.String(), varholder, template_name, holdreflect)
|
||||
return out
|
||||
case *parse.NilNode:
|
||||
panic("Nil is not a command x.x")
|
||||
case *parse.PipeNode:
|
||||
if debug {
|
||||
fmt.Println("Pipe Node!")
|
||||
fmt.Println(n)
|
||||
}
|
||||
|
||||
/*for _, cmd := range n.Cmds {
|
||||
if debug {
|
||||
fmt.Println("Pipe Bit: ")
|
||||
fmt.Println(cmd)
|
||||
}
|
||||
out += c.compile_if_varsub_n(n.String(), varholder, template_name, holdreflect)
|
||||
}*/
|
||||
|
||||
if debug {
|
||||
fmt.Println("Args: ")
|
||||
fmt.Println(node.Args)
|
||||
}
|
||||
|
||||
/*argcopy := node.Args[1:]
|
||||
for _, arg := range argcopy {
|
||||
if debug {
|
||||
fmt.Println("Pipe Arg: ")
|
||||
fmt.Println(arg)
|
||||
fmt.Println(reflect.ValueOf(arg).Elem().Type().Name())
|
||||
fmt.Println(reflect.ValueOf(arg).Kind())
|
||||
}
|
||||
|
||||
switch arg.(type) {
|
||||
case *parse.IdentifierNode:
|
||||
out += c.compile_identswitch(varholder, holdreflect, template_name, node)
|
||||
break
|
||||
case *parse.PipeNode:
|
||||
break
|
||||
//out += c.compile_if_varsub_n(a.String(), varholder, template_name, holdreflect)
|
||||
default:
|
||||
panic("Unknown Pipe Arg type! Did Mario get stuck in the pipes again?")
|
||||
}
|
||||
//out += c.compile_varswitch(arg.String(), holdreflect, template_name, arg)
|
||||
}*/
|
||||
out += c.compile_identswitch(varholder, holdreflect, template_name, node)
|
||||
|
||||
if debug {
|
||||
fmt.Println("Out: ")
|
||||
fmt.Println(out)
|
||||
}
|
||||
return out
|
||||
default:
|
||||
fmt.Println("Unknown Kind: ")
|
||||
fmt.Println(reflect.ValueOf(firstWord).Elem().Kind())
|
||||
fmt.Println("Unknown Type: ")
|
||||
fmt.Println(reflect.ValueOf(firstWord).Elem().Type().Name())
|
||||
panic("I don't know what node this is! Grr...")
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_identswitch(varholder string, holdreflect reflect.Value, template_name string, node *parse.CommandNode) (out string) {
|
||||
ArgLoop:
|
||||
for pos, id := range node.Args {
|
||||
if debug {
|
||||
fmt.Println(id)
|
||||
}
|
||||
|
||||
switch id.String() {
|
||||
case "not":
|
||||
out += "!"
|
||||
case "or":
|
||||
out += " || "
|
||||
case "and":
|
||||
out += " && "
|
||||
case "le":
|
||||
out += c.compile_if_varsub_n(node.Args[pos + 1].String(), varholder, template_name, holdreflect) + " <= " + c.compile_if_varsub_n(node.Args[pos + 2].String(), varholder, template_name, holdreflect)
|
||||
break ArgLoop
|
||||
default:
|
||||
if debug {
|
||||
fmt.Println("Variable!")
|
||||
}
|
||||
out += c.compile_if_varsub_n(id.String(), varholder, template_name, holdreflect)
|
||||
}
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_reflectswitch(varholder string, holdreflect reflect.Value, template_name string, node *parse.CommandNode) (out string, outVal reflect.Value) {
|
||||
firstWord := node.Args[0]
|
||||
switch n := firstWord.(type) {
|
||||
case *parse.FieldNode:
|
||||
if debug {
|
||||
fmt.Println("Field Node: ")
|
||||
fmt.Println(n.Ident)
|
||||
|
||||
for _, id := range n.Ident {
|
||||
fmt.Println("Field Bit: ")
|
||||
fmt.Println(id)
|
||||
}
|
||||
}
|
||||
/* Use reflect to determine if the field is for a method, otherwise assume it's a variable. Coming Soon. */
|
||||
return c.compile_if_varsub(n.String(), varholder, template_name, holdreflect)
|
||||
case *parse.ChainNode:
|
||||
if debug {
|
||||
fmt.Println("Chain Node: ")
|
||||
fmt.Println(n.Node)
|
||||
fmt.Println(node.Args)
|
||||
}
|
||||
return "", outVal
|
||||
/*case *parse.IdentifierNode:
|
||||
fmt.Println("Identifier Node: ")
|
||||
fmt.Println(node)
|
||||
fmt.Println(node.Args)
|
||||
|
||||
ArgLoop:
|
||||
for pos, id := range node.Args {
|
||||
fmt.Println(id)
|
||||
switch id.String() {
|
||||
case "not":
|
||||
out += "!"
|
||||
case "or":
|
||||
out += " || "
|
||||
case "and":
|
||||
out += " && "
|
||||
case "le":
|
||||
out += c.compile_if_varsub_n(node.Args[pos + 1].String(), varholder, holdreflect) + " <= " + c.compile_if_varsub_n(node.Args[pos + 2].String(), varholder, holdreflect)
|
||||
break ArgLoop
|
||||
default:
|
||||
fmt.Println("Variable!")
|
||||
out += c.compile_if_varsub_n(id.String(), varholder, holdreflect)
|
||||
}
|
||||
}
|
||||
return out*/
|
||||
case *parse.DotNode:
|
||||
return varholder, holdreflect
|
||||
case *parse.NilNode:
|
||||
panic("Nil is not a command x.x")
|
||||
default:
|
||||
//panic("I don't know what node this is")
|
||||
}
|
||||
return "", outVal
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_if_varsub_n(varname string, varholder string, template_name string, cur reflect.Value) (out string) {
|
||||
out, _ = c.compile_if_varsub(varname, varholder, template_name, cur)
|
||||
return out
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_if_varsub(varname string, varholder string, template_name string, cur reflect.Value) (out string, val reflect.Value) {
|
||||
if varname[0] != '.' && varname[0] != '$' {
|
||||
return varname, cur
|
||||
}
|
||||
|
||||
bits := strings.Split(varname,".")
|
||||
if varname[0] == '$' {
|
||||
var res VarItemReflect
|
||||
if varname[1] == '.' {
|
||||
res = c.localVars[template_name]["."]
|
||||
} else {
|
||||
res = c.localVars[template_name][strings.TrimPrefix(bits[0],"$")]
|
||||
}
|
||||
out += res.Destination
|
||||
cur = res.Value
|
||||
|
||||
if cur.Kind() == reflect.Interface {
|
||||
cur = cur.Elem()
|
||||
}
|
||||
} else {
|
||||
if cur.Kind() == reflect.Interface {
|
||||
cur = cur.Elem()
|
||||
out += varholder + ".(" + cur.Type().Name() + ")"
|
||||
} else {
|
||||
out += varholder
|
||||
}
|
||||
}
|
||||
bits[0] = strings.TrimPrefix(bits[0],"$")
|
||||
|
||||
if debug {
|
||||
fmt.Println("Cur Kind: ")
|
||||
fmt.Println(cur.Kind())
|
||||
fmt.Println("Cur Type: ")
|
||||
fmt.Println(cur.Type().Name())
|
||||
}
|
||||
|
||||
for _, bit := range bits {
|
||||
if debug {
|
||||
fmt.Println("Variable Field!")
|
||||
fmt.Println(bit)
|
||||
}
|
||||
|
||||
if bit == "" {
|
||||
continue
|
||||
}
|
||||
|
||||
cur = cur.FieldByName(bit)
|
||||
if cur.Kind() == reflect.Interface {
|
||||
cur = cur.Elem()
|
||||
out += "." + bit + ".(" + cur.Type().Name() + ")"
|
||||
} else {
|
||||
out += "." + bit
|
||||
}
|
||||
|
||||
if debug {
|
||||
fmt.Println("Data Kind: ")
|
||||
fmt.Println(cur.Kind())
|
||||
fmt.Println("Data Type: ")
|
||||
fmt.Println(cur.Type().Name())
|
||||
}
|
||||
}
|
||||
|
||||
for _, varItem := range c.varList {
|
||||
if strings.HasPrefix(out, varItem.Destination) {
|
||||
out = strings.Replace(out, varItem.Destination, varItem.Name, 1)
|
||||
}
|
||||
}
|
||||
return out, cur
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_boolsub(varname string, varholder string, template_name string, val reflect.Value) string {
|
||||
out, val := c.compile_if_varsub(varname, varholder, template_name, val)
|
||||
switch val.Kind() {
|
||||
case reflect.Int:
|
||||
out += " > 0"
|
||||
case reflect.Bool:
|
||||
// Do nothing
|
||||
case reflect.String:
|
||||
out += " != \"\""
|
||||
case reflect.Int64:
|
||||
out += " > 0"
|
||||
default:
|
||||
panic("I don't know what this variable's type is o.o\n")
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_varsub(varname string, val reflect.Value) string {
|
||||
for _, varItem := range c.varList {
|
||||
if strings.HasPrefix(varname, varItem.Destination) {
|
||||
varname = strings.Replace(varname, varItem.Destination, varItem.Name, 1)
|
||||
}
|
||||
}
|
||||
|
||||
if val.Kind() == reflect.Interface {
|
||||
val = val.Elem()
|
||||
}
|
||||
|
||||
switch val.Kind() {
|
||||
case reflect.Int:
|
||||
return "tmpl += strconv.Itoa(" + varname + ")\n"
|
||||
case reflect.Bool:
|
||||
return "if " + varname + " {\ntmpl += \"true\"} else {\ntmpl += \"false\"\n}\n"
|
||||
case reflect.String:
|
||||
if val.Type().Name() != "string" {
|
||||
return "tmpl += string(" + varname + ")\n"
|
||||
} else {
|
||||
return "tmpl += " + varname + "\n"
|
||||
}
|
||||
case reflect.Int64:
|
||||
return "tmpl += strconv.FormatInt(" + varname + ", 10)"
|
||||
default:
|
||||
fmt.Println("Unknown Kind: ")
|
||||
fmt.Println(val.Kind())
|
||||
fmt.Println("Unknown Type: ")
|
||||
fmt.Println(val.Type().Name())
|
||||
panic("// I don't know what this variable's type is o.o\n")
|
||||
}
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_subtemplate(pvarholder string, pholdreflect reflect.Value, node *parse.TemplateNode) (out string) {
|
||||
if debug {
|
||||
fmt.Println("Template Node: " + node.Name)
|
||||
}
|
||||
|
||||
fname := strings.TrimSuffix(node.Name, filepath.Ext(node.Name))
|
||||
varholder := "tmpl_" + fname + "_vars"
|
||||
var holdreflect reflect.Value
|
||||
if node.Pipe != nil {
|
||||
for _, cmd := range node.Pipe.Cmds {
|
||||
firstWord := cmd.Args[0]
|
||||
switch firstWord.(type) {
|
||||
case *parse.DotNode:
|
||||
varholder = pvarholder
|
||||
holdreflect = pholdreflect
|
||||
break
|
||||
case *parse.NilNode:
|
||||
panic("Nil is not a command x.x")
|
||||
default:
|
||||
out = "var " + varholder + " := false\n"
|
||||
out += c.compile_command(cmd)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
res, err := ioutil.ReadFile(c.dir + node.Name)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
content := string(res)
|
||||
|
||||
tree := parse.New(node.Name, c.funcMap)
|
||||
var treeSet map[string]*parse.Tree = make(map[string]*parse.Tree)
|
||||
tree, err = tree.Parse(content,"{{","}}", treeSet, c.funcMap)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
c.tlist[fname] = tree
|
||||
subtree := c.tlist[fname]
|
||||
if debug {
|
||||
fmt.Println(subtree.Root)
|
||||
}
|
||||
|
||||
c.localVars[fname] = make(map[string]VarItemReflect)
|
||||
c.localVars[fname]["."] = VarItemReflect{".",varholder,holdreflect}
|
||||
|
||||
for _, node := range subtree.Root.Nodes {
|
||||
if debug {
|
||||
fmt.Println("Node: " + node.String())
|
||||
}
|
||||
out += c.compile_switch(varholder, holdreflect, fname, node)
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (c *CTemplateSet) compile_command(*parse.CommandNode) (out string) {
|
||||
return ""
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
{{template "header.html" . }}
|
||||
<div class="alert_success">Your data was successfully updated</div>
|
||||
<div class="colblock_left">
|
||||
<div class="rowitem"><a>My Account</a></div>
|
||||
<div class="rowitem passive"><a href="/user/edit/avatar/">Edit Avatar</a></div>
|
||||
<div class="rowitem passive"><a href="/user/edit/username/">Edit Username</a></div>
|
||||
<div class="rowitem passive"><a href="/user/edit/critical/">Edit Password</a></div>
|
||||
<div class="rowitem passive"><a>Coming Soon</a></div>
|
||||
<div class="rowitem passive"><a>Coming Soon</a></div>
|
||||
<div class="rowitem passive"><a>Coming Soon</a></div>
|
||||
</div>
|
||||
<div class="colblock_right">
|
||||
<div class="rowitem"><a>Edit Avatar</a></div>
|
||||
</div>
|
||||
{{ if .CurrentUser.HasAvatar }}
|
||||
<div class="colblock_right">
|
||||
<div class="rowitem"><img src="{{.CurrentUser.Avatar}}" height="128px" max-width="128px" /></div>
|
||||
</div>
|
||||
{{end}}
|
||||
<div class="colblock_right">
|
||||
<form action="/user/edit/avatar/submit/" method="post" enctype="multipart/form-data">
|
||||
<div class="formrow">
|
||||
<div class="formitem"><a>Upload Avatar</a></div>
|
||||
<div class="formitem"><input name="account-avatar" type="file" /></div>
|
||||
</div>
|
||||
<div class="formrow">
|
||||
<div class="formitem"><button name="account-button" class="formbutton">Update</div></div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
{{template "footer.html" . }}
|
|
@ -4,7 +4,9 @@
|
|||
</div>
|
||||
<div class="rowblock">
|
||||
{{range .ItemList}}<div class="rowitem passive" style="{{ if .Avatar }}background-image: url({{ .Avatar }});background-position: left;background-repeat: no-repeat;background-size: 64px;padding-left: 72px;{{end}}{{ if .Sticky }}background-color: #FFFFCC;{{end}}">
|
||||
<a href="/topic/{{.ID}}">{{.Title}}</a> {{if .Is_Closed}}<span class="topic_status topic_status_closed">closed</span>{{else}}<span class="topic_status topic_status_open">open</span>{{end}}
|
||||
<a href="/topic/{{.ID}}">{{.Title}}</a> {{if .Is_Closed}}<span class="username topic_status_e topic_status_closed" style="float: right;">closed</span>
|
||||
{{else}}<span class="username topic_status_e topic_status_open" style="float: right;">open</span>{{end}}
|
||||
<span class="username" style="border-right: 0;float: right;">Status</span>
|
||||
</div>{{end}}
|
||||
</div>
|
||||
{{if .Something}}
|
||||
|
|
|
@ -12,3 +12,4 @@
|
|||
<body>
|
||||
<div class="container">
|
||||
{{template "menu.html" .}}
|
||||
{{range .NoticeList}}<div class="alert">{{.}}</div>{{end}}
|
|
@ -16,15 +16,15 @@
|
|||
<div class="rowitem"><a>Comments</a></div>
|
||||
</div>
|
||||
<div class="colblock_right" style="overflow: hidden;">
|
||||
{{range $index, $element := .ItemList}}
|
||||
<div class="rowitem passive deletable_block editable_parent" style="{{ if $element.Avatar }}background-image: url({{$element.Avatar}}), url(/static/white-dot.jpg);background-position: 0px {{if le $element.ContentLines 5}}-1{{end}}0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;{{$element.Css}}{{end}}">
|
||||
<span class="editable_block user_content">{{$element.ContentHtml}}</span>
|
||||
{{range .ItemList}}
|
||||
<div class="rowitem passive deletable_block editable_parent" style="{{ if .Avatar }}background-image: url({{.Avatar}}), url(/static/white-dot.jpg);background-position: 0px {{if le .ContentLines 5}}-1{{end}}0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;{{.Css}}{{end}}">
|
||||
<span class="editable_block user_content">{{.ContentHtml}}</span>
|
||||
<br /><br />
|
||||
<a href="/user/{{$element.CreatedBy}}" class="username">{{$element.CreatedByName}}</a>
|
||||
{{if $.CurrentUser.Is_Mod}}<a href="/profile/reply/edit/submit/{{$element.ID}}"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/profile/reply/delete/submit/{{$element.ID}}"><button class="username delete_item">Delete</button></a>{{end}}
|
||||
<a href="/report/submit/{{$element.ID}}?session={{$.CurrentUser.Session}}&type=user-reply"><button class="username report_item">Report</button></a>
|
||||
{{ if $element.Tag }}<a class="username" style="float: right;">{{$element.Tag}}</a>{{end}}
|
||||
<a href="/user/{{.CreatedBy}}" class="username">{{.CreatedByName}}</a>
|
||||
{{if $.CurrentUser.Is_Mod}}<a href="/profile/reply/edit/submit/{{.ID}}"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/profile/reply/delete/submit/{{.ID}}"><button class="username delete_item">Delete</button></a>{{end}}
|
||||
<a href="/report/submit/{{.ID}}?session={{$.CurrentUser.Session}}&type=user-reply"><button class="username report_item">Report</button></a>
|
||||
{{ if .Tag }}<a class="username" style="float: right;">{{.Tag}}</a>{{end}}
|
||||
</div>{{end}}
|
||||
</div>
|
||||
{{if not .CurrentUser.Is_Banned}}
|
||||
|
|
|
@ -8,6 +8,10 @@
|
|||
<div class="formitem"><a>Account Name</a></div>
|
||||
<div class="formitem"><input name="username" type="text" placeholder="Account Name" /></div>
|
||||
</div>
|
||||
<div class="formrow">
|
||||
<div class="formitem"><a>Email</a></div>
|
||||
<div class="formitem"><input name="email" type="email" placeholder="joe.doe@example.com" /></div>
|
||||
</div>
|
||||
<div class="formrow">
|
||||
<div class="formitem"><a>Password</a></div>
|
||||
<div class="formitem"><input name="password" type="password" autocomplete="new-password" placeholder="*****" /></div>
|
||||
|
|
|
@ -32,16 +32,16 @@
|
|||
</div>
|
||||
</div><br />
|
||||
<div class="rowblock" style="overflow: hidden;">
|
||||
{{range $index, $element := .ItemList}}
|
||||
<div class="rowitem passive deletable_block editable_parent" style="{{ if $element.Avatar }}background-image: url({{$element.Avatar}}), url(/static/white-dot.jpg);background-position: 0px {{if le $element.ContentLines 5}}-1{{end}}0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;{{$element.Css}}{{end}}">
|
||||
<span class="editable_block user_content">{{$element.ContentHtml}}</span>
|
||||
{{range .ItemList}}
|
||||
<div class="rowitem passive deletable_block editable_parent" style="{{ if .Avatar }}background-image: url({{.Avatar}}), url(/static/white-dot.jpg);background-position: 0px {{if le .ContentLines 5}}-1{{end}}0px;background-repeat: no-repeat, repeat-y;background-size: 128px;padding-left: 136px;{{.Css}}{{end}}">
|
||||
<span class="editable_block user_content">{{.ContentHtml}}</span>
|
||||
<br /><br />
|
||||
<a href="/user/{{$element.CreatedBy}}" class="username">{{$element.CreatedByName}}</a>
|
||||
{{if $.CurrentUser.Is_Mod}}<a href="/reply/edit/submit/{{$element.ID}}"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/reply/delete/submit/{{$element.ID}}"><button class="username delete_item">Delete</button></a>{{end}}
|
||||
<a href="/report/submit/{{$element.ID}}?session={{$.CurrentUser.Session}}&type=reply"><button class="username report_item">Report</button></a>
|
||||
{{if $element.Tag}}<a class="username" style="float: right;">{{$element.Tag}}</a>{{else if $element.URLName}}<a href="{{$element.URL}}" class="username" style="color: #505050;float: right;" rel="nofollow">{{$element.URLName}}</a>
|
||||
<a class="username" style="color: #505050;float: right;border-right: 0;">{{$element.URLPrefix}}</a>{{end}}
|
||||
<a href="/user/{{.CreatedBy}}" class="username">{{.CreatedByName}}</a>
|
||||
{{if $.CurrentUser.Is_Mod}}<a href="/reply/edit/submit/{{.ID}}"><button class="username edit_item">Edit</button></a>
|
||||
<a href="/reply/delete/submit/{{.ID}}"><button class="username delete_item">Delete</button></a>{{end}}
|
||||
<a href="/report/submit/{{.ID}}?session={{$.CurrentUser.Session}}&type=reply"><button class="username report_item">Report</button></a>
|
||||
{{if .Tag}}<a class="username" style="float: right;">{{.Tag}}</a>{{else if .URLName}}<a href="{{.URL}}" class="username" style="color: #505050;float: right;" rel="nofollow">{{.URLName}}</a>
|
||||
<a class="username" style="color: #505050;float: right;border-right: 0;">{{.URLPrefix}}</a>{{end}}
|
||||
</div>{{end}}
|
||||
</div>
|
||||
{{if not .CurrentUser.Is_Banned}}
|
||||
|
|
74
user.go
74
user.go
|
@ -1,5 +1,5 @@
|
|||
package main
|
||||
import "log"
|
||||
//import "log"
|
||||
import "strings"
|
||||
import "strconv"
|
||||
import "net/http"
|
||||
|
@ -46,35 +46,81 @@ func SetPassword(uid int, password string) (error) {
|
|||
return nil
|
||||
}
|
||||
|
||||
func SessionCheck(w http.ResponseWriter, r *http.Request) (User) {
|
||||
user := User{0,"",0,false,false,false,false,false,false,"",false,"","","","",""}
|
||||
var err error
|
||||
var cookie *http.Cookie
|
||||
|
||||
func SessionCheck(w http.ResponseWriter, r *http.Request) (user User, noticeList map[int]string, success bool) {
|
||||
// Are there any session cookies..?
|
||||
// Assign it to user.name to avoid having to create a temporary variable for the type conversion
|
||||
cookie, err = r.Cookie("uid")
|
||||
cookie, err := r.Cookie("uid")
|
||||
if err != nil {
|
||||
return user
|
||||
return user, noticeList, true
|
||||
}
|
||||
user.Name = cookie.Value
|
||||
user.ID, err = strconv.Atoi(user.Name)
|
||||
if err != nil {
|
||||
return user
|
||||
return user, noticeList, true
|
||||
}
|
||||
cookie, err = r.Cookie("session")
|
||||
if err != nil {
|
||||
return user
|
||||
return user, noticeList, true
|
||||
}
|
||||
user.Session = cookie.Value
|
||||
|
||||
// Is this session valid..?
|
||||
err = get_session_stmt.QueryRow(user.ID,user.Session).Scan(&user.ID, &user.Name, &user.Group, &user.Is_Super_Admin, &user.Session, &user.Avatar, &user.Message, &user.URLPrefix, &user.URLName)
|
||||
if err == sql.ErrNoRows {
|
||||
return user
|
||||
return user, noticeList, true
|
||||
} else if err != nil {
|
||||
log.Print(err)
|
||||
return user
|
||||
InternalError(err,w,r,user)
|
||||
return user, noticeList, false
|
||||
}
|
||||
|
||||
user.Is_Admin = user.Is_Super_Admin || groups[user.Group].Is_Admin
|
||||
user.Is_Super_Mod = groups[user.Group].Is_Mod || user.Is_Admin
|
||||
user.Is_Mod = user.Is_Super_Mod
|
||||
user.Is_Banned = groups[user.Group].Is_Banned
|
||||
user.Loggedin = !user.Is_Banned || user.Is_Super_Mod
|
||||
if user.Is_Banned && user.Is_Super_Mod {
|
||||
user.Is_Banned = false
|
||||
}
|
||||
|
||||
if user.Is_Banned {
|
||||
noticeList[0] = "You have been banned. Your ability to post has been revoked."
|
||||
}
|
||||
|
||||
if user.Avatar != "" {
|
||||
if user.Avatar[0] == '.' {
|
||||
user.Avatar = "/uploads/avatar_" + strconv.Itoa(user.ID) + user.Avatar
|
||||
}
|
||||
} else {
|
||||
user.Avatar = strings.Replace(noavatar,"{id}",strconv.Itoa(user.ID),1)
|
||||
}
|
||||
return user, noticeList, true
|
||||
}
|
||||
|
||||
func SimpleSessionCheck(w http.ResponseWriter, r *http.Request) (user User, success bool) {
|
||||
// Are there any session cookies..?
|
||||
// Assign it to user.name to avoid having to create a temporary variable for the type conversion
|
||||
cookie, err := r.Cookie("uid")
|
||||
if err != nil {
|
||||
return user, true
|
||||
}
|
||||
user.Name = cookie.Value
|
||||
user.ID, err = strconv.Atoi(user.Name)
|
||||
if err != nil {
|
||||
return user, true
|
||||
}
|
||||
cookie, err = r.Cookie("session")
|
||||
if err != nil {
|
||||
return user, true
|
||||
}
|
||||
user.Session = cookie.Value
|
||||
|
||||
// Is this session valid..?
|
||||
err = get_session_stmt.QueryRow(user.ID,user.Session).Scan(&user.ID, &user.Name, &user.Group, &user.Is_Super_Admin, &user.Session, &user.Avatar, &user.Message, &user.URLPrefix, &user.URLName)
|
||||
if err == sql.ErrNoRows {
|
||||
return user, true
|
||||
} else if err != nil {
|
||||
InternalError(err,w,r,user)
|
||||
return user, false
|
||||
}
|
||||
|
||||
user.Is_Admin = user.Is_Super_Admin || groups[user.Group].Is_Admin
|
||||
|
@ -93,5 +139,5 @@ func SessionCheck(w http.ResponseWriter, r *http.Request) (User) {
|
|||
} else {
|
||||
user.Avatar = strings.Replace(noavatar,"{id}",strconv.Itoa(user.ID),1)
|
||||
}
|
||||
return user
|
||||
return user, true
|
||||
}
|
Loading…
Reference in New Issue