WordPress
ソースコードリーディング
CurrentUser

WordPressソースコードリーディングで現在のユーザを取得するところについての記述

More than 1 year has passed since last update.

WordPressのソースコードを徘徊してたら、面白いところが見つかりました。

ちなみに、僕のソースコードを読む時の戦略は、「眺める」ことです。わけわかめでも大丈夫。だんだんわかってくるから、重要なことは、毎日読むことだと思います。

金かかる学習プラットフォームや、本を買うよりいいと思います。

決して、自然言語を読むように読んではいけません。

僕は、PhpStormがいいと聞いていたので、PhpStormを使っています。ソースコードのトレースもスムーズにできるので、便利です。

では、解説していきたいと思います。

/**

* Retrieves the current user object.
*
* Will set the current user, if the current user is not set. The current user
* will be set to the logged-in person. If no user is logged-in, then it will
* set the current user to 0, which is invalid and won't have any permissions.
*
* This function is used by the pluggable functions wp_get_current_user() and
* get_currentuserinfo(), the latter of which is deprecated but used for backward
* compatibility.
*
* @since 4.5.0
* @access private
*
* @see wp_get_current_user()
* @global WP_User $current_user Checks if the current user is set.
*
* @return WP_User Current WP_User instance.
*/
function _wp_get_current_user() {
global $current_user;

if ( ! empty( $current_user ) ) {
if ( $current_user instanceof WP_User ) {
return $current_user;
}

// Upgrade stdClass to WP_User
if ( is_object( $current_user ) && isset( $current_user->ID ) ) {
$cur_id = $current_user->ID;
$current_user = null;
wp_set_current_user( $cur_id );
return $current_user;
}

// $current_user has a junk value. Force to WP_User with ID 0.
$current_user = null;
wp_set_current_user( 0 );
return $current_user;
}

if ( defined('XMLRPC_REQUEST') && XMLRPC_REQUEST ) {
wp_set_current_user( 0 );
return $current_user;
}

/**
* Filters the current user.
*
* The default filters use this to determine the current user from the
* request's cookies, if available.
*
* Returning a value of false will effectively short-circuit setting
* the current user.
*
* @since 3.9.0
*
* @param int|bool $user_id User ID if one has been determined, false otherwise.
*/
$user_id = apply_filters( 'determine_current_user', false );
if ( ! $user_id ) {
wp_set_current_user( 0 );
return $current_user;
}

wp_set_current_user( $user_id );

return $current_user;
}

この関数は、現在のユーザを設定します。ログインしているユーザがいる場合は、ログインしているユーザとして設定し、誰もログインしていないときは、0を返します。

この関数は、Pluggableである関数、wp_get_current_user()から呼び出されることがあります。

    global $current_user;

このグローバルというのは、\$current_userをグローバル変数とします。\$current_userは、現在のユーザーをグローバルで格納しているようです。

    if ( ! empty( $current_user ) ) {

if ( $current_user instanceof WP_User ) {
return $current_user;
}

// Upgrade stdClass to WP_User
if ( is_object( $current_user ) && isset( $current_user->ID ) ) {
$cur_id = $current_user->ID;
$current_user = null;
wp_set_current_user( $cur_id );
return $current_user;
}

// $current_user has a junk value. Force to WP_User with ID 0.
$current_user = null;
wp_set_current_user( 0 );
return $current_user;
}

この部分では、if ( ! empty( \$current_user ) ) { によって、現在のユーザが設定されているかどうかをチェックして、設定されていたら、

        if ( $current_user instanceof WP_User ) {

return $current_user;
}

この部分により、\$current_userが、WP_Userのインスタンスであるかどうかをチェックします。インスタンスであったなら、\$current_userを返り値として、関数を返します。普通ですよね

        // Upgrade stdClass to WP_User

if ( is_object( $current_user ) && isset( $current_user->ID ) ) {
$cur_id = $current_user->ID;
$current_user = null;
wp_set_current_user( $cur_id );
return $current_user;
}

\$current_userが、stdClassである可能性を考えています。そんなことあるんですね。\$current_user->IDが設定されていた場合、wp_set_current_user( \$cur_id );によって、\$cur_idを\$current_userにセットした後、\$current_userを返します。

この関数だけ見ると、\$current_userに、\$cur_idがセットされていないように感じますが、一応設定されているようです。

ただ、ちょっとやるべきプロセスがあるようで、単純な代入ではないようです。では、wp_set_current_user( $cur_id );によって、どのようなプロセスが実行されているかを見てみましょう。

function wp_set_current_user($id, $name = '') {

global $current_user;

// If `$id` matches the user who's already current, there's nothing to do.
if ( isset( $current_user )
&& ( $current_user instanceof WP_User )
&& ( $id == $current_user->ID )
&& ( null !== $id )
) {
return $current_user;
}

$current_user = new WP_User( $id, $name );

setup_userdata( $current_user->ID );

/**
* Fires after the current user is set.
*
* @since 2.0.1
*/
do_action( 'set_current_user' );

return $current_user;
}

$current_user = new WP_User( $id, $name );によって、ユーザーidを設定していますね。あとは、setup_userdata( $current_user->ID );を起動しており、また、do_action( 'set_current_user' );を起動しています。

function setup_userdata($for_user_id = '')は、後方互換性のためのもののようで、こういうアプリを作るときは、後方互換性は重要になってくるのかもしれません。

do_action( 'set_current_user' );では、'set_current_user'で指定された関数をフックするようです。ちょっとなぜフックする必要があるのかはよくわからないです。

最初のソースコードに、XMLRPC_REQUESTという謎のキーワードがありますが、XMLRPCリクエストという、そういうリクエストが存在するようですね。

https://ja.wikipedia.org/wiki/XML-RPC

これは、XMLRPCリクエストには、ユーザーという概念がない(と僕は予測する)ので、wp_set_current_user( 0 );によって、カレントユーザーを0に設定して、返すんだと思います。

ところで、最近、ソースコードを読んで実行させずに、本ばっかり読むことは、「恋愛本ばかり読んで、女性に触れようとしない」(女性の場合は、(女性→男性)に読み替えてください。)のと同じかなと思い始めました。