Introduce 'RenderTreeBuilder.AddComponentParameter()'#46562
Conversation
|
Note to reviewers: This PR will be easier to review by looking at individual commits 🙂 |
|
We'll also want to do an API review of this once we've confirmed this is the general strategy we'll be taking. |
|
This looks good to me. Nice job, @MackinnonBuck! One thing I'd still like to check: do you think we still have adequate unit test coverage for the case where existing RCLs continue to use It's quite possible this coverage is already handled in this PR by virtue of not modifying certain existing tests. But that's very difficult to establish by reading a diff which only shows the things you have modified :) So is this something you could clarify? |
| /// <param name="sequence">An integer that represents the position of the instruction in the source code.</param> | ||
| /// <param name="name">The name of the attribute.</param> | ||
| /// <param name="value">The value of the attribute.</param> | ||
| public void AddComponentParameter(int sequence, string name, object? value) |
There was a problem hiding this comment.
How does this approach work when the parameters are splatted?
There was a problem hiding this comment.
That calls AddMultipleAttributes(int sequence, IEnumerable<KeyValuePair<string, object>>? attributes) which doesn't have the same overload resolution issue.
If you're suggesting adding a AddMultipleComponentParameters method we could do but it would have no difference in behavior. I agree the aesthetics of still having to use AddMultipleAttributes for components are a bit strange, but if RenderTreeBuilder is only intended as a compiler target it's less of a priority.
|
Oh one other idea: would it technically be valid to mark the Perhaps that's too dramatic and too soon, especially given how we never actually intend to remove the method since we never want to break older RCLs. |
|
Is there a way in which we can solve this without requiring a compiler change? I am a bit worried that this is a lot of work to support a niche scenario like implicit type conversions. It seems more trouble than it is worth. |
|
Is it a lot of work? It looks like the PR here is already at a production standard, so what remains is the Razor compiler change. It should be a really trivial change to the actual compiler logic. The only nontrivial bit is that a lot of test baselines will get updated. And there's no time constraint, as the runtime will retain back-compat so the Razor compiler change can be done any time during the 8.0 timeline. Unless I'm missing something of course! |
I think we do - we still have all the |
|
Regarding marking |
Totally fine. It would have been an unnecessary extra point of friction for us to obsolete it without a clear need. |
SteveSandersonMS
left a comment
There was a problem hiding this comment.
I'm fine with this based on the discussion here.
Before merging, do you think it's worth trying to get some kind of signal from the compiler team that they will likely be able to make the corresponding change on their side within the next couple of months? If for some reason they had a problem with this that might force us to re-think. But if they are unconcerned we could be pretty confident.
|
@jaredpar Do you think the Razor Compiler team can make the changes corresponding to those in this PR? |
|
API review issue: #46575 |
|
Random drive-by thought: If there is going to need to be a compiler change anyway, couldn't the compiler change to add |
|
@davidwengier had similar thoughts. I think understanding why that would or wouldn't work would help us prioritize. |
|
Yep had the same thought also. Given the want to obsolete the existing method though, I wasn't sure if there were other issues with it that this API fixes. |
|
@jaredpar, @davidwengier, @chsienki, The Even in the current |
|
Looks like this PR hasn't been active for some time and the codebase could have been changed in the meantime. |
Introduce
RenderTreeBuilder.AddComponentParameter()Fixes an issue where user-defined implicit conversion operators may cause undesirable
RenderTreeBuilder.AddAttribute()overloads to be resolved.Description
Suppose you have defined the following class:
Now let's say you have a Blazor component
MyComponentthat has a parameter of typeFoo. The generatedRenderTreeBuilder.AddAttribute(...)call to set the parameter value will look something like this:We want the
AddAttribute(int sequence, string name, object? value)overload to be resolved, but sinceFoodefines an implicit conversion tostring, theAddAttribute(int sequence, string name, string value)overload gets resolved instead. As a result, the framework later tries to set the component parameter of typeFooto a value of typestring, and an exception is thrown.To solve this problem, this PR adds an
AddComponentParameter(int sequence, string name, object? value)method toRenderTreeBuilder. There is only one overload to choose from, so we don't experience the same problem as we did withAddAttribute(). Also, since component parameter values always get boxed eventually (to be added to aRenderTreeFrame), we're not losing anything by performing the boxing earlier.A corresponding change will have to be made in the Razor compiler so that generated code makes use of the new
AddComponentParameter()method.Validation
Contributes to #18042