Significado da função de mapa em couchdb-pythons ViewField
-
28-10-2019 - |
Pergunta
Estou usando couchdb.mapping em um de meus projetos. Eu tenho uma classe chamada SupportCase
derivada de Document
que contém todos os campos que desejo.
Meu banco de dados (denominado admin
) contém vários tipos de documentos. Eu tenho um campo type
em todos os documentos que utilizo para distingui-los. Tenho muitos documentos do tipo "case"
que desejo obter usando uma visualização. Eu tenho um documento de design chamado support
com uma visão dentro dele chamada cases
. Se eu solicitar os resultados dessa visualização usando db.view("support/cases)
, recebo uma lista de Row
s que têm o que desejo.
No entanto, quero que de alguma forma isso seja envolvido pela classe SupportCase
para poder chamar uma única função e obter uma lista de todos os SupportCase
s no sistema. Eu criei uma propriedade ViewField
@ViewField.define('cases')
def all(self, doc):
if doc.get("type","") == "case":
yield doc["_id"], doc
Agora, se eu chamar SupportCase.all(db)
, recebo de volta todos os casos.
O que não entendo é se esta visão é pré-computada e armazenada no banco de dados ou feita sob demanda semelhante a db.query
. Se for o último, será lento e quero usar uma visualização pré-computada. Como eu faço isso?
Solução
Acho que você precisa:
@classmethod
def all(cls):
result = cls.view(db, "support/all", include_docs=True)
return result.rows
A classe Document
tem um classmethod view
que envolve as linhas por classe na qual é chamada.Portanto, o seguinte retorna um ViewResult
com linhas do tipo SupportCase
e obtendo .rows
que fornece uma lista de casos de suporte.
SupportCase.view(db, viewname, include_docs=True)
E eu não acho que você precisa entrar na magia do ViewField.Mas deixe-me explicar como funciona.Considere o seguinte exemplo da documentação CouchDB-python
.
class Person(Document):
@ViewField.define('people')
def by_name(doc):
yield doc['name'], doc
Acho que isso é equivalente a:
class Person(Document):
@classmethod
def by_name(cls, db, **kw):
return cls.view(db, **kw)
Com a função original anexada a People.by_name.map_fun
.
Outras dicas
A função de mapa é, em alguns aspectos, análoga a um índice em um banco de dados relacional.Isso não é feito novamente todas as vezes, e quando novos documentos são adicionados, a maneira como são atualizados não exige que tudo seja refeito (é uma espécie de estrutura de árvore).
Este tem um ótimo resumo
ViewField usa uma visão pré-definida, portanto, uma vez construída, será rápida.Definitivamente, não usa uma visualização temporária.