forked from haruyama/golang-goji-sample
/
core.go
121 lines (100 loc) · 3.03 KB
/
core.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
package system
import (
"html/template"
"io"
"net/http"
"os"
"path/filepath"
"reflect"
"strings"
"crypto/sha256"
"github.com/coopernurse/gorp"
"github.com/golang/glog"
"github.com/gorilla/sessions"
"github.com/haruyama/golang-goji-sample/models"
"github.com/pelletier/go-toml"
"github.com/zenazn/goji/web"
)
type CsrfProtection struct {
Key string
Cookie string
Header string
Secure bool
}
type Application struct {
Config *toml.TomlTree
Template *template.Template
Store *sessions.CookieStore
DbMap *gorp.DbMap
CsrfProtection *CsrfProtection
}
func (application *Application) Init(filename *string) {
config, err := toml.LoadFile(*filename)
if err != nil {
glog.Fatalf("TOML load failed: %s\n", err)
}
hash := sha256.New()
io.WriteString(hash, config.Get("cookie.mac_secret").(string))
application.Store = sessions.NewCookieStore(hash.Sum(nil))
application.Store.Options = &sessions.Options{
HttpOnly: true,
Secure: config.Get("cookie.secure").(bool),
}
dbConfig := config.Get("database").(*toml.TomlTree)
application.DbMap = models.GetDbMap(
dbConfig.Get("user").(string),
dbConfig.Get("password").(string),
dbConfig.Get("hostname").(string),
dbConfig.Get("port").(string),
dbConfig.Get("database").(string))
application.CsrfProtection = &CsrfProtection{
Key: config.Get("csrf.key").(string),
Cookie: config.Get("csrf.cookie").(string),
Header: config.Get("csrf.header").(string),
Secure: config.Get("cookie.secure").(bool),
}
application.Config = config
}
func (application *Application) LoadTemplates() error {
var templates []string
fn := func(path string, f os.FileInfo, err error) error {
if f.IsDir() != true && strings.HasSuffix(f.Name(), ".html") {
templates = append(templates, path)
}
return nil
}
err := filepath.Walk(application.Config.Get("general.template_path").(string), fn)
if err != nil {
return err
}
application.Template = template.Must(template.ParseFiles(templates...))
return nil
}
func (application *Application) Close() {
glog.Info("Bye!")
}
func (application *Application) Route(controller interface{}, route string) interface{} {
fn := func(c web.C, w http.ResponseWriter, r *http.Request) {
c.Env["Content-Type"] = "text/html"
methodValue := reflect.ValueOf(controller).MethodByName(route)
methodInterface := methodValue.Interface()
method := methodInterface.(func(c web.C, r *http.Request) (string, int))
body, code := method(c, r)
if session, exists := c.Env["Session"]; exists {
err := session.(*sessions.Session).Save(r, w)
if err != nil {
glog.Errorf("Can't save session: %v", err)
}
}
switch code {
case http.StatusOK:
if _, exists := c.Env["Content-Type"]; exists {
w.Header().Set("Content-Type", c.Env["Content-Type"].(string))
}
io.WriteString(w, body)
case http.StatusSeeOther, http.StatusFound:
http.Redirect(w, r, body, code)
}
}
return fn
}