Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

fetch: Getting cookies from fetch response

I'm trying to implement client login using fetch on react.

I'm using passport for authentication. The reason I'm using fetch and not regular form.submit(), is because I want to be able to recieve error messages from my express server, like: "username or password is wrong".

I know that passport can send back messages using flash messages, but flash requires sessions and I would like to avoid them.

This is my code:

fetch('/login/local', {
      method: 'POST',
      headers: {
        Accept: 'application/json',
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        username: this.state.username,
        password: this.state.password,
      }),
    }).then(res => {
      console.log(res.headers.get('set-cookie')); // undefined
      console.log(document.cookie); // nope
      return res.json();
    }).then(json => {
      if (json.success) {
        this.setState({ error: '' });
        this.context.router.push(json.redirect);
      }
      else {
        this.setState({ error: json.error });
      }
    });

The server sends the cookies just fine, as you can see on chrome's dev tools: Network - Cookies Network - Headers

But chrome doesn't set the cookies, in Application -> Cookies -> localhost:8080: "The site has no cookies".

Any idea how to make it work?

like image 278
Gershon Papi Avatar asked Aug 28 '16 05:08

Gershon Papi


People also ask

Does fetch automatically send cookies?

If you set credentials to same-origin : Fetch will send 1st party cookies to its own server. It will not send cookies to other domains or subdomains. If you set credentials to include : Fetch will continue to send 1st party cookies to its own server.

How do you pass cookies in fetch request?

If you want to pass cookies with this request, you can do so by passing the credentials option to the fetch request. fetch("http://example.com/data.json", { credentials: "same-origin" }) . then(response => response. json()) .

How do I get data from a fetch response?

Use the fetch() method to return a promise that resolves into a Response object. To get the actual data, you call one of the methods of the Response object e.g., text() or json() . These methods resolve into the actual data.

How do you get response cookies in react?

In class-based components, you can get the cookie by using a withCookies() higher-order component. import React, { Component } from "react"; import { withCookies } from "react-cookie"; class App extends Component { state = { // getting the cookie user: this. props. cookies.


1 Answers

The problem turned out to be with the fetch option credentials: same-origin/include not being set. As the fetch documentation mentions this option to be required for sending cookies on the request, it failed to mention this when reading a cookie.

So I just changed my code to be like this:

fetch('/login/local', {
      method: 'POST',
      headers: {
        Accept: 'application/json',
        'Content-Type': 'application/json',
      },
      credentials: 'same-origin',
      body: JSON.stringify({
        username: this.state.username,
        password: this.state.password,
      }),
    }).then(res => {
      return res.json();
    }).then(json => {
      if (json.success) {
        this.setState({ error: '' });
        this.context.router.push(json.redirect);
      }
      else {
        this.setState({ error: json.error });
      }
    });
like image 152
Gershon Papi Avatar answered Sep 28 '22 19:09

Gershon Papi