I have the following code in test.php
:
<?php
$request_method = $_SERVER['REQUEST_METHOD']; // contains 'GET', as it should
echo 'json_encode($_GET) = ' . json_encode($_GET); echo "\n"; // works, prints the GET variables
echo "\n";
echo 'json_encode(${\'_\' . \'GET\'}) = ' . json_encode(${'_' . 'GET'}); echo "\n"; // also works, prints the GET variables
echo "\n";
echo '$request_method = ' . $request_method; echo "\n";
echo 'json_encode(${\'_\' . $request_method}) = ' . json_encode(${'_' . $request_method}); echo "\n"; // fails
echo "\n";
$a = 'GET';
echo '$a = ' . $a; echo "\n";
echo 'json_encode(${\'_\' . $a}) = ' . json_encode(${'_' . $a}); echo "\n"; // fails
echo "\n";
$x = '_GET';
echo '$x = ' . $x; echo "\n";
echo 'json_encode(${$x}) = ' . json_encode(${$x}); echo "\n"; // fails
if I do a GET request with the query string ?action=getUsername
it results in the following output:
json_encode($_GET) = {"action":"getUsername"}
json_encode(${'_' . 'GET'}) = {"action":"getUsername"}
$request_method = GET
json_encode(${'_' . $request_method}) = {"action":"getUsername"}
$a = GET
json_encode(${'_' . $a}) = {"action":"getUsername"}
$x = _GET
json_encode(${$x}) = {"action":"getUsername"}
which is OK.
But, when I'm using the code in a function from a different .php file, then, I get the following output:
json_encode($_GET) = {"action":"getUsername"}
json_encode(${'_' . 'GET'}) = {"action":"getUsername"}
$request_method = GET
json_encode(${'_' . $request_method}) = null
$a = GET
json_encode(${'_' . $a}) = null
$x = _GET
json_encode(${$x}) = null
and I don't understand what am I doing wrong.
EDIT:
This is AuthController.php
, from where I normally do the request but it fails:
class AuthController extends BaseController
{
protected function handlePostRequest(): void
{
switch ($this->action) {
case 'login': $this->{'handle_' . $this->action}(); break;
default: $this->respond_action_not_found();
}
}
protected function handleGetRequest(): void
{
switch ($this->action) {
case 'getUsername': $this->{'handle_' . $this->action}(); break;
default: $this->respond_action_not_found();
}
}
private function handle_login(): void
{
echo 'login';
}
private function handle_getUsername(): void {
echo "getUsername";
}
}
(new AuthController())->handleRequest();
And this is the BaseController.php
:
<?php
use JetBrains\PhpStorm\NoReturn;
require_once '../domain/StatusCode.php';
abstract class BaseController
{
protected string $request_method;
protected mixed $request_variables;
protected string $action;
public function __construct()
{
$request_method = $_SERVER['REQUEST_METHOD']; // contains 'GET', as it should
echo 'json_encode($_GET) = ' . json_encode($_GET); echo "\n"; // works, prints the GET variables
echo "\n";
echo 'json_encode(${\'_\' . \'GET\'}) = ' . json_encode(${'_' . 'GET'}); echo "\n"; // also works, prints the GET variables
echo "\n";
echo '$request_method = ' . $request_method; echo "\n";
echo 'json_encode(${\'_\' . $request_method}) = ' . json_encode(${'_' . $request_method}); echo "\n"; // fails
echo "\n";
$a = 'GET';
echo '$a = ' . $a; echo "\n";
echo 'json_encode(${\'_\' . $a}) = ' . json_encode(${'_' . $a}); echo "\n"; // fails
echo "\n";
$x = '_GET';
echo '$x = ' . $x; echo "\n";
echo 'json_encode(${$x}) = ' . json_encode(${$x}); echo "\n"; // fails
echo ""; echo "\n";
// echo $this->request_method; // 1
// echo "\n";
// echo json_encode($_GET); // 2
// echo "\n";
// echo json_encode(${'_' . $this->request_method}); // 3
// echo "\n";
// echo json_encode(${'_' . $_SERVER['REQUEST_METHOD']}); // 4
// echo "\n";
// echo json_encode(${'_' . 'GET'}); // 5
// echo "\n";
// $a = "_" . $this->request_method;
// echo json_encode($a); // 6
// echo "\n";
// error_log($a);
// error_log($$a);
// echo json_encode($$a); // 7
// echo "\n";
// echo "should work: " . json_encode(${'_GET'});
// echo "\n";
// echo "request method: " . $this->request_method;
// echo "\n";
//// $x = ${'_' . $this->request_method};
// $x = ${'_' . $_SERVER['REQUEST_METHOD']};
// echo "should work too : " . json_encode($x);
// echo "\n";
// echo "should work too : " . $x;
// echo "\n";
$this->request_variables = ${'_' . $this->request_method};
$this->action = $this->request_variables['action'];
}
abstract protected function handlePostRequest(): void;
abstract protected function handleGetRequest(): void;
public function handleRequest(): void {
if (!isset($this->action))
$this->respond(StatusCode::BAD_REQUEST, "Action is not set");
switch ($this->request_method) {
case "POST": {$this->handlePostRequest(); break; }
case "GET": {$this->handleGetRequest(); break; }
default:
}
}
#[NoReturn] protected function respond(int $status_code, mixed $content = ""): void {
http_response_code($status_code);
echo json_decode($content);
exit;
}
#[NoReturn] protected function respond_success(int $status_code, mixed $content = ""): void {
$this->respond(StatusCode::OK, $content);
}
#[NoReturn] protected function respond_action_not_found(): void {
$this->respond(StatusCode::BAD_REQUEST, "Action not found");
}
#[NoReturn] protected function respond_invalid_parameters(string $additional_message = ""): void {
$this->respond(StatusCode::BAD_REQUEST, "Invalid parameters. " . $additional_message);
}
}
EDIT 2: Workaround
From @Kubo2 in Superglobals can't be accessed via variable variables in a function?
$a = "_GET";
echo json_encode($GLOBALS[$a]);
CodePudding user response:
You can't access the superglobals via variable variables (as you did with expressions like ${'_' . $a}
) as stated in the manual Variable variables:
Warning Please note that variable variables cannot be used with PHP's Superglobal arrays within functions or class methods. The variable
$this
is also a special variable that cannot be referenced dynamically.