provide preset concept lists (via type option qualifier:assign) for create and edit dialog
git-svn-id: svn://svn.cy55.de/Zope3/src/loops/trunk@1616 fd906abe-77d9-0310-91a1-e0d9ade77398
This commit is contained in:
parent
d44b721a89
commit
483a730c6c
3 changed files with 80 additions and 5 deletions
41
README.txt
41
README.txt
|
@ -608,6 +608,45 @@ Creating an object
|
|||
>>> from loops.browser.form import CreateObjectForm, CreateObject
|
||||
>>> form = CreateObjectForm(m112, TestRequest())
|
||||
|
||||
The form provides a set of data entry fields derived from the interface
|
||||
associated with the new object's resource (or concept) type.
|
||||
|
||||
In addition it allows to assign concepts as parents to the object. Beside
|
||||
an integrated free search for concepts to assign there may be a list of
|
||||
preset concepts, e.g. depending on the target of the current node:
|
||||
|
||||
>>> form.assignments
|
||||
()
|
||||
>>> m112.target = cc1
|
||||
>>> form = CreateObjectForm(m112, TestRequest())
|
||||
>>> form.assignments
|
||||
(<...ConceptRelationView object ...>,)
|
||||
|
||||
There also may be preset concept types that directly provide lists of
|
||||
concepts to select from.
|
||||
|
||||
To show this let's start with a new type, the customer type.
|
||||
|
||||
>>> customer = concepts['customer'] = Concept('Customer')
|
||||
>>> customer.conceptType = concepts.getTypeConcept()
|
||||
>>> from loops.type import ConceptType, TypeConcept
|
||||
>>> custType = TypeConcept(customer)
|
||||
>>> custType.options
|
||||
[]
|
||||
>>> cust1 = concepts['cust1'] = Concept(u'Zope Corporation')
|
||||
>>> cust2 = concepts['cust2'] = Concept(u'cyberconcepts')
|
||||
>>> for c in (cust1, cust2): c.conceptType = customer
|
||||
>>> custType.options = ('qualifier:assign',)
|
||||
>>> ConceptType(cust1).qualifiers
|
||||
('concept', 'assign')
|
||||
|
||||
>>> form = CreateObjectForm(m112, TestRequest())
|
||||
>>> form.presetTypesForAssignment
|
||||
[{'token': 'loops:concept:customer', 'title': 'Customer'}]
|
||||
|
||||
OK, so much about the form - now we want to create a new object based
|
||||
on data provided in this form:
|
||||
|
||||
>>> from loops.interfaces import INote, ITypeConcept
|
||||
>>> from loops.type import TypeConcept
|
||||
>>> from loops.resource import NoteAdapter
|
||||
|
@ -708,7 +747,7 @@ target object's view here:
|
|||
[<loops.browser.common.Action object ...>]
|
||||
>>> action = view.virtualTarget.getActions()[0]
|
||||
>>> action.url
|
||||
'http://127.0.0.1/loops/views/m1/m11/m111/.target16'
|
||||
'http://127.0.0.1/loops/views/m1/m11/m111/.target19'
|
||||
|
||||
|
||||
Import/Export
|
||||
|
|
|
@ -40,12 +40,13 @@ from zope.security.proxy import isinstance
|
|||
|
||||
from cybertools.ajax import innerHtml
|
||||
from cybertools.browser.form import FormController
|
||||
from cybertools.typology.interfaces import IType
|
||||
from cybertools.typology.interfaces import IType, ITypeManager
|
||||
from loops.concept import ResourceRelation
|
||||
from loops.interfaces import IConcept, IResourceManager, IDocument
|
||||
from loops.interfaces import IFile, IExternalFile, INote
|
||||
from loops.browser.node import NodeView
|
||||
from loops.browser.concept import ConceptRelationView
|
||||
from loops.query import ConceptQuery
|
||||
from loops.resource import Resource
|
||||
from loops.type import ITypeConcept
|
||||
from loops import util
|
||||
|
@ -98,8 +99,27 @@ class ObjectForm(NodeView):
|
|||
|
||||
@Lazy
|
||||
def defaultPredicate(self):
|
||||
return util.getUidForObject(
|
||||
self.loopsRoot.getConceptManager().getDefaultPredicate())
|
||||
return self.loopsRoot.getConceptManager().getDefaultPredicate()
|
||||
|
||||
@Lazy
|
||||
def typeManager(self):
|
||||
return ITypeManager(self.context)
|
||||
|
||||
@Lazy
|
||||
def presetTypesForAssignment(self):
|
||||
types = list(self.typeManager.listTypes(include=('assign',)))
|
||||
assigned = [r.context.conceptType for r in self.assignments]
|
||||
types = [t for t in types if t.typeProvider not in assigned]
|
||||
return [dict(title=t.title, token=t.tokenForSearch) for t in types]
|
||||
|
||||
def conceptsForType(self, token):
|
||||
noSelection = dict(token='none', title=u'not selected')
|
||||
result = sorted(ConceptQuery(self).query(type=token), key=lambda x: x.title)
|
||||
predicateUid = util.getUidForObject(self.defaultPredicate)
|
||||
return ([noSelection] +
|
||||
[dict(title=o.title,
|
||||
token='%s:%s' % (util.getUidForObject(o), predicateUid))
|
||||
for o in result])
|
||||
|
||||
|
||||
class WidgetController(object):
|
||||
|
@ -241,6 +261,9 @@ class EditObject(FormController):
|
|||
if fn.startswith(self.conceptPrefix) and value:
|
||||
self.collectConcepts(fn[len(self.conceptPrefix):], value)
|
||||
else:
|
||||
if not value and fn == 'data' and IFile.providedBy(adapted):
|
||||
# empty file data - don' change
|
||||
continue
|
||||
if isinstance(value, FileUpload):
|
||||
filename = getattr(value, 'filename', '')
|
||||
value = value.read()
|
||||
|
@ -273,7 +296,7 @@ class EditObject(FormController):
|
|||
predicate = util.getObjectForUid(p)
|
||||
obj.deassignConcept(concept, [predicate])
|
||||
for v in self.selected:
|
||||
if v not in self.old:
|
||||
if v != 'none' and v not in self.old:
|
||||
c, p = v.split(':')
|
||||
concept = util.getObjectForUid(c)
|
||||
predicate = util.getObjectForUid(p)
|
||||
|
|
|
@ -105,6 +105,19 @@
|
|||
|
||||
<metal:assignments define-macro="assignments">
|
||||
<tbody id="form.assignments">
|
||||
<tr tal:repeat="type view/presetTypesForAssignment">
|
||||
<td><span i18n:translate="">Type: </span></td>
|
||||
<td><b tal:content="type/title" /></td>
|
||||
<td><span i18n:translate="">Select value: </span></td>
|
||||
<td colspan="2">
|
||||
<select name="form.assignments.selected:list">
|
||||
<tal:concepts repeat="concept python: view.conceptsForType(type['token'])">
|
||||
<option tal:attributes="value concept/token"
|
||||
tal:content="concept/title">Zope Corp</option>
|
||||
</tal:concepts>
|
||||
</select>
|
||||
</td>
|
||||
</tr>
|
||||
<tr tal:repeat="relation view/assignments">
|
||||
<td colspan="5">
|
||||
<input type="hidden" name="form.assignments.old:list"
|
||||
|
|
Loading…
Add table
Reference in a new issue