5e8fe792e9dfa3e1a5e86e03fb038f337b9d41d8
[pycalendar.git] / pycalendar / dtype / time.py
1 # Copyright (C) 2013 W. Trevor King <wking@tremily.us>
2 #
3 # This file is part of pycalender.
4 #
5 # pycalender is free software: you can redistribute it and/or modify it under
6 # the terms of the GNU General Public License as published by the Free Software
7 # Foundation, either version 3 of the License, or (at your option) any later
8 # version.
9 #
10 # pycalender is distributed in the hope that it will be useful, but WITHOUT ANY
11 # WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
12 # A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU General Public License along with
15 # pycalender.  If not, see <http://www.gnu.org/licenses/>.
16
17 """Functions for processing times without dates
18
19 As defined in :RFC:`5545`, section 3.3.12 (Time).
20 """
21
22 import datetime as _datetime
23
24 import pytz as _pytz
25
26 from . import base as _base
27
28
29 class Time (_base.DataType):
30     name = 'TIME'
31
32     @classmethod
33     def decode(cls, property, value):
34         """Decode times without dates
35
36         As defined in :RFC:`5545`, section 3.3.12 (Time).
37
38         >>> Time.decode(property={}, value='230000')
39         datetime.time(23, 0)
40         >>> Time.decode(property={}, value='070000Z')
41         datetime.time(7, 0, tzinfo=datetime.timezone.utc)
42         >>> Time.decode(property={}, value='083000')
43         datetime.time(8, 30)
44         >>> Time.decode(property={}, value='133000Z')
45         datetime.time(13, 30, tzinfo=datetime.timezone.utc)
46         >>> Time.decode(property={'TZID': 'America/New_York'}, value='083000')
47         ... # doctest: +NORMALIZE_WHITESPACE
48         datetime.time(8, 30,
49           tzinfo=<DstTzInfo 'America/New_York' EST-1 day, 19:00:00 STD>)
50         """
51         tzinfo = property.get('TZID', None)
52         if len(value) not in [6,7]:
53             raise ValueError(value)
54         hour = int(value[0:2])
55         minute = int(value[2:4])
56         second = int(value[4:6])
57         if second == 60:  # positive leap second not supported by Python
58             second = 59
59         if value.endswith('Z'):
60             tzinfo = _datetime.timezone.utc
61         elif tzinfo:
62             tzinfo = _pytz.timezone(tzinfo)
63         return _datetime.time(
64             hour=hour, minute=minute, second=second, tzinfo=tzinfo)
65
66     @classmethod
67     def encode(cls, property, value):
68         if value.tzinfo == _datetime.timezone.utc:
69             return value.strftime('%H%M%SZ')
70         return value.strftime('%H%M%S')