web/views/calendar.py
author Sylvain Thénault <sylvain.thenault@logilab.fr>
Fri, 19 Feb 2010 09:34:14 +0100
branchstable
changeset 4643 921737d2e3a8
parent 4582 d12b81facd1d
child 5421 8167de96c523
permissions -rw-r--r--
fix optimisation with super session that may lead to integrity loss at some point I've decided to stop ensuring ?1 cardinality was respected when adding a new relation using a super session, to avoid the cost of the delete query. That was yet discussable because it introduced unexpected difference between execute and unsafe_execute, which is imo not worth it. Also, now that rql() in migration script default to unsafe_execute, we definitly don't want that implicit behaviour change (which already cause bug when for instance adding another default workflow for an entity type: without that fix we end up with *two* default workflows while the schema tells we can have only one. IMO we should go to the direction that super session skip all security check, but nothing else, unless explicitly asked.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
     1
"""html calendar views
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
     2
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
     3
:organization: Logilab
4212
ab6573088b4a update copyright: welcome 2010
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 2996
diff changeset
     4
:copyright: 2001-2010 LOGILAB S.A. (Paris, FRANCE), license is LGPL v2.
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
     5
:contact: http://www.logilab.fr/ -- mailto:contact@logilab.fr
1977
606923dff11b big bunch of copyright / docstring update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1881
diff changeset
     6
:license: GNU Lesser General Public License, v2.1 - http://www.gnu.org/licenses
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
     7
"""
1881
75540944ae18 fix dc_description format arg
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1802
diff changeset
     8
__docformat__ = "restructuredtext en"
75540944ae18 fix dc_description format arg
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1802
diff changeset
     9
_ = unicode
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    10
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
    11
from datetime import datetime, date, timedelta
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    12
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
    13
from logilab.mtconverter import xml_escape
4466
8b0ca7904820 moved generic datetime manipulation function to lgc
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4252
diff changeset
    14
from logilab.common.date import strptime, date_range, todate, todatetime
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    15
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    16
from cubicweb.interfaces import ICalendarable
692
800592b8d39b replace deprecated cubicweb.common.selectors by its new module path (cubicweb.selectors)
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 524
diff changeset
    17
from cubicweb.selectors import implements
767
b094cf8535b4 cleanup
sylvain.thenault@logilab.fr
parents: 729
diff changeset
    18
from cubicweb.view import EntityView
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    19
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    20
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    21
# useful constants & functions ################################################
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    22
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
    23
ONEDAY = timedelta(1)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    24
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    25
WEEKDAYS = (_("monday"), _("tuesday"), _("wednesday"), _("thursday"),
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    26
            _("friday"), _("saturday"), _("sunday"))
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    27
MONTHNAMES = ( _('january'), _('february'), _('march'), _('april'), _('may'),
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    28
               _('june'), _('july'), _('august'), _('september'), _('october'),
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    29
               _('november'), _('december')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    30
               )
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
    31
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    32
# Calendar views ##############################################################
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    33
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    34
try:
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    35
    from vobject import iCalendar
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    36
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    37
    class iCalView(EntityView):
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    38
        """A calendar view that generates a iCalendar file (RFC 2445)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    39
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    40
        Does apply to ICalendarable compatible entities
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    41
        """
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    42
        __select__ = implements(ICalendarable)
4244
2c3de1953d00 rename need_navigation into paginable
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4212
diff changeset
    43
        paginable = False
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    44
        content_type = 'text/calendar'
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    45
        title = _('iCalendar')
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    46
        templatable = False
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
    47
        __regid__ = 'ical'
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    48
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    49
        def call(self):
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    50
            ical = iCalendar()
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
    51
            for i in range(len(self.cw_rset.rows)):
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
    52
                task = self.cw_rset.complete_entity(i, 0)
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    53
                event = ical.add('vevent')
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    54
                event.add('summary').value = task.dc_title()
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    55
                event.add('description').value = task.dc_description()
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    56
                if task.start:
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    57
                    event.add('dtstart').value = task.start
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    58
                if task.stop:
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    59
                    event.add('dtend').value = task.stop
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    60
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    61
            buff = ical.serialize()
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    62
            if not isinstance(buff, unicode):
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
    63
                buff = unicode(buff, self._cw.encoding)
1644
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    64
            self.w(buff)
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    65
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    66
except ImportError:
45bec81a9e1c makes vobject optional
sylvain.thenault@logilab.fr
parents: 1635
diff changeset
    67
    pass
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    68
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    69
class hCalView(EntityView):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    70
    """A calendar view that generates a hCalendar file
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    71
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    72
    Does apply to ICalendarable compatible entities
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    73
    """
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
    74
    __regid__ = 'hcal'
728
a95b284150d1 first pass to use __select__ instead of __selectors__
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 692
diff changeset
    75
    __select__ = implements(ICalendarable)
4244
2c3de1953d00 rename need_navigation into paginable
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4212
diff changeset
    76
    paginable = False
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    77
    title = _('hCalendar')
524
eee3983e29e9 hcal is a microformat and can be inserted in html
sylvain.thenault@logilab.fr
parents: 431
diff changeset
    78
    #templatable = False
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    79
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    80
    def call(self):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    81
        self.w(u'<div class="hcalendar">')
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
    82
        for i in range(len(self.cw_rset.rows)):
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
    83
            task = self.cw_rset.complete_entity(i, 0)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    84
            self.w(u'<div class="vevent">')
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
    85
            self.w(u'<h3 class="summary">%s</h3>' % xml_escape(task.dc_title()))
1881
75540944ae18 fix dc_description format arg
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1802
diff changeset
    86
            self.w(u'<div class="description">%s</div>'
75540944ae18 fix dc_description format arg
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1802
diff changeset
    87
                   % task.dc_description(format='text/html'))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    88
            if task.start:
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
    89
                self.w(u'<abbr class="dtstart" title="%s">%s</abbr>' % (task.start.isoformat(), self._cw.format_date(task.start)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    90
            if task.stop:
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
    91
                self.w(u'<abbr class="dtstop" title="%s">%s</abbr>' % (task.stop.isoformat(), self._cw.format_date(task.stop)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    92
            self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    93
        self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
    94
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    95
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    96
class CalendarItemView(EntityView):
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
    97
    __regid__ = 'calendaritem'
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    98
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
    99
    def cell_call(self, row, col, dates=False):
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   100
        task = self.cw_rset.complete_entity(row, 0)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   101
        task.view('oneline', w=self.w)
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   102
        if dates:
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   103
            if task.start and task.stop:
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   104
                self.w('<br/>' % self._cw._('from %(date)s' % {'date': self._cw.format_date(task.start)}))
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   105
                self.w('<br/>' % self._cw._('to %(date)s' % {'date': self._cw.format_date(task.stop)}))
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   106
                self.w('<br/>to %s'%self._cw.format_date(task.stop))
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   107
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   108
class CalendarLargeItemView(CalendarItemView):
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
   109
    __regid__ = 'calendarlargeitem'
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   110
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   111
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   112
class _TaskEntry(object):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   113
    def __init__(self, task, color, index=0):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   114
        self.task = task
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   115
        self.color = color
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   116
        self.index = index
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   117
        self.length = 1
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   118
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   119
    def in_working_hours(self):
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   120
        """predicate returning True is the task is in working hours"""
1799
183acfaa3cde ensure start/stop are datetime before access to .hour
sylvain.thenault@logilab.fr
parents: 1644
diff changeset
   121
        if todatetime(self.task.start).hour > 7 and todatetime(self.task.stop).hour < 20:
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   122
            return True
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   123
        return False
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   124
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   125
    def is_one_day_task(self):
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   126
        task = self.task
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   127
        return task.start and task.stop and task.start.isocalendar() ==  task.stop.isocalendar()
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   128
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   129
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   130
class OneMonthCal(EntityView):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   131
    """At some point, this view will probably replace ampm calendars"""
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
   132
    __regid__ = 'onemonthcal'
728
a95b284150d1 first pass to use __select__ instead of __selectors__
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 692
diff changeset
   133
    __select__ = implements(ICalendarable)
4244
2c3de1953d00 rename need_navigation into paginable
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4212
diff changeset
   134
    paginable = False
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   135
    title = _('one month')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   136
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   137
    def call(self):
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   138
        self._cw.add_js('cubicweb.ajax.js')
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   139
        self._cw.add_css('cubicweb.calendar.css')
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   140
        # XXX: restrict courses directy with RQL
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   141
        _today =  datetime.today()
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   142
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   143
        if 'year' in self._cw.form:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   144
            year = int(self._cw.form['year'])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   145
        else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   146
            year = _today.year
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   147
        if 'month' in self._cw.form:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   148
            month = int(self._cw.form['month'])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   149
        else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   150
            month = _today.month
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   151
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   152
        first_day_of_month = date(year, month, 1)
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   153
        firstday = first_day_of_month - timedelta(first_day_of_month.weekday())
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   154
        if month >= 12:
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   155
            last_day_of_month = date(year + 1, 1, 1) - timedelta(1)
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   156
        else:
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   157
            last_day_of_month = date(year, month + 1, 1) - timedelta(1)
4582
d12b81facd1d [calendar view] fix related to the date_range mess (max value exclusion). Calendar views authors should check if more similar fixes needed
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4466
diff changeset
   158
        # date range exclude last day so we should at least add one day, hence
d12b81facd1d [calendar view] fix related to the date_range mess (max value exclusion). Calendar views authors should check if more similar fixes needed
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4466
diff changeset
   159
        # the 7
d12b81facd1d [calendar view] fix related to the date_range mess (max value exclusion). Calendar views authors should check if more similar fixes needed
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4466
diff changeset
   160
        lastday = last_day_of_month + timedelta(7 - last_day_of_month.weekday())
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   161
        month_dates = list(date_range(firstday, lastday))
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   162
        dates = {}
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   163
        task_max = 0
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   164
        for row in xrange(self.cw_rset.rowcount):
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   165
            task = self.cw_rset.get_entity(row, 0)
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   166
            if len(self.cw_rset[row]) > 1 and self.cw_rset.description[row][1] == 'CWUser':
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   167
                user = self.cw_rset.get_entity(row, 1)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   168
            else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   169
                user = None
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   170
            the_dates = []
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   171
            tstart = task.start
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   172
            if tstart:
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   173
                tstart = todate(task.start)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   174
                if tstart > lastday:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   175
                    continue
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   176
                the_dates = [tstart]
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   177
            tstop = task.stop
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   178
            if tstop:
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   179
                tstop = todate(tstop)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   180
                if tstop < firstday:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   181
                    continue
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   182
                the_dates = [tstop]
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   183
            if tstart and tstop:
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   184
                if tstart.isocalendar() == tstop.isocalendar():
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   185
                    if firstday <= tstart <= lastday:
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   186
                        the_dates = [tstart]
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   187
                else:
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   188
                    the_dates = date_range(max(tstart, firstday),
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   189
                                           min(tstop, lastday))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   190
            if not the_dates:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   191
                continue
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   192
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   193
            for d in the_dates:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   194
                d_tasks = dates.setdefault((d.year, d.month, d.day), {})
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   195
                t_users = d_tasks.setdefault(task, set())
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   196
                t_users.add( user )
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   197
                if len(d_tasks) > task_max:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   198
                    task_max = len(d_tasks)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   199
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   200
        days = []
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   201
        nrows = max(3, task_max)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   202
        # colors here are class names defined in cubicweb.css
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   203
        colors = [ "col%x" % i for i in range(12) ]
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   204
        next_color_index = 0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   205
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   206
        visited_tasks = {} # holds a description of a task
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   207
        task_colors = {}   # remember a color assigned to a task
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   208
        for mdate in month_dates:
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   209
            d_tasks = dates.get((mdate.year, mdate.month, mdate.day), {})
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   210
            rows = [None] * nrows
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   211
            # every task that is "visited" for the first time
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   212
            # require a special treatment, so we put them in
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   213
            # 'postpone'
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   214
            postpone = []
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   215
            for task in d_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   216
                if task in visited_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   217
                    task_descr = visited_tasks[ task ]
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   218
                    rows[task_descr.index] = task_descr
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   219
                else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   220
                    postpone.append(task)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   221
            for task in postpone:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   222
                # to every 'new' task we must affect a color
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   223
                # (which must be the same for every user concerned
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   224
                # by the task)
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   225
                for i, t in enumerate(rows):
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   226
                    if t is None:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   227
                        if task in task_colors:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   228
                            color = task_colors[task]
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   229
                        else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   230
                            color = colors[next_color_index]
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   231
                            next_color_index = (next_color_index+1)%len(colors)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   232
                            task_colors[task] = color
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   233
                        task_descr = _TaskEntry(task, color, i)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   234
                        rows[i] = task_descr
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   235
                        visited_tasks[task] = task_descr
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   236
                        break
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   237
                else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   238
                    raise RuntimeError("is it possible we got it wrong?")
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   239
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   240
            days.append( rows )
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   241
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   242
        curdate = first_day_of_month
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   243
        self.w(u'<div id="onemonthcalid">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   244
        # build schedule
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   245
        self.w(u'<table class="omcalendar">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   246
        prevlink, nextlink = self._prevnext_links(curdate)  # XXX
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   247
        self.w(u'<tr><th><a href="%s">&lt;&lt;</a></th><th colspan="5">%s %s</th>'
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   248
               u'<th><a href="%s">&gt;&gt;</a></th></tr>' %
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   249
               (xml_escape(prevlink), self._cw._(curdate.strftime('%B').lower()),
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   250
                curdate.year, xml_escape(nextlink)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   251
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   252
        # output header
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   253
        self.w(u'<tr><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th></tr>' %
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   254
               tuple(self._cw._(day) for day in WEEKDAYS))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   255
        # build calendar
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   256
        for mdate, task_rows in zip(month_dates, days):
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   257
            if mdate.weekday() == 0:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   258
                self.w(u'<tr>')
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   259
            self._build_calendar_cell(mdate, task_rows, curdate)
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   260
            if mdate.weekday() == 6:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   261
                self.w(u'</tr>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   262
        self.w(u'</table></div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   263
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   264
    def _prevnext_links(self, curdate):
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   265
        prevdate = curdate - timedelta(31)
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   266
        nextdate = curdate + timedelta(31)
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   267
        rql = self.cw_rset.printable_rql()
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   268
        prevlink = self._cw.build_ajax_replace_url('onemonthcalid', rql, 'onemonthcal',
1801
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   269
                                                   year=prevdate.year,
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   270
                                                   month=prevdate.month)
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   271
        nextlink = self._cw.build_ajax_replace_url('onemonthcalid', rql, 'onemonthcal',
1801
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   272
                                                   year=nextdate.year,
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   273
                                                   month=nextdate.month)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   274
        return prevlink, nextlink
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   275
1149
1e19b6ef53a1 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1132
diff changeset
   276
    def _build_calendar_cell(self, celldate, rows, curdate):
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   277
        curmonth = curdate.month
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   278
        classes = ""
1149
1e19b6ef53a1 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1132
diff changeset
   279
        if celldate.month != curmonth:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   280
            classes += " outOfRange"
1149
1e19b6ef53a1 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1132
diff changeset
   281
        if celldate == date.today():
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   282
            classes += " today"
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   283
        self.w(u'<td class="cell%s">' % classes)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   284
        self.w(u'<div class="calCellTitle%s">' % classes)
1149
1e19b6ef53a1 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1132
diff changeset
   285
        self.w(u'<div class="day">%s</div>' % celldate.day)
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   286
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   287
        if len(self.cw_rset.column_types(0)) == 1:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   288
            etype = list(self.cw_rset.column_types(0))[0]
3460
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   289
            url = self._cw.build_url(vid='creation', etype=etype,
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   290
                                     schedule=True,
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   291
                                     start=self._cw.format_date(celldate), stop=self._cw.format_date(celldate),
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   292
                                     __redirectrql=self.cw_rset.printable_rql(),
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   293
                                     __redirectparams=self._cw.build_url_params(year=curdate.year, month=curmonth),
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   294
                                     __redirectvid=self.__regid__
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   295
                                     )
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   296
            self.w(u'<div class="cmd"><a href="%s">%s</a></div>' % (xml_escape(url), self._cw._(u'add')))
2996
866a2c135c33 B #345282 xhtml requires to use &#160; instead of &nbsp;
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 2312
diff changeset
   297
            self.w(u'&#160;')
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   298
        self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   299
        self.w(u'<div class="cellContent">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   300
        for task_descr in rows:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   301
            if task_descr:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   302
                task = task_descr.task
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   303
                self.w(u'<div class="task %s">' % task_descr.color)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   304
                task.view('calendaritem', w=self.w )
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   305
                url = task.absolute_url(vid='edition',
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   306
                                        __redirectrql=self.cw_rset.printable_rql(),
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   307
                                        __redirectparams=self._cw.build_url_params(year=curdate.year, month=curmonth),
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   308
                                        __redirectvid=self.__regid__
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   309
                                        )
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   310
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   311
                self.w(u'<div class="tooltip" ondblclick="stopPropagation(event); window.location.assign(\'%s\'); return false;">' % xml_escape(url))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   312
                task.view('tooltip', w=self.w )
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   313
                self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   314
            else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   315
                self.w(u'<div class="task">')
2996
866a2c135c33 B #345282 xhtml requires to use &#160; instead of &nbsp;
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 2312
diff changeset
   316
                self.w(u"&#160;")
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   317
            self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   318
        self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   319
        self.w(u'</td>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   320
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   321
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   322
class OneWeekCal(EntityView):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   323
    """At some point, this view will probably replace ampm calendars"""
3377
dd9d292b6a6d use __regid__ instead of id on appobject classes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 2996
diff changeset
   324
    __regid__ = 'oneweekcal'
728
a95b284150d1 first pass to use __select__ instead of __selectors__
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 692
diff changeset
   325
    __select__ = implements(ICalendarable)
4244
2c3de1953d00 rename need_navigation into paginable
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 4212
diff changeset
   326
    paginable = False
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   327
    title = _('one week')
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   328
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   329
    def call(self):
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   330
        self._cw.add_js( ('cubicweb.ajax.js', 'cubicweb.calendar.js') )
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   331
        self._cw.add_css('cubicweb.calendar.css')
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   332
        # XXX: restrict directly with RQL
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   333
        _today =  datetime.today()
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   334
        if 'year' in self._cw.form:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   335
            year = int(self._cw.form['year'])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   336
        else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   337
            year = _today.year
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   338
        if 'week' in self._cw.form:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   339
            week = int(self._cw.form['week'])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   340
        else:
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   341
            week = _today.isocalendar()[1]
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   342
        # week - 1 since we get week number > 0 while we want it to start from 0
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   343
        first_day_of_week = todate(strptime('%s-%s-1' % (year, week - 1), '%Y-%U-%w'))
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   344
        lastday = first_day_of_week + timedelta(6)
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   345
        firstday = first_day_of_week
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   346
        dates = [[] for i in range(7)]
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   347
        task_colors = {}   # remember a color assigned to a task
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   348
        # colors here are class names defined in cubicweb.css
1132
96752791c2b6 pylint cleanup
sylvain.thenault@logilab.fr
parents: 1033
diff changeset
   349
        colors = [ "col%x" % i for i in range(12) ]
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   350
        next_color_index = 0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   351
        done_tasks = []
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   352
        for row in xrange(self.cw_rset.rowcount):
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   353
            task = self.cw_rset.get_entity(row, 0)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   354
            if task in done_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   355
                continue
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   356
            done_tasks.append(task)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   357
            the_dates = []
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   358
            tstart = task.start
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   359
            tstop = task.stop
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   360
            if tstart:
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   361
                tstart = todate(tstart)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   362
                if tstart > lastday:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   363
                    continue
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   364
                the_dates = [tstart]
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   365
            if tstop:
1800
05c36cf3c813 [calendar] ensure task.start / task.stop are available before calling todate()
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1799
diff changeset
   366
                tstop = todate(tstop)
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   367
                if tstop < firstday:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   368
                    continue
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   369
                the_dates = [tstop]
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   370
            if tstart and tstop:
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   371
                the_dates = date_range(max(tstart, firstday),
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   372
                                       min(tstop, lastday))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   373
            if not the_dates:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   374
                continue
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   375
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   376
            if task not in task_colors:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   377
                task_colors[task] = colors[next_color_index]
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   378
                next_color_index = (next_color_index+1) % len(colors)
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   379
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   380
            for d in the_dates:
1016
26387b836099 use datetime instead of mx.DateTime
sylvain.thenault@logilab.fr
parents: 767
diff changeset
   381
                day = d.weekday()
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   382
                task_descr = _TaskEntry(task, task_colors[task])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   383
                dates[day].append(task_descr)
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   384
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   385
        self.w(u'<div id="oneweekcalid">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   386
        # build schedule
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   387
        self.w(u'<table class="omcalendar" id="week">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   388
        prevlink, nextlink = self._prevnext_links(first_day_of_week)  # XXX
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   389
        self.w(u'<tr><th class="transparent"></th>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   390
        self.w(u'<th><a href="%s">&lt;&lt;</a></th><th colspan="5">%s %s %s</th>'
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   391
               u'<th><a href="%s">&gt;&gt;</a></th></tr>' %
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   392
               (xml_escape(prevlink), first_day_of_week.year,
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   393
                self._cw._(u'week'), first_day_of_week.isocalendar()[1],
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   394
                xml_escape(nextlink)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   395
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   396
        # output header
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   397
        self.w(u'<tr>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   398
        self.w(u'<th class="transparent"></th>') # column for hours
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   399
        _today = date.today()
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   400
        for i, day in enumerate(WEEKDAYS):
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   401
            wdate = first_day_of_week + timedelta(i)
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   402
            if wdate.isocalendar() == _today.isocalendar():
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   403
                self.w(u'<th class="today">%s<br/>%s</th>' % (self._cw._(day), self._cw.format_date(wdate)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   404
            else:
3457
0924d0d08d60 [api] __regid__, cw_* and friends
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3451
diff changeset
   405
                self.w(u'<th>%s<br/>%s</th>' % (self._cw._(day), self._cw.format_date(wdate)))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   406
        self.w(u'</tr>')
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   407
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   408
        # build week calendar
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   409
        self.w(u'<tr>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   410
        self.w(u'<td style="width:5em;">') # column for hours
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   411
        extra = ""
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   412
        for h in range(8, 20):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   413
            self.w(u'<div class="hour" %s>'%extra)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   414
            self.w(u'%02d:00'%h)
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   415
            self.w(u'</div>')
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   416
        self.w(u'</td>')
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   417
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   418
        for i, day in enumerate(WEEKDAYS):
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   419
            wdate = first_day_of_week + timedelta(i)
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   420
            classes = ""
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   421
            if wdate.isocalendar() == _today.isocalendar():
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   422
                classes = " today"
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   423
            self.w(u'<td class="column %s" id="%s">' % (classes, day))
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   424
            if len(self.cw_rset.column_types(0)) == 1:
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   425
                etype = list(self.cw_rset.column_types(0))[0]
3460
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   426
                url = self._cw.build_url(vid='creation', etype=etype,
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   427
                                         schedule=True,
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   428
                                         __redirectrql=self.cw_rset.printable_rql(),
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   429
                                         __redirectparams=self._cw.build_url_params(year=year, week=week),
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   430
                                         __redirectvid=self.__regid__
e4843535db25 [api] some more _cw / __regid__, automatic tests now pass again
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3457
diff changeset
   431
                                         )
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   432
                extra = ' ondblclick="addCalendarItem(event, hmin=8, hmax=20, year=%s, month=%s, day=%s, duration=2, baseurl=\'%s\')"' % (
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   433
                    wdate.year, wdate.month, wdate.day, xml_escape(url))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   434
            else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   435
                extra = ""
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   436
            self.w(u'<div class="columndiv"%s>'% extra)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   437
            for h in range(8, 20):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   438
                self.w(u'<div class="hourline" style="top:%sex;">'%((h-7)*8))
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   439
                self.w(u'</div>')
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   440
            if dates[i]:
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   441
                self._build_calendar_cell(wdate, dates[i])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   442
            self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   443
            self.w(u'</td>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   444
        self.w(u'</tr>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   445
        self.w(u'</table></div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   446
        self.w(u'<div id="coord"></div>')
2996
866a2c135c33 B #345282 xhtml requires to use &#160; instead of &nbsp;
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 2312
diff changeset
   447
        self.w(u'<div id="debug">&#160;</div>')
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   448
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   449
    def _build_calendar_cell(self, date, task_descrs):
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   450
        inday_tasks = [t for t in task_descrs if t.is_one_day_task() and  t.in_working_hours()]
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   451
        wholeday_tasks = [t for t in task_descrs if not t.is_one_day_task()]
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   452
        inday_tasks.sort(key=lambda t:t.task.start)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   453
        sorted_tasks = []
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   454
        for i, t in enumerate(wholeday_tasks):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   455
            t.index = i
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   456
        ncols = len(wholeday_tasks)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   457
        while inday_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   458
            t = inday_tasks.pop(0)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   459
            for i, c in enumerate(sorted_tasks):
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   460
                if not c or c[-1].task.stop <= t.task.start:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   461
                    c.append(t)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   462
                    t.index = i+ncols
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   463
                    break
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   464
            else:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   465
                t.index = len(sorted_tasks) + ncols
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   466
                sorted_tasks.append([t])
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   467
        ncols += len(sorted_tasks)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   468
        if ncols == 0:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   469
            return
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   470
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   471
        inday_tasks = []
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   472
        for tasklist in sorted_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   473
            inday_tasks += tasklist
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   474
        width = 100.0/ncols
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   475
        for task_desc in wholeday_tasks + inday_tasks:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   476
            task = task_desc.task
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   477
            start_hour = 8
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   478
            start_min = 0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   479
            stop_hour = 20
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   480
            stop_min = 0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   481
            if task.start:
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   482
                if date < todate(task.start) < date + ONEDAY:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   483
                    start_hour = max(8, task.start.hour)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   484
                    start_min = task.start.minute
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   485
            if task.stop:
1025
aebf37f460c1 some datetime fixes
sylvain.thenault@logilab.fr
parents: 1016
diff changeset
   486
                if date < todate(task.stop) < date + ONEDAY:
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   487
                    stop_hour = min(20, task.stop.hour)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   488
                    if stop_hour < 20:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   489
                        stop_min = task.stop.minute
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   490
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   491
            height = 100.0*(stop_hour+stop_min/60.0-start_hour-start_min/60.0)/(20-8)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   492
            top = 100.0*(start_hour+start_min/60.0-8)/(20-8)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   493
            left = width*task_desc.index
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   494
            style = "height: %s%%; width: %s%%; top: %s%%; left: %s%%; " % \
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   495
                (height, width, top, left)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   496
            self.w(u'<div class="task %s" style="%s">' % \
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   497
                       (task_desc.color, style))
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   498
            task.view('calendaritem', dates=False, w=self.w)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   499
            url = task.absolute_url(vid='edition',
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   500
                                    __redirectrql=self.cw_rset.printable_rql(),
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   501
                                    __redirectparams=self._cw.build_url_params(year=date.year, week=date.isocalendar()[1]),
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   502
                                    __redirectvid=self.__regid__
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   503
                                 )
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   504
2312
af4d8f75c5db use xml_escape
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 1977
diff changeset
   505
            self.w(u'<div class="tooltip" ondblclick="stopPropagation(event); window.location.assign(\'%s\'); return false;">' % xml_escape(url))
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   506
            task.view('tooltip', w=self.w)
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   507
            self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   508
            if task.start is None:
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   509
                self.w(u'<div class="bottommarker">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   510
                self.w(u'<div class="bottommarkerline" style="margin: 0px 3px 0px 3px; height: 1px;">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   511
                self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   512
                self.w(u'<div class="bottommarkerline" style="margin: 0px 2px 0px 2px; height: 1px;">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   513
                self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   514
                self.w(u'<div class="bottommarkerline" style="margin: 0px 1px 0px 1px; height: 3ex; color: white; font-size: x-small; vertical-align: center; text-align: center;">')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   515
                self.w(u'end')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   516
                self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   517
                self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   518
            self.w(u'</div>')
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   519
1604
fd943737d630 delete-trailing-whitespaces
sylvain.thenault@logilab.fr
parents: 1398
diff changeset
   520
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   521
    def _prevnext_links(self, curdate):
1033
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   522
        prevdate = curdate - timedelta(7)
f5be65616a31 more datetime fixes and cleanup
sylvain.thenault@logilab.fr
parents: 1025
diff changeset
   523
        nextdate = curdate + timedelta(7)
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   524
        rql = self.cw_rset.printable_rql()
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   525
        prevlink = self._cw.build_ajax_replace_url('oneweekcalid', rql, 'oneweekcal',
1801
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   526
                                                   year=prevdate.year,
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   527
                                                   week=prevdate.isocalendar()[1])
3451
6b46d73823f5 [api] work in progress, use __regid__, cw_*, etc.
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 3377
diff changeset
   528
        nextlink = self._cw.build_ajax_replace_url('oneweekcalid', rql, 'oneweekcal',
1801
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   529
                                                   year=nextdate.year,
672acc730ce5 ajax_replace_url becomes obsolete, req.build_ajax_replace_url should be used instead
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 1800
diff changeset
   530
                                                   week=nextdate.isocalendar()[1])
0
b97547f5f1fa Showtime !
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
diff changeset
   531
        return prevlink, nextlink