Help us understand the problem. What is going on with this article?

[GO]GOを使ってCookieでFlashMessageを作る

More than 1 year has passed since last update.

1. Cookieの作成

まずはじめにクッキーを作成します。

func setMessage(w http.ResponseWriter, r *http.Request) {
    msg := []byte("Hello World")
   //ヘッダ内ではクッキーの値をURLエンコードする必要があるらしい
    c := http.Cookie{
      Name:   "Qiita",
      Value: base64.URLEncoding.EncodeToString(msg),
    HttpOnly: true
    }
    http.SetCookie(w, &c)
}

2. Cookieを元にフラッシュメッセージを作成

func showMessage(w http.ResponseWriter, r *http.Request){
   //構造体Requestの中には名前付きクッキーを取り出せるCookieメソッドがある。
  //Name: "Qiita"のクッキーを探す、ない場合はerrにエラー文が入る。
    c, err := r.Cookie("Qiita")
    if err != nil {
        if err == http.ErrNoCookie{
            fmt.Fprintln(w, "メッセージがありません")
            //fmt.Fprintln(w, err)
            //エラー文が見たい人は上のコメントアウト外してみて
        }
    } else {
        rc := http.Cookie{
            Name: "Qiita",
            MaxAge: -1,
            Expires: time.Unix(1,0),
        }
        http.SetCookie(w, &rc)
        val, _ := base64.URLEncoding.DecodeString(c.Value)
        fmt.Fprintln(w, string(val))
    }
}

3. 作ったハンドラ関数(showMessage, setMessage)をハンドラに変換、マルチプレクサにぶち込む

func main() {

    server := http.Server{
        Addr: "127.0.0.1:8080",
    }
    http.HandleFunc("/set_message", setMessage)
    http.HandleFunc("/show_message", showMessage)

    server.ListenAndServe()
}

完成形

main.go
package main

import (
"encoding/base64"
"fmt"
"net/http"
"time"
)

func setMessage(w http.ResponseWriter, r *http.Request){
    msg := []byte("Hello World")
    c := http.Cookie{
        Name: "Qiita",
        Value: base64.URLEncoding.EncodeToString(msg),
    }
    http.SetCookie(w, &c)
}


func showMessage(w http.ResponseWriter, r *http.Request){
    //名前付きクッキーを取り出すメソッドCookie、指定したクッキーがないときエラーを返す
    c, err := r.Cookie("Qiita")

    //Name: "cookie"のcookieの構造体が存在しないとエラー文"http: named cookie not present"が送られてくる。
    if err != nil {
        if err == http.ErrNoCookie{
            fmt.Fprintln(w, "メッセージがありません")
            fmt.Fprintln(w, err)
        }
    } else {
        rc := http.Cookie{
            Name: "Qiita",
            MaxAge: -1,
            Expires: time.Unix(1,0),
        }
        http.SetCookie(w, &rc)
        val, _ := base64.URLEncoding.DecodeString(c.Value)
        fmt.Fprintln(w, string(val))
    }
}

func main() {
    server := http.Server{
        Addr: "127.0.0.1:8080",
    }

    http.HandleFunc("/set_message", setMessage)
    http.HandleFunc("/show_message", showMessage)

    server.ListenAndServe()
}

検証

まずビルドして

$go build main.go
$./main

http://127.0.0.1.8080/set_messageを開いてみてください
chromeの検証機能を使ってCookieが作られていることが確認できますね

スクリーンショット 2019-02-13 18.41.17.png

次に、http://127.0.0.1:8080/show_messageを開いてみてください。

Hello Wold

と出ましたでしょうか?

スクリーンショット 2019-02-13 18.41.38.png

検証機能を使えばcookieが消えていることがわかります。

最後にCookieの構造体(モデル)載せておきますね〜

Cookie_struct.go
type Cookie struct{
 Name:           string
 Value:          string
 Path:           string
 Domain:         string
 Expires:        time.Time
 RawExpires:     string
 MaxAge:         int
 Secure:         bool
 HttpOnly:       bool
 Raw:            string
 Unparsed:       []string
}
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away