14

I'm developing a user login/register feature as part of a larger project and am working on localhost (apollo server and react apollo front-end). I'm using express-session for my sessions.

When submitting my login I can see the response header has set-cookie inside, but its not set in Application->Cookies.

I've tried different browsers, using createHttpLink, apollo-boost, and using include & same-origin (using same-origin).

I've been trying to get this working for 2 weeks now and have run out of things to try, this was my last option! I know its going to be something really trivial but I just can't see it.

If I use GraphqL Playground and change the settings to include credentials, I can see the cookie being set there.

Server is running on localhost:8080/graphql Client is running on localhost:3000

Client:

const client = new ApolloClient({
    link: new HttpLink({
        uri: 'http://localhost:8080/graphql',
        credentials: 'same-origin',
    }),
    cache: new InMemoryCache()
});

Cors:

app.use(
    cors({ 
        origin: 'http://localhost:3000',
        credentials: true
    })
);

Express-Session:

app.use(
    session({
        name: "sess",
        secret: process.env.SESSION_SECRET,
        resave: false,
        saveUninitialized: false,
        cookie: {
            httpOnly: true,
            secure: false,
            maxAge: 1000 * 60 * 60 * 24 * 7,
        },
    })
);

Response Cookie:

HTTP/1.1 200 OK
X-Powered-By: Express
Access-Control-Allow-Origin: *
Vary: Origin
Access-Control-Allow-Credentials: true
Content-Type: application/json
Content-Length: 69
set-cookie: sess=s%3AAZXnGb5BVc1aAOwH6zBNiT8mB6Ebf75k.in%2BPU1OvxymDPdPIZBf8%2FQzrRmM0S04tXFzXDwYCnk8; Path=/; Expires=Sat, 03 Nov 2018 13:59:57 GMT; HttpOnly
Date: Sat, 27 Oct 2018 13:59:57 GMT
Connection: keep-alive
Michael Ross
  • 139
  • 1
  • 4
  • 1
    Localhost:3000 and localhost:8080 are not the same origin, so they cannot share cookies using credentials: same-origin. – Benjie Oct 27 '18 at 14:33
  • I get multiple CORS policy errors when I try to use include, either: "The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'." OR "Request header field content-type is not allowed by Access-Control-Allow-Headers in preflight response." – Michael Ross Oct 27 '18 at 15:31

5 Answers5

3

I had the same issue. Incase you're still looking for an answer after 2 years set credentials in the client to "include" like this:

const client = new ApolloClient({
  uri: 'http://localhost:4000/graphql',
  cache: new InMemoryCache(),
  credentials: 'include'
});
ChristianYami
  • 586
  • 1
  • 9
  • 17
2

I tried to fix it by using express. But it didn't work with Apollo GraphQL.

const corsOptions = {
    origin: "http://localhost:3000",
    credentials: true
  };
app.use(cors(corsOptions));

So, I tried configuring cors inside GraphQL server and It Worked.

For Apollo Server

const corsOptions = {
    origin: "http://localhost:3000",
    credentials: true
  };

const server = new ApolloServer({
  typeDefs,
  resolvers,
  cors: corsOptions
});

server.listen().then(({ url }) => {
  console.log(` Server ready at ${url}`);
});

For GraphQL Yoga

const options = {
  cors: corsOptions
};

server.start(options, () =>
  console.log("Server is running on http://localhost:4000")
);
l3lackcurtains
  • 162
  • 3
  • 6
0

The issue seems to be one of CORS configuration. First, change the HttpLink to use credentials: 'include'; then try this CORS middleware:

app.use(
  cors({ 
    origin: 'http://localhost:3000',
    credentials: true,
    allowedHeaders: ['Content-Type', 'Authorization'],
  })
);

If you still get the error The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'. then it suggests that the CORS middleware is not correctly setting Access-Control-Allow-Origin: http://localhost:3000 (your example shows it is returning * but I'm not sure if this was a copy/paste issue, since the cors module docs suggest this should work.)

Benjie
  • 7,701
  • 5
  • 29
  • 44
  • 2
    Thanks for the reply, I just keep getting this: `Access to fetch at 'http://localhost:8080/graphql' from origin 'http://localhost:3000' has been blocked by CORS policy: The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'.` – Michael Ross Nov 02 '18 at 21:55
0

I managed to solve this by passing the CORS settings to the applyMiddleware directly.

Michael Ross
  • 139
  • 1
  • 4
0

if you are using cors package from npm, then its creating the issue, so use default graphql server cros option like bellow:

server

    await server.start()
    server.applyMiddleware({
        app, cors: {
            origin: true,
            credentials: true
        }
    })

client:

const client = new ApolloClient({
  uri: 'http://localhost:2424/graphql',
  cache: new InMemoryCache(),
  credentials: 'include'
})

Mr Joker
  • 21
  • 4