如何在javascript扩展样式中扩展动态c#对象?

时间:2016-12-02 11:14:42

标签: javascript c# .net json expandoobject

**这是一个自我回答的问题,因为我找到了解决方案,但我没有在这里找到**

用例

来自应用程序A (C#后端)的未明确定义的结构化数据必须传递给应用程序B (SignalR前端的ASP.Net C#应用程序)使用HTTP,只需使用SignalR将消息传递给javascript客户端。

数据用于实时登录。

为什么不创建课程? 由于传入的数据可以更改,因此不必由应用程序B进行分析,并且每个类的代码不能在两端之间共享(C#/ JavaScript)。

另外,我希望能够做到这样的事情:

var foo = DynamicExtend(
    new { propExtendedFromDynamic1 = true }, 
    new { propExtendedFromDynamic2 = true }
);
string jsonText = Newtonsoft.Json.JsonConvert.SerializeObject(foo);
dynamic unserializedFoo = JObject.Parse(jsonText);

1 个答案:

答案 0 :(得分:0)

使用expando对象

由于无法轻易修改动态对象,因此需要使用ExpandoObject。

唯一的缺点是它无法完成具有其他动态属性的原始动态对象,并且仍然使用与$.extend(true, {p1:1},{p2:2})相同的引用(如果你知道jQuery,你会理解)。

public static dynamic DynamicExtend(params dynamic[] extendedItems)
{
        if (extendedItems == null || extendedItems.Length == 0 || extendedItems[0] == null)
            throw new Exception("Missing initial dynamic property");

        if (extendedItems.Length == 1)
            return extendedItems.First();

        dynamic r = new ExpandoObject();
        // We will need that casted value or the r[propertyName]="someValue" will fail
        var dynamicReturnedEditable = (IDictionary<string, object>)r;

        // For each dynamic object passed in
        foreach (dynamic extensionHolder in extendedItems)
        {
            var expandoCase = extensionHolder as IDictionary<string, object>;
            if (expandoCase == null)
            {
                // Pour chaque propriété
                foreach (var property in ((object)extensionHolder).GetType().GetProperties())
                {
                    // Faire la copie sur l'ExpandoObject (qui gère nativement le rajout de propriété) en utilisant les données extraites de l'objet dynamique
                    dynamicReturnedEditable[property.Name] = property.GetValue(extensionHolder, null);
                }
            }
            else
            {
                foreach (var propertyName in expandoCase.Keys)
                {
                    // Faire la copie sur l'ExpandoObject (qui gère nativement le rajout de propriété) en utilisant les données extraites de l'objet dynamique
                    dynamicReturnedEditable[propertyName] = expandoCase[propertyName];
                }
            }
        }

        return r;
}

注意:它不支持JObject.Parse(jsonText);产生的参数,因为它必须从中读取属性。