120 lines
2.6 KiB
Go
120 lines
2.6 KiB
Go
package main
|
|
|
|
import (
|
|
"database/sql"
|
|
"encoding/json"
|
|
"flag"
|
|
"fmt"
|
|
"github.com/gorilla/csrf"
|
|
"github.com/gorilla/sessions"
|
|
_ "github.com/lib/pq"
|
|
"net/http"
|
|
"os"
|
|
)
|
|
|
|
const (
|
|
VERSION = "0.1"
|
|
MAX_DB_CONNS = 10 // already excessive for personal app
|
|
)
|
|
|
|
type Config struct {
|
|
Sql struct {
|
|
Host string
|
|
Dbname string
|
|
Username string
|
|
Password string
|
|
}
|
|
Port string
|
|
Url string
|
|
}
|
|
|
|
const (
|
|
flash_err = "_flash_err"
|
|
flash_info = "_flash_info"
|
|
)
|
|
|
|
var (
|
|
config Config
|
|
db *sql.DB
|
|
store = sessions.NewCookieStore([]byte("key-store-auth-secret"))
|
|
)
|
|
|
|
func loadConfig(env string) {
|
|
file, err := os.Open("config/" + env + ".json")
|
|
if err != nil {
|
|
fmt.Println("Error: cannot open config file: config/" + env + ".json")
|
|
os.Exit(-1)
|
|
}
|
|
defer file.Close()
|
|
decoder := json.NewDecoder(file)
|
|
err = decoder.Decode(&config)
|
|
if err != nil {
|
|
fmt.Println("Error: cannot decode config file: ", err)
|
|
os.Exit(-1)
|
|
}
|
|
}
|
|
|
|
func dbConnect() {
|
|
var err error
|
|
db, err = sql.Open("postgres", fmt.Sprintf("postgres://%s:%s@%s/%s?sslmode=require", config.Sql.Username, config.Sql.Password, config.Sql.Host, config.Sql.Dbname))
|
|
|
|
if err != nil {
|
|
fmt.Println("DB ERROR: ", err)
|
|
}
|
|
db.SetMaxIdleConns(MAX_DB_CONNS)
|
|
err = db.Ping()
|
|
if err != nil {
|
|
fmt.Println("DB Error on Ping(): ", err)
|
|
os.Exit(-1)
|
|
}
|
|
}
|
|
|
|
func csrfSecret() string {
|
|
file, err := os.Open("csrf-secret.txt")
|
|
if err != nil {
|
|
fmt.Println("Error: cannot open csrf-secret.txt (run gen-csrf.sh to generate)")
|
|
os.Exit(-1)
|
|
}
|
|
defer file.Close()
|
|
var bytes []byte = make([]byte, 32)
|
|
n, err := file.Read(bytes)
|
|
if err != nil || n != 32 {
|
|
fmt.Println("Error: cannot open csrf-secret.txt (run gen-csrf.sh to generate)")
|
|
}
|
|
return string(bytes)
|
|
}
|
|
type CSRFErrorHandler struct {}
|
|
|
|
func (self CSRFErrorHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
fmt.Println("csrf Failure: ")
|
|
fmt.Println(csrf.FailureReason(r))
|
|
fmt.Println("-----")
|
|
}
|
|
|
|
func main() {
|
|
fmt.Println("transmet ", VERSION)
|
|
|
|
envFlag := flag.String("env", "local", "load config/{env}.json")
|
|
flag.Parse()
|
|
|
|
fmt.Println("Loading...")
|
|
|
|
loadConfig(*envFlag)
|
|
dbConnect()
|
|
initTemplates()
|
|
muxRouter := init_route_handlers()
|
|
//errHandler := csrf.ErrorHandler( CSRFErrorHandler{} )
|
|
|
|
// Terrible. TODO: Get SSL for prod, and then wrap in if(dev) { {
|
|
csrfSecurityOption := csrf.Secure(false)
|
|
|
|
fmt.Println("Listening on", config.Port, "...")
|
|
|
|
err := http.ListenAndServe(":"+config.Port, csrf.Protect([]byte(csrfSecret()), /*errHandler,*/ csrfSecurityOption)(muxRouter))
|
|
if err != nil {
|
|
fmt.Println("Fatal Error: ", err)
|
|
}
|
|
|
|
db.Close()
|
|
}
|