berridgeab Posted October 21, 2013 Share Posted October 21, 2013 Hi, I'm looking to create a basic superglobal class wrapper for the PHP super globals. I don't know how to go about setting nested array keys / values within the object. Here is my basic class wrapper - class superGlobal { protected $superGlobal; public function __construct(array $superGlobal) { $this->superGlobal = $superGlobal; } public function set($value, $arrayKey = null) { if(is_scalar($arrayKey)) { $this->superGlobal[$arrayKey] = $value; } else { $this->superGlobal[] = $value; } } public function get() { return $this->superGlobal; } } A very simple wrapper. Thanks to the addition of array literials in PHP5.5 I can access single or nested array values easily like below so no problem here. $nestedArray = array( "Unnested Array Value", array( "Nested Array Value")); $superGlobal = new \superGlobal($nestedArray); //Outputs "Unnested Array Value" echo $superGlobal->get()[0] //Outputs "Nested Array Value" echo $superGlobal->get()[1][0] However I have no idea how to write a "set" function that can accept a nested key . Any ideas? Currently I have to get the nested array, store it in a temporary variable like below. //Create superglobal object with random nested array and output $superGlobal = new \superGlobal(array()); $superGlobal->set(array(0 => array(0 => array(0 => "Apples"))), "nestedItem"); //Output array echo "<pre>" , print_r($superGlobal->get(), 1) , "</pre>"; //Grab array and store $temporaryStore = $superGlobal->get()['nestedItem']; //Add new value to the nested array $temporaryStore[0][0][1] = "Oranges"; //Now reset the value $superGlobal->set($temporaryStore, "nestedItem"); //Output array echo "<pre>" , print_r($superGlobal->get(), 1) , "</pre>"; Basically I want to cut out the step of having to store the array into a temporary variable, modify it and reassigning it. I could make the variable public, but I would prefer not to. Link to comment https://forums.phpfreaks.com/topic/283156-php-superglobal-class-wrapper/ Share on other sites More sharing options...
vinny42 Posted October 21, 2013 Share Posted October 21, 2013 It looks like you are creating a registry pattern. Basically I want to cut out the step of having to store the array into a temporary variable, modify it and reassigning it That would mean making the class aware of what you are storing in it, which I feel goes beyong the scope of what a superglobal of registry is supposed to do. I'd feel more comfortable with a "fruitlist" object that you can store in the registry, then you can modify that by getting it from the registry and calling a modifier method on it to replace the element. Link to comment https://forums.phpfreaks.com/topic/283156-php-superglobal-class-wrapper/#findComment-1454781 Share on other sites More sharing options...
ignace Posted October 21, 2013 Share Posted October 21, 2013 untested class RecursiveArrayWrapper extends \ArrayObject { public function offsetGet($offset) { $data = parent::offsetGet($offset); if (is_array($data)) { return new static($data, $this->getFlags(), $this->getIteratorClass()); } return $data; } // add functionality as needed public function merge($array) { if ($array instanceof self) { $array = $array->getArrayCopy(); } $this->exchangeArray(array_merge($this->getArrayCopy(), $array)); return $this; } } $array = new RecursiveArrayWrapper(array( 'foo' => array('bar' => array('bat' => 'baz')) ), ArrayObject::ARRAY_AS_PROPS); var_dump($array->foo->bar->bat); var_dump($array->foo->merge(array('bar' => array('bat' => 'foo')))->bar->bat);Does exactly what you want but instead of calling it something as meaningless as superGlobal, I called it something so that it can be re-used for something more then just as a superGlobal container (which it really wasn't either). This is kinda more what I would call it: class HttpRequest { public $get; public $post; public $cookie; public $session; public $server; public $files; public $env; public $globals; public function __construct() { foreach (array('get', 'post', 'cookie', 'session', 'server', 'files', 'env', 'globals') as $superGlobal) { if (isset(${'_' . strtoupper($superGlobal)})) { $this->$superGlobal = new RecursiveArrayWrapper(${'_' . strtoupper($superGlobal)}, ArrayObject::ARRAY_AS_PROPS); } } } } $request = new HttpRequest; var_dump($request->get->foo); Link to comment https://forums.phpfreaks.com/topic/283156-php-superglobal-class-wrapper/#findComment-1454825 Share on other sites More sharing options...
berridgeab Posted October 22, 2013 Author Share Posted October 22, 2013 Very nice ignace, the HTTPRequest class doesn't get filled but I think thats down to not being able to use variable variables with PHPs superglobals. http://php.net/manual/en/language.variables.variable.php Anyway thats a minor issue, you've gave me some ideas and a direction to follow. Thanks for your response. Edit - Updated HTTPRequest class to get around variable variable issue. class HttpRequest { public $get; public $post; public $cookie; public $session; public $server; public $files; public $env; public function __construct() { foreach (array('get', 'post', 'cookie', 'session', 'server', 'files', 'env') as $superGlobal) { $globals = $GLOBALS; if(isset($globals['_' . strtoupper($superGlobal)])) { $this->$superGlobal = new RecursiveArrayWrapper($globals['_' . strtoupper($superGlobal)], ArrayObject::ARRAY_AS_PROPS); } } } } Link to comment https://forums.phpfreaks.com/topic/283156-php-superglobal-class-wrapper/#findComment-1454883 Share on other sites More sharing options...
Recommended Posts
Archived
This topic is now archived and is closed to further replies.