'How to save cookies in browser using GO + REACT?
I created a login page using react over Go rest-API but I found that Browser did not save cookie established in the login phase. I tried a number of similar issues solved over stackoverflow but none of them worked for me. -- I wish anyone can help me resolve that issue
GO - Backend
func main(){
HandleRequests()
}
func HandleRequests(){
r := mux.NewRouter().StrictSlash(true)
r.HandleFunc("/login", Middleware(Login)).Methods("POST")
handler := cors.Default().Handler(r)
log.Fatal(http.ListenAndServe(":8081", handler))
}
func Middleware(h http.HandlerFunc) http.HandlerFunc {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "application/json")
h.ServeHTTP(w, r)
})
}
func Login(w http.ResponseWriter, r *http.Request) {
/*
Compare Both User Name && Password
READ - BODY
Create New JWT
*/
cookie := &http.Cookie{
Name: "jwt",
Value: token,
Expires: time.Now().Add(time.Minute * 60),
HttpOnly: true,
}
http.SetCookie(w, cookie)
respondWithJson(w, http.StatusOK, struct {
Ok string `json:"ok"`
}{
Ok: "Success, Welcome back our friend !",
})
}
func respondWithJson(w http.ResponseWriter, code int, payload interface{}) {
response, _ := json.Marshal(payload)
w.Header().Set("Content-Type", "application/json")
w.WriteHeader(code)
w.Write(response)
}
REACT - Router - Frontend React Runs over, http://localhost:3000
import React, { SyntheticEvent, useState } from 'react';
import { Redirect } from 'react-router-dom';
const Login = () => {
const[username, setUsername] = useState('');
const[password, setPassword] = useState('');
const[redirect, setRedirect] = useState(false)
const submit = async (e : SyntheticEvent) => {
e.preventDefault();
await fetch('http://localhost:8081/login', {
method : 'POST',
headers: {'Content-Type':'application/json'},
body: JSON.stringify({
username,
password
}),
credentials:'include'
});
setRedirect(true);
}
if (redirect) {
return <Redirect to = "/"/>;
}
return (
<form onSubmit={submit}>
<h1 className="h3 mb-3 fw-normal">Please sign in</h1>
<input type="text" className="form-control" placeholder="Username" required
onChange = {e => setUsername(e.target.value)}/>
<input type="password" className="form-control" placeholder="Password" required
onChange = {e => setPassword(e.target.value)}/>
<div className="checkbox mb-3">
<label>
<input type="checkbox" value="remember-me" /> Remember me
</label>
</div>
<button className="w-100 btn btn-lg btn-primary" type="submit">Sign in</button>
</form>
);
};
Solution 1:[1]
Browser can't save cookie because HttpOnly options is true. If you want to save cookies to client browser, set your HttpOnly option false. but this is not safe to defend XSS attack.
cookie := &http.Cookie{
Name: "jwt",
Value: token,
Expires: time.Now().Add(time.Minute * 60),
HttpOnly: false,
}
Solution 2:[2]
To include de Cookie generated by Go in the Request to your server the required code is:
cookie := &http.Cookie{
Name: "jwt",
Value: token,
Expires: time.Now().Add(time.Minute * 60),
HttpOnly: true,
Secure: true,
SameSite: http.SameSiteNoneMode, // if you pretend to enable cross-site
}
Note: HttpOnly, Secure and SameSite is required.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | |
| Solution 2 | erikwco |
