// shutdown: process exit with logging. func shutdown(reason shutdownCause) { // close down the storage connections storage.Close() // for testing: run alternateShutdown instead, if defined if alternateShutdown != nil { alternateShutdown(reason) panic(reason) // shouldn't get here } // log reason for shutdown and exit switch reason { case unknownShutdown: log.Fatal("Exiting: normal shutdown.") case startupFailureShutdown: log.Fatal("Exiting: initialization failure.") case runtimeFailureShutdown: log.Fatal("Exiting: runtime failure.") case caughtSignalShutdown: log.Fatal("Exiting: caught signal.") case listenerFailureShutdown: log.Fatal("Exiting: web server failed.") default: log.Fatal("Exiting: unknown cause.") } }
func TestNullInput(t *testing.T) { testSetup(t) defer storage.Close() null := new(bytes.Buffer) err := listener(os.Stdout, null) if err != nil { t.Fatalf("CLI failure: %v", err) } }
func TestMarkdown(t *testing.T) { testSetup(t) defer storage.Close() in := bytes.NewBufferString("markdown\nmarkdown on\nmarkdown off\n") out := new(bytes.Buffer) err := listener(out, in) if err != nil { t.Fatalf("CLI failure: %v", err) } expected := "Markdown is off\nMarkdown is on\nMarkdown is off\n" result := out.String() if result != expected { t.Errorf("Got %q, expected %q", result, expected) } }
func TestBackFail(t *testing.T) { testSetup(t) defer storage.Close() in := bytes.NewBufferString("back\n") out := new(bytes.Buffer) err := listener(out, in) if err != nil { t.Fatalf("CLI failure: %v", err) } expected := "No choices to undo.\n" result := out.String() if result != expected { t.Errorf("Got %q, expected %q", result, expected) } }
func main() { // log initialization log.SetOutput(os.Stderr) // storage initialization cacheId, databaseId, err := storage.Connect() if err != nil { log.Printf("Error during storage initialization: %v", err) os.Exit(1) } defer storage.Close() log.Printf("Connected to cache at %q", cacheId) log.Printf("Connected to database at %q", databaseId) // serve err = listener(os.Stdout, os.Stdin) if err != nil { log.Printf("CLI failure: %v", err) os.Exit(1) } os.Exit(0) }
func TestIssue11(t *testing.T) { storageConnect(t, "TestIssue11") defer storage.Close() // server srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { if testing.Short() { t.Logf("Handling %s %s...", r.Method, r.URL.Path) } s := &session{sid: getCookie(w, r)} s.load(w, r) s.rootHandler(w, r) })) defer srv.Close() // client jar, e := cookiejar.New(nil) if e != nil { t.Fatalf("Failed to create cookie jar: %v", e) } c := http.Client{Jar: jar} // for each test puzzle for _, td := range testData { r, e := c.Get(srv.URL + "/reset/" + td.name) if e != nil || r.StatusCode != http.StatusOK { t.Fatalf("Request error on /reset/%s: %v", td.name, e) } // read the puzzle contents r, e = c.Get(srv.URL + "/api/state") if e != nil { t.Fatalf("State before request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("State before status was %v not %v", r.StatusCode, http.StatusOK) } stateOriginal, e := ioutil.ReadAll(r.Body) r.Body.Close() if e != nil { t.Fatalf("Read error on original state: %v", e) } // do the assignments for i, choice := range td.choices { b, e := json.Marshal(choice) if e != nil { t.Fatalf("Case %d: Failed to encode choice: %v", i, e) } r, e := c.Post(srv.URL+"/api/assign", "application/json", strings.NewReader(string(b))) if e != nil { t.Fatalf("assignment %d: Request error: %v", i, e) } if r.StatusCode != http.StatusOK { t.Errorf("case %d: Status was %v, expected %v", i, r.StatusCode, http.StatusOK) } _, e = ioutil.ReadAll(r.Body) r.Body.Close() if e != nil { t.Fatalf("test %d: Read error on update: %v", i, e) } } // read the puzzle contents r, e = c.Get(srv.URL + "/api/state") if e != nil { t.Fatalf("State before request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("State before status was %v not %v", r.StatusCode, http.StatusOK) } stateBefore, e := ioutil.ReadAll(r.Body) r.Body.Close() if e != nil { t.Fatalf("Read error on state before: %v", e) } // read the puzzle contents again, compare r, e = c.Get(srv.URL + "/api/state") if e != nil { t.Fatalf("State after request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("State after status was %v not %v", r.StatusCode, http.StatusOK) } stateAfter, e := ioutil.ReadAll(r.Body) r.Body.Close() if e != nil { t.Fatalf("Read error on state after: %v", e) } if string(stateAfter) != string(stateBefore) { t.Errorf("States don't match before (%+v) and after (%+v).", stateBefore, stateAfter) } // now go back over all the choices for i := range td.choices { r, e = c.Get(srv.URL + "/api/back/") if e != nil { t.Fatalf("Go Back %d error: %v", i, e) } if r.StatusCode != http.StatusOK { t.Errorf("Go Back %d status was %v not %v", i, r.StatusCode, http.StatusOK) } } // read the puzzle contents r, e = c.Get(srv.URL + "/api/state") if e != nil { t.Fatalf("State before request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("State before status was %v not %v", r.StatusCode, http.StatusOK) } stateEnding, e := ioutil.ReadAll(r.Body) r.Body.Close() if e != nil { t.Fatalf("Read error on ending state: %v", e) } if string(stateOriginal) != string(stateEnding) { t.Errorf("States don't match original (%+v) and ending (%+v).", stateOriginal, stateEnding) } } }
func TestIssue1(t *testing.T) { storageConnect(t, "TestIssue1") defer storage.Close() // server srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { s := &session{sid: getCookie(w, r)} s.load(w, r) if testing.Short() { t.Logf("Session %v handling %s %s.", s.sid, r.Method, r.URL.Path) } http.Error(w, "This is a test", http.StatusOK) })) defer srv.Close() // client jar, e := cookiejar.New(nil) if e != nil { t.Fatalf("Failed to create cookie jar: %v", e) } c := http.Client{Jar: jar} // for each heroku protocol indicator, do two pairs of // requests, one to get the cookie set, one to use it. We // also handle the case where there is no heroku protocol // indicator, which is a bit of overkill, since no server // should get both Heroku and non-Heroku requests, but you // never know :). for i, herokuProtocol := range []string{"", "http", "https"} { for j, expectSetCookie := range []bool{true, false} { target := fmt.Sprintf("%s/home", srv.URL) req, e := http.NewRequest("GET", target, nil) if e != nil { t.Fatalf("Failed to create request %d: %v", 2*i+j, e) } if herokuProtocol != "" { req.Header.Add("X-Forwarded-Proto", herokuProtocol) } r, e := c.Do(req) if e != nil { t.Fatalf("Request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("Got status %q, expected OK", r.Status) } r.Body.Close() if expectSetCookie { if h := r.Header.Get("Set-Cookie"); h == "" { t.Errorf("No Set-Cookie received on request %d.", 2*i+j) } } else { if h := r.Header.Get("Set-Cookie"); h != "" { t.Errorf("Set-Cookie received on request %d.", 2*i+j) } } } } // now make sure the protocol cookies are set for the next round for i, herokuProtocol := range []string{"", "http", "https"} { for j, expectSetCookie := range []bool{false, false} { target := fmt.Sprintf("%s", srv.URL) req, e := http.NewRequest("GET", target, nil) if e != nil { t.Fatalf("Failed to create request %d: %v", 2*i+j, e) } if herokuProtocol != "" { req.Header.Add("X-Forwarded-Proto", herokuProtocol) } r, e := c.Do(req) if e != nil { t.Fatalf("Request error: %v", e) } if r.StatusCode != http.StatusOK { t.Errorf("Got status %q, expected OK", r.Status) } r.Body.Close() if expectSetCookie { if h := r.Header.Get("Set-Cookie"); h == "" { t.Errorf("No Set-Cookie received on request %d.", 2*i+j) } } else { if h := r.Header.Get("Set-Cookie"); h != "" { t.Errorf("Set-Cookie received on request %d.", 2*i+j) } } } } }