0

I'm parsing js file containing object values to C# objects. For now - I've converted JS code to JSON and then tried to convert to C# object.
I'm having problem with coming up to idea of how to generate objects in C#. I've tried doing multiple various tries, mostly with Dictionaries (Dictionary<string,[object]). I Googled, visited SO in multiple questions, no success for now - all my ideas resulted in null object.

Important note - I can't change the source of JS, can change anything after that.

Latest objects idea:

   public class SingleFarm
   {
        public List<string> Modules { get; set; }
        public List<string> Servers { get; set; }
   }

    public class SingleEnv
    {
        public Dictionary<string, SingleFarm> Farms { get; set; }
    }

    public class FarmsModel
    {
        public Dictionary<string, SingleEnv> FarmsModel { get; set; }
    }

Parsing code:

var farmsText = File.ReadAllText(filePath);

//using Jurassic
var engine = new ScriptEngine();
var result = engine.Evaluate(farmsText);
var json = JSONObject.Stringify(engine, result);

var parsed = JsonConvert.DeserializeObject<FarmsModel>(json);

JS file source:

var environments = {};
environments['ENV1'] = {
    "WWW": {
        "Modules": [
            "module21"
        ],
        "Servers": [
            "a-1"
        ]
    }
};

environments['ENV2'] = {
    "FARM1": {
        "Modules": [
            "module41"
        ],
        "Servers": [
            "s1",
            "s2"
        ]
    },
    "FARM2": {
        "Modules": [
            "module11"
        ],
        "Servers": [
            ""
        ]
    },
    "FARM3": {
        "Modules": [
            "module1"
        ],
        "Servers": [
            ""
        ]
    }
};

environments['ENV3'] = {
    "FARM1": {
        "Modules": [
            "module10"
        ],
        "Servers": [
            "server1"
        ]
    },
    "FARM2": {
        "Modules": [
            "module22"
        ],
        "Servers": [
            ""
        ]
    },
    "FARM3": {
        "Modules": [
            "module33"
        ],
        "Servers": [
            "server3"
        ]
    }
};

JSON looks as follows:

{
    "ENV1": {
        "WWW": {
            "Modules": [
                "module21"
            ],
            "Servers": [
                "a-1"
            ]
        }
    },
    "ENV2": {
        "FARM1": {
            "Modules": [
                "module41"
            ],
            "Servers": [
                "s1",
                "s2"
            ]
        },
        "FARM2": {
            "Modules": [
                "module11"
            ],
            "Servers": [
                ""
            ]
        },
        "FARM3": {
            "Modules": [
                "module1"
            ],
            "Servers": [
                ""
            ]
        }
    },
    "ENV3": {
        "FARM1": {
            "Modules": [
                "module10"
            ],
            "Servers": [
                "server1"
            ]
        },
        "FARM2": {
            "Modules": [
                "module22"
            ],
            "Servers": [
                ""
            ]
        },
        "FARM3": {
            "Modules": [
                "module33"
            ],
            "Servers": [
                "server3"
            ]
        }
    }
}

Do you have any ideas?

Karolina Ochlik
  • 908
  • 6
  • 8
  • Why must you “generate objects”? You can [deserialize JSON to a `Dictionary`](https://stackoverflow.com/questions/1207731/) is that not what you want? – Dour High Arch Aug 16 '20 at 17:49
  • What does the deserialization code look like? – ESG Aug 16 '20 at 17:50
  • @ESG I added it to my question – Karolina Ochlik Aug 16 '20 at 17:55
  • Really depends whether you just want a Dictionary of strings, or if you'd prefer to have DataContract classes with various type serialization. If you prefer the latter, have a look at https://www.newtonsoft.com/json/help/html/Introduction.htm – defines Aug 16 '20 at 17:57

1 Answers1

1

You shouldn't be trying to serialize dictionaries to objects since it will try to map the property names.

If you use

var parsed = JsonConvert.DeserializeObject<Dictionary<string, Dictionary<string, SingleFarm>>>(json);

It should work. Fiddle

ESG
  • 8,988
  • 3
  • 35
  • 52
  • Yes, it does work, but unfortunately I need the name of environment in my objects. – Karolina Ochlik Aug 16 '20 at 18:08
  • @GrzegorzOchlik it's there, it's the key of the dictionary – ESG Aug 16 '20 at 18:09
  • I tried it on "live" data and on a mock I provided. Result is the same: `Newtonsoft.Json.JsonSerializationException: 'Cannot deserialize the current JSON array (e.g. [1,2,3]) into type 'tsunamigui.Models.SingleFarm' because the type requires a JSON object (e.g. {"name":"value"}) to deserialize correctly.` – Karolina Ochlik Aug 16 '20 at 18:24
  • @GrzegorzOchlik it works in the fiddle with the json you provided above, I can't do more with the information provided. – ESG Aug 16 '20 at 18:48
  • Marking it as answer, as it helped me the most :) I modified the text from file to explicitly return the array: `farmsText = $"(function(){{ {farmsText} return environments;}})()";` and it works. Gotta do some parsing with it. Thank you! – Karolina Ochlik Aug 16 '20 at 18:56