0

This question is related to what I have asked here

I'm getting this output in my apex controller and I'm looking a way to extract or parse this output string into List or Class?

18:59:48:001 USER_DEBUG [21]|DEBUG|--debuglogbranch:
{attributes={type=Account, url=/services/data/v38.0/sobjects/Account/0014100000BNrJEAA1}, 
   Id=0014100000BNrJEAA1, Name=test2, ParentId=00141000009mTavAAE, 
   children=[
    {
       attributes={type=Account, 
       url=/services/data/v38.0/sobjects/Account/0014100000BNrLIAA1},     
       Id=0014100000BNrLIAA1, Name=test2.2, 
       ParentId=0014100000BNrJEAA1, 
       level=3, 
       expanded=false, 
       uid=0.7055100027498606, 
       parent_uid=0.11747820325450764, 
       children=[]
     }
    ], 
    level=2, 
    expanded=true, 
    uid=0.11747820325450764, 
    parent_uid=0.33335628016211594, 
    selected=true
}

I have tried something like this:

@RemoteAction
public static void mymethod(String branch){
Map<String, Object> root = (Map<String, Object>)JSON.deserializeUntyped(branch);
    List<Object> items = (List<Object>)root.get('attributes'); //ERROR
    for (Object item : items) {
        Map<String, Object> i = (Map<String, Object>)item;
        System.debug(i.get('id'));
    }
}

got this error:

> Visualforce Remoting Exception: , column 1: Invalid conversion
> from runtime type String to Map<String,ANY>
4
  • Use workbench to check returned json
    – o-lexi
    Commented Dec 6, 2016 at 1:44
  • "attributes" : { "type" : "Account", "url" : "/services/data/v38.0/sobjects/Account/0014100000BNrLIAA1" }, "Id" : "0014100000BNrLIAA1",
    – o-lexi
    Commented Dec 6, 2016 at 1:46
  • do you a link how you check the returned type in workbench
    – Nick
    Commented Dec 6, 2016 at 1:46
  • okay i'm in the workbench and i see the account record but where do you see the returned type?
    – Nick
    Commented Dec 6, 2016 at 1:47

1 Answer 1

2

I hit a very similar issue to this the other day, I didn't bother trying to establish why this works but I found that going via an intermediate variable helped, but I was indexing the list directly because I only cared about the first entry:

List<Object> messageResults = (List<Object>)resBody.get('messages');
Map<String, Object> messageResult = (Map<String, Object>)messageResults[0];

A sub-standard workaround for your scenario might be to use a regular for loop:

for (Integer i = 0; i < items.size(); i++)
    Map<String, Object> item = (Map<String, Object>)items[i];
    System.debug(item.get('id'));
}

Although you'd expect Object to be a pure reference to any object there is definitely some funkiness around how it's been implemented; I've hit a scenario before where some code just wouldn't work as expected when using it.

3
  • You just said line 27... without any line numbers ;) Try splitting that in two maybe: Object tempItems = (Object)root.get('attributes'); List<Object> items = (List<Object>)tempItems;
    – Matt Lacey
    Commented Dec 6, 2016 at 1:04
  • even after splitting that into two getting the error column 1: Invalid conversion from runtime type Map<String,ANY> to List<ANY>
    – Nick
    Commented Dec 6, 2016 at 1:17
  • 2
    That's because "attributes" maps to a Map<String, Object>, not a List<Object>. Key-value pairs.
    – Adrian Larson
    Commented Dec 6, 2016 at 2:49

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .