Re: Alias stdClass to DynamicObject?

From: Date: Wed, 08 Sep 2021 20:48:22 +0000
Subject: Re: Alias stdClass to DynamicObject?
References: 1 2 3 4 5 6  Groups: php.internals 
Request: Send a blank email to internals+get-116016@lists.php.net to get a copy of this message
Wow! I notice that ArrayObject already does everything we would need for json_encode(). assert(json_encode(new ArrayObject([5])) === '{"0":5}'); However, it does so in a very strange way, not using any of the public methods, but also not using dynamic properties. It seems there is a hard-coded internal implementation when calling json_encode() or converting to array. https://3v4l.org/rAc4K I think we would want something more clean and transparent. On Wed, 8 Sept 2021 at 21:58, Andreas Hennings <andreas@dqxtech.net> wrote: > > On Wed, 8 Sept 2021 at 18:33, Lynn <kjarli@gmail.com> wrote: > > > > On Wed, Sep 8, 2021 at 5:38 PM Mike Schinkel <mike@newclarity.net> wrote: > > > > > A couple more things; add a > > > JSON_OUTPUT_DYNAMIC_OBJECT flag to output to > > > DynamicObject for json_decode(), add a 3rd parameter > > > for flags to > > > var_export() for the same reason, a > > > 'return_dynamic_object' option for > > > unserialize(), and so on. > > > > > > > It would also be interesting to enter a user-defined class here to work as > > a reversed JsonSerializable. Could be a static factory method for all I > > care, and would omit the requirement of serialization libraries for > > "simple" things where you still want decent object typing. Could also work > > together with interfaces accepting properties, effectively making the > > result of json_decode an anonymous class that still adheres to an > > interface. In case of the custom 'deserialization' you can throw exceptions > > if the format is not correct. In the case of an anonymous class with an > > interface it could throw an exception if the structure doesn't match > > (possibly controlled by flags?). > > I think we want round-trips of json_decode() + json_encode() to work > loss-free, without any custom classes or extra parameters. > > Currently, '{}' and '[]' have different results with json_decode(). > > assert(json_encode(json_decode('{}')) === '{}'); // Perfect round-trip. > assert(json_encode(json_decode('{}', JSON_OBJECT_AS_ARRAY)) === '[]'); > // Lossy round-trip. > > This can only work if we have a built-in data transfer object, > distinct from arrays. > Currently this is \stdClass, using the dynamic property mechanism. > > But one could easily imagine a different kind of data transfer object, > which would use a different mechanism instead of dynamic properties. > > A native implementation of JsonSerializable does not really work here, > because ->jsonSerialize() would have to return \stdClass to result in > '{}'. > Instead, what about something with a "->getData(): array" method, but > then json_decode() would encode it as '{}'? > > assert(json_decode('{}') instanceof DataTransferObject); > assert(json_decode('{}')->getData() === []); > assert(json_encode(json_decode('{}')->getData()) === '[]'); > assert(json_encode(json_decode('{}')) === '{}'); > > For the proposed rename: > - If we can fully deprecate and replace dynamic properties long-term, > I would rather keep the name \stdClass until it dies. > - Instead of an alias or rename, I would rather have a new data > transfer object class which would not rely on dynamic properties, but > on a new mechanism. > > Imo, creating an alias won't actually make life easier for anyone, > unless we can fully remove and replace \stdClass. > It would mean that developers need to learn both names, and understand > how aliases work - something you don't really need to learn otherwise. > Think of the silly wtfs that can occur if people don't fully > understand aliases, or are not aware that DynamicObject is just an > alias, while \ReflectionClass and get_class() still return 'stdClass' > as the class name. > > -- Andreas

« previous php.internals (#116016) next »