# # Copyright (c) 2012 Helmut Merz helmutm@cy55.de # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA # """ Report type, report concept adapter, and other reporting stuff. """ from zope import schema, component from zope.component import adapts from zope.interface import Interface, Attribute, implements from zope.cachedescriptors.property import Lazy from zope.security.proxy import removeSecurityProxy from zope.traversing.api import getName from cybertools.composer.report.base import Report as BaseReport from cybertools.composer.report.base import LeafQueryCriteria, CompoundQueryCriteria from cybertools.composer.report.interfaces import IReport as IBaseReport from cybertools.composer.report.interfaces import IReportParams from cybertools.composer.report.result import ResultSet, Row from cybertools.util.jeep import Jeep from loops.common import AdapterBase from loops.interfaces import ILoopsAdapter from loops.type import TypeInterfaceSourceList from loops import util from loops.util import _ # interfaces class IReport(ILoopsAdapter, IReportParams): """ The report adapter for the persistent object (concept) that stores the report in the concept map. """ reportType = schema.Choice( title=_(u'Report Type'), description=_(u'The type of the report.'), default=None, source='loops.expert.reportTypeSource', required=True) name = Attribute('The name of the report.') class IReportInstance(IBaseReport): """ The report-type-specific object (an adapter on the report) that does the real report execution stuff. """ # report concept adapter and instances class Report(AdapterBase): implements(IReport) _contextAttributes = list(IReport) @Lazy def name(self): return getName(self.context) TypeInterfaceSourceList.typeInterfaces += (IReport,) class ReportInstance(BaseReport): implements(IReportInstance) adapts(IReport) rowFactory = Row #headerRowFactory = Row view = None # set upon creation def __init__(self, context): self.context = context self.name = self.type def getResultsRenderer(self, name, macros): return macros[name] @property def queryCriteria(self): return self.context.queryCriteria def getResults(self, dynaParams=None): crit = self.queryCriteria limits = self.limits if crit is None: parts = Jeep() #return ResultSet(self, []) else: if dynaParams is not None: for k, v in dynaParams.items(): if k == 'limits': limits = v break if k in crit.parts.keys(): crit.parts[k].comparisonValue = v parts = Jeep(crit.parts) if getattr(self, 'limitsCount', ''): limits = None result = list(self.selectObjects(parts)) # may modify parts qc = CompoundQueryCriteria(parts) return ResultSet(self, result, rowFactory=self.rowFactory, sortCriteria=self.getSortCriteria(), queryCriteria=qc, limits=limits) def selectObjects(self, parts): # to be implemented by subclass return [] @Lazy def conceptManager(self): return self.view.conceptManager @Lazy def recordManager(self): return self.view.loopsRoot.getRecordManager() @Lazy def hasReportPredicate(self): return self.conceptManager['hasreport'] class ReportTypeSourceList(object): implements(schema.interfaces.IIterableSource) def __init__(self, context): self.context = context def __iter__(self): return iter(self.reportTypes) def __contains__(self, value): return value in [item[0] for item in self] @Lazy def reportTypes(self): result = [] for item in component.getAdapters([self.context], IReportInstance): name, adapter = item adapter = removeSecurityProxy(adapter) label = getattr(adapter, 'label', name) result.append((name, label,)) return result def __len__(self): return len(self.reportTypes) # default concept report class DefaultConceptReportInstance(ReportInstance): label = u'Default Concept Report'