-
Notifications
You must be signed in to change notification settings - Fork 4.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
How useful is C# "dynamic" with System.Text.Json.Nodes.JsonObject? #53195
Comments
Tagging subscribers to this area: @eiriktsarpalis, @layomia Issue DetailsCurrently Although dynamic support has been requested, I believe it was primarily desired as a work-around since System.Text.Json didn't have a writeable DOM feature yet. Since System.Text.Json now has a writable DOM through In theory, support for dynamic could make code sharing between C# and scripting languaged like JavaScript a bit easier, but what are other benefits are there? Some negatives of dynamic:
Here's a brief sample of dynamic and non-dynamic programming models: const string Json = "{\"MyNumber\":42, \"MyArray\":[10,11]}";
// dynamic
{
dynamic obj = JsonNode.Parse(Json);
int number = (int)obj.MyNumber;
Debug.Assert(number == 42);
obj.MyString = "Hello";
Debug.Assert((string)obj.MyString == "Hello");
}
// non-dynamic
{
JsonObject obj = JsonNode.Parse(Json).AsObject();
int number = (int)obj["MyNumber"];
Debug.Assert(number == 42);
obj["MyString"] = "Hello";
Debug.Assert((string)obj["MyString"] == "Hello");
} Note that properties on a strongly-typed POCO and collection elements can also be declared as dynamic, and the
|
Well, in my opinion, dynamic makes it a lot cleaner to read/write DOM in applications where speed isn’t a major issue. |
cc @JamesNK |
System.Linq.Expression is "archived component". |
@jkotas are there any plans to update it? Aren’t dynamics a good way to interop with non-statically typed languages? |
I am not aware of any plans around better More discussion on this is at dotnet/designs#163 (comment) |
Maybe in later dotnet versions then. Thanks. |
@KrzysztofCwalina comments on supporting a better version of dynamic (with IntelliSense perhaps)? |
@CyrusNajmabadi how crazy would it be to do something with embedded languages and JSON? Using the JSON to drive IntelliSense of the dynamic object being returned from these APIs? Of course it's easy when you have a JSON literal but I wonder if the schema for IntelliSense could come from outside of the C# type system and feed into it (I guess it's effectively F# type providers). |
My feedback is the same:
|
I prefer the dynamic approach because it is implementation agnostic after deserialization occurs. As a secondary reason, there are common workflows using RESTful WebAPI to send and receive JSON via dynamic. I think this speaks to the importance of supporting dynamic deserialization up and down the stack. |
My understanding of this feature (deserialization to dynamic) is that it was supposed to ship in .NET 6.0, having missed the cut-off for 5.0. |
Unrelated to this issue, is there a list of "archived component" to let us know what are not in actively developed? |
There was apparently a list of archived components in #27790, but I don't know if more components have been archived since then. |
Archived components are tagged in https://github.com/dotnet/runtime/blob/main/docs/area-owners.md |
I prefer a strongly-typed approach. In Manatee.Json (now deprecated), I set up implicit casts from compatible types into my
Limiting it to these types keeps a nice strong type model but also allows for fairly dynamic building. var obj = new JsonObject
{
["key"] = "value",
["otherKey"] = 9
}
var array = new JsonArray { "value", 9, obj }; Using implicit casts this way may give some people (cough E. Lippert cough) a bit of heartburn, but it makes for some very readable code. It's not 100% copy-paste-able from JS, but it's pretty close. Secondarily, I tend to stay as far away from |
I really like the approach from @gregsdennis! But I assume not everyone likes implicit casts. It would be really cool if we could define implicit casts in extension methods. Then we could have an extension class in a namespace |
I think using dynamic for writing/mutating the DOM is clunky, but I think it's very useful for reading. We have many Azure SDK libraries that return raw JSON payloads (as opposed to deserialized "model" types) and we are hoping to use JsonNode with dynamic to access the returned data, e.g.
It does worry me that 'dynamic' is considered to be archived. |
Just to clarify, Krzysztof, it worries you in general about |
I know the question wasn't directed at me, but I'm definitely worried that the JSON API could be dependent on |
Both. New JSON APIs should not depend on "archived" technologies. But on the other hand, the web is full of untyped data and it would be great if BCL had a modern tech to access such data. |
To recap feedback:
Based on this, I'm inclined to suggest removing the "dynamic" support for V6 unless I hear feedback otherwise from @KrzysztofCwalina or others. |
That sounds like the right decision to me, @steveharter. |
Who's working on the "This potential newer flavor" of dynamic? I do think we need it at some point. It might be a syntactic sugar, but the current syntax obscures the user intent enough that our current plan for untyped APIs in the Azure SDK might not be viable without it. After all C# is just syntactic sugar for IL, and you would not enjoy coding in IL, would you? :-) cc: @MadsTorgersen |
Having said that, I would totally prefer a new dynamic flavor. There is no reason to involve the DLR into what amounts to syntactic sugar over dictionary access. I would prefer if dynamic was implemented as a set of attributes applied to simple lookup and cast APIs. |
what are being "archived" ? dynamic or System.Linq.Expression ? |
@John0King Both dynamic (as it exists today) and System.Linq.Expression are archived components. See #27790 for the discussion. |
@jkotas Linq and Expression are largely used in many many place, such as EF Core, And I believe many people do not know about the talking even start, your team should have a announcement to the community that you are discussing about those , I find that any news in https://github.com/dotnet/announcements/issues be noticed by me is also too late, you already done the change and is waiting for feedback about the new change. In fact, today's IMO, you can declare something should not be used , but there must be a replacement, otherwise, how can anyone who used those code and move forward together with the .Net version ? Please don't drop developers ! there no more developers of .net to drop anymore! |
We are not deleting any of these APIs. The existing code that uses these APIs can be moved to new .Net versions just fine. |
@jkotas I think "archived" means: ready for obsolete and deprecated |
It does not. The meaning as we use it is spelled out in the README for the relevant library: |
Wasn't the whole point of #29690 to allow WebAPI to accept untyped json payloads and access them easily. e.g model.Property1? Seems strange you would regress this functionality previously provided by Newtonsoft.Json
|
Yes, but it was concluded that |
Currently
JsonObject
supports C# "dynamic" which primarily means an instance ofJsonObject
can get\set a property value without having to use a string for the property name.Although dynamic support has been requested, I believe it was primarily desired as a work-around since System.Text.Json didn't have a writeable DOM feature yet.
Since System.Text.Json now has a writable DOM through
JsonNode
without dynamic, is the dynamic capability redundant and should it be removed?In theory, support for dynamic could make code sharing between C# and scripting languaged like JavaScript a bit easier, but what are other benefits are there?
Some negatives of dynamic:
GetValue<T>()
, so the copy-paste ability for JavaScript doesn't quite work.System.Text.Json.dll
to have a reference to the largeSystem.Linq.Expressions.dll
, although the IL Linker removes that if dynamic is not used.Here's a brief sample of dynamic and non-dynamic programming models:
Note that properties on a strongly-typed POCO and collection elements can also be declared as dynamic, and the
JsonSerializer
can also support dynamic.The text was updated successfully, but these errors were encountered: