質問

UPDATE THREE

Since I am getting the correct responses from my own api, can I modify the responses I am getting. In the console I see this:

{readyState: 4, getResponseHeader: ƒ, getAllResponseHeaders: ƒ, setRequestHeader: ƒ, overrideMimeType: ƒ, …}
abort: ƒ (a)
always: ƒ ()
complete: ƒ ()
done: ƒ ()
error: ƒ ()
fail: ƒ ()
getAllResponseHeaders: ƒ ()
getResponseHeader: ƒ (a)
overrideMimeType: ƒ (a)
pipe: ƒ ()
progress: ƒ ()
promise: ƒ (a)
readyState: 4
responseText: "{"success":true}
↵<!DOCTYPE html>
↵<html lang="en-"
setRequestHeader: ƒ (a,b)
state: ƒ ()
status: 404
statusCode: ƒ (a)
arguments: null
caller: null
length: 1
name: "statusCode"
prototype: {constructor: ƒ}
__proto__: ƒ ()
[[FunctionLocation]]: jquery.js?ver=1.12.4-wp:4
[[Scopes]]: Scopes[3]
statusText: "Not Found"
success: ƒ ()
then: ƒ ()
__proto__: Object

I tried using status_header(); in my php but that didn't work.

UPDATE TWO

Is the problem related to this: https://stackoverflow.com/questions/3445270/jquery-ajax-returning-404-error-but-correct-response

If so, I'm not sure I know what to do...

UPDATE

If I use just test_login_file.php as the AJAX url I can include these lines again:

defined( 'ABSPATH' ) or die( 'No access this way' );
add_shortcode('myLogin', 'myLogin');

and remove the ridiculous:

aCompletelyUnlikelyfunction();

In that case the cookie is set, the page doesn't refresh (good so far...), but I get a 404 not found error for the url in the console. This response includes the expected {"success": true} JSON, but also a mass of HTML for a 404 page, so the AJAX response handling doesn't work - which I obviously need to do something else.

Clearly this must be the 'ABSPATH', otherwise it would throw an error as it did previously.

What the heck is going on? Is this a WordPress issue, or am I fundamentally not understanding something?

Thanks for looking!


I am trying to use WordPress, installed via Bitnami on Google Cloud Platform, to build a website, but use another system on a different server (server B) to manage users and content. I want to be able to log a user in to my B server, get a JSON web token, and use that to authenticate users in other parts of the site.

The code below works and sets a secure, httpOnly cookie with the value of my token.

But, in order to do this I have to stop the ajax by using the incorrect line:

aCompletelyUnlikelyfunction();

otherwise it doesn’t set the cookie (possibly because the AJAX causes some output?). This also cause the page to refresh.

If I remove this line, the AJAX works correctly, giving me the appropriate pop up depending on what I submit. But as pointed out above, it doesn't set the cookie.

I had to comment out these lines to get the AJAX to work:

//defined( 'ABSPATH' ) or die( 'No access this way' );
//add_shortcode('myLogin', 'myLogin');

The form:

html
      <form id="loginform" name="loginform" method="post">
         <div>
            Email:
            <input type="text" name="email" id="email" />
            Password:
            <input type="password" name="password" id="password" />
            <input type="hidden" name="call" id="call" value="1"/>
            <input type="submit" name="loginBtn" id="loginBtn" value="Login" />
         </div>
      </form>

The jQuery:

<script type="text/javascript">
jQuery(document).ready(function() {
    jQuery('#loginform').submit(function(e) {
        e.preventDefault();
        jQuery.ajax({
            type: "POST",
            url: '/wp-content/plugins/test_login_file.php',
            data: jQuery(this).serialize(),
            aCompletelyUnlikelyfunction(); //I know this is very wrong!
            success: function(response){
                console.log(response);
                var jsonData = JSON.parse(response);
 
                if (jsonData.success === true)
                {
                    alert('Logged In');
                }
                else
                {
                    alert('Invalid Credentials!');
                }
           },
           error: function(error){
                console.log("Error");
                console.log(error);
           }
           
       });
     });
});
     </script>

And the php:

<?php
/**
 * Plugin Name: Test Login
 * Plugin URI: 
 * Description: Test Login
 * Version: 1.0
 * Author: PMP
 * Author URI:
 **/
//defined( 'ABSPATH' ) or die( 'No access this way' );
//add_shortcode('myLogin', 'myLogin');

function get_token()
{  
    ob_start();
    $method  = 'POST';
    $url     = 'https:my_B_server/session';
    $headers = array(
        'Accept: application/json',
        'Content-Type: application/json'
    );
    $curl = curl_init($url);
    curl_setopt($curl, CURLOPT_POST, true);
    curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($_REQUEST));
    curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
    curl_setopt($curl, CURLOPT_SSLVERSION, 4);
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    $response = curl_exec($curl);
    
    $code = curl_getinfo($curl, CURLINFO_HTTP_CODE);
    curl_close($curl);
        
    if ($code == 200) {
        
        /*if (isset($_COOKIE["my_token"]))
        {
        echo json_encode(array(
        "success" => 'Logged In'
        ));
        }
        else*/
        //{
        $response = json_decode($response, true);
        $token    = $response["session_token"];
        $expiry   = strtotime('+1 month');
        setcookie("my_token", $token, $expiry, COOKIEPATH, COOKIE_DOMAIN, true, true);
        $thing = json_encode(array(
            "success" => true
        ));
        //}
    } else {
        
        $response = json_decode($response, true);
        $context  = $response["error"]["message"];
        $token    = null;
        setcookie("my_token", "error", time() - 3600);
        
        $thing = json_encode(array(
            "error" => $context
        ));
    }
    echo $thing;
    ob_end_flush();
}
if (isset($_POST['call'])) {
    $pmp = $_POST['call']; {
        if ($pmp == 1) {
            get_token();
        }
    }
}
役に立ちましたか?

解決

Seems odd to answer my own question, but in case it is of use to someone, this is the answer.

To make an ajax call to a plugin, and receive the response correctly you must register that endpoint with the plugin. This allows you to sidestep the protection Wordpress is putting in your way. I'm not sure if links to YouTube are allowed/accepted on here, but there is an excellent video here. I will remove if this is considered bad practice.

php for plugin

add_action ( 'rest_api_init', 'add_callback_url_endpoint' );

function add_callback_url_endpoint(){
    register_rest_route(
    'my_route/',
    'receive_callback',
     array(
       'methods' => 'POST',
       'callback' => 'my_receive_callback'
        )
     );
  }


function my_receive_callback($request_data){
    $data = array();
    $params = $request_data -> get_params();
    $index = $params['index'];

if(isset($index)){
        $data = array(
'index' => $index,
'status' => 'OK'
);    
}else{
            $data = array(
'status' => 'Not OK'
}
   return $data;
}
ライセンス: CC-BY-SA帰属
所属していません wordpress.stackexchange
scroll top