Le jeu. 15 mai 2025 à 16:06, Larry Garfield <la...@garfieldtech.com> a écrit :
> On Thu, May 15, 2025, at 1:22 AM, Stephen Reay wrote: > > > I may be missing something here.. > > > > So far the issues are "how do we deal with a parameter for the actual > > object, vs new properties to apply", "should __clone be called before > > or after the changes" and "this won't allow regular readonly properties > > to be modified". > > > > Isn't the previous suggestion of passing the new property arguments > > directly to the __clone method the obvious solution to all three > > problems? > > > > There's no potential for a conflicting property name, the developer can > > use the new property values in the order they see fit relative to the > > logic in the __clone call, and it's inherently in scope to write to any > > (unlocked during __clone) readonly properties. > > I did some exploratory design a few years ago on this front, looking at > the implications of different possible syntaxes. > > https://peakd.com/hive-168588/@crell/object-properties-part-2-examples > > What that article calls "initonly" is essentially what became readonly. > The second example is roughly what this RFC would look like if the extra > arguments were passed to __clone(). As noted in the article, the result is > absolutely awful. > > Auto-setting the values while using the clone($object, ...$args) syntax is > the cleanest solution. Given that experimentation, I would not support an > implementation that passes args to __clone and makes the developer figure > it out. That just makes a mess. > > Rob makes a good point elsewhere in thread that running __clone() > afterward is a way to allow the object to re-inforce validation if > necessary. My concern is whether the method knows it needs to do the extra > validation or not, since it may be arbitrarily complex. It would also > leave no way to reject the changes other than throwing an exception, though > in fairness the same is true of set hooks. Which also begs the question of > whether a set hook would be sufficient that __clone() doesn't need to do > extra validation? At least in the typical case? > > One possibility (just brainstorming) would be to update first, then call > __clone(), but give clone a new optional arg that just tells it what > properties were modified by the clone call. It can then recheck just those > properties or ignore it entirely, as it prefers. If that handles only > complex cases (eg, firstName was updated so the computed fullName needs to > be updated) and set hooks handle the single-property ones, that would > probably cover all bases reasonably well. I like where this is going but here is a variant that'd be even more capable: we could pass the original object to __clone. The benefits I see: - Allow implementing this validation logic you're talking about. - Allow to skip deep-cloning of already updated properties (that's a significant drawback of the current proposal - deep cloning before setting is a potential perf/mem hog built into the engine) : guarding deep-cloning with a strict comparison would be enough. - Allow implementing WeakMap that are able to clone weak-properties as objects are cloned. On this last aspect, I think it's new to the discussion but it's something I've always found very limiting when using weak-map: let's say some metadata are stored about object $foo in a weakmap, it's currently not possible to track those metadata across clones without using some nasty tricks. If __clone were given the original object, it's be easy to duplicate meta-data from $foo to $clone. I have just one concern significant with adding an argument to __clone: it'dbe a BC break to mandate this argument at the declaration level, and adding one right now generates an error with current versions of PHP. However, I think we could (and should if confirmed) provide some FC/BC layer by allowing one to use func_get_args() in __clone. The engine could then verify at compile time that __clone has either one non-nullable "object" argument, or zero. Nicolas