diff --git a/expert/README.txt b/expert/README.txt index d3fd786..545c865 100644 --- a/expert/README.txt +++ b/expert/README.txt @@ -27,7 +27,7 @@ configuration): >>> concepts, resources, views = t.setup() >>> len(concepts) + len(resources) - 36 + 38 >>> loopsRoot = site['loops'] @@ -47,11 +47,11 @@ Type- and text-based queries >>> from loops.expert import query >>> qu = query.Title('ty*') >>> list(qu.apply()) - [0, 2, 65] + [0, 2, 69] >>> qu = query.Type('loops:*') >>> len(list(qu.apply())) - 36 + 38 >>> qu = query.Type('loops:concept:predicate') >>> len(list(qu.apply())) diff --git a/expert/search.txt b/expert/search.txt index 18df101..d66ed00 100755 --- a/expert/search.txt +++ b/expert/search.txt @@ -66,13 +66,13 @@ zcml in real life: >>> t = searchView.typesForSearch() >>> len(t) - 15 + 16 >>> t.getTermByToken('loops:resource:*').title 'Any Resource' >>> t = searchView.conceptTypesForSearch() >>> len(t) - 12 + 13 >>> t.getTermByToken('loops:concept:*').title 'Any Concept' @@ -91,7 +91,7 @@ a controller attribute for the search view. >>> searchView.submitReplacing('1.results', '1.search.form', pageView) 'submitReplacing("1.results", "1.search.form", - "http://127.0.0.1/loops/views/page/.target96/@@searchresults.html");...' + "http://127.0.0.1/loops/views/page/.target100/@@searchresults.html");...' Basic (text/title) search ------------------------- @@ -177,7 +177,7 @@ of the concepts' titles: >>> request = TestRequest(form=form) >>> view = Search(page, request) >>> view.listConcepts() - u"{identifier: 'id', items: [{label: 'Zope (Thema)', name: 'Zope', id: '101'}, {label: 'Zope 2 (Thema)', name: 'Zope 2', id: '103'}, {label: 'Zope 3 (Thema)', name: 'Zope 3', id: '105'}]}" + u"{identifier: 'id', items: [{label: 'Zope (Thema)', name: 'Zope', id: '105'}, {label: 'Zope 2 (Thema)', name: 'Zope 2', id: '107'}, {label: 'Zope 3 (Thema)', name: 'Zope 3', id: '109'}]}" Preset Concept Types on Search Forms ------------------------------------ @@ -219,9 +219,9 @@ and thus include the customer type in the preset search types. >>> searchView.conceptsForType('loops:concept:customer') [{'token': 'none', 'title': u'not selected'}, - {'token': '74', 'title': u'Customer 1'}, - {'token': '76', 'title': u'Customer 2'}, - {'token': '78', 'title': u'Customer 3'}] + {'token': '78', 'title': u'Customer 1'}, + {'token': '80', 'title': u'Customer 2'}, + {'token': '82', 'title': u'Customer 3'}] Let's use this new search option for querying: diff --git a/external/README.txt b/external/README.txt index 24e3816..5fddc0e 100644 --- a/external/README.txt +++ b/external/README.txt @@ -17,7 +17,7 @@ Let's set up a loops site with basic and example concepts and resources. >>> concepts, resources, views = t.setup() >>> loopsRoot = site['loops'] >>> len(concepts), len(resources), len(views) - (33, 3, 1) + (35, 3, 1) Importing loops Objects @@ -44,7 +44,7 @@ Creating the corresponding objects >>> loader = Loader(loopsRoot) >>> loader.load(elements) >>> len(concepts), len(resources), len(views) - (34, 3, 1) + (36, 3, 1) >>> from loops.common import adapted >>> adMyquery = adapted(concepts['myquery']) @@ -118,7 +118,7 @@ Extracting elements >>> extractor = Extractor(loopsRoot, os.path.join(dataDirectory, 'export')) >>> elements = list(extractor.extract()) >>> len(elements) - 65 + 67 Writing object information to the external storage -------------------------------------------------- diff --git a/knowledge/data/knowledge_de.dmp b/knowledge/data/knowledge_de.dmp index d1a0e36..83367d9 100644 --- a/knowledge/data/knowledge_de.dmp +++ b/knowledge/data/knowledge_de.dmp @@ -4,6 +4,8 @@ type(u'competence', u'Kompetenz', viewName=u'', type(u'person', u'Person', viewName=u'', typeInterface=u'loops.knowledge.interfaces.IPerson', options=u'action.portlet:createQualification,editPerson') +type(u'report', u'Report', viewName=u'', + typeInterface='loops.expert.report.IReport') type(u'task', u'Aufgabe', viewName=u'', typeInterface=u'loops.knowledge.interfaces.ITask', options=u'action.portlet:createTask,editTask') @@ -26,6 +28,10 @@ concept(u'requires', u'requires', u'predicate') concept(u'issubtype', u'is Subtype', u'predicate', options=u'hide_children', predicateInterface='loops.interfaces.IIsSubtype') +# reports +concept(u'qualification_overview', u'Qualification Overview', u'report', + reportType=u'qualification_overview') + # structure child(u'general', u'competence', u'standard') child(u'general', u'depends', u'standard') diff --git a/knowledge/data/knowledge_update_de.dmp b/knowledge/data/knowledge_update_de.dmp index 403589f..2a359c2 100644 --- a/knowledge/data/knowledge_update_de.dmp +++ b/knowledge/data/knowledge_update_de.dmp @@ -26,6 +26,10 @@ concept(u'requires', u'requires', u'predicate') concept(u'issubtype', u'is Subtype', u'predicate', options=u'hide_children', predicateInterface='loops.interfaces.IIsSubtype') +# reports +concept(u'qualification_overview', u'Qualification Overview', u'report', + reportType=u'qualification_overview') + # structure child(u'general', u'competence', u'standard') child(u'general', u'depends', u'standard') diff --git a/knowledge/qualification/browser.py b/knowledge/qualification/browser.py index 29b53d6..e9e6641 100644 --- a/knowledge/qualification/browser.py +++ b/knowledge/qualification/browser.py @@ -1,5 +1,5 @@ # -# Copyright (c) 2013 Helmut Merz helmutm@cy55.de +# Copyright (c) 2014 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 @@ -18,7 +18,7 @@ """ Definition of view classes and other browser related stuff for the -loops.knowledge package. +loops.knowledge.qualification package. """ from zope import interface, component @@ -27,10 +27,9 @@ from zope.cachedescriptors.property import Lazy from loops.expert.browser.report import ResultsConceptView from loops.knowledge.browser import template, knowledge_macros -from loops.knowledge.qualification.base import QualificationRecord -class PersonQualificationView(ResultsConceptView): +class Qualifications(ResultsConceptView): - pass + reportName = 'qualification_overview' diff --git a/knowledge/qualification/configure.zcml b/knowledge/qualification/configure.zcml index dea246f..a6ca61b 100644 --- a/knowledge/qualification/configure.zcml +++ b/knowledge/qualification/configure.zcml @@ -15,4 +15,26 @@ + + + + + + + + + + diff --git a/knowledge/qualification/report.py b/knowledge/qualification/report.py new file mode 100644 index 0000000..7b0a8e8 --- /dev/null +++ b/knowledge/qualification/report.py @@ -0,0 +1,43 @@ +# +# Copyright (c) 2014 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 +# + +""" +Qualification management report definitions. +""" + +from cybertools.util.jeep import Jeep +from loops.expert.report import ReportInstance +from loops.organize.work.report import WorkRow +from loops.organize.work.report import deadline, day, task, party, state +from loops.organize.work.report import workTitle, workDescription + + +class QualificationOverview(ReportInstance): + + type = "qualification_overview" + label = u'Qualification Overview' + + rowFactory = WorkRow + + fields = Jeep((day, deadline, party, task, workTitle, state)) + + taskTypeNames = ('folder','query', 'competence',) + defaultOutputFields = fields + + def getTasks(self, parts): + return [] diff --git a/knowledge/tests.py b/knowledge/tests.py index 8340a79..11f8ec4 100755 --- a/knowledge/tests.py +++ b/knowledge/tests.py @@ -7,6 +7,7 @@ from zope import component from zope.interface.verify import verifyClass from zope.testing.doctestunit import DocFileSuite +from loops.expert.report import IReport, Report from loops.knowledge.qualification.base import Competence from loops.knowledge.survey.base import Questionnaire, Question, FeedbackItem from loops.knowledge.survey.interfaces import IQuestionnaire, IQuestion, \ @@ -19,6 +20,7 @@ importPath = os.path.join(os.path.dirname(__file__), 'data') def importData(loopsRoot): + component.provideAdapter(Report, provides=IReport) baseImportData(loopsRoot, importPath, 'knowledge_de.dmp') def importSurvey(loopsRoot): diff --git a/organize/README.txt b/organize/README.txt index 110efe6..c80f403 100644 --- a/organize/README.txt +++ b/organize/README.txt @@ -410,7 +410,7 @@ Send Email to Members >>> form.subject u"loops Notification from '$site'" >>> form.mailBody - u'\n\nEvent #1\nhttp://127.0.0.1/loops/views/menu/.113\n\n' + u'\n\nEvent #1\nhttp://127.0.0.1/loops/views/menu/.117\n\n' Show Presence of Other Users diff --git a/system/sync/README.txt b/system/sync/README.txt index 5ed477f..143c6a9 100644 --- a/system/sync/README.txt +++ b/system/sync/README.txt @@ -18,7 +18,7 @@ Let's set up a loops site with basic and example concepts and resources. >>> concepts, resources, views = t.setup() >>> loopsRoot = site['loops'] >>> len(concepts), len(resources), len(views) - (33, 3, 1) + (35, 3, 1) >>> from cybertools.tracking.btree import TrackingStorage >>> from loops.system.job import JobRecord diff --git a/xmlrpc/README.txt b/xmlrpc/README.txt index 3ea6557..de55ea2 100755 --- a/xmlrpc/README.txt +++ b/xmlrpc/README.txt @@ -35,7 +35,7 @@ ZCML setup): Let's look what setup has provided us with: >>> len(concepts) - 22 + 24 Now let's add a few more concepts: @@ -73,7 +73,7 @@ applied in an explicit assignment. >>> sorted(t['name'] for t in xrf.getConceptTypes()) [u'competence', u'customer', u'domain', u'file', u'note', u'person', - u'predicate', u'task', u'textdocument', u'topic', u'type'] + u'predicate', u'report', u'task', u'textdocument', u'topic', u'type'] >>> sorted(t['name'] for t in xrf.getPredicates()) [u'depends', u'issubtype', u'knows', u'ownedby', u'provides', u'requires', u'standard'] @@ -96,7 +96,7 @@ All methods that retrieve one object also returns its children and parents: u'hasType' >>> sorted(c['name'] for c in ch[0]['objects']) [u'competence', u'customer', u'domain', u'file', u'note', u'person', - u'predicate', u'task', u'textdocument', u'topic', u'type'] + u'predicate', u'report', u'task', u'textdocument', u'topic', u'type'] >>> pa = defaultPred['parents'] >>> len(pa) @@ -115,7 +115,7 @@ We can also retrieve children and parents explicitely: u'hasType' >>> sorted(c['name'] for c in ch[0]['objects']) [u'competence', u'customer', u'domain', u'file', u'note', u'person', - u'predicate', u'task', u'textdocument', u'topic', u'type'] + u'predicate', u'report', u'task', u'textdocument', u'topic', u'type'] >>> pa = xrf.getParents('5') >>> len(pa) @@ -174,14 +174,14 @@ Updating the concept map >>> topicId = xrf.getObjectByName('topic')['id'] >>> xrf.createConcept(topicId, u'zope2', u'Zope 2') - {'description': u'', 'title': u'Zope 2', 'type': '36', 'id': '72', + {'description': u'', 'title': u'Zope 2', 'type': '38', 'id': '76', 'name': u'zope2'} The name of the concept is checked by a name chooser; if the corresponding parameter is empty, the name will be generated from the title. >>> xrf.createConcept(topicId, u'', u'Python') - {'description': u'', 'title': u'Python', 'type': '36', 'id': '74', + {'description': u'', 'title': u'Python', 'type': '38', 'id': '78', 'name': u'python'} If we try to deassign a ``hasType`` relation nothing will happen; a