AJAX response is not retaining the order of LinkedHashMap returned from the server

1.2k Views Asked by At

I am using a LinkedHashMap to store map entries sorted by some business rule and I am sending it to the client, but my AJAX response always gets sorted by the map key.

My sort function:

protected Map<Long, String> sortWarehousesMap(Map<Long, String> warehousesMapTemp) {
    List<Map.Entry<Long, String>> entries = new ArrayList<Map.Entry<Long, String>>(warehousesMapTemp.entrySet());

    Collections.sort(entries, new Comparator<Map.Entry<Long, String>>() {

        public int compare(Map.Entry<Long, String> a, Map.Entry<Long, String> b) {
            return a.getValue().compareTo(b.getValue());
        }
    });
    Map<Long, String> sortedWarehousesMapTemp = new LinkedHashMap<Long, String>();
    for (Map.Entry<Long, String> entry : entries) {
        sortedWarehousesMapTemp.put(entry.getKey(), entry.getValue());
    }
    return sortedWarehousesMapTemp;
}

Please help me what am I doing wrong.

2

There are 2 best solutions below

2
On

You mention an AJAX response, so I'm assuming that at some point this is being translated into a JSON representation. As you're using a Map this is going to be converted into a JSON object, and unfortunately the JSON specification makes no guarantees as to the order of properties in an object (see Does JavaScript Guarantee Object Property Order?), it is literally unspecified. Whichever library you are using to convert between Java objects and a JSON representation is probably sorting the keys for you.

If you absolutely must preserve the order of something in JSON, you'll have to use a JSON array.

0
On

I've had the same problem and it didn't happen in FF.
The problem is that the returned map is interpreted as array.
The key of your map is a Long (the same if you use String but with integer value, like "5" for example) so the result is an Array.
My solution has been to add an "_" in front of the key in order to have a fake key.