rfc:to-array

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
Last revisionBoth sides next revision
rfc:to-array [2019/12/04 17:41] stevenwadejrrfc:to-array [2020/02/11 13:04] – Update error message comment stevenwadejr
Line 3: Line 3:
   * Date: 2019-08-28   * Date: 2019-08-28
   * Author: Steven Wade, stevenwadejr@gmail.com   * Author: Steven Wade, stevenwadejr@gmail.com
-  * Status: Draft+  * Status: Under Discussion
   * First Published at: http://wiki.php.net/rfc/to-array   * First Published at: http://wiki.php.net/rfc/to-array
  
 ===== Introduction ===== ===== Introduction =====
-PHP contains many [[https://www.php.net/manual/en/language.oop5.magic.php|magic methods]] that give a class greater control over its interaction with the language. The methods [[https://wiki.php.net/rfc/custom_object_serialization|__serialize() and __unserialize()]] give a class control over how it is serialized, <nowiki>__clone()</nowiki> allows control over how self copies are made, and <nowiki>__toString()</nowiki> allows a class to control how it is represented when converted to a string.  
  
 This RFC proposes to add a new magic method called <nowiki>__toArray()</nowiki> to allow a class to control how it is represented when converted to an array. This RFC proposes to add a new magic method called <nowiki>__toArray()</nowiki> to allow a class to control how it is represented when converted to an array.
 +
 +PHP contains many [[https://www.php.net/manual/en/language.oop5.magic.php|magic methods]] that give a class greater control over its interaction with the language. The methods [[https://wiki.php.net/rfc/custom_object_serialization|__serialize() and __unserialize()]] give a class control over how it is serialized, <nowiki>__clone()</nowiki> allows control over how self copies are made, and <nowiki>__toString()</nowiki> allows a class to control how it is represented when converted to a string. Adding a <nowiki>__toArray()</nowiki> method gives developers the ability to transform a class to an array in similar fashion.
  
 ===== Proposal ===== ===== Proposal =====
Line 43: Line 44:
  
 <code php> <code php>
-print_r($person); // calls __toArray() 
- 
-// Output 
-/* 
-Array 
-( 
-    [name] => John Doe 
-    [email] => j.doe@example.com 
-) 
-*/ 
- 
 $personArray = (array) $person; // casting triggers __toArray() $personArray = (array) $person; // casting triggers __toArray()
 </code> </code>
  
-===== Use in Array Contexts ===== +==== What this is ==== 
- +The example above shows the method <nowiki>__toArray()</nowiki> used in a type-casting context.  This proposal would have objects implementing the <nowiki>__toArray()</nowiki> magic method called within //any// array context including type hinting and return types (only when using weak typing - strong typing will throw an error).
-The example above shows the method <nowiki>__toArray()</nowiki> used in a type-casting context.  This proposal would have objects implementing the <nowiki>__toArray()</nowiki> magic method called within //any// array context including type hinting and return types.+
  
 Similar to PHP's current implementation of <nowiki>__toString()</nowiki>, a copy of the given object's value as an array is made upon conversion. Similar to PHP's current implementation of <nowiki>__toString()</nowiki>, a copy of the given object's value as an array is made upon conversion.
Line 65: Line 54:
 **Type Hinting** **Type Hinting**
  
-<code>+<code php>
 function foo(array $person) { function foo(array $person) {
     var_dump($person);     var_dump($person);
Line 83: Line 72:
 **Return Type** **Return Type**
  
-<code>+<code php>
 function bar(Person $person): array { function bar(Person $person): array {
     return $person;     return $person;
Line 101: Line 90:
 </code> </code>
  
-==== What this is ==== +**array_*  and built-in functions** 
-Describe what this RFC covers and what internal functions trigger <nowiki>__toArray()</nowiki> (array_keys())+ 
 +The array operating functions listed on the [[https://www.php.net/manual/en/ref.array.php|Array Functions]] would first convert an object implementing the <nowiki>__toArray()</nowiki> method before continuing operations. 
 + 
 +<code php> 
 +print_r( 
 +    array_keys($person) 
 +); 
 + 
 +// Output 
 +/* 
 +Array 
 +
 +    [0] => first 
 +    [1] => email 
 +
 +*/ 
 +</code> 
 + 
 +=== Strict Types === 
 + 
 +Automatic casting will not work when using strict types. 
 + 
 +<code php> 
 +declare(strict_types=1)
 + 
 +function bar(Person $person): array { 
 +    return $person; 
 +
 + 
 +bar($person); // Throws an error: "Return value of bar() must be of the type array, object returned" 
 + 
 +function foo(array $person) { 
 +    var_dump($person); 
 +
 + 
 +foo($person); // Throws an error: "Argument 1 passed to foo() must be of the type array, object given" 
 +</code> 
 + 
 +Manual casting within strict types will continue to work and is allowed. 
 + 
 +<code php> 
 +declare(strict_types=1); 
 + 
 +function bar(Person $person): array { 
 +    return (array$person; 
 +
 + 
 +bar($person); // Returns an array 
 + 
 +function foo(array $person) { 
 +    var_dump($person); 
 +
 + 
 +foo((array) $person); // Allowed 
 +</code>
  
 ==== What this is not ==== ==== What this is not ====
-Discuss what the RFC does not cover (accessing and setting values as  you would in a normal array.+This proposal does not allow accessing and setting values as you would in a normal array, that functionality remains with classes implementing the [[https://www.php.net/manual/en/class.arrayaccess.php|ArrayAccess]] interface. 
 + 
 +Array functions that operate on an array by reference such as <nowiki>sort</nowiki> or <nowiki>shuffle</nowiki> will not work on an object implementing <nowiki>__toArray()</nowiki> under this proposal.
  
 ===== Backward Incompatible Changes ===== ===== Backward Incompatible Changes =====
-What breaks, and what is the justification for it?+None
  
 ===== Proposed PHP Version(s) ===== ===== Proposed PHP Version(s) =====
Line 115: Line 160:
 ===== RFC Impact ===== ===== RFC Impact =====
 ==== To SAPIs ==== ==== To SAPIs ====
-Describe the impact to CLI, Development web server, embedded PHP etc.+:?: Help needed
  
 ==== To Existing Extensions ==== ==== To Existing Extensions ====
-Will existing extensions be affected?+:?: Help needed
  
 ==== To Opcache ==== ==== To Opcache ====
-It is necessary to develop RFC's with opcache in mind, since opcache is a core extension distributed with PHP.+:?: Help needed
  
-Please explain how you have verified your RFC's compatibility with opcache.+===== Concerns =====
  
-===== Open Issues ===== +A [[https://externals.io/message/105589#105594|concern raised in the initial RFC proposal discussion]] referred to the existing behavior of casting and exposing object state:
-Make sure there are no open issues when the vote starts!+
  
-===== Unaffected PHP Functionality ===== +>As it currently stands, the array cast is the only operation capable of exposing object state without triggering any kind of access guards: it is very much required for anything that works with reflection and typed properties, and possibly the only operation in PHP that operates on state without some contraption intercepting its execution.
-List existing areas/features of PHP that will not be changed by the RFC.+
  
-This helps avoid any ambiguityshows that you have thought deeply about the RFC's impact, and helps reduces mail list noise. +As a response to this concern, the new <nowiki>get_mangled_object_vars()</nowiki> function was added in [[https://github.com/php/php-src/commit/eecd8961d94c50cc6cdc94ec80df8c1ce4881a76|PHP 7.4]].
- +
-===== Future Scope ===== +
-This section details areas where the feature might be improved in future, but that are not currently proposed in this RFC.+
  
 ===== Proposed Voting Choices ===== ===== Proposed Voting Choices =====
-Include these so readers know where you are heading and can discuss the proposed voting options.+Vote will require 2/3 majority
  
 ===== Patches and Tests ===== ===== Patches and Tests =====
-Links to any external patches and tests go here. +No patch exists yetA [[https://github.com/sgolemon/php-src/tree/experimental.toarray|proof of concept]] for type casting was created by Sara Golemonbut no official patch has been created Will need help with this.
- +
-If there is no patch, make it clear who will create a patch, or whether a volunteer to help with implementation is needed. +
- +
-Make it clear if the patch is intended to be the final patch, or is just a prototype. +
- +
-For changes affecting the core languageyou should also provide a patch for the language specification. +
- +
-===== Implementation ===== +
-After the project is implemented, this section should contain  +
-  - the version(s) it was merged into +
-  - a link to the git commit(s) +
-  - a link to the PHP manual entry for the feature +
-  - a link to the language specification section (if any)+
  
 ===== References ===== ===== References =====
-Links to external referencesdiscussions or RFCs+  * PHP Manual: [[https://www.php.net/manual/en/language.oop5.magic.php|magic methods]][[https://www.php.net/manual/en/ref.array.php|Array Functions]], [[https://www.php.net/manual/en/class.arrayaccess.php|ArrayAccess]] .  
 +  * PHP RFC: [[https://wiki.php.net/rfc/custom_object_serialization|New custom object serialization mechanism]] .  
 +  * Initial idea and discussion: [[https://externals.io/message/105589]] . 
  
 ===== Rejected Features ===== ===== Rejected Features =====
-Keep this updated with features that were discussed on the mail lists.+
rfc/to-array.txt · Last modified: 2020/02/11 13:57 by stevenwadejr