Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 39 additions & 12 deletions nosqlite.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@
class MalformedQueryException(Exception):
pass

class MalformedDocument(Exception):
pass


class Connection(object):
"""
Expand Down Expand Up @@ -120,7 +123,12 @@ def insert(self, document):
:returns: inserted document with id
"""
if '_id' in document:
return self.update(document)
return self.update({'_id': document['_id']},
document)

# Check if document is a dict
if type(document) != dict:
raise MalformedDocument('document must be a dictionary, not a %s' % type(document))

# Create it and return a modified one with the id
cursor = self.db.execute("""
Expand All @@ -130,25 +138,27 @@ def insert(self, document):
document['_id'] = cursor.lastrowid
return document

def update(self, document):
def update(self, spec, document):
"""
DEPRECATED in pymongo
Updates a document stored in this collection. If the document does not
already have an '_id' value, it will be created
"""
if '_id' not in document:
return self.insert(document)
#spec = {'key': 'value'}
to_update = self.find(query=spec, skip=0, limit=1)
if to_update: to_update = to_update[0]
else: return None

# Update the stored document, removing the id
copy = document.copy()
del copy['_id']
_id = to_update['_id']

self.db.execute("""
update %s set data = ? where id = ?
""" % self.name, (json.dumps(copy), document['_id']))
""" % self.name, (json.dumps(document), _id))

document['_id'] = _id
return document

def remove(self, document):
def _remove(self, document):
"""
Removes a document from this collection. This will raise AssertionError if the
document does not have an _id attribute
Expand All @@ -164,9 +174,22 @@ def save(self, document):

def delete(self, document):
"""
DEPRECATED
Alias for ``remove``
"""
return self.remove(document)
return self._remove(document)

def delete_one(self, filter):
"""
Delete only the first document according the filter
Params:
- filter: dict with the condition ({'foo':'bar'})
"""
try:
document = self.find(query=filter, limit=1)[0]
except:
return None
return self._remove(document)

def _load(self, id, data):
"""
Expand All @@ -179,20 +202,24 @@ def _load(self, id, data):
document['_id'] = id
return document

def find(self, query=None, limit=None):
def find(self, query=None, skip=None, limit=None):
"""
Returns a list of documents in this collection that match a given query
"""
results = []
query = query or {}
if skip == None: skip = 0

# TODO: When indexes are implemented, we'll need to intelligently hit one of the
# index stores so we don't do a full table scan
cursor = self.db.execute("select id, data from %s" % self.name)
apply = partial(self._apply_query, query)

for match in filter(apply, starmap(self._load, cursor.fetchall())):
results.append(match)
if skip > 0: #Discard match before skip
skip =- 1
else:
results.append(match)

# Just return if we already reached the limit
if limit and len(results) == limit:
Expand Down