merge
authorNicolas Chauvat <nicolas.chauvat@logilab.fr>
Tue, 21 Apr 2009 14:35:11 -0500
changeset 1590 7f523ae475d2
parent 1589 496fdc081e25 (current diff)
parent 1413 ad19d7e6a291 (diff)
child 1591 e85bf08a123b
merge
doc/book/en/B1020-define-views.en.txt
schemas/Card.py
web/views/baseviews.py
web/views/card.py
--- a/cwctl.py	Tue Apr 21 14:29:31 2009 -0500
+++ b/cwctl.py	Tue Apr 21 14:35:11 2009 -0500
@@ -614,8 +614,6 @@
     
     def upgrade_application(self, appid):
         from logilab.common.changelog import Version
-        if not (CubicWebConfiguration.mode == 'dev' or self.config.nostartstop):
-            self.stop_application(appid)
         config = CubicWebConfiguration.config_for(appid)
         config.creating = True # notice we're not starting the server
         config.verbosity = self.config.verbosity
@@ -659,6 +657,9 @@
             return
         for cube, fromversion, toversion in toupgrade:
             print '**** %s migration %s -> %s' % (cube, fromversion, toversion)
+        # only stop once we're sure we have something to do
+        if not (CubicWebConfiguration.mode == 'dev' or self.config.nostartstop):
+            self.stop_application(appid)
         # run cubicweb/componants migration scripts
         mih.migrate(vcconf, reversed(toupgrade), self.config)
         # rewrite main configuration file
--- a/doc/book/en/B1020-define-views.en.txt	Tue Apr 21 14:29:31 2009 -0500
+++ b/doc/book/en/B1020-define-views.en.txt	Tue Apr 21 14:35:11 2009 -0500
@@ -153,12 +153,115 @@
         search_states = ('linksearch',)
 
     
+Rendering methods and attributes for ``PrimaryView``
+----------------------------------------------------
 
+By default, `CubicWeb` provides a primary view for each new entity type
+you create. The first view you might be interested in modifying.
 
+Let's have a quick look at the EntityView ``PrimaryView`` as well as
+its rendering method::
+    
+    class PrimaryView(EntityView):
+    """the full view of an non final entity"""
+        id = 'primary'
+        title = _('primary')
+        show_attr_label = True
+        show_rel_label = True
+        skip_none = True
+        skip_attrs = ('eid', 'creation_date', 'modification_date')
+        skip_rels = ()
+        main_related_section = True
+
+        ...
+
+    def cell_call(self, row, col):
+        self.row = row
+        self.render_entity(self.complete_entity(row, col))
+
+    def render_entity(self, entity):
+        """return html to display the given entity"""
+        siderelations = []
+        self.render_entity_title(entity)
+        self.render_entity_metadata(entity)
+        # entity's attributes and relations, excluding meta data
+        # if the entity isn't meta itself
+        self.w(u'<div>')
+        self.w(u'<div class="mainInfo">')
+        self.render_entity_attributes(entity, siderelations)
+        self.w(u'</div>')
+        self.content_navigation_components('navcontenttop')
+        if self.main_related_section:
+            self.render_entity_relations(entity, siderelations)
+        self.w(u'</div>')
+        # side boxes
+        self.w(u'<div class="primaryRight">')
+        self.render_side_related(entity, siderelations)
+        self.w(u'</div>')
+        self.w(u'<div class="clear"></div>')
+        self.content_navigation_components('navcontentbottom')
+
+    ...
+
+``cell_call`` is executed for each entity of a result set and apply ``render_entity``.
+
+The methods you want to modify while customizing a ``PrimaryView`` are:
+
+*render_entity_title(self, entity)* 
+    Renders the entity title based on the assumption that the method 
+    ``def content_title(self)`` is implemented for the given entity type.
+
+*render_entity_metadata(self, entity)*
+    Renders the entity metadata based on the assumption that the method
+    ``def summary(self)`` is implemented for the given entity type.
+
+*render_entity_attributes(self, entity, siderelations)*
+    Renders all the attribute of an entity with the exception of attribute
+    of type `Password` and `Bytes`.
+
+*content_navigation_components(self, context)*
+
+*render_entity_relations(self, entity, siderelations)*
+    Renders all the relations of the entity.
+        
+*render_side_related(self, entity, siderelations)*
+    Renders side related relations.
+
+Also, please note that by setting the following attributes in you class,
+you can already customize some of the rendering:
+
+*show_attr_label*
+    Renders the attribute label next to the attribute value if set to True.
+    Otherwise, does only display the attribute value.
+
+*show_rel_label* 
+    Renders the relation label next to the relation value if set to True.
+    Otherwise, does only display the relation value.
+
+*skip_none*
+    Does not render an attribute value that is None if set to True.
+
+*skip_attrs*
+    Given a list of attributes name, does not render the value of the attributes listed.
+
+*skip_rels*
+    Given a list of relations name, does not render the relations listed.
+
+*main_related_section*
+    Renders the relations of the entity if set to True.
+
+A good practice is for you to identify the content of your entity type for which
+the default rendering does not answer your need so that you can focus on the specific
+method (from the list above) that needs to be modified. We do not recommand you to
+overwrite ``render_entity`` as you might potentially loose the benefits of the side
+boxes handling.
 
 Example of a view customization
 -------------------------------
 
+[FIXME] XXX Example needs to be rewritten as it shows how to modify cell_call which
+contredicts our advise of not modifying it.
+
 We'll show you now an example of a ``primary`` view and how to customize it.
 
 If you want to change the way a ``BlogEntry`` is displayed, just override 
--- a/doc/book/en/C011-installation.en.txt	Tue Apr 21 14:29:31 2009 -0500
+++ b/doc/book/en/C011-installation.en.txt	Tue Apr 21 14:35:11 2009 -0500
@@ -181,6 +181,14 @@
 
     createlang -U pgadmin plpythonu template1
 
+MySql configuration
+-------------------
+Yout must add the following lines in /etc/mysql/my.cnf file::
+
+    transaction-isolation = READ-COMMITTED
+    default-storage-engine=INNODB
+    default-character-set=utf8
+    max_allowed_packet = 128M
 
 Pyro configuration
 ------------------
--- a/entities/lib.py	Tue Apr 21 14:29:31 2009 -0500
+++ b/entities/lib.py	Tue Apr 21 14:35:11 2009 -0500
@@ -139,20 +139,6 @@
     def action_url(self):
         return self.absolute_url() + '/follow'
 
-
-class Card(AnyEntity):
-    """customized class for Card entities"""
-    id = 'Card'
-    rest_attr = 'wikiid'
-    
-    fetch_attrs, fetch_order = fetch_config(['title'])
-
-    def dc_title(self):
-        return self.title
-
-    def dc_description(self, format='text/plain'):
-        return self.synopsis or u''
-
 class ECache(AnyEntity):
     """Cache"""
     id = 'ECache'
--- a/schema.py	Tue Apr 21 14:29:31 2009 -0500
+++ b/schema.py	Tue Apr 21 14:35:11 2009 -0500
@@ -877,8 +877,8 @@
     def _load_definition_files(self, cubes):
         for filepath in (self.include_schema_files('bootstrap')
                          + self.include_schema_files('base')
-                         + self.include_schema_files('Bookmark')
-                         + self.include_schema_files('Card')):
+                         + self.include_schema_files('Bookmark')):
+#                         + self.include_schema_files('Card')):
             self.info('loading %s', filepath)
             self.handle_file(filepath)
         for cube in cubes:
--- a/schemas/Card.py	Tue Apr 21 14:29:31 2009 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,18 +0,0 @@
-from cubicweb.schema import format_constraint
-
-class Card(EntityType):
-    """a card is a textual content used as documentation, reference, procedure reminder"""
-    permissions = {
-        'read':   ('managers', 'users', 'guests'),
-        'add':    ('managers', 'users'),
-        'delete': ('managers', 'owners'),
-        'update': ('managers', 'owners',),
-        }
-    
-    title    = String(required=True, fulltextindexed=True, maxsize=256)
-    synopsis = String(fulltextindexed=True, maxsize=512,
-                      description=_("an abstract for this card"))
-    content_format = String(meta=True, internationalizable=True, maxsize=50,
-                            default='text/rest', constraints=[format_constraint])
-    content  = String(fulltextindexed=True)
-    wikiid = String(maxsize=64, indexed=True)
--- a/sobjects/notification.py	Tue Apr 21 14:29:31 2009 -0500
+++ b/sobjects/notification.py	Tue Apr 21 14:35:11 2009 -0500
@@ -296,10 +296,3 @@
         return  u'%s #%s (%s)' % (self.req.__('New %s' % entity.e_schema),
                                   entity.eid, self.user_login())
 
-
-class CardAddedView(NormalizedTextView):
-    """get notified from new cards"""
-    accepts = ('Card',)
-    content_attr = 'synopsis'
-    
-
--- a/web/views/baseviews.py	Tue Apr 21 14:29:31 2009 -0500
+++ b/web/views/baseviews.py	Tue Apr 21 14:35:11 2009 -0500
@@ -158,6 +158,9 @@
         self.render_entity_metadata(entity)
         # entity's attributes and relations, excluding meta data
         # if the entity isn't meta itself
+        boxes = self._preinit_side_related(entity) or siderelations
+        if boxes:
+            self.w(u'<table width="100%"><tr><td width="75%">')
         self.w(u'<div>')
         self.w(u'<div class="mainInfo">')
         self.render_entity_attributes(entity, siderelations)
@@ -166,13 +169,16 @@
         if self.main_related_section:
             self.render_entity_relations(entity, siderelations)
         self.w(u'</div>')
-        # side boxes
-        self.w(u'<div class="primaryRight">')
-        self.render_side_related(entity, siderelations)
-        self.w(u'</div>')
-        self.w(u'<div class="clear"></div>')
+        if boxes:
+            self.w(u'</td><td>')
+            # side boxes
+            self.w(u'<div class="primaryRight">')
+            self.render_side_related(entity, siderelations)
+            self.w(u'</div>')
+            self.w(u'</td></tr></table>')
         self.content_navigation_components('navcontentbottom')
 
+        
     def content_navigation_components(self, context):
         self.w(u'<div class="%s">' % context)
         for comp in self.vreg.possible_vobjects('contentnavigation',
@@ -255,18 +261,26 @@
                 continue
             self._render_related_entities(entity, rschema, related, x)
 
+    def _preinit_side_related(self, entity):
+        self._sideboxes = None
+        if hasattr(self, 'get_side_boxes_defs'):
+            self._sideboxes = [(label, rset) for label, rset in self.get_side_boxes_defs(entity)
+                               if rset]
+        self._boxes_in_context = list(self.vreg.possible_vobjects('boxes', self.req, self.rset,
+                                                 row=self.row, view=self,
+                                                 context='incontext'))
+        return self._sideboxes or self._boxes_in_context
+        
+            
     def render_side_related(self, entity, siderelations):
         """display side related relations:
         non-meta in a first step, meta in a second step
         """
-        if hasattr(self, 'get_side_boxes_defs'):
-            sideboxes = [(label, rset) for label, rset in self.get_side_boxes_defs(entity)
-                         if rset]
-            if sideboxes:
-                for label, rset in sideboxes:
-                    self.w(u'<div class="sideRelated">')
-                    self.wview('sidebox', rset, title=label)
-                    self.w(u'</div>')
+        if self._sideboxes:
+            for label, rset in self._sideboxes:
+                self.w(u'<div class="sideRelated">')
+                self.wview('sidebox', rset, title=label)
+                self.w(u'</div>')
         elif siderelations:
             self.w(u'<div class="sideRelated">')
             for relatedinfos in siderelations:
@@ -274,11 +288,9 @@
                 #    continue
                 self._render_related_entities(entity, *relatedinfos)
             self.w(u'</div>')
-        boxes = list(self.vreg.possible_vobjects('boxes', self.req, self.rset,
-                                                 row=self.row, view=self,
-                                                 context='incontext'))
-        if boxes:
-            for box in boxes:
+
+        if self._boxes_in_context:
+            for box in self._boxes_in_context:
                 try:
                     box.dispatch(w=self.w, row=self.row)
                 except NotImplementedError:
--- a/web/views/card.py	Tue Apr 21 14:29:31 2009 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,36 +0,0 @@
-"""Specific views for cards
-
-:organization: Logilab
-:copyright: 2001-2008 LOGILAB S.A. (Paris, FRANCE), all rights reserved.
-:contact: http://www.logilab.fr/ -- mailto:contact@logilab.fr
-"""
-__docformat__ = "restructuredtext en"
-
-from cubicweb.web.views import baseviews
-from logilab.mtconverter import html_escape
-
-_ = unicode
-
-class CardPrimaryView(baseviews.PrimaryView):
-    accepts = ('Card',)
-    skip_attrs = baseviews.PrimaryView.skip_attrs + ('title', 'synopsis', 'wikiid')
-    show_attr_label = False
-
-    def content_title(self, entity):
-        return html_escape(entity.dc_title())
-    
-    def summary(self, entity):
-        return html_escape(entity.dc_description())
-
-
-class CardInlinedView(CardPrimaryView):
-    """hide card title and summary"""
-    id = 'inlined'
-    title = _('inlined view')
-    main_related_section = False
-    
-    def render_entity_title(self, entity):
-        pass
-    
-    def render_entity_metadata(self, entity):
-        pass