Wordpress

时间:2018-02-12 17:17:36

标签: javascript wordpress http jwt mamp

我无法使用Authorization: Bearer -token-来发布内容,我几乎不怀疑我的服务器配置。 我在基于wordpress的服务器中使用MAMP Pro。该服务器提供API(这不是Rest API wordpress插件)。当我使用Postman时,此API工作正常。

我的典型用例是:

  1. 在POST中从https://front-end.com/login.html发布到https://back-end.com/api/users/auth,用户名/ pwd作为参数。
  2. 返回一个名为myToken
  3. 的JWT令牌
  4. 在POST中从https://front-end.com/index.html发布到https://back-end.com/api/alert,其中input1 / input2作为参数,Authorization: Bearer <myToken>作为标题。
  5. 第1步的JS代码

    const API_ROOT_URL = "https://back-end.com";
    const API_AUTH = "api/users/auth";
    const API_ALERT = "api/alert";
    const METHOD_POST = "POST";
    
    return new Promise((resolve: any, reject: any) => {
    let request = new XMLHttpRequest();
                request.open(METHOD_POST, API_ROOT_URL+"/"+API_AUTH);
               // request.setRequestHeader('Content-Type', 'multipart/form-data');
                request.onload = () => resolve(request.response);
                request.onerror = () => reject(request.response);
                request.send(formData);
    

    第3步的JS代码:

            return new Promise((resolve: any, reject: any) => {
            let request = new XMLHttpRequest();
            request.open(METHOD_POST, API_ROOT_URL+"/"+API_ALERT);
            request.setRequestHeader('Authorization', "Bearer  "+ AnotherClass.getJwtToken());
          //  request.setRequestHeader('Content-Type', 'multipart/form-data');
            request.onload = () => resolve(request.status);
            request.onerror = () => reject(request.status);
            request.send(formData);
        });
    

    第1步正常。使用Postman或我的常规Webapp在front-end.com上检索JWT令牌。

    第3步与Postman合作正常,我的表格已成功发布,我收到了200。 但是当我在WebApp中使用它时,我无法传递预检OPTION请求。

    请注意,我还使用mockable.io(也是https)来模拟我的API并且请求成功通过;这在我们的案例中并不重要,但这就是我怀疑服务器配置错误的原因。

    经过测试:

    一个。在MAMP虚拟主机中重写规则:

    RewriteEngine on RewriteCond %{HTTP:Authorization} ^(.*) RewriteRule ^(.*) - [E=HTTP_AUTHORIZATION:%1]

    B中。在我的wordpress服务器的htaccess中重写规则(与上面相同,在现有重写规则之后推送)

    ℃。出于测试目的,删除&#34;授权:承载&#34;查看请求是否转到POST(并且毫不奇怪)

    d。试图在.htaccess中添加SetEnvIf Authorization "(.*)" HTTP_AUTHORIZATION=$1 ,无论是否有以前的重写规则。

    电子。如上面的JS代码所述,尝试将Contet-Type硬件设置为multipart,没有任何改进。

    F。尝试在端点API_ALERT中添加/,以防万一wordpress执行愚蠢的重定向(之前经历过)

    我现在完全不知道在哪里寻找。我怀疑是Apache配置阻止了授权,还是Wordpress搞乱Cors或授权。

1 个答案:

答案 0 :(得分:0)

如果这有副标题,那就是“使用无需插件的自定义Wordpress上的JWT授权故事,使用Service Workers和XHR在另一个域上使用JavaScript WebApp”

自我祝贺,但特别感谢https://www.html5rocks.com/en/tutorials/cors/,提供有关服务器和脚本如何交互的清晰信息。

使用Wordpress,我的解决方案是(我的JS代码没有改变):

  1. 添加以下之前 #BEGIN WordPress声明

    <IfModule mod_rewrite.c>
    RewriteEngine on
    RewriteCond %{HTTP:Authorization} ^(.*)
    RewriteRule ^(.*) - [E=HTTP_AUTHORIZATION:%1]
    </IfModule>
    
  2. 在您的路线服务中,使用以下方式野蛮地绕过“addRoute”方法:

    $this->routes[] = [ltrim("/api/alert", '/'), [$myApiController, 'alertAction']];
    
  3. 在API控制器$myApiControler中创建入口点函数alertAction

    public function alertAction()
    {
      $request = Request::getInstance();
      if(!$request->isXmlHttpRequest()) {
        switch($request->getMethod()) {
            case Request::METHOD_OPTIONS:
                $this->handleOptionsMethod();
                break;
            case Request::METHOD_POST:
                $this->handlePostMethod($request);
                break;
            default:
                $response = new Result(404);
                status_header($result->getCode());
                echo $response;
                die();
                break;
        }
    }
    

    }

  4. handleOptionsMethod()方法中,使用所需的标题

    创建相应的选项响应
    private function handleOptionsMethod() {
      $response = new Result(200);
      status_header($response->getCode());
      header('Access-Control-Allow-Origin: *');
      header('Access-Control-Allow-Methods: POST');
      header('Access-Control-Allow-Headers: Authorization');
      echo $response;
      die();
    }   
    
  5. 在handlePostMethod()方法中,尽你所能。

    private function handlePostMethod($request) {
    
      $requestData = $request->request->all();
      $authorization = $request->headers->get('Authorization');
    
      $jwt = str_replace('Bearer ', '', $authorization);
      $decoded = JWT::decode($jwt, JWT_SECRET_KEY, array('HS256'));
      $userId = (int) $decoded->data->userId;
      ...
      $response = new Result(200)
      status_header($result->getCode());
      echo $response;
      die();
    }
    
  6. 然而,基本上:    - 允许您的服务器读取其他HTTP信息    - 允许您的wordpress实例在OPTIONS请求中执行特定的操作    - 创建脚本需要的响应标头以允许预检请求(在我的情况下允许“授权”自定义标头)    - 创建常规请求处理程序(您的帖子或获取)。

    希望这会对你们中的一些人有所帮助。

    我的问题的最后一部分是,现在POST请求成功触发,Service Worker不起作用,因此我无法访问“响应”并正确处理它。但我已向前迈出了一大步,并希望与你们中的一些人分享。