Ticket #3931 (closed Bug: fixed)

Opened 9 years ago

Last modified 5 years ago

"upcoming events" portlet lacks trailing "more..."

Reported by: tomcloyd Owned by:
Priority: trivial Milestone: 2.1
Component: Templates/CSS Version:
Keywords: Cc:

Description

(Nidelen-it.no is doing my hosting - I don't know Apache ver., and can't find Plone ver.)

"upcoming events" portlet: the "recent items" and "news" portlets have a trailing "more..." link which is very nice, as it alerts the viewer to the fact that they are seeing on a partial listing of this content type. "upcoming events" HAS NO SUCH LINK, and this is nuts. It especially needs to remind the viewer that there is more, when there is.

Change History

comment:1 Changed 9 years ago by optilude

Scheduling for 2.1

comment:2 Changed 9 years ago by lucas

Index: portlet_events.pt =================================================================== --- portlet_events.pt (revision 6719) +++ portlet_events.pt (working copy) @@ -12,7 +12,7 @@

end={'query': here.ZopeTime(),

'range': 'min'},

sort_on='start',

  • review_state='published')[:5];"

+ review_state='published')[:2];"

tal:condition="results">

<div class="portlet" id="portlet-events">

@@ -43,6 +43,18 @@

</tal:block>

+ <div class="portletContent odd"> + + <a href="" + class="portletMore" + tal:attributes="href string:${utool}/events" + i18n:translate="box_morelink" + > + More... + </a> + + </div> +

</div>

</div>

comment:3 Changed 9 years ago by lucas

source for events_listing.pt:

<html xmlns=" http://www.w3.org/1999/xhtml" xml:lang="en"

lang="en" metal:use-macro="here/main_template/macros/master" i18n:domain="plone">

<head>

</head> <body> <div metal:fill-slot="main" id="content-news"

tal:define="results python:here.portal_catalog.searchResults(

portal_type='Event', end={'query': here.ZopeTime(),

'range': 'min'},

sort_on='start', review_state='published');

results python:[r for r in results if r.getObject()]; Batch python:modules['Products.CMFPlone'].Batch; b_start python:request.get('b_start',0); portal_discussion nocall:here/portal_discussion; isDiscussionAllowedFor nocall:portal_discussion/isDiscussionAllowedFor; getDiscussionFor nocall:portal_discussion/getDiscussionFor; home_url python: mtool.getHomeUrl;">

<form name="searchresults" action="" method="post" tal:condition="results"

tal:define="batch python:Batch(results, 15, int(b_start), orphan=1)">

<metal:block tal:repeat="result batch">

<div class="newsItem"

metal:define-macro="listitem" tal:define="resultObject result/getObject;

creator result/Creator; resulturl resultObject/absolute_url;">

<h2>

<a href="/view"

tal:attributes="href resulturl" tal:content="result/Title">

Event headline

</a>

</h2>

<div class="newsContent">

<p tal:content="result/Description">

Description

</p>

<ul class="newsAbout">

<li> <span tal:replace="python:modules['string'].join(resultObject.Subject(), ' ')"> Conference </span> </li> <li> <span tal:replace="python:resultObject.toLocalizedTime(resultObject.start(), long_format=1)">Start Date Time</span> <span i18n:translate="event_and">to</span> <span tal:replace="python:resultObject.toLocalizedTime(resultObject.end(), long_format=1)">End Date Time</span>. </li> <li>

<span tal:omit-tag="" i18n:translate="posted_by">Posted by</span>

<span class="link-user">

<a href=""

tal:attributes="href python: home_url(creator)" tal:content="creator">

Author

</a>

</span>.

</li> <li>

<span tal:omit-tag="" i18n:translate="label_published">Published</span>: <span tal:replace="python:here.toLocalizedTime(result.Date)" />

</li>

</ul>

<ul class="newsFooter" tal:define="is_discussable python: isDiscussionAllowedFor(resultObject);">

<li>

<a href="/view" tal:attributes="href resulturl" i18n:translate="read_more">

Read More</a>

</li>

<tal:discussable condition="is_discussable"> <li tal:attributes="class python: test(has_replies, 'visualCommentAlign link-comment','visualCommentAlign');"

tal:define="talkback python: getDiscussionFor(resultObject);

has_replies python: talkback.hasReplies(resultObject);">

<a href=""

tal:define="reply_count python:talkback.replyCount(resultObject)" tal:condition="reply_count" tal:attributes="href string:${resulturl}#comments;"> (<span tal:replace="python: reply_count" />)</a>

</li> </tal:discussable>

</ul>

</div>

</div>

</metal:block>

<!-- Navigation --> <div metal:use-macro="here/batch_macros/macros/navigation" />

</form>

<p tal:condition="not: results" i18n:translate="no_new_news">

No news has been posted.

</p>

<div tal:define="contentTypes here/getAllowedTypes" tal:omit-tag="python:1">

<tal:add_button metal:use-macro="here/folder_contents/macros/add_button"/>

</div>

</div>

</body> </html>

comment:4 Changed 9 years ago by lucas

diff for alphas.py:

Index: alphas.py =================================================================== --- alphas.py (revision 6719) +++ alphas.py (working copy) @@ -98,6 +98,12 @@

# Add news topic addNewsTopic(portal, out)

+ # Add events folder + addEventsFolder(portal, out) + + # Add events topic + addEventsTopic(portal, out) +

# Add exclude_from_nav index reindex += addExclude_from_navMetadata(portal, out)

@@ -134,6 +140,9 @@

# Make sure the News folder is cataloged indexNewsFolder(portal, out)

+ # Make sure the Events folder is cataloged + indexEventsFolder(portal, out) +

# Add non_default_page_types site property addDisableFolderSectionsSiteProperty(portal, out)

@@ -567,7 +576,31 @@

pass

out.append("Added default view for news folder.")

+def addEventsFolder(portal, out): + """Add events folder to portal root""" + if 'events' not in portal.objectIds(): + _createObjectByType('Large Plone Folder', portal, id='events', + title='Events', description='Site Events') + out.append("Added events folder.") + events = getattr(aq_base(portal), 'events')

+ # Enable ConstrainTypes and set to Event + addable_types = Event? + if getattr(events.aq_base, 'setConstrainTypesMode', None) is not None: + events.setConstrainTypesMode(1) + events.setImmediatelyAddableTypes(addable_types) + events.setLocallyAllowedTypes(addable_types) + out.append("Set constrain types for events folder.") + + # Add events_listing.pt as default page + # property manager hasProperty can give odd results ask forgiveness instead + try: + events.manage_addProperty('default_page', ['events_topic','events_listing','index_html'], 'lines') + except BadRequest: + pass + out.append("Added default view for events folder.") + +

def addExclude_from_navMetadata(portal, out):

"""Adds the exclude_from_nav metadata.""" catalog = getToolByName(portal, 'portal_catalog', None)

@@ -666,6 +699,15 @@

out.append('Recataloged news folder.')

+def indexEventsFolder(portal, out): + """Makes sure the Events folder is cataloged.""" + catalog = getToolByName(portal, 'portal_catalog', None) + if catalog is not None: + if hasattr(aq_base(portal), 'events'): + portal.events.indexObject() + out.append('Recataloged events folder.') + +

class Record:

def init(self, kw):

self.dict.update(kw)

@@ -793,6 +835,20 @@

out.append('Topic default news folder view already in place or ATCT is not installed.')

+def addEventsTopic(portal, out): + events = portal.events + if 'events_topic' not in events.objectIds() and getattr(portal,'portal_atct', None) is not None: + _createObjectByType('Topic', events, id='events_topic', + title='Events', description='Site Events') + topic = events.events_topic + type_crit = topic.addCriterion('Type','ATPortalTypeCriterion') + type_crit.setValue('Event') + sort_crit = topic.addCriterion('start','ATSortCriterion') + out.append('Added Topic for default events folder view.') + else: + out.append('Topic default events folder view already in place or ATCT is not installed.') + +

def addDisableFolderSectionsSiteProperty(portal, out):

"""Adds disable_folder_sections site property.""" # Boolean to disable using toplevel folders as tabs

@@ -806,4 +862,4 @@

propSheet.manage_addProperty('disable_folder_sections',

False, 'boolean')

  • out.append("Added 'disable_folder_sections' property to site_properties.")

\ No newline at end of file + out.append("Added 'disable_folder_sections' property to site_properties.")

comment:5 Changed 9 years ago by lucas

diff for testPortalCreation.py

Index: testPortalCreation.py =================================================================== --- testPortalCreation.py (revision 6719) +++ testPortalCreation.py (working copy) @@ -273,6 +273,35 @@

self.assertEqual(topic._getPortalTypeName(), 'Topic') self.assertEqual(topic.buildQuery()Type?, ('News Item',))

+ def testEventsFolder(self): + # The portal should contain events folder + self.failUnless('events' in self.portal.objectIds()) + events = getattr(self.portal.aq_base, 'events') + self.assertEqual(events._getPortalTypeName(), 'Large Plone Folder') + self.assertEqual(events.Title(), 'Events') + self.assertEqual(events.Description(), 'Site Events') + self.assertEqual(list(events.getProperty('default_page')), ['events_topic','events_listing','index_html']) + self.assertEqual(list(events.getImmediatelyAddableTypes()),Event?) + self.assertEqual(list(events.getLocallyAllowedTypes()),Event?) + self.assertEqual(events.getConstrainTypesMode(), 1) + + def testEventsFolderIsIndexed(self): + # Events folder should be cataloged + res = self.catalog(id='events') + self.assertEqual(len(res), 1) + self.assertEqual(res[0].getId, 'events') + self.assertEqual(res[0].Title, 'Events') + self.assertEqual(res[0].Description, 'Site Events') + + def testEventsTopic(self): + # Events topic is in place as default view and has a criterion to show + # only Events Items. + events = self.portal.events + self.failUnless('events_topic' in events.objectIds()) + topic = getattr(events.aq_base, 'events_topic') + self.assertEqual(topic._getPortalTypeName(), 'Topic') + self.assertEqual(topic.buildQuery()Type?, ('Event',)) +

def testObjectButtonActions(self):

installed = [(a.getId(), a.getCategory()) for a in self.actions.listActions()] self.failUnless(('cut', 'object_buttons') in installed)

comment:6 Changed 9 years ago by lucas

diff for testMigrations.py

Index: testMigrations.py =================================================================== --- testMigrations.py (revision 6719) +++ testMigrations.py (working copy) @@ -30,6 +30,7 @@

from Products.CMFPlone.migrations.v2_1.alphas import addNonDefaultPageTypesSiteProperty from Products.CMFPlone.migrations.v2_1.alphas import removePortalTabsActions from Products.CMFPlone.migrations.v2_1.alphas import addNewsFolder

+from Products.CMFPlone.migrations.v2_1.alphas import addEventsFolder

from Products.CMFPlone.migrations.v2_1.alphas import addExclude_from_navMetadata from Products.CMFPlone.migrations.v2_1.alphas import addIs_FolderishMetadata from Products.CMFPlone.migrations.v2_1.alphas import indexMembersFolder

@@ -39,6 +40,7 @@

from Products.CMFPlone.migrations.v2_1.alphas import addSortable_TitleIndex from Products.CMFPlone.migrations.v2_1.alphas import addDefaultTypesToPortalFactory from Products.CMFPlone.migrations.v2_1.alphas import addNewsTopic

+from Products.CMFPlone.migrations.v2_1.alphas import addEventsTopic

from Products.CMFPlone.migrations.v2_1.alphas import addDisableFolderSectionsSiteProperty

@@ -568,6 +570,54 @@

addNewsTopic(self.portal, []) self.failUnless('news_topic' not in news.objectIds())

+ def testAddEventsFolder(self): + #Should add the new events folder with appropriate default view settings + self.portal._delObject('events') + self.failIf('events' in self.portal.objectIds()) + addEventsFolder(self.portal, []) + self.failUnless('events' in self.portal.objectIds()) + events = getattr(self.portal.aq_base, 'events') + self.assertEqual(events._getPortalTypeName(), 'Large Plone Folder') + self.assertEqual(list(events.getProperty('default_page')), ['events_topic', 'events_listing','index_html']) + self.assertEqual(list(events.getImmediatelyAddableTypes()),Event?) + self.assertEqual(list(events.getLocallyAllowedTypes()),Event?) + self.assertEqual(events.getConstrainTypesMode(), 1) + + def testAddEventsFolderTwice(self): + #Should not fail when done twice + self.portal._delObject('events') + self.failIf('events' in self.portal.objectIds()) + addEventsFolder(self.portal, []) + addEventsFolder(self.portal, []) + self.failUnless('events' in self.portal.objectIds()) + + def testAddEventsTopic(self): + #Should add the default view for the events folder, a topic + events = self.portal.events + events._delObject('events_topic') + self.failIf('events_topic' in events.objectIds()) + addEventsTopic(self.portal, []) + self.failUnless('events_topic' in events.objectIds()) + topic = getattr(events.aq_base, 'events_topic') + self.assertEqual(topic._getPortalTypeName(), 'Topic') + + def testAddEventsTopicTwice(self): + #Should not fail if done twice + events = self.portal.events + events._delObject('events_topic') + self.failIf('events_topic' in events.objectIds()) + addEventsTopic(self.portal, []) + addEventsTopic(self.portal, []) + self.failUnless('events_topic' in events.objectIds()) + + def testAddEventsTopicNoATCT(self): + #Should not do anything unless ATCT is installed + events = self.portal.events + events._delObject('events_topic') + self.portal._delObject('portal_atct') + addEventsTopic(self.portal, []) + self.failUnless('events_topic' not in events.objectIds()) +

def testAddExclude_from_navMetadata(self):

# Should add getObjSize to schema self.catalog.delColumn('exclude_from_nav')

comment:7 Changed 9 years ago by naro

  • Status changed from new to closed
  • Resolution set to fixed

Resolved in r6762. Somebody forgot to close this bug.

comment:8 Changed 5 years ago by hannosch

  • Component changed from Usability to Templates/CSS
Note: See TracTickets for help on using tickets.