OLD | NEW |
---|---|
1 package main | 1 package main |
2 | 2 |
3 import ( | 3 import ( |
4 "encoding/json" | |
4 "flag" | 5 "flag" |
5 "net/http" | 6 "net/http" |
6 ) | 7 » "time" |
7 | 8 |
8 import ( | |
9 "github.com/golang/glog" | 9 "github.com/golang/glog" |
10 "github.com/gorilla/mux" | |
11 | |
12 "skia.googlesource.com/buildbot.git/go/database" | |
13 "skia.googlesource.com/buildbot.git/golden/go/analysis" | |
14 "skia.googlesource.com/buildbot.git/golden/go/db" | |
15 "skia.googlesource.com/buildbot.git/golden/go/expstorage" | |
16 "skia.googlesource.com/buildbot.git/golden/go/filediffstore" | |
17 "skia.googlesource.com/buildbot.git/perf/go/filetilestore" | |
10 ) | 18 ) |
11 | 19 |
12 // flags | 20 // flags |
13 var ( | 21 var ( |
14 » port = flag.String("port", ":9000", "HTTP service address (e.g., ': 9000')") | 22 » port = flag.String("port", ":9000", "HTTP service address (e.g., ':9000')") |
15 » staticDir = flag.String("static", "./app", "Directory with static conten t to serve") | 23 » local = flag.Bool("local", false, "Running locally if true. As op posed to in production.") |
24 » staticDir = flag.String("static_dir", "./app", "Directory with static content to serve") | |
25 » tileStoreDir = flag.String("tile_store_dir", "/tmp/tileStore", "What dir ectory to look for tiles in.") | |
26 » imageDiffDir = flag.String("image_diff_dir", "/tmp/imagediffdir", "What directory to store diff images in.") | |
27 » gsBucketName = flag.String("gs_bucket", "chromium-skia-gm", "Name of the google storage bucket that holds uploaded images.") | |
28 » mysqlConnStr = flag.String("mysql_conn", "", "MySQL connection string fo r backend database. If 'local' is false the password in this string will be subs tituted via the metadata server.") | |
29 » sqlitePath = flag.String("sqlite_path", "./golden.db", "Filepath of th e embedded SQLite database. Requires 'local' to be set to true and 'mysql_conn' to be empty to take effect.") | |
30 ) | |
16 | 31 |
17 // TODO (stephana): Just ideas to be sorted out later | 32 // Response envelope. All responses follow this format. Some fields might |
jcgregorio
2014/10/18 00:09:03
Comments begin with the name of the thing being de
stephana
2014/10/20 12:56:08
Done.
| |
18 // tempDir = flag.String("temp", "./.cache", | 33 // be empty depending on context. |
19 // "Directory to store temporary file and application cache") | 34 type ResponseEnvelope struct { |
20 ) | 35 » Data *interface{} `json:"data"` |
36 » Err *string `json:"err"` | |
37 » Status int `json:"status"` | |
38 } | |
39 | |
40 var analyzer *analysis.Analyzer = nil | |
41 | |
42 // Get the aggregated counts | |
43 func tileCountsHandler(w http.ResponseWriter, r *http.Request) { | |
44 » result, err := analyzer.GetTileCounts() | |
45 » if err != nil { | |
46 » » sendErrorResponse(w, err.Error(), http.StatusInternalServerError ) | |
47 » » return | |
48 » } | |
49 | |
50 » sendResponse(w, result, http.StatusOK) | |
51 } | |
52 | |
53 // Process a diff request send via HTTP. | |
jcgregorio
2014/10/18 00:09:03
sent
stephana
2014/10/20 12:56:08
Done.
| |
54 func testCountsHandler(w http.ResponseWriter, r *http.Request) { | |
55 » testName := mux.Vars(r)["testname"] | |
56 » result, err := analyzer.GetTestCounts(testName) | |
57 » if err != nil { | |
58 » » sendErrorResponse(w, err.Error(), http.StatusInternalServerError ) | |
59 » » return | |
60 » } | |
61 | |
62 » sendResponse(w, result, http.StatusOK) | |
63 } | |
64 | |
65 // Send an error response with the given error message. | |
66 func sendErrorResponse(w http.ResponseWriter, errorMsg string, status int) { | |
67 » resp := ResponseEnvelope{nil, &errorMsg, status} | |
68 » sendJson(w, &resp) | |
69 } | |
70 | |
71 // Send a non-error response with the given data. | |
72 func sendResponse(w http.ResponseWriter, data interface{}, status int) { | |
73 » resp := ResponseEnvelope{&data, nil, status} | |
74 » sendJson(w, &resp) | |
75 } | |
76 | |
77 // Sends the response envelope rendered as JSON. | |
78 func sendJson(w http.ResponseWriter, resp *ResponseEnvelope) { | |
79 » jsonBytes, err := json.Marshal(resp) | |
80 » if err != nil { | |
81 » » http.Error(w, err.Error(), http.StatusInternalServerError) | |
82 » » return | |
83 » } | |
84 | |
85 » w.Header().Set("Content-Type", "application/json") | |
86 » w.Write(jsonBytes) | |
87 } | |
21 | 88 |
22 func main() { | 89 func main() { |
23 // parse the arguments | 90 // parse the arguments |
24 flag.Parse() | 91 flag.Parse() |
25 | 92 |
26 » // // Static file handling | 93 » // Get the expecations storage, the filediff storage and the tilestore. |
27 » http.Handle("/", http.FileServer(http.Dir(*staticDir))) | 94 » diffStore := filediffstore.NewFileDiffStore(nil, *imageDiffDir, *gsBucke tName) |
95 » vdb := database.NewVersionedDB(db.GetDatabaseConfig(*mysqlConnStr, *sqli tePath, *local)) | |
96 » expStore := expstorage.NewSQLExpectationStore(vdb) | |
97 » tileStore := filetilestore.NewFileTileStore(*tileStoreDir, "golden", -1) | |
28 | 98 |
29 » // Wire up the resources | 99 » // Initialize the Analyzer |
100 » analyzer = analysis.NewAnalyzer(expStore, tileStore, diffStore, 5*time.M inute) | |
101 | |
102 » router := mux.NewRouter() | |
103 | |
104 » // Wire up the resources. We use the 'rest' prefix to avoid any name | |
105 » // clashes witht the static files being served. | |
106 » // TODO (stephana): Wrap the handlers in autogzip unless we defer that t o | |
107 » // the front-end proxy. | |
108 » router.HandleFunc("/rest/tilecounts", tileCountsHandler) | |
109 » router.HandleFunc("/rest/tilecounts/{testname}", testCountsHandler) | |
110 | |
111 » // Everything else is served out of the static directory. | |
112 » router.PathPrefix("/").Handler(http.FileServer(http.Dir(*staticDir))) | |
113 | |
114 » // Send all requests to the router | |
115 » http.Handle("/", router) | |
30 | 116 |
31 // Start the server | 117 // Start the server |
32 glog.Infoln("Serving on http://127.0.0.1" + *port) | 118 glog.Infoln("Serving on http://127.0.0.1" + *port) |
33 glog.Fatal(http.ListenAndServe(*port, nil)) | 119 glog.Fatal(http.ListenAndServe(*port, nil)) |
34 } | 120 } |
OLD | NEW |