Hi,

I made a small patch to fix the problem with ORDER BY queries. It
works with ORDER BY ?var, DESC(?var) or ASC(?var). Functions are not
yet supported. The patch also fixes LIMIT.

Cheers,
Mikael
Index: rdflib/sparql/bison/SPARQLEvaluate.py
===================================================================
--- rdflib/sparql/bison/SPARQLEvaluate.py	(revision 866)
+++ rdflib/sparql/bison/SPARQLEvaluate.py	(working copy)
@@ -17,7 +17,7 @@
 from Util import ListRedirect
 from Operators import *
 from FunctionLibrary import *
-from SolutionModifier import DESCENDING_ORDER
+from SolutionModifier import ASCENDING_ORDER
 from Query import AskQuery, SelectQuery
 
 DEBUG = False
@@ -379,14 +379,23 @@
             orderBy     = []
             orderAsc    = []
             for orderCond in query.query.solutionModifier.orderClause:
-                expr = orderCond.expression.reduce()
-                assert isinstance(expr,Variable),"Support for ORDER BY with anything other than a variable is not supported: %s"%expr
-                orderBy.append(expr)
-                orderAsc.append(orderCond.order == DESCENDING_ORDER)
+                # is it a variable?
+                if isinstance(orderCond,Variable):
+                    orderBy.append(orderCond)
+                    orderAsc.append(ASCENDING_ORDER)
+                # is it another expression, only variables are supported
+                else:
+                    expr = orderCond.expression
+                    assert isinstance(expr,Variable),"Support for ORDER BY with anything other than a variable is not supported: %s"%expr
+                    orderBy.append(expr)                    
+                    orderAsc.append(orderCond.order == ASCENDING_ORDER)
+
+        limit = query.query.solutionModifier.limitClause and int(query.query.solutionModifier.limitClause) or None
+
         offset = query.query.solutionModifier.offsetClause and int(query.query.solutionModifier.offsetClause) or 0
         return result.select(query.query.variables,
                              query.query.distinct,
-                             query.query.solutionModifier.limitClause,
+                             limit,
                              orderBy,
                              orderAsc,
                              offset
from rdflib import ConjunctiveGraph, plugin
from rdflib.store import Store
from StringIO import StringIO
import unittest

test_data = """ 
@prefix foaf:       <http://xmlns.com/foaf/0.1/> .
@prefix rdf:        <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .

_:a  foaf:name       "Alice" .
_:b  foaf:name       "Bob" .
_:c  foaf:name       "Charlie" .
_:d  foaf:name       "David" .
_:e  foaf:name       "Eve" .
"""

class LimitAndOffsetTest(unittest.TestCase):
    correctOrder = ["Alice", "Bob", "Charlie", "David", "Eve"]
    
    def _query(self, query):
        graph = ConjunctiveGraph(plugin.get('IOMemory',Store)())
        graph.parse(StringIO(test_data), format="n3")
        return graph.query(query)
        
    def testLimit(self):
        test_query = """
        PREFIX foaf: <http://xmlns.com/foaf/0.1/>

        SELECT ?x ?name

        WHERE { ?x foaf:name ?name . }
        LIMIT 4
        """
        self.assertEqual(len(self._query(test_query)), 4)

    def testOffset(self):
        test_query = """
        PREFIX foaf: <http://xmlns.com/foaf/0.1/>

        SELECT ?x ?name

        WHERE { ?x foaf:name ?name . }
        OFFSET 2
        """
        self.assertEqual(len(self._query(test_query)), 3)

def main():
    unittest.main()
        
if __name__ == '__main__':
    main()
from rdflib import ConjunctiveGraph, plugin
from rdflib.store import Store
from StringIO import StringIO
import unittest

test_data = """ 
@prefix foaf:       <http://xmlns.com/foaf/0.1/> .
@prefix rdf:        <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .

_:a  foaf:name       "Alice" .
_:b  foaf:name       "Bob" .
_:c  foaf:name       "Charlie" .
_:d  foaf:name       "David" .
_:e  foaf:name       "Eve" .
"""

class OrderByTest(unittest.TestCase):
    correctOrder = ["Alice", "Bob", "Charlie", "David", "Eve"]
    
    def _query(self, query):
        graph = ConjunctiveGraph(plugin.get('IOMemory',Store)())
        graph.parse(StringIO(test_data), format="n3")
        return graph.query(query)
        
    def testOrderBy(self):
        test_query = """
        PREFIX foaf: <http://xmlns.com/foaf/0.1/>

        SELECT ?x ?name

        WHERE { ?x foaf:name ?name . }
        ORDER BY ?name
        """
        self.assertEqual([str(literal) for (node, literal) in self._query(test_query)], self.correctOrder)

    def testOrderByAsc(self):
        test_query = """
        PREFIX foaf: <http://xmlns.com/foaf/0.1/>

        SELECT ?x ?name

        WHERE { ?x foaf:name ?name . }
        ORDER BY ASC(?name)
        """
        self.assertEqual([str(literal) for (node, literal) in self._query(test_query)], self.correctOrder)

    def testOrderByDesc(self):
        self.correctOrder.reverse()
        test_query = """
        PREFIX foaf: <http://xmlns.com/foaf/0.1/>

        SELECT ?x ?name

        WHERE { ?x foaf:name ?name . }
        ORDER BY DESC(?name)
        """
        self.assertEqual([str(literal) for (node, literal) in self._query(test_query)], self.correctOrder)
        
def main():
    unittest.main()
        
if __name__ == '__main__':
    main()
_______________________________________________
Dev mailing list
[email protected]
http://rdflib.net/mailman/listinfo/dev

Reply via email to