Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Wordpress Auth + Nonces + Ajax + No Templating - Cookie nonce is invalid

I understand the process of using nonces when I create my own templates. But I am developing a ReactJS App which uses ONLY the Wordpress REST API for pulling data, so the user never gets to the index.php, but does Ajax calls to the WP Rest Api.

Now I cannot get the nonce stuff to work. This is what I have done so far:

I added the following endpoints:

register_rest_route('frontend', '/customer/', array(
    'methods' => 'GET',
    'callback' => 'get_customer'
));

register_rest_route('frontend', '/customer/', array(
    'methods' => 'POST',
    'callback' => 'create_user_and_login'
));

These are my functions:

function get_customer()
{
    return get_current_user_id();
}


function create_user_and_login(){
    // dummy data for testing
    $credentials = ['user_login' => '[email protected]', 'user_password' => 'XXXX', 'remember' => true];

    // create a new user/customer via woocommerce
    $customerId = wc_create_new_customer($credentials['user_login'], $credentials['user_login'], $credentials['user_password']);
    if(is_a($customerId,'WP_Error')) {
        return $customerId;
    }
    // get the user & log in
    $user = get_user_by( 'id', $customerId );
    if( $user ) {
        wp_set_current_user( $customerId);
        wp_set_auth_cookie( $customerId );
    }
    // create new nonce and return it
    $my_nonce = wp_create_nonce('wp_rest');
    return $my_nonce;
}

If I now run a POST to /customer which triggers create_user_and_login(), the newly created nonce is returned in the ajax response. Then I use the returned nonce to run my next request, a GET to /customer?_wpnonce=MY-NONCE, but I get the error:

{
    "code": "rest_cookie_invalid_nonce",
    "message": "Cookie nonce is invalid",
    "data": {
        "status": 403
    }
}

I checked the nonce documentation but I could not find a solution for my problem. Could it be that the sessions are out of sync? So that the nonce is created on the wrong session or wp_set_auth_cookie and wp_set_current_user are not called correctly? Or do I have to use the wp_localize_script function? This will get problematic, as I want to have the ReactJS and the Wordpress backend separated.

I got two cookies after the POST, a wordpress cookie and a wordpress_logged_in cookie.

What am I missing?

like image 323
Dario Avatar asked Oct 04 '17 12:10

Dario


1 Answers

Check this answer

It seems that when you call $my_nonce = wp_create_nonce('wp_rest'); the nonce is created with the old session cookie, even when you call wp_set_auth_cookie and wp_set_current_user. But in the next request the session is updated, meaning that the nonce is wrong.

As in the answer, add the following hook (functions.php for example) to force an update of the cookie:

        function my_update_cookie( $logged_in_cookie ){
            $_COOKIE[LOGGED_IN_COOKIE] = $logged_in_cookie;
        }
        add_action( 'set_logged_in_cookie', 'my_update_cookie' );
like image 171
Felix Hagspiel Avatar answered Sep 26 '22 12:09

Felix Hagspiel