Skip to content

Commit

Permalink
Improve login response and JWT wordflow
Browse files Browse the repository at this point in the history
  • Loading branch information
marioshtika committed May 22, 2020
1 parent bf8bf05 commit d3e1354
Show file tree
Hide file tree
Showing 3 changed files with 88 additions and 94 deletions.
1 change: 1 addition & 0 deletions apppresser.php
Original file line number Diff line number Diff line change
Expand Up @@ -136,6 +136,7 @@ function __construct() {
require_once( self::$inc_path . 'AppPresser_Remote_Scripts.php' );
require_once( self::$inc_path . 'AppPresser_AppGeo.php' );
require_once( self::$inc_path . 'AppPresser_WPAPI_Mods.php' );
require_once( self::$inc_path . 'AppPresser_User.php' );
require_once( self::$inc_path . 'AppPresser_User_Roles.php' );
require_once( self::$inc_path . 'AppPresser_Plugin_Updater.php' );
require_once( self::$inc_path . 'AppPresser_Theme_Updater.php' );
Expand Down
82 changes: 82 additions & 0 deletions inc/AppPresser_Users.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
<?php

use \Firebase\JWT\JWT;

class AppPresser_User
{
/**
* Returns the login response for the given user
*/
public static function getLoginResponse($user)
{
// Used for setting auth cookie on iframe pages. See AppPresser_Theme_Switcher->maybe_set_auth()
$cookie_auth = self::doCookieAuth($user->ID);

$data = array(
'message' => apply_filters('appp_login_success', sprintf(__('Welcome back %s!', 'apppresser'), $user->display_name), $user->ID),
'username' => $user->user_login,
'email' => $user->user_email,
'avatar' => get_avatar_url($user->ID),
'cookie_auth' => $cookie_auth,
'login_redirect' => AppPresser_Ajax_Extras::get_login_redirect(), // v3 only
'success' => true,
'user_id' => $user->ID
);

if ($token = self::generateToken($user)) {
$data['access_token'] = $token;
}

$data = apply_filters('appp_login_data', $data, $user->ID);

$retval = rest_ensure_response($data);

return $retval;
}

/*
* Encrypts string for later decoding
*/
private static function doCookieAuth($userId)
{
if (function_exists('openssl_encrypt')) {
$key = substr(AUTH_KEY, 2, 5);
$iv = substr(AUTH_KEY, 0, 16);
$cipher = "AES-128-CBC";
$ciphertext = openssl_encrypt($userId, $cipher, $key, null, $iv);
} else {
// no openssl installed
$ciphertext = $userId;
}

update_user_meta($userId, 'app_cookie_auth', $ciphertext);

return $ciphertext;
}

private static function generateToken($user)
{
$secretKey = defined('JWT_AUTH_SECRET_KEY') ? JWT_AUTH_SECRET_KEY : false;
$issuedAt = time();
$notBefore = apply_filters('jwt_auth_not_before', $issuedAt, $issuedAt);
$expire = apply_filters('jwt_auth_expire', $issuedAt + (DAY_IN_SECONDS * 7), $issuedAt);

$token = array(
'iss' => get_bloginfo('url'),
'iat' => $issuedAt,
'nbf' => $notBefore,
'exp' => $expire,
'data' => array(
'user' => array(
'id' => $user->data->ID,
),
),
);

if (class_exists('Jwt_Auth')) {
return JWT::encode($token, $secretKey);
} else {
return null;
}
}
}
99 changes: 5 additions & 94 deletions inc/AppPresser_WPAPI_Mods.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,6 @@ public function hooks() {

// CORS
add_action( 'rest_api_init', array( $this, 'appp_cors') );

// Add access-token from the JWT Authentication plugin
add_filter( 'appp_login_data', array( $this, 'appp_login_data_add_access_token' ), 10, 2 );
}

/**
Expand Down Expand Up @@ -139,37 +136,6 @@ public function appp_cors() {

}

/**
* Adds the access token from the JWT Authorization plugin to the AppPresser login data which gets sent back to the app
*
* @param $login_data array The existing login data just prior to being sent to the app
* @param $user_id integer The current user's ID
*
* @return $login_data array
*/
function appp_login_data_add_access_token($login_data, $user_id)
{
if ($login_data['success'] === false) {
return $login_data;
}

if (class_exists('Jwt_Auth_Public')) {
if (isset($_REQUEST['username']) && isset($_REQUEST['password'])) {
$request = new WP_REST_Request('POST', '/wp-json/jwt-auth/v1/token');
$request->set_param('username', $_REQUEST['username']);
$request->set_param('password', $_REQUEST['password']);
$JWT = new Jwt_Auth_Public('jwt-auth', '1.1.0');
$auth_object = $JWT->generate_token($request);
if (!is_wp_error($auth_object)) {
// add user id to data after login so we can use that for posting stuff to BP
$login_data['access_token'] = $auth_object['token'];
}
}
}

return $login_data;
}

public function add_api_fields() {

/***
Expand Down Expand Up @@ -298,30 +264,10 @@ public function api_login( $request ) {

return rest_ensure_response( $msg );

} else {

// used for setting auth cookie on iframe pages. See AppPresser_Theme_Switcher->maybe_set_auth()
$cookie_auth = $this->do_cookie_auth( $user_signon->ID );

$msg = array(
'message' => apply_filters( 'appp_login_success', sprintf( __('Welcome back %s!', 'apppresser'), $user_signon->display_name), $user_signon->ID ),
'username' => $info['user_login'],
'email' => $user_signon->user_email,
'avatar' => get_avatar_url( $user_signon->ID ),
'cookie_auth' => $cookie_auth,
'login_redirect' => AppPresser_Ajax_Extras::get_login_redirect(), // v3 only
'success' => true,
'user_id' => $user_signon->ID
);

}

$msg = apply_filters( 'appp_login_data', $msg, $user_signon->ID );

$retval = rest_ensure_response( $msg );

return $retval;

// If everything is successfull, return login response
return AppPresser_User::getLoginResponse($user_signon);
}

/**
Expand Down Expand Up @@ -355,29 +301,6 @@ public function api_logout( $request ) {

}

/*
* Encrypts string for later decoding
*/
public function do_cookie_auth( $user_id ) {

if( function_exists('openssl_encrypt') ) {

$key = substr( AUTH_KEY, 2, 5 );
$iv = substr( AUTH_KEY, 0, 16 );
$cipher="AES-128-CBC";
$ciphertext = openssl_encrypt($user_id, $cipher, $key, null, $iv );

} else {
// no openssl installed
$ciphertext = $user_id;
}

update_user_meta( $user_id, 'app_cookie_auth', $ciphertext );

return $ciphertext;

}

/**
* Register user via API
* First, we add the user to WordPress, and set a meta key of app_unverified to true
Expand Down Expand Up @@ -552,24 +475,12 @@ public function verify_user( $request ) {
);
}

$message = array(
'message' => apply_filters( 'appp_login_success', sprintf( __('Welcome back %s!', 'apppresser'), $user_signon->display_name), $user_signon->ID ),
'username' => $info['user_login'],
'avatar' => get_avatar_url( $user_signon->ID ), // v3 only
'success' => true,
'user_id' => $user_signon->ID,
'email' => $user_signon->user_email
);

// adds user_id and auth token
$message = apply_filters( 'appp_login_data', $message, $user_signon->ID );

// If everything is successfull, return login response
$retval = AppPresser_User::getLoginResponse($user_signon);

do_action( 'appp_register_verified', $user_signon->ID );

$retval = rest_ensure_response( $message );

return $retval;

}

/**
Expand Down

0 comments on commit d3e1354

Please sign in to comment.