-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathmain.go
95 lines (77 loc) · 2.05 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
88
89
90
91
92
93
94
95
package main
import (
"encoding/json"
"fmt"
"log"
"net/http"
"os"
"regexp"
"time"
"internal/callback"
"internal/urlshortener"
"github.com/gorilla/mux"
)
var shortener *urlshortener.Shortener
type shortenParams struct {
Url string `json:"url"`
}
func shorten(w http.ResponseWriter, r *http.Request) {
var params shortenParams
json.NewDecoder(r.Body).Decode(¶ms)
shortUrl, err := shortener.CreateShortUrl(params.Url)
if err != nil {
log.Fatalln(err)
}
body := map[string]string{"shortUrl": shortUrl}
json_body, _ := json.Marshal(body)
w.Write(json_body)
}
func redirect(w http.ResponseWriter, r *http.Request) {
params := mux.Vars(r)
id := params["id"]
clientIp := r.Header.Get("x-forwarded-for")
if clientIp == "" {
re := regexp.MustCompile(`:\d+`)
clientIp = re.ReplaceAllString(r.RemoteAddr, "") // strip port number
}
fmt.Printf("Received request from %s: %s\n", clientIp, id)
url, err := shortener.UseShortUrl(id)
if err != nil {
w.WriteHeader(http.StatusNotFound)
fmt.Fprintf(w, "%s", err)
return
}
http.Redirect(w, r, url, http.StatusTemporaryRedirect)
if shortener.HasCallbackUrl() { // don't callback if the url is not configured
data := &callback.Callback{
EventType: "click",
MsgId: id,
Link: url,
ClickTime: time.Now().Unix(),
UserAgent: r.Header.Get("User-Agent"),
ClientIp: clientIp,
}
go callback.Clicked(shortener.CallbackUrl, data)
}
}
func stats(w http.ResponseWriter, r *http.Request) {
stats := shortener.Stats()
body, _ := json.Marshal(stats)
w.Write(body)
}
func main() {
if len(os.Args) < 2 {
log.Fatalf("Usage: %s configuration.yaml", os.Args[0])
}
file := os.Args[1]
shortener = urlshortener.New(file)
authToken := os.Getenv("AUTH_TOKEN")
if authToken == "" {
log.Fatalln("AUTH_TOKEN missing in environment")
}
r := mux.NewRouter()
r.HandleFunc("/shorten", shorten).Methods("POST").HeadersRegexp("X-Auth-Token", authToken)
r.HandleFunc("/stats", stats).Methods("GET")
r.HandleFunc("/{id}", redirect).Methods("GET")
log.Fatal(http.ListenAndServe(":8080", r))
}