-1

As a beginner of GO, I've got a situation as following:

t, err := template.ParseFiles("/template/login.tpl")

err = t.Execute(w, nil)         //if executed before SetCookie

http.SetCookie(...)          //failed, browser received nothing

If the sequence is changed, to SetCookie first, it'll work.

My plan was to ParseForm() username and password in login.tpl, if success, a sessionID would be sent by SetCookie. But now SetCookie() must be placed before login.tpl is Executed, which also makes ParseForm() run before login.tpl is executed :

r.ParseForm( )                          //ParseForm() works even before template is executed

email := r.FormValue("email")
pass := r.FormValue("pass")

var loginPass = checkLogin(email, pass) //verify username and password

if loginPass == true {                  //if correct

    cookie1 := http.Cookie{Name: "test", Value: "testvalue", Path: "/", MaxAge: 86400}
    http.SetCookie(w, &cookie1)         //setCookie works

    fmt.Println("Login success: ", email)

} else {                                //if incorrect username or pass

    fmt.Println("Please login: ", email)

}

t, err := template.ParseFiles("/template/login.tpl")
err = t.Execute(w, nil)                 //now template execution is here, also works

But why it should be written like this? Please anyone give me some advice! Thanks a lot.

Vasfed
  • 18,013
  • 10
  • 47
  • 53
eleecn
  • 1

1 Answers1

3

This is a common error tied to the HTTP protocol working: the cookie is sent in a header of the HTTP respo7nse, which cannot be changed after the body start being sent.

So, when you do the t.Execute(w, nil) call, you start writing the body of the response and thus cannot add cookies afterwards.

This is the exact same reason why in PHP the session_start() call must be the very first instruction of the page, even before any whitespace.

Elwinar
  • 9,103
  • 32
  • 40