Question

I'm using the couchdb.mapping in one of my projects. I have a class called SupportCase derived from Document that contains all the fields I want.

My database (called admin) contains multiple document types. I have a type field in all the documents which I use to distinguish between them. I have many documents of type "case" which I want to get at using a view. I have design document called support with a view inside it called cases. If I request the results of this view using db.view("support/cases), I get back a list of Rows which have what I want.

However, I want to somehow have this wrapped by the SupportCase class so that I can call a single function and get back a list of all the SupportCases in the system. I created a ViewField property

@ViewField.define('cases')
def all(self, doc):
    if doc.get("type","") == "case":
        yield doc["_id"], doc

Now, if I call SupportCase.all(db), I get back all the cases.

What I don't understand is whether this view is precomputed and stored in the database or done on demand similar to db.query. If it's the latter, it's going to be slow and I want to use a precomputed view. How do I do that?

Was it helpful?

Solution

I think what you need is:

@classmethod
def all(cls):
    result = cls.view(db, "support/all", include_docs=True)
    return result.rows

Document class has a classmethod view which wraps the rows by class on which it is called. So the following returns you a ViewResult with rows of type SupportCase and taking .rows of that gives a list of support cases.

SupportCase.view(db, viewname, include_docs=True)

And I don't think you need to get into the ViewField magic. But let me explain how it works. Consider the following example from the CouchDB-python documentation.

class Person(Document):
     @ViewField.define('people')
     def by_name(doc):
         yield doc['name'], doc

I think this is equivalent to:

class Person(Document):
    @classmethod
    def by_name(cls, db, **kw):
        return cls.view(db, **kw)

With the original function attached to People.by_name.map_fun.

OTHER TIPS

The map function is in some ways analogous to an index in a relational database. It is not done again every time, and when new documents are added the way it is updated does not require everything to be redone (it's a kind of tree structure).

This has a pretty good summary

ViewField uses a pre-defined view so, once built, will be fast. It definitely doesn't use a temporary view.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top