func main() { log.SetFlags(0) // Read configuration. flag.Usage = usage flag.Parse() // Validate arguments. if *dataDir == "" { log.Fatal("data directory required: --data-dir") } else if *certFile != "" && *keyFile == "" { log.Fatal("key file required: --key-file") } else if *keyFile != "" && *certFile == "" { log.Fatal("certificate file required: --cert-file") } var useTLS = (*certFile != "" && *keyFile != "") // Initialize data directory. if err := os.MkdirAll(*dataDir, 0700); err != nil { log.Fatal(err) } // Seed the PRNG for API key generation. rand.Seed(time.Now().Unix()) // Initialize db. var db db.DB if err := db.Open(filepath.Join(*dataDir, "db"), 0666); err != nil { log.Fatal(err) } defer db.Close() // Initialize handler. h, err := server.NewHandler(&db) if err != nil { log.Fatal(err) } logHandler := handlers.CombinedLoggingHandler(os.Stdout, h) // Start servers. log.Printf("Listening on http://localhost%s", *addr) if useTLS { log.Printf("Listening on http://localhost%s", *tlsAddr) } log.SetFlags(log.LstdFlags) go func() { log.Fatal(http.ListenAndServe(*addr, logHandler)) }() if useTLS { go func() { log.Fatal(http.ListenAndServeTLS(*tlsAddr, *certFile, *keyFile, logHandler)) }() } select {} }
// withHandler executes a function with an open handler. func withHandler(fn func(*Handler)) { f, _ := ioutil.TempFile("", "skybox-") path := f.Name() f.Close() os.Remove(path) defer os.RemoveAll(path) // Create database. var db db.DB if err := db.Open(path, 0666); err != nil { panic("db open error: " + err.Error()) } defer db.Close() // Initialize handler. h, err := NewHandler(&db) if err != nil { panic("handler error: " + err.Error()) } fn(h) }
// NewHandler creates a new Handler instance. func NewHandler(db *db.DB) (*Handler, error) { secret, err := db.Secret() if err != nil { return nil, err } // Setup the handler. h := &Handler{ Router: mux.NewRouter(), db: db, store: sessions.NewCookieStore(secret), } h.Handle("/track.png", http.HandlerFunc(h.track)).Methods("GET") NewRootHandler(h) NewAccountHandler(h) NewFunnelHandler(h) return h, nil }