Golang を使ってウェブサーバに POST する最小限のサンプルをつくる。 POSTを受けるサーバは Micronaut で用意する。
なお、OS は Ubuntu 20.04, go version go1.16.4 linux/amd64, Micronaut Version: 2.5.7 で試しています。
$ mn create-app myapp --build=gradle --lang=groovy
$ cd myapp
$ mn create-controller item
生成したコントローラ src/main/groovy/myapp/ItemController.groovy を編集:
package myapp
import io.micronaut.http.annotation.Controller
import io.micronaut.http.annotation.Post
import io.micronaut.http.annotation.Body
@Controller("/item")
class ItemController {
@Post(uri="/", consumes=["application/json"], produces="text/plain")
String index(@Body def contents) {
contents.toString()
}
}
http://localhost:8080/item/ に POST すると POST された内容をそのままオウム返します。
./gradlew run
してサーバを起動しておきます。
$ curl -X POST "http://localhost:8080/item/" -d '{ "hello": "world" }' -H "Content-Type: application/json"
{ "hello": "world" }
できました。
curl と同じ機能を果たすクライアントを実装します。
$ mkdir client
$ cd client
$ go mod init client
main.go を準備:
package main
import (
"bytes"
"fmt"
"io/ioutil"
"net/http"
"time"
)
type Params struct {
url string
json string
}
func contents(resp *http.Response) (string, error) {
b, err := ioutil.ReadAll(resp.Body)
if err != nil {
return "", err
}
return string(b), nil
}
func doPost(params *Params) (string, error) {
req, err := http.NewRequest("POST", params.url, bytes.NewBuffer([]byte(params.json)))
if err != nil {
return "", err
}
client := &http.Client{Timeout: time.Second * 10}
response, err := client.Do(req)
if err != nil {
return "", err
}
defer response.Body.Close()
statusCode := response.StatusCode
if statusCode != 200 {
return "", fmt.Errorf("StatusCode %d is not expected.", statusCode)
}
result, err := contents(response)
if err != nil {
return "", err
}
return result, nil
}
func main() {
params := Params{
url: "http://localhost:8080/item/",
json: "{\"hello\":\"world\"}",
}
result, err := doPost(¶ms)
if err != nil {
fmt.Println(fmt.Errorf("Got error %s", err.Error()))
}
fmt.Println( fmt.Sprintf("%s", result) )
}
実行:
$ go run main.go
{"hello":"world"}
できました。