2
votes

I have got a Database class where multiple methods are defined such as find_one, find, update, etc. Here is the example:

@staticmethod
def find(collection, query):
    return Database.DATABASE[collection].find(query)

To return all of the items and return them as class elements which I can later loop through I use the following code inside some other class:

@classmethod
def all(cls):
    return [cls(**elem) for elem in Database.find(ItemConstants.COLLECTION, {})]

What I'm trying to do is to return minimum value based on the column name I'm passing through:

@classmethod
def get_by_parameters(cls, name, category, url, size):
    return [cls(**elem) for elem in Database.find(ItemConstants.COLLECTION,
                                                  {"name": name, "category": category, "url": url,
                                                   "size": size}).sort('time', pymongo.DESCENDING).limit(1)][0]

And this work completely fine and returns one single class item.

But what I'm struggling with is I'm trying to create a method within Database class which is called find_min here is the code for the that: Database class:

@staticmethod
def find_min(collection, query, column):
    Database.DATABASE[collection].find(query).sort({column: pymongo.ASCENDING}).limit(1)

And this is how I'm using another method to call it up.

@classmethod
def get_by_parameters(cls, name, category, url, size):
    return cls(**Database.find_min(ItemConstants.COLLECTION,
                                   {"name": name, "category": category, "url": url,
                                    "size": size}, 'time'))

And it doesn't work, I'm getting the following error:

File "D:\python_projects\price_tracker\venv\lib\site-packages\pymongo\cursor.py", line 676, in sort keys = helpers._index_list(key_or_list, direction) File "D:\python_projects\price_tracker\venv\lib\site-packages\pymongo\helpers.py", line 63, in _index_list raise TypeError("if no direction is specified, " TypeError: if no direction is specified, key_or_list must be an instance of list

1

1 Answers

1
votes

I was missing a return statement. So currently my Database find min method looks like this:

@staticmethod
def find_min(collection, query, column):
    return Database.DATABASE[collection].find(query).sort(column, pymongo.ASCENDING).limit(1)

Which returns a list with one dictionary element inside!

The other URL class which calls the method above looks like this:

@classmethod
def find_oldest(cls):
    return cls(**Database.find_min(URLConstants.COLLECTION, {}, "last_run_time")[0])

To pick up this signle dictionary element inside the list which Database class has passed us over I use slicing method at the enc of a line [0]

I understand that pymongo.find returns a list, but it sort of goes against the option asking pymongo to limit the list to 1 which in my opinion should no longer be a list.