Revision: 84d48ee0a7f6
Branch: default
Author: Janne Piironen <janne.piiro...@gmail.com>
Date: Mon May 12 13:09:05 2014 UTC
Log: DateTime: Refactored Convert Date to use epoch seconds
internally. Added output options for milliseconds and timestamp formatting.
Update issue 415
Implemented optional milliseconds and output formatting for timestamp
representation to Convert Date keyword.
http://code.google.com/p/robotframework/source/detail?r=84d48ee0a7f6
Modified:
/atest/testdata/standard_libraries/datetime/convert_date_input_format.txt
/atest/testdata/standard_libraries/datetime/convert_date_result_format.txt
/src/robot/libraries/DateTime.py
=======================================
---
/atest/testdata/standard_libraries/datetime/convert_date_input_format.txt
Tue May 6 22:22:41 2014 UTC
+++
/atest/testdata/standard_libraries/datetime/convert_date_input_format.txt
Mon May 12 13:09:05 2014 UTC
@@ -3,50 +3,50 @@
Library DateTime
Variables datesandtimes.py
-*** Test Cases *** INPUT FORMAT
OUTPUT
-String inputs 2014-04-24 21:45:12.123 ${NONE}
2014-04-24 21:45:12.123
- 2014-04-24 21:45:12 ${NONE}
2014-04-24 21:45:12
- 2014-04-24T21:45:12.123 ${NONE}
2014-04-24 21:45:12.123
- 2014.04+24@@21/45!12,123 ${NONE}
2014-04-24 21:45:12.123
+*** Test Cases *** INPUT
OUTPUT INPUT FORMAT
+String inputs 2014-04-24 21:45:12.123
2014-04-24 21:45:12.123
+ 2014-04-24 21:45:12
2014-04-24 21:45:12.000
+ 2014-04-24T21:45:12.123
2014-04-24 21:45:12.123
+ 2014.04+24@@21/45!12,123
2014-04-24 21:45:12.123
-Formatted strings 2014-04-24 21:45:12.123 %Y-%m-%d %H:%M:%S.%f
2014-04-24 21:45:12.123
- 2014-04-24T21:45:12.123 %Y-%m-%dT%H:%M:%S.%f
2014-04-24 21:45:12.123
- 24.4.2014 21:45:12-123 %d.%m.%Y %H:%M:%S-%f
2014-04-24 21:45:12.123
- 04/24/2014T21.45.12 %m/%d/%YT%H.%M.%S
2014-04-24 21:45:12
- 24.04.2014 %d.%m.%Y
2014-04-24 00:00:00
- 24-04.2014@21 %d-%m.%Y@%H
2014-04-24 21:00:00
+Formatted strings 2014-04-24 21:45:12.123
2014-04-24 21:45:12.123 %Y-%m-%d %H:%M:%S.%f
+ 2014-04-24T21:45:12.123
2014-04-24 21:45:12.123 %Y-%m-%dT%H:%M:%S.%f
+ 24.4.2014 21:45:12-123
2014-04-24 21:45:12.123 %d.%m.%Y %H:%M:%S-%f
+ 04/24/2014T21.45.12
2014-04-24 21:45:12.000 %m/%d/%YT%H.%M.%S
+ 24.04.2014
2014-04-24 00:00:00.000 %d.%m.%Y
+ 24-04.2014@21
2014-04-24 21:00:00.000 %d-%m.%Y@%H
-Formatted with %f in middle
- [Template] NONE
- Run Keyword If sys.version_info < (2, 6) or sys.platform == 'cli'
- ... Run Keyword And Expect Error ValueError: %f directive is
supported only at the end of the format string on this Python interpreter.
- ... Date Conversion Should Succeed 21:45:12.123
24.04.2014 %H:%M:%S.%f %d.%m.%Y 2014-04-24 21:45:12.123
- ... ELSE
- ... Date Conversion Should Succeed 21:45:12.123
24.04.2014 %H:%M:%S.%f %d.%m.%Y 2014-04-24 21:45:12.123
+Epoch ${1398365112.0}
2014-04-24 21:45:12.000
+ ${1398365112.123}
2014-04-24 21:45:12.123
-Epoch ${1398365112.0} ${NONE}
2014-04-24 21:45:12
- ${1398365112.123} ${NONE}
2014-04-24 21:45:12.123
-
-Datetime object ${datetime(2014, 4, 24, 21, 45, 12, 123000)}
${NONE} 2014-04-24 21:45:12.123
- ${datetime(2014, 4, 24, 21)}
${NONE} 2014-04-24 21:00:00
+Datetime object ${datetime(2014, 4, 24, 21, 45, 12, 123000)}
2014-04-24 21:45:12.123
+ ${datetime(2014, 4, 24, 21)}
2014-04-24 21:00:00.000
Pad zeroes to missing values
- 2014-04-24 ${NONE}
2014-04-24 00:00:00
- 2014.04.24 21 ${NONE}
2014-04-24 21:00:00
+ 2014-04-24
2014-04-24 00:00:00.000
+ 2014.04.24 21
2014-04-24 21:00:00.000
Rounding milliseconds
- 2014-04-24 21:45:12.123456
${NONE} 2014-04-24 21:45:12.123
- 2014-04-24 21:45:12.1234
${NONE} 2014-04-24 21:45:12.123
- 2014-04-24 21:45:12.1235
${NONE} 2014-04-24 21:45:12.124
-
2014-04-24T21:45:12.123456 %Y-%m-%dT%H:%M:%S.%f 2014-04-24
21:45:12.123
-
2014-04-24T21:45:12.1234 %Y-%m-%dT%H:%M:%S.%f 2014-04-24
21:45:12.123
-
2014-04-24T21:45:12.1235 %Y-%m-%dT%H:%M:%S.%f 2014-04-24
21:45:12.124
- ${1398365112.123456}
${NONE} 2014-04-24 21:45:12.123
- ${1398365112.1234}
${NONE} 2014-04-24 21:45:12.123
- ${1398365112.1235}
${NONE} 2014-04-24 21:45:12.124
- ${datetime(2014, 4, 24, 21, 45, 12, 123456)}
${NONE} 2014-04-24 21:45:12.123
- ${datetime(2014, 4, 24, 21, 45, 12, 123400)}
${NONE} 2014-04-24 21:45:12.123
- ${datetime(2014, 4, 24, 21, 45, 12, 123500)}
${NONE} 2014-04-24 21:45:12.124
+ 2014-04-24 21:45:12.123456
2014-04-24 21:45:12.123
+ 2014-04-24 21:45:12.1234
2014-04-24 21:45:12.123
+ 2014-04-24 21:45:12.1235
2014-04-24 21:45:12.124
+ 2014-04-24T21:45:12.123456
2014-04-24 21:45:12.123 %Y-%m-%dT%H:%M:%S.%f
+ 2014-04-24T21:45:12.1234
2014-04-24 21:45:12.123 %Y-%m-%dT%H:%M:%S.%f
+ 2014-04-24T21:45:12.1235
2014-04-24 21:45:12.124 %Y-%m-%dT%H:%M:%S.%f
+ ${1398365112.123456}
2014-04-24 21:45:12.123
+ ${1398365112.1234}
2014-04-24 21:45:12.123
+ ${1398365112.1235}
2014-04-24 21:45:12.124
+ ${datetime(2014, 4, 24, 21, 45, 12, 123456)}
2014-04-24 21:45:12.123
+ ${datetime(2014, 4, 24, 21, 45, 12, 123400)}
2014-04-24 21:45:12.123
+ ${datetime(2014, 4, 24, 21, 45, 12, 123500)}
2014-04-24 21:45:12.124
+
+Formatted with %f in middle
+ [Template] NONE
+ Run Keyword If sys.version_info < (2, 6) or sys.platform == 'cli'
+ ... Run Keyword And Expect Error ValueError: %f directive is
supported only at the end of the format string on this Python interpreter.
+ ... Date Conversion Should Succeed 21:45:12.123 24.04.2014
2014-04-24 21:45:12.123 %H:%M:%S.%f %d.%m.%Y
+ ... ELSE
+ ... Date Conversion Should Succeed 21:45:12.123 24.04.2014
2014-04-24 21:45:12.123 %H:%M:%S.%f %d.%m.%Y
Invalid input format
[Documentation] FAIL ValueError: Unsupported input 'None'.
@@ -55,6 +55,6 @@
*** Keywords ***
Date Conversion Should Succeed
- [Arguments] ${input} ${input_format} ${expected}
+ [Arguments] ${input} ${expected} ${input_format}=${NONE}
${ts} = Convert Date ${input} input_format=${input_format}
Should Be Equal ${ts} ${expected}
=======================================
---
/atest/testdata/standard_libraries/datetime/convert_date_result_format.txt
Tue May 6 11:27:13 2014 UTC
+++
/atest/testdata/standard_libraries/datetime/convert_date_result_format.txt
Mon May 12 13:09:05 2014 UTC
@@ -1,32 +1,48 @@
*** Settings ***
-Library DateTime
-Test Template Date Conversion Should Succeed
-Variables datesandtimes.py
+Test Template Date Conversion Should Succeed
+Library DateTime
+Variables datesandtimes.py
*** Variables ***
-${DATE} ${datetime(2014, 4, 24, 21, 45, 12, 123000)}
+${DATE} ${datetime(2014, 4, 24, 21, 45, 12, 123000)}
-*** Test Cases ***
+*** Test Cases *** INPUT
FORMAT OUTPUT INPUT FORMAT
Should convert to timestamp
- 2014-04-24 21:45:12.123 timeSTAMP ${NONE}
2014-04-24 21:45:12.123
- 2014-04-24 21:45:12.123 tImestamp %Y-%m-%d %H:%M:%S.%f
2014-04-24 21:45:12.123
- ${1398365112.0} TIMEstamp ${NONE}
2014-04-24 21:45:12
- ${DATE} TimeStamp ${NONE}
2014-04-24 21:45:12.123
+ 2014-04-24 21:45:12.123
timeSTAMP 2014-04-24 21:45:12.123
+ 2014-04-24 21:45:12.123
tImestamp 2014-04-24
21:45:12.123 %Y-%m-%d %H:%M:%S.%f
+ ${1398365112.0}
TIMEstamp 2014-04-24 21:45:12.000
+ ${DATE}
TimeStamp 2014-04-24 21:45:12.123
+
+Should convert to timestamp with format
+ 2014-04-24 21:45:12.123
TimeStamp:%H:%M:%S %Y-%m-%d 21:45:12 2014-04-24
+ 2014/04/24 21:45:12.123
timestamp:%H:%M %Y-%m-%d 21:45
2014-04-24 %Y/%m/%d %H:%M:%S.%f
Should convert to epoch
- 2014-04-24 21:45:12.123 epoch ${NONE}
${1398365112.0}
- 2014-04-24 21:45:12.123 epoch %Y-%m-%d %H:%M:%S.%f
${1398365112.0}
- ${1398365112.0} epoch ${NONE}
${1398365112.0}
- ${DATE} epoch ${NONE}
${1398365112.0}
+ 2014-04-24 21:45:12.123
epoch ${1398365112.123}
+ 2014-04-24 21:45:12.123
epoch
${1398365112.123} %Y-%m-%d %H:%M:%S.%f
+ ${1398365112.0}
epoch ${1398365112.0}
+ ${DATE}
epoch ${1398365112.123}
Should convert to datetime
- 2014-04-24 21:45:12.123 datetime ${NONE} ${DATE}
- 2014-04-24 21:45:12.123 datetime %Y-%m-%d %H:%M:%S.%f ${DATE}
- ${1398365112.123} dateTiMe ${NONE} ${DATE}
- ${DATE} datetimE ${NONE} ${DATE}
+ 2014-04-24 21:45:12.123
datetime ${DATE}
+ 2014-04-24 21:45:12.123
datetime
${DATE} %Y-%m-%d %H:%M:%S.%f
+ ${1398365112.123}
dateTiMe ${DATE}
+ ${DATE}
datetimE ${DATE}
+
+Should exclude milliseconds
+ [Template] Date Conversion Should Succeed Without
Milliseconds
+ 2014-04-24 21:45:12.123
timestamp 2014-04-24 21:45:12
+ 2014-04-24 21:45:12.999
timestamp 2014-04-24 21:45:13
+ ${DATE}
timestamp 2014-04-24 21:45:12
+ ${1398365112.123}
datetime ${datetime(2014, 4, 24, 21, 45, 12)}
*** Keywords ***
Date Conversion Should Succeed
- [Arguments] ${input} ${output_format} ${input_format}
${expected}
+ [Arguments] ${input} ${output_format} ${expected}
${input_format}=${NONE}
${ts} = Convert Date ${input} ${output_format}
${input_format}
Should Be Equal ${ts} ${expected}
+
+Date Conversion Should Succeed Without Milliseconds
+ [Arguments] ${input} ${output_format} ${expected}
+ ${ts} = Convert Date ${input} ${output_format}
exclude_millis=True
+ Should Be Equal ${ts} ${expected}
=======================================
--- /src/robot/libraries/DateTime.py Tue May 6 22:22:41 2014 UTC
+++ /src/robot/libraries/DateTime.py Mon May 12 13:09:05 2014 UTC
@@ -4,7 +4,7 @@
import sys
import re
-from robot.utils import elapsed_time_to_string, secs_to_timestr,
timestr_to_secs
+from robot.utils import elapsed_time_to_string, secs_to_timestr,
timestr_to_secs, parse_time
class DateTime(object):
@@ -12,8 +12,8 @@
def convert_time(self, time, result_format='number',
exclude_millis=False):
return Time(time).convert(result_format, millis=not exclude_millis)
- def convert_date(self, date, result_format='timestamp',
input_format=None):
- return Date(date, input_format).convert(result_format)
+ def convert_date(self, date, result_format='timestamp',
input_format=None, exclude_millis=False):
+ return Date(date, input_format).convert(result_format, millis=not
exclude_millis)
class Time(object):
@@ -68,29 +68,26 @@
class Date(object):
def __init__(self, dt, input_format):
- self.dt = self._convert_to_dt(dt, input_format)
+ self.seconds = self._convert_to_secs(dt, input_format)
- def _convert_to_dt(self, dt, input_format):
- if isinstance(dt, basestring):
- dt = self._string_to_datetime(dt, input_format)
- elif isinstance(dt, (int, long, float)):
- dt = self._dt_from_timestamp(dt)
- elif not isinstance(dt, datetime):
- raise ValueError("Unsupported input '%s'." % dt)
- return self._round_dt_to_millis(dt)
+ def _convert_to_secs(self, timestamp, input_format):
+ if isinstance(timestamp, basestring):
+ timestamp = self._string_to_epoch(timestamp, input_format)
+ elif isinstance(timestamp, datetime):
+ timestamp = self._mktime_with_millis(timestamp)
+ elif not isinstance(timestamp, (int, long, float)):
+ raise ValueError("Unsupported input '%s'." % timestamp)
+ return round(timestamp, 3)
- def _round_dt_to_millis(self, dt):
- return datetime(dt.year, dt.month, dt.day, dt.hour, dt.minute,
- dt.second, int(round(dt.microsecond, -3)))
-
- def _string_to_datetime(self, dt, input_format):
+ def _string_to_epoch(self, dt, input_format):
if not input_format:
dt = self._normalize_timestamp(dt)
input_format = '%Y-%m-%d %H:%M:%S.%f'
if '%f' in input_format and (sys.version_info < (2, 6) or
sys.platform == 'cli'):
return self._handle_un_supported_f_directive(dt, input_format)
- return datetime.strptime(dt, input_format)
+ else:
+ return self._mktime_with_millis(datetime.strptime(dt,
input_format))
def _normalize_timestamp(self, date):
ts = ''.join(d for d in date if d in string.digits).ljust(20, '0')
@@ -106,7 +103,7 @@
dt = dt[:-len(micro)]
epoch = time.mktime(time.strptime(dt, input_format))
epoch += float(micro) / 10**len(micro)
- return self._dt_from_timestamp(epoch)
+ return epoch
def _dt_from_timestamp(self, ts):
# Jython and IronPython handle floats incorrectly. For example,
@@ -115,20 +112,33 @@
return datetime(dt.year, dt.month, dt.day, dt.hour, dt.minute,
dt.second, int(round(ts % 1 * 10**6, -3)))
- def convert(self, format):
+ def _mktime_with_millis(self, dt):
+ return time.mktime(dt.timetuple()) + dt.microsecond / 10.0**6
+
+ def convert(self, format, millis=True):
+ if ':' in format:
+ format, output_format = format.split(':', 1)
+ return self._convert_to_timestamp(self.seconds, millis,
output_format)
try:
result_converter = getattr(self, '_convert_to_%s' %
format.lower())
except AttributeError:
raise ValueError("Unknown format '%s'." % format)
- return result_converter(self.dt)
-
- def _convert_to_timestamp(self, dt):
- if dt.microsecond:
- return str(dt)[:-3]
- return str(dt)
+ dt = self.seconds if millis else round(self.seconds)
+ return result_converter(dt, millis)
- def _convert_to_epoch(self, dt):
- return time.mktime(dt.timetuple())
+ def _convert_to_timestamp(self, dt, millis=True, output_format=None):
+ dtime = self._dt_from_timestamp(dt)
+ if output_format:
+ return datetime.strftime(dtime, output_format)
+ if dtime.microsecond and millis:
+ return str(dtime)[:-3]
+ elif millis:
+ return str(dtime) + '.000'
+ else:
+ return str(dtime)
- def _convert_to_datetime(self, dt):
+ def _convert_to_epoch(self, dt, millis=True):
return dt
+
+ def _convert_to_datetime(self, dt, millis=True):
+ return self._dt_from_timestamp(dt)
--
---
You received this message because you are subscribed to the Google Groups "robotframework-commit" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to robotframework-commit+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.