func ConsoleHandler(w http.ResponseWriter, r *http.Request) { c := appengine.NewContext(r) ds := appwrap.NewAppengineDatastore(c) if strings.HasSuffix(r.URL.Path, "/job") { id, _ := strconv.ParseInt(r.FormValue("id"), 10, 64) jobKey := datastore.NewKey(c, JobEntity, "", id, nil) q := datastore.NewQuery(TaskEntity).Filter("Job =", jobKey) var tasks []JobTask taskKeys, err := q.GetAll(c, &tasks) if err != nil { http.Error(w, "Internal error: "+err.Error(), http.StatusInternalServerError) return } running := 0 pending := 0 done := 0 failed := 0 for i := range tasks { switch tasks[i].Status { case TaskStatusPending: pending++ case TaskStatusRunning: running++ case TaskStatusDone: done++ case TaskStatusFailed: failed++ } } t := template.New("main") t, _ = t.Parse(jobPage) err = t.Execute(w, struct { Id int64 Tasks []JobTask TaskKeys []*datastore.Key Pending, Running, Done, Failed int }{id, tasks, taskKeys, pending, running, done, failed}) if err != nil { http.Error(w, "Internal error: "+err.Error(), http.StatusInternalServerError) return } } else if strings.HasSuffix(r.URL.Path, "/delete") { id, _ := strconv.ParseInt(r.FormValue("id"), 10, 64) if err := RemoveJob(ds, id); err != nil { http.Error(w, "Internal error: "+err.Error(), http.StatusInternalServerError) return } jobList(w, r, id) } else { jobList(w, r, 0) } }
func (h urlHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) { c := h.getContext(r) ds := appwrap.NewAppengineDatastore(c) monitorTimeout := time.Minute * 30 if appengine.IsDevAppServer() { monitorTimeout = time.Second * 10 } if strings.HasSuffix(r.URL.Path, "/map-monitor") || strings.HasSuffix(r.URL.Path, "/reduce-monitor") { if jobKeyStr := r.FormValue("jobKey"); jobKeyStr == "" { http.Error(w, "jobKey parameter required", http.StatusBadRequest) } else if jobKey, err := datastore.DecodeKey(jobKeyStr); err != nil { http.Error(w, fmt.Sprintf("invalid jobKey: %s", err.Error()), http.StatusBadRequest) } else if strings.HasSuffix(r.URL.Path, "/map-monitor") { w.WriteHeader(mapMonitorTask(c, ds, h.pipeline, jobKey, r, monitorTimeout)) } else { w.WriteHeader(reduceMonitorTask(c, ds, h.pipeline, jobKey, r, monitorTimeout)) } return } var taskKey *datastore.Key var err error if taskKeyStr := r.FormValue("taskKey"); taskKeyStr == "" { http.Error(w, "taskKey parameter required", http.StatusBadRequest) return } else if taskKey, err = datastore.DecodeKey(taskKeyStr); err != nil { http.Error(w, fmt.Sprintf("invalid taskKey: %s", err.Error()), http.StatusBadRequest) return } if strings.HasSuffix(r.URL.Path, "/reduce") { reduceTask(c, ds, h.baseUrl, h.pipeline, taskKey, w, r) } else if strings.HasSuffix(r.URL.Path, "/map") { mapTask(c, ds, h.baseUrl, h.pipeline, taskKey, w, r) } else if strings.HasSuffix(r.URL.Path, "/mapstatus") || strings.HasSuffix(r.URL.Path, "/reducestatus") { updateTask(ds, taskKey, "", 0, r.FormValue("msg"), nil) } else { http.Error(w, "unknown request url", http.StatusNotFound) return } }