126
129
return revision_ids
129
def format_highres_date(t, offset=0):
130
"""Format a date, such that it includes higher precision in the
133
:param t: The local time in fractional seconds since the epoch
135
:param offset: The timezone offset in integer seconds
138
Example: format_highres_date(time.time(), -time.timezone)
139
this will return a date stamp for right now,
140
formatted for the local timezone.
142
>>> from bzrlib.osutils import format_date
143
>>> format_date(1120153132.350850105, 0)
144
'Thu 2005-06-30 17:38:52 +0000'
145
>>> format_highres_date(1120153132.350850105, 0)
146
'Thu 2005-06-30 17:38:52.350850105 +0000'
147
>>> format_date(1120153132.350850105, -5*3600)
148
'Thu 2005-06-30 12:38:52 -0500'
149
>>> format_highres_date(1120153132.350850105, -5*3600)
150
'Thu 2005-06-30 12:38:52.350850105 -0500'
151
>>> format_highres_date(1120153132.350850105, 7200)
152
'Thu 2005-06-30 19:38:52.350850105 +0200'
153
>>> format_highres_date(1152428738.867522, 19800)
154
'Sun 2006-07-09 12:35:38.867522001 +0530'
157
assert isinstance(t, float)
159
# This has to be formatted for "original" date, so that the
160
# revision XML entry will be reproduced faithfully.
163
tt = time.gmtime(t + offset)
165
return (time.strftime("%a %Y-%m-%d %H:%M:%S", tt)
166
+ ('%.9f' % (t - int(t)))[1:] # Get the high-res seconds, but ignore the 0
167
+ ' %+03d%02d' % (offset / 3600, (offset / 60) % 60))
170
def unpack_highres_date(date):
171
"""This takes the high-resolution date stamp, and
172
converts it back into the tuple (timestamp, timezone)
173
Where timestamp is in real UTC since epoch seconds, and timezone is an integer
174
number of seconds offset.
176
:param date: A date formated by format_highres_date
179
>>> import time, random
180
>>> unpack_highres_date('Thu 2005-06-30 12:38:52.350850105 -0500')
181
(1120153132.3508501, -18000)
182
>>> unpack_highres_date('Thu 2005-06-30 17:38:52.350850105 +0000')
183
(1120153132.3508501, 0)
184
>>> unpack_highres_date('Thu 2005-06-30 19:38:52.350850105 +0200')
185
(1120153132.3508501, 7200)
186
>>> unpack_highres_date('Sun 2006-07-09 12:35:38.867522001 +0530')
187
(1152428738.867522, 19800)
188
>>> from bzrlib.osutils import local_time_offset
190
>>> o = local_time_offset()
191
>>> t2, o2 = unpack_highres_date(format_highres_date(t, o))
196
>>> t -= 24*3600*365*2 # Start 2 years ago
198
>>> for count in xrange(500):
199
... t += random.random()*24*3600*30
200
... o = ((o/3600 + 13) % 25 - 12)*3600 # Add 1 wrap around from [-12, 12]
201
... date = format_highres_date(t, o)
202
... t2, o2 = unpack_highres_date(date)
203
... if t != t2 or o != o2:
204
... print 'Failed on date %r, %s,%s diff:%s' % (date, t, o, t2-t)
208
import time, calendar
209
# Up until the first period is a datestamp that is generated
210
# as normal from time.strftime, so use time.strptime to
212
dot_loc = date.find('.')
215
'Date string does not contain high-precision seconds: %r' % date)
216
base_time = time.strptime(date[:dot_loc], "%a %Y-%m-%d %H:%M:%S")
217
fract_seconds, offset = date[dot_loc:].split()
218
fract_seconds = float(fract_seconds)
222
hours = int(offset / 100)
223
minutes = (offset % 100)
224
seconds_offset = (hours * 3600) + (minutes * 60)
226
# time.mktime returns localtime, but calendar.timegm returns UTC time
227
timestamp = calendar.timegm(base_time)
228
timestamp -= seconds_offset
229
# Add back in the fractional seconds
230
timestamp += fract_seconds
231
return (timestamp, seconds_offset)
234
132
class BundleSerializer(object):
235
133
"""The base class for Serializers.