diff --git a/src/pfwbged/tabellio/documents.py b/src/pfwbged/tabellio/documents.py index 2cad618..88ad795 100644 --- a/src/pfwbged/tabellio/documents.py +++ b/src/pfwbged/tabellio/documents.py @@ -13,10 +13,15 @@ from plone.dexterity.content import Container, Item from plone.supermodel import model from collective.dms.basecontent.dmsdocument import IDmsDocument, DmsDocument +from collective.dms.basecontent.dmsfile import DmsFile +from . import typenames from . import _ +def db_connection(): + return api.portal.get().db._wrapper.connection + class IDocumentsFolder(model.Schema): pass @@ -27,15 +32,12 @@ class DocumentsFolder(Container): _v_dbcache = None # volatile attribute - @property - def db_connection(self): - return api.portal.get().db._wrapper.connection def __iter__(self): if not self._v_dbcache: self._v_dbcache = {} - cursor = self.db_connection.cursor(cursor_factory=psycopg2.extras.NamedTupleCursor) + cursor = db_connection().cursor(cursor_factory=psycopg2.extras.NamedTupleCursor) cursor.execute('''SELECT id, ts, intit, textdefts FROM t_document''') while True: @@ -54,16 +56,8 @@ class DocumentsFolder(Container): except ValueError: pass else: - cursor = self.db_connection.cursor(cursor_factory=psycopg2.extras.NamedTupleCursor) - cursor.execute('''SELECT id, st, ts, type, no, sess, nodoc, anx, date, intit - FROM t_document - WHERE id = %(id)s''', {'id': id}) - row = cursor.fetchone() - cursor.close() - if row is not None: - t = Document.from_named_row(row) - t.portal_type = Document._v_portal_type - return aq_chain(t.__of__(self))[0] + t = Document.from_db(id) + return aq_chain(t.__of__(self))[0] return super(DocumentsFolder, self).__getitem__(id) def keys(self): @@ -191,16 +185,70 @@ class Document(DmsDocument): _v_portal_type = 'pfwbged.tabellio.document' @classmethod - def from_named_row(cls, row): + def from_db(cls, id): + cursor = db_connection().cursor(cursor_factory=psycopg2.extras.NamedTupleCursor) + cursor.execute('''SELECT id, st, ts, type, no, sess, nodoc, anx, date, intit, + text1id, text2id, imageid, textprovts, textdefts + FROM t_document + WHERE id = %(id)s''', {'id': id}) + row = cursor.fetchone() + cursor.close() + if row is None: + raise KeyError() obj = cls() + obj.portal_type = cls._v_portal_type obj.id = row.id obj.title = row.intit - obj.doctype = row.type + obj.doctype = typenames.MAPPING.get(row.type, row.type) obj.no = row.no obj.session = row.sess obj.nodoc = row.nodoc obj.noannexe = row.anx + obj._v_versions = [] + if row.text2id: + obj._v_versions.append(row.text2id) + if row.text1id and not row.text1id in obj._v_versions: + obj._v_versions.append(row.text1id) + if row.imageid: + obj._v_versions.append(row.imageid) return obj + def __getitem__(self, id): + if id.startswith('version-'): + t = DmsFile() + t.id = id.split('-', 1)[1] + t.title = t.id + t.file = None + t.UID = lambda: 'tabellio-' + t.id + t.portal_type = 'dmsmainfile' + return aq_chain(t.__of__(self))[0] + return super(Document, self).__getitem__(id) + + def getFolderContents(self, *args, **kwargs): - return [] + folder = self + parent_path = '/'.join(folder.getPhysicalPath()) + '/' + parent_url = folder.absolute_url() + '/' + + class FakeBrain(object): + portal_type = 'dmsmainfile' + + def __init__(self, object_id): + self.id = 'version-' + object_id + self.title = object_id + + def getObject(self): + return folder[self.id] + + def Title(self): + return self.title + + def getPath(self): + return parent_path + self.id + + def getURL(self, relative=True): + if relative: + return self.id + return parent_url + self.id + + return [FakeBrain(x) for x in reversed(self._v_versions)] diff --git a/src/pfwbged/tabellio/typenames.py b/src/pfwbged/tabellio/typenames.py new file mode 100644 index 0000000..3d41397 --- /dev/null +++ b/src/pfwbged/tabellio/typenames.py @@ -0,0 +1,70 @@ +# -*- coding: utf-8 -*- + +MAPPING = { + 'DECCCF': u'Décret', + 'PJDB': u'Projet de décret budgétaire', + 'PJD': u'Projet de décret', + 'RAPP': u'Rapport de commission', + 'PPD': u'Proposition de décret', + 'CRI': u'Compte rendu intégral', + 'CRICOM': u'Compte rendu intégral de commission', + 'AMENDCOM': u'Amendements en commission', + 'DG-PPR': u'Proposition de résolution', + 'INTERP': u'Interpellation', + 'QO': u'Question orale', + 'QE': u'Question écrite', + 'BQR': u'Bulletin des questions et réponses', + 'BUR': u'Bureau', + 'QE': u'Question écrite', + 'QO': u'Question orale', + 'QA': u'Question d\'actualité', + 'INTERP': u'Interpellation', + 'RP-RACT': u'Rapport d\'activités', + 'ACA': u'Avis d\'une commission annexe', + 'ACCOP': u'Accord de coopération', + 'AMENDSCE': u'Amendements en séance', + 'ANNEXE': u'Annexe', + 'ARRREA': u'Arrêté de réallocation', + 'AVIS': u'Avis', + 'BUDADM': u'Budget administratif', + 'BUFONCPCF': u'Budget de fonctionnement du PCF', + 'CONTRAGES': u'Contrat de gestion', + 'CRI-RE': u'Compte rendu de réunion', + 'DECLAGOUV': u'Déclaration du Gouvernement', + 'ENTENTE': u'Entente', + 'ERRATUM': u'Erratum', + 'ETATRA': u'État des travaux', + 'EXGEBU': u'Exposé général du budget', + 'LICA': u'Liste des candidatures', + 'LISTE': u'Liste', + 'PCM': u'Poursuite à charge d\'un membre', + 'PLAN': u'Plan', + 'PROGJ': u'Programme justificatif', + 'PROGQUINQ': u'Programme quinquennal', + 'RAPPORT': u'Rapport', + 'RAPVERI': u'Rapport de vérification des comptes', + 'REGLPARL': u'Règlement du Parlement', + 'RESO': u'Résolution', + 'COMMUNI': u'Communication de la Présidence', + 'DECLGOUV': u'Déclaration du Gouvernement', + 'DIVERS': u'Divers', + 'ELOGE': u'Éloges funèbres', + 'RESOLU': u'Résolution', + 'PPMR': u'Proposition de modification du règlement', + 'RP-COBS': u'Cahier d\'observations', + 'RP-PREF': u'Préfiguration des résultats', + 'CETAT': u'Avis du Conseil d\'État', + 'CREACOMEN': u'Enquête parlementaire', + 'DG-PJMS': u'Projet de motion', + 'DG-PJR': u'Projet de résolution', + 'DG-PPMS': u'Proposition de motion', + 'BUDDIVERS': u'Budget (divers)', + 'ALLOC': u'Allocution de la Présidence', + 'BUDFON': u'Budget de Fonctionnement du Parlement (sans numéro)', + 'BUDFONN': u'Budget de Fonctionnement du Parlement', + 'DICO': u'Discussion générale conjointe', + 'PRORESN': u'Proposition de résolution (sans numéro)', + 'RASANU': u'Rapport (sans numéro)', + 'DT': u'Débat thématique', + 'EXPART': u'Exposé particulier', +}