diff --git a/gen/__init__.py b/gen/__init__.py
index 261daa8..8ef53ae 100644
--- a/gen/__init__.py
+++ b/gen/__init__.py
@@ -189,6 +189,15 @@ class Type:
res = True
return res
+ def isSortable(self, usage='search'):
+ '''Can fields of this type be used for sorting purposes (when sorting
+ search results (p_usage="search") or when sorting reference fields
+ (p_usage="ref")?'''
+ if usage == 'search': return self.indexed
+ elif usage == 'ref':
+ return self.type in ('Integer', 'Float', 'Boolean', 'Date') or \
+ ((self.type == 'String') and (self.format == 0))
+
class Integer(Type):
def __init__(self, validator=None, multiplicity=(0,1), index=None,
default=None, optional=False, editDefault=False, show=True,
diff --git a/gen/plone25/mixins/__init__.py b/gen/plone25/mixins/__init__.py
index 82ece9c..3323f40 100644
--- a/gen/plone25/mixins/__init__.py
+++ b/gen/plone25/mixins/__init__.py
@@ -668,6 +668,13 @@ class AbstractMixin:
reverse = rq.get('reverse') == 'True'
self.appy().sort(fieldName, sortKey=sortKey, reverse=reverse)
+ def isRefSortable(self, fieldName):
+ '''Can p_fieldName, which is a field defined on self, be used as a sort
+ key in a reference field?'''
+ appyType = self.getAppyType(fieldName, asDict=False)
+ if not appyType: return True # Probably implicit field 'title'.
+ return appyType.isSortable(usage='ref')
+
def getWorkflow(self, appy=True):
'''Returns the Appy workflow instance that is relevant for this
object. If p_appy is False, it returns the DC workflow.'''
diff --git a/gen/plone25/skin/macros.pt b/gen/plone25/skin/macros.pt
index 153c91d..7473154 100644
--- a/gen/plone25/skin/macros.pt
+++ b/gen/plone25/skin/macros.pt
@@ -857,7 +857,7 @@
class="listing nosort" width="100%" cellpadding="0" cellspacing="0">