Web app logout request CORS issues

AI-generated summary

The user emurillo is experiencing CORS issues when trying to trigger the admin/users/:id/logout endpoint from their web app using Axios. The request works fine with cURL, but the server logs show a “No route matches” error when sent from the web app. Falco pointed out the security risk of exposing the admin API key from the frontend and advised setting up an endpoint on the server to handle the logout, rather than calling the API directly from the frontend.

Hey everyone, thanks for Discourse I’ve find it pretty easy to set up, up until this point.

I have a SSO setup that works fine with my web app, however when I trigger the admin/users/:id/logout endpoint, it won’t work from the web app.

For some reason it’ll accept a cURL just fine:

 curl 'http://localhost/admin/users/2/log_out' \
  -X 'POST' \
  -H 'Api-Key: <>' \
  -H 'Content-Type: multipart/form-data;' -v

*   Trying 127.0.0.1:80...
* Connected to localho.st (127.0.0.1) port 80 (#0)
> POST /admin/users/2/log_out HTTP/1.1
> Host: localho.st
> User-Agent: curl/7.77.0
> Accept: */*
> Api-Key: <>
> Content-Type: multipart/form-data;
>
* Mark bundle as not supporting multiuse
< HTTP/1.1 200 OK
< Content-Type: application/json; charset=utf-8
< Transfer-Encoding: chunked
< Connection: keep-alive
< Status: 200 OK
< Cache-Control: no-cache, no-store
< Access-Control-Allow-Origin: http://localhost:3000
< Vary: Accept
< Referrer-Policy: strict-origin-when-cross-origin
< X-Permitted-Cross-Domain-Policies: none
< X-XSS-Protection: 1; mode=block
< X-Request-Id: 26dfcbf6-497c-45db-8e3d-17aef9ba812c
< X-Discourse-Route: users/log_out
< Access-Control-Allow-Headers: Content-Type, Cache-Control, X-Requested-With, X-CSRF-Token, Discourse-Present, User-Api-Key, User-Api-Client-Id, Authorization
< Access-Control-Allow-Credentials: true
< Access-Control-Allow-Methods: POST, PUT, GET, OPTIONS, DELETE
< X-Download-Options: noopen
< X-Runtime: 0.190266
< X-Frame-Options: SAMEORIGIN
< X-Content-Type-Options: nosniff
< X-Discourse-Username: emurillo
< Date: Tue, 30 Nov 2021 21:12:58 GMT
< X-Powered-By: Phusion Passenger(R) 6.0.10
< Server: nginx/1.20.1 + Phusion Passenger(R) 6.0.10
<
* Connection #0 to host localho.st left intact
{"success":"OK"}

and the server logs:

Started POST "/admin/users/2/log_out" for 172.18.0.1 at 2021-11-30 21:12:58 +0000
Processing by Admin::UsersController#log_out as */*
  Parameters: {"user_id"=>"2"}
Can't verify CSRF token authenticity.
Completed 200 OK in 75ms (Views: 0.9ms | ActiveRecord: 0.0ms | Allocations: 2350)

But then when I try from the web app:

axios.post('http://localhost/admin/users/2/log_out', {}, {
  headers: {
    'User-Api-Key': '<>',
    'Content-Type': 'multipart/form-data'
  }
});

the server logs show:

Started POST "/admin/users/2/log_out" for 172.18.0.1 at 2021-11-30 21:08:26 +0000
ActionController::RoutingError (No route matches [POST] "/admin/users/2/log_out")

some more evidence:


xxxxxxxxxxx

xxxxxxxxxxx

What do you mean by “from the webapp”. Are you trying to call this API endpoint from front-end javascript? That would expose the admin API key.

That’s right, wanted to verify first in the front-end, but if you recommend setting up an endpoint on my server to handle the logout (and there is no shorter path around it) I’ll follow your advice.