From 77708e1ca1299feb446379fcf6587457a3b25127 Mon Sep 17 00:00:00 2001
From: chedi toueiti <chedi.toueiti@gmail.com>
Date: Fri, 29 May 2015 03:41:28 +0100
Subject: [PATCH] Fix for the ArrayFiel get_FIELD_display() bug

---
 django/contrib/postgres/fields/array.py | 22 ++++++++++++++++++++++
 django/db/models/base.py                |  6 ++++++
 2 files changed, 28 insertions(+)

diff --git a/django/contrib/postgres/fields/array.py b/django/contrib/postgres/fields/array.py
index 9da7ec4..14949a6 100644
--- a/django/contrib/postgres/fields/array.py
+++ b/django/contrib/postgres/fields/array.py
@@ -1,4 +1,5 @@
 import json
+import collections
 
 from django.contrib.postgres import lookups
 from django.contrib.postgres.forms import SimpleArrayField
@@ -160,6 +161,27 @@ class ArrayField(Field):
         defaults.update(kwargs)
         return super(ArrayField, self).formfield(**defaults)
 
+    def _get_flatchoices(self):
+        flat = []
+        for choice, value in self.choices:
+            if isinstance(value, (list, tuple)):
+                flat.extend(value)
+            elif isinstance(choice, collections.Hashable):
+                flat.append((choice, value))
+            elif isinstance(choice, list):
+                flat.append((tuple(choice), value))
+        return flat
+
+    def _get_hashable(self, value):
+        if isinstance(value, collections.Hashable):
+            return value
+        elif isinstance(value, list):
+            return tuple(value)
+        else:
+            raise ValueError('Unexpected unhashable type')
+
+    flatchoices = property(_get_flatchoices)
+
 
 @ArrayField.register_lookup
 class ArrayContains(lookups.DataContains):
diff --git a/django/db/models/base.py b/django/db/models/base.py
index b679d08..610cefc 100644
--- a/django/db/models/base.py
+++ b/django/db/models/base.py
@@ -3,6 +3,7 @@ from __future__ import unicode_literals
 import copy
 import inspect
 import warnings
+import collections
 from itertools import chain
 
 from django.apps import apps
@@ -839,6 +840,11 @@ class Model(six.with_metaclass(ModelBase)):
 
     def _get_FIELD_display(self, field):
         value = getattr(self, field.attname)
+        if not isinstance(value, collections.Hashable):
+            try:
+                value = field._get_hashable(value)
+            except:
+                raise ValueError('Value hashing failed')
         return force_text(dict(field.flatchoices).get(value, value), strings_only=True)
 
     def _get_next_or_previous_by_FIELD(self, field, is_next, **kwargs):
-- 
2.4.1

