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 <andr...@dqxtech.net> wrote:
>
> On Wed, 8 Sept 2021 at 18:33, Lynn <kja...@gmail.com> wrote:
> >
> > On Wed, Sep 8, 2021 at 5:38 PM Mike Schinkel <m...@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

-- 
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: https://www.php.net/unsub.php

Reply via email to