Fix day filter
[cds-indico.git] / indico / util / event.py
blob971cb9443b894a34b68a42f58a526e1fd29671eb
1 # This file is part of Indico.
2 # Copyright (C) 2002 - 2015 European Organization for Nuclear Research (CERN).
4 # Indico is free software; you can redistribute it and/or
5 # modify it under the terms of the GNU General Public License as
6 # published by the Free Software Foundation; either version 3 of the
7 # License, or (at your option) any later version.
9 # Indico is distributed in the hope that it will be useful, but
10 # WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 # General Public License for more details.
14 # You should have received a copy of the GNU General Public License
15 # along with Indico; if not, see <http://www.gnu.org/licenses/>.
17 """
18 Event-related utils
19 """
21 import re
24 UID_RE = re.compile(r'^(?P<event>\w+)(?:\.s(?P<session>\w+))?(?:\.(?P<contrib>\w+))?(?:\.(?P<subcont>\w+))?$')
27 def uniqueId(obj):
28 from indico.modules.events.notes.models.notes import EventNote
29 from MaKaC import conference
31 ret = obj.getId() if hasattr(obj, 'getId') else obj.id
33 if isinstance(obj, conference.Contribution):
34 ret = "%s.%s" % (obj.getConference().getId(), ret)
35 elif isinstance(obj, conference.SubContribution):
36 ret = "%s.%s.%s" % (obj.getConference().getId(),
37 obj.getContribution().getId(), ret)
38 elif isinstance(obj, conference.Session):
39 ret = "%s.s%s" % (obj.getConference().getId(), ret)
40 elif isinstance(obj, conference.SessionSlot):
41 ret = "%s.s%s.%s" % (obj.getConference().getId(),
42 obj.getSession().getId(), ret)
43 elif isinstance(obj, EventNote):
44 ret = '{}.n{}'.format(uniqueId(obj.linked_object), ret)
46 return ret
49 def truncate_path(full_path, chars=30, skip_first=True):
50 """Truncate the path of a category to the number of character.
52 Only the path is truncated by removing nodes, but the nodes
53 themselves are never truncated.
55 If the last node is longer than the ``chars`` constraint, then it is
56 returned as is (with ``None`` for the first and inner nodes.)
57 This is the only case where the ``chars`` constraint might not be
58 respected.
60 If ``skip_first`` is ``True``, the first node will be skipped,
61 except if the path has 1 or 2 nodes only and the first node fits
62 under the ``chars`` constraint
64 :param full_path: list -- all the nodes of the path in order
65 :param chars: int -- the desired length in characters of the path
66 :param skip_first: bool -- whether to ignore the first node or not
67 If the path only has 1 or 2 nodes, then the first
68 node will not be skipped if it can fit within the
69 ``chars`` constraint.
71 :returns: tuple -- the first node, the inner nodes, the last node
72 and whether the path was truncated. If any of the values
73 have been truncated, they will be ``None``.
75 """
76 truncated = False
77 if skip_first:
78 skip, full_path = full_path[:1], full_path[1:]
79 skip = skip[0] if skip else None
80 else:
81 skip = None
83 if not full_path:
84 return None, None, skip, truncated
85 if len(full_path) == 1:
86 if skip is not None and len(skip) + len(full_path[0]) <= chars:
87 return skip, None, full_path[0], truncated
88 else:
89 return None, None, full_path[0], skip is not None # only truncated if we skip the first
91 first_node, inner, last_node = full_path[0], full_path[1:-1], full_path[-1]
92 char_length = len(last_node)
94 if char_length + len(first_node) > chars:
95 first_node = None
96 truncated = True
97 else:
98 char_length += len(first_node)
100 if not inner:
101 return first_node, None, last_node, truncated
103 path = []
104 prev = inner.pop()
105 while char_length + len(prev) <= chars:
106 char_length += len(prev)
107 path.append(prev)
108 if not inner:
109 break
110 prev = inner.pop()
111 else:
112 truncated = True
114 return first_node, path[::-1], last_node, truncated