diff --git a/http_server/echo/main.go b/http_server/echo/main.go index f9533fd..ab8cb0a 100644 --- a/http_server/echo/main.go +++ b/http_server/echo/main.go @@ -24,6 +24,7 @@ func main() { e.GET("/square", squareHandler) // POST Bodyの読み込み e.POST("/incr", incrementHandler) + e.POST("/fizzbuzz", fizzbuzzHandler) // 8080ポートで起動 e.Logger.Fatal(e.Start(":8080")) @@ -50,6 +51,9 @@ func squareHandler(c echo.Context) error { // 他のエラーの可能性もあるがサンプルとして纏める return echo.NewHTTPError(http.StatusBadRequest, "num is not integer") } + if num >= 100 { + return echo.NewHTTPError(http.StatusBadRequest, "num is over 100") + } // fmt.Sprintfでフォーマットに沿った文字列を生成できる。 return c.String(http.StatusOK, fmt.Sprintf("Square of %d is equal to %d", num, num*num)) } @@ -62,7 +66,43 @@ func incrementHandler(c echo.Context) error { return echo.NewHTTPError(http.StatusInternalServerError, "Internal Server Error") } counter += incrRequest.Num - return c.String(http.StatusOK, fmt.Sprintf("Value of Counter is %d \n", counter)) + + jsonMap := map[string]int{ + "counter": counter, + } + + return c.JSON(http.StatusOK, jsonMap) +} + +func fizzbuzzHandler(c echo.Context) error { + fizzbuzzRequest := fizzbuzzRequest{} + if err := c.Bind(&fizzbuzzRequest); err != nil { + return echo.NewHTTPError(http.StatusInternalServerError, "Internal Server Error") + } + + var fizzbuzz string + num := fizzbuzzRequest.Num + + switch { + case num%15 == 0: + fizzbuzz = "FIZZ BUZZ!" + case num%3 == 0: + fizzbuzz = "FIZZ!" + case num%5 == 0: + fizzbuzz = "BUZZ!" + default: + fizzbuzz = strconv.Itoa(num) + } + + jsonMap := map[string]string{ + "fizzbuzz": fizzbuzz, + } + + return c.JSON(http.StatusOK, jsonMap) +} + +type fizzbuzzRequest struct { + Num int `json:"num"` } type incrRequest struct { diff --git a/http_server/net_http/main.go b/http_server/net_http/main.go index 15c9f10..56c62d0 100644 --- a/http_server/net_http/main.go +++ b/http_server/net_http/main.go @@ -24,6 +24,8 @@ func main() { // POST Bodyの読み込み http.HandleFunc("/incr", incrementHandler) + http.HandleFunc("/fizzbuzz", fizzbuzzHandler) + // 8080ポートで起動 http.ListenAndServe(":8080", nil) } @@ -48,10 +50,16 @@ func squareHandler(w http.ResponseWriter, req *http.Request) { num, err := strconv.Atoi(numStr) if err != nil { // 他のエラーの可能性もあるがサンプルとして纏める - w.WriteHeader(http.StatusBadRequest) + w.WriteHeader(http.StatusMethodNotAllowed) fmt.Fprint(w, "num is not integer") return } + + if num >= 100 { + w.WriteHeader(http.StatusBadRequest) + fmt.Fprint(w, "too many numbers lol") + return + } // fmt.Sprintfでフォーマットに沿った文字列を生成できる。 fmt.Fprint(w, fmt.Sprintf("Square of %d is equal to %d", num, num*num)) } @@ -59,6 +67,11 @@ func squareHandler(w http.ResponseWriter, req *http.Request) { // Bodyから数字を取得してその数字だけCounterをIncrementするハンドラー // DBがまだないので簡易的なもの func incrementHandler(w http.ResponseWriter, req *http.Request) { + if req.Method != "POST" { + w.WriteHeader(http.StatusMethodNotAllowed) + fmt.Fprint(w, fmt.Sprintf("Only POST method is permitted\n")) + return + } body := req.Body // bodyの読み込みに開いたio Readerを最後にCloseする defer body.Close() @@ -74,6 +87,42 @@ func incrementHandler(w http.ResponseWriter, req *http.Request) { fmt.Fprint(w, fmt.Sprintf("Value of Counter is %d \n", counter)) } +func fizzbuzzHandler(w http.ResponseWriter, req *http.Request) { + if req.Method != "POST" { + fmt.Fprint(w, fmt.Sprintf("Only POST method is permitted\n")) + return + } + + body := req.Body + defer body.Close() + + buf := new(bytes.Buffer) + io.Copy(buf, body) + + var fizzbuzzRequest fizzbuzzRequest + json.Unmarshal(buf.Bytes(), &fizzbuzzRequest) + + var fizzbuzz string + num := fizzbuzzRequest.Num + + switch { + case num%15 == 0: + fizzbuzz = "FIZZ BUZZ!" + case num%3 == 0: + fizzbuzz = "FIZZ!" + case num%5 == 0: + fizzbuzz = "BUZZ!" + default: + fizzbuzz = strconv.Itoa(num) + } + + fmt.Fprint(w, fmt.Sprintf("%s\n", fizzbuzz)) +} + +type fizzbuzzRequest struct { + Num int `json:"num"` +} + type incrRequest struct { // jsonタグをつける事でjsonのunmarshalが出来る // jsonパッケージに渡すので、Publicである必要がある