/
main.go
87 lines (74 loc) · 1.97 KB
/
main.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
// Dependency: golang.org/x/crypto/acme/autocert
package main
import (
"crypto/tls"
"flag"
"fmt"
"io"
"log"
"net/http"
"time"
"golang.org/x/crypto/acme/autocert"
)
const (
domain = "<your-domain.com"
)
func handleIndex(w http.ResponseWriter, r *http.Request) {
io.WriteString(w, `<html><body>Hello, world!</body></html>`)
}
func makeServerFromMux(mux *http.ServeMux) *http.Server {
// set timeouts so that a slow or malicious client doesn't
// hold resources forever
return &http.Server{
ReadTimeout: 5 * time.Second,
WriteTimeout: 5 * time.Second,
IdleTimeout: 120 * time.Second,
Handler: mux,
}
}
func makeHTTPServer() *http.Server {
mux := &http.ServeMux{}
mux.HandleFunc("/", handleIndex)
return makeServerFromMux(mux)
}
func makeHTTPToHTTPSRedirectServer() *http.Server {
handleRedirect := func(w http.ResponseWriter, req *http.Request) {
newURI := "https://" + req.Host + req.URL.String()
http.Redirect(w, req, newURI, http.StatusFound)
}
mux := &http.ServeMux{}
mux.HandleFunc("/", handleRedirect)
return makeServerFromMux(mux)
}
func main() {
redirect := true
flag.BoolVar(&redirect, "redirect", true, "if true, redirect http to https")
flag.Parse()
// also start http.
if redirect {
httpSrv := makeHTTPToHTTPSRedirectServer()
httpSrv.Addr = ":80"
fmt.Printf("Starting HTTP server on :80\n")
go func() {
err := httpSrv.ListenAndServe()
if err != nil {
log.Fatalf("httpSrv.ListenAndServe() failed with %s", err)
}
}()
}
var httpsSrv *http.Server
dataDir := "."
m := autocert.Manager{
Prompt: autocert.AcceptTOS,
HostPolicy: autocert.HostWhitelist(domain),
Cache: autocert.DirCache(dataDir),
}
httpsSrv = makeHTTPServer()
httpsSrv.Addr = ":443"
httpsSrv.TLSConfig = &tls.Config{GetCertificate: m.GetCertificate}
fmt.Printf("Starting HTTPS server on %s\n", httpsSrv.Addr)
err := httpsSrv.ListenAndServeTLS("", "")
if err != nil {
log.Fatalf("httpsSrv.ListendAndServeTLS() failed with %s", err)
}
}