diff --git a/browser/concept.py b/browser/concept.py
index 982bce6..c17feaa 100644
--- a/browser/concept.py
+++ b/browser/concept.py
@@ -44,6 +44,7 @@ from zope.security.proxy import removeSecurityProxy
from cybertools.typology.interfaces import IType, ITypeManager
from loops.interfaces import IConcept
+from loops.interfaces import ITypeConcept
from loops.concept import Concept, ConceptTypeSourceList, PredicateSourceList
from loops.browser.common import EditForm, BaseView, LoopsTerms
from loops import util
@@ -133,20 +134,25 @@ class ConceptView(BaseView):
@Lazy
def view(self):
+ context = self.context
viewName = self.request.get('loops.viewName') or getattr(self, '_viewName', None)
if not viewName:
- ti = IType(self.context).typeInterface
+ ti = IType(context).typeInterface
# TODO: check the interface (maybe for a base interface IViewProvider)
# instead of the viewName attribute:
- if ti and 'viewName' in ti:
+ if ti and ti != ITypeConcept and 'viewName' in ti:
typeAdapter = ti(self.context)
viewName = typeAdapter.viewName
+ if not viewName:
+ tp = IType(context).typeProvider
+ if tp:
+ viewName = ITypeConcept(tp).viewName
if viewName:
# ??? Would it make sense to use a somehow restricted interface
# that should be provided by the view like IQuery?
#viewInterface = getattr(typeAdapter, 'viewInterface', None) or IQuery
- adapter = component.queryMultiAdapter((self.context, self.request),
- interface.Interface, name=viewName)
+ adapter = component.queryMultiAdapter((context, self.request),
+ name=viewName)
if adapter is not None:
return adapter
#elif type provides view: use this
diff --git a/integrator/README.txt b/integrator/README.txt
index 2614360..670e057 100644
--- a/integrator/README.txt
+++ b/integrator/README.txt
@@ -98,9 +98,11 @@ Working with the External Collection
>>> res = coll01.getResources()
>>> len(res)
2
- >>> sorted((r.__name__, r.title) for r in res)
- [(u'programming_beautifulprogram.pdf', u'BeautifulProgram'),
- (u'programming_zope_zope3.txt', u'zope3')]
+ >>> sorted((r.__name__, r.title, r._storageName) for r in res)
+ [(u'programming_beautifulprogram.pdf', u'BeautifulProgram', 'fullpath'),
+ (u'programming_zope_zope3.txt', u'zope3', 'fullpath')]
+
+To do: Check storage parameters.
Fin de partie
diff --git a/integrator/browser.py b/integrator/browser.py
new file mode 100644
index 0000000..626d694
--- /dev/null
+++ b/integrator/browser.py
@@ -0,0 +1,48 @@
+#
+# Copyright (c) 2007 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
+#
+
+"""
+View class(es) for intergrating external objects.
+
+$Id$
+"""
+
+from zope import interface, component
+from zope.app.pagetemplate import ViewPageTemplateFile
+from zope.cachedescriptors.property import Lazy
+
+from cybertools.typology.interfaces import IType
+from loops.browser.concept import ConceptView
+
+
+class ExternalCollectionView(ConceptView):
+
+ macro_template = ViewPageTemplateFile('collection_macros.pt')
+
+ @property
+ def macro(self):
+ return self.macro_template.macros['render_collection']
+
+ def update(self):
+ if 'update' in self.request.form:
+ ti = IType(self.context).typeInterface
+ if ti is not None:
+ adapted = ti(self.context)
+ adapted.update()
+ return True
+
diff --git a/integrator/collection.py b/integrator/collection.py
index 870462f..529236f 100644
--- a/integrator/collection.py
+++ b/integrator/collection.py
@@ -70,6 +70,7 @@ class ExternalCollectionAdapter(AdapterBase):
for addr, mdate in provider.collect(self):
if addr in old:
if mdate > self.lastUpdated:
+ # force reindexing
notify(ObjectModifiedEvent(old[addr]))
else:
new.append(addr)
@@ -113,7 +114,7 @@ class DirectoryCollectionProvider(object):
title=title,
resourceType=extFileType,
externalAddress=addr,
- storage='fullpath',
+ storageName='fullpath',
storageParams=dict(subdirectory=directory))
yield obj
diff --git a/integrator/collection_macros.pt b/integrator/collection_macros.pt
new file mode 100644
index 0000000..e824484
--- /dev/null
+++ b/integrator/collection_macros.pt
@@ -0,0 +1,11 @@
+
+
+
+
+
+
+
+
diff --git a/integrator/configure.zcml b/integrator/configure.zcml
index ad7799a..3f40343 100644
--- a/integrator/configure.zcml
+++ b/integrator/configure.zcml
@@ -19,4 +19,15 @@
+
+
+
+
diff --git a/integrator/testsetup.py b/integrator/testsetup.py
index 1b491cd..83ab22f 100644
--- a/integrator/testsetup.py
+++ b/integrator/testsetup.py
@@ -8,9 +8,9 @@ import os
from zope import component
from loops import util
-from loops.interfaces import IExternalFile
+from loops.interfaces import IFile, IExternalFile
from loops.concept import Concept
-from loops.resource import Resource
+from loops.resource import Resource, FileAdapter, ExternalFileAdapter
from loops.integrator.interfaces import IExternalCollection
from loops.knowledge.setup import SetupManager as KnowledgeSetupManager
from loops.setup import SetupManager, addAndConfigureObject
@@ -28,6 +28,9 @@ class TestSite(BaseTestSite):
component.provideAdapter(KnowledgeSetupManager, name='knowledge')
concepts, resources, views = self.baseSetup()
+ component.provideAdapter(FileAdapter, provides=IFile)
+ component.provideAdapter(ExternalFileAdapter, provides=IExternalFile)
+
tType = concepts.getTypeConcept()
tExtFile = addAndConfigureObject(concepts, Concept, 'extfile',
title=u'External File', conceptType=tType,
diff --git a/resource.py b/resource.py
index 8ee01db..d87f6a4 100644
--- a/resource.py
+++ b/resource.py
@@ -305,6 +305,9 @@ class ExternalFileAdapter(FileAdapter):
implements(IExternalFile)
+ _adapterAttributes = (FileAdapter._adapterAttributes
+ + ('storageParams', 'externalAddress'))
+
def getStorageParams(self):
params = getattr(self.context, '_storageParams', None)
if params is not None:
diff --git a/setup.py b/setup.py
index 35d894d..b2f1cc7 100644
--- a/setup.py
+++ b/setup.py
@@ -114,9 +114,12 @@ def addAndConfigureObject(container, class_, name, **kw):
basicKw = dict([(k, kw[k]) for k in kw if k in basicAttributes])
obj = addObject(container, class_, name, **basicKw)
ti = IType(obj).typeInterface
- adapted = ti is not None and ti(obj) or obj
+ if ti is not None:
+ adapted = ti(obj)
+ else:
+ adapted = obj
adapterAttributes = [k for k in kw if k not in basicAttributes]
for attr in adapterAttributes:
- setattr(obj, attr, kw[attr])
+ setattr(adapted, attr, kw[attr])
notify(ObjectModifiedEvent(obj))
return obj
diff --git a/tests/setup.py b/tests/setup.py
index 7e79cf9..97401f8 100644
--- a/tests/setup.py
+++ b/tests/setup.py
@@ -19,13 +19,13 @@ from cybertools.typology.interfaces import IType
from loops import Loops
from loops import util
from loops.common import NameChooser
-from loops.interfaces import IIndexAttributes
+from loops.interfaces import IIndexAttributes, IDocument
from loops.concept import Concept
from loops.concept import IndexAttributes as ConceptIndexAttributes
from loops.resource import Resource
from loops.resource import IndexAttributes as ResourceIndexAttributes
from loops.setup import SetupManager, addObject
-from loops.type import ConceptType, ResourceType, TypeConcept
+from loops.type import LoopsType, ConceptType, ResourceType, TypeConcept
class TestSite(object):
@@ -42,8 +42,9 @@ class TestSite(object):
component.provideUtility(relations, IRelationRegistry)
component.provideAdapter(IndexableRelationAdapter)
+ component.provideAdapter(LoopsType)
component.provideAdapter(ConceptType)
- component.provideAdapter(ResourceType)
+ component.provideAdapter(ResourceType, (IDocument,))
component.provideAdapter(TypeConcept)
component.provideAdapter(NameChooser)