Welcome, guest | Sign In | My Account | Store | Cart

Notice! PyPM is being replaced with the ActiveState Platform, which enhances PyPM’s build and deploy capabilities. Create your free Platform account to download ActivePython or customize Python with the packages you require and get automatic updates.

Download
ActivePython
INSTALL>
pypm install sact.epoch

How to install sact.epoch

  1. Download and install ActivePython
  2. Open Command Prompt
  3. Type pypm install sact.epoch
 Python 2.7Python 3.2Python 3.3
Windows (32-bit)
1.0.2 Failed View build log
1.0.0 Failed View build log
Windows (64-bit)
1.0.0
1.0.2 Failed View build log
1.0.0 Available View build log
Mac OS X (10.5+)
1.0.2 Available View build log
1.0.0 Available View build log
Linux (32-bit)
1.0.2 Available View build log
1.0.0 Available View build log
Linux (64-bit)
1.0.2 Available View build log
1.0.0 Available View build log
 
License
BSD License
Imports
Lastest release
version 1.0.2 on Jun 24th, 2011

This packages provides a time abstraction mecanism, allowing code that would use it as reference to be diverted both on the local time zone and the real time.

This allows clock-dependent code to be tested. See Getting started section for a more thorough explanation.

Additionnaly, as an abstraction of the legacy datetime object, Time object provided in sact.epoch.Time provides some common helpers and force this object to always provide a timezone.

sact.epoch objects will be of some help:

  • if your application manage 2+ different timezones (ie: UTC and local

System Message: WARNING/2 (<string>, line 17)

Bullet list ends without a blank line; unexpected unindent.

timezone), and you are tired of legacy "naive" datetime object on this matter.

  • if you want to be able to divert local Time, or TimeZone of your application

System Message: WARNING/2 (<string>, line 20)

Bullet list ends without a blank line; unexpected unindent.

for test purpose.

Contents

Time

subclass of datetime, represent an absolute instant of time (with timezone). It forces datetime usage to be aware of the timezone. Additionally, Time.now() will ask the Zope Component Architecture registry for a Clock Utility to provide the real time.

Clock

Clock objects are general reference for getting Time object. The default clock is our common normal clock, but ZCA allows to substiture the reference and provide other type of Clock as sact.epoch.ManageableClock which can be managed (this means it can be stopped, set, translated in the future or the past).

TimeZone

TimeZone objects represents a specific timezone, sact.epoch.TzLocal() will get the local system time zone. This call can be diverted also via the ZCA to provide another TimeZone. sact.epoch.testTimeZone is a common divert target timezone that is provided to help testing code.

Getting started

sact.epoch.Time is meant as a replacement of datetime.datetime. As a subclass of this later one, it'll provide the same functionality, and thus can be used almost anywhere you are using datetime.datetime.

Additionaly, using sact.epoch.Time ensures that:

  • all instances will get a time zone. Which isn't the case for datetime

System Message: WARNING/2 (<string>, line 59)

Bullet list ends without a blank line; unexpected unindent.

objects.

  • .now() method will use the Zope Component Architecture registry to get

System Message: WARNING/2 (<string>, line 62)

Bullet list ends without a blank line; unexpected unindent.

a common Utility that is in charge of giving the real time. This allows simple overriding mecanism.

Get timestamp from a datetime

Let's say you have some code using datetime.datetime.now():

>>> import datetime
>>> now = datetime.datetime.now()

First issue: if this variable is meant to represent a time stored as UTC in a database.

How do you get UTC timestamp from datetime ? (cf: http://bugs.python.org/issue1457227)

This is a common question. (cf: http://stackoverflow.com/questions/5067218/get-utc-timestamp-in-python-with-datetime/5499906#5499906)

The answer is datetime.datetime objects can be naive, which means unaware of the timezone. Thus, it is impossible to get UTC timestamp from this form of datetime unless you can guess the timezone yourself.

Hopefully, the timezone of your system didn't change between the datetime object creation and the moment you want to get a timestamp, if this is the case you can safely use:

>>> import sact.epoch.utils
>>> utc_timestamp = sact.epoch.utils.datetime_to_timestamp(now)

datetime_to_timestamp will ask your system for the number of seconds between EPOCH in the current timezone and the provided datetime. This is why you must ensure that datetime object was created when the same TimeZone on the system than when you run this function.

No doctest is given to your eyes on the content of the variable utc_timestamp because the output depends on the current time. And this can be often an issue you'll encounter: having complex code that depends on the current date, how do you test it ? This is the purpose of sact.epoch.Time.

Forcing to use only aware datetime

Quite quickly, you'll ask yourself: but what use have I of naive datetime.datetime objects if they can't be used in lots of cases ?

The answer is: there are no use of naive datetime.datetime.

Aware datetime objects as sact.epoch.Time contains all additional information allowing to:

  • get an UTC timestamp
  • compare two Time object whatever there timezone is.

Using naive datetime might even be concidered harmfull. sact.epoch.Time will ensure that all your objects are aware. By default, TimeZone won't even be dependent of your system local time, but will be stored in UTC timezone.

datetime objects:

>>> print repr(datetime.datetime.now().tzinfo)

System Message: ERROR/3 (<string>, line 125)

Inconsistent literal block quoting.

None >>> print repr(datetime.datetime(1970, 1, 1, 1, 1).tzinfo) None

In comparison, sact.epoch.Time object will always set a timezone:

>>> print repr(sact.epoch.Time.now().tzinfo)

System Message: ERROR/3 (<string>, line 132)

Inconsistent literal block quoting.

<TimeZone: UTC> >>> print repr(sact.epoch.Time(1970, 1, 1, 1, 1).tzinfo) <TimeZone: UTC>

Of course, as Time object is aware, a simple timestamp property is available:

>>> epoch = sact.epoch.Time(1970, 1, 1, 0, 0)
>>> epoch.timestamp

System Message: ERROR/3 (<string>, line 141)

Inconsistent literal block quoting.

0

Diverting time

If you use sact.epoch.Time.now() in place of datetime.datetime.now(), your code will have seams to divert real time reference without touching the system clock.

Say your code is:

>>> db_timestamp = epoch.timestamp
>>> def is_it_ok():

System Message: ERROR/3 (<string>, line 155)

Inconsistent literal block quoting.

... now = sact.epoch.Time.now().timestamp ... print 0 == ((now - db_timestamp) % 2)

is_it_ok function code should print True if number of seconds between now and epoch is odd.

This is the type of function which is quite difficult to test if you are using datetime.datetime.now(). Whole application will make extensive usage of the system clock, and will eventually be difficult to test unless you used sact.epoch.Time.now() in place of datetime.

Here's the test of the function:

>>> clock = sact.epoch.clock.ManageableClock()

By default, the clock is following the system clock. Let's stop it and set it to epoch (more on manageable clock in the docstring of the class ManageableClock):

>>> clock.stop()
>>> clock.ts = 0

Now let's use ZCA to declare this clock as new reference clock:

>>> from zope.component import globalSiteManager as gsm
>>> gsm.registerUtility(clock)

We are ready to test the function:

>>> sact.epoch.Time.now().timestamp

System Message: ERROR/3 (<string>, line 185)

Inconsistent literal block quoting.

0 >>> is_it_ok() True

>>> clock.ts = 1
>>> sact.epoch.Time.now().timestamp
1
>>> is_it_ok()
False

Please note that ManageableClock have a wait method:

>>> clock.wait(minutes=1)
>>> sact.epoch.Time.now().timestamp

System Message: ERROR/3 (<string>, line 199)

Inconsistent literal block quoting.

61 >>> is_it_ok() False

Of course, the execution of clock.wait is immediate. You can use a datetime.timedelta as argument of wait or any keyword args you would send to datetime.timedelta constructor (this includes days, seconds, microseconds, milliseconds, minutes, hours, weeks as of python version 2.7.1, cf: http://docs.python.org/library/datetime.html#datetime.timedelta)

Diverting timezone of system

When displaying times to the user, it is appreciated to show the time in local timezone:

>>> def what_time_is_it():

System Message: ERROR/3 (<string>, line 218)

Inconsistent literal block quoting.

... print sact.epoch.Time.now().iso_local

Notice the shortcut iso_local property which will be of some help.

This property uses sact.epoch.TzLocal() which is responsible of giving the system local timezone:

>>> sact.epoch.TzLocal()
<TimeZone: System>

Let use the ZCA to divert the TzLocal mechanism to get the system local:

>>> from sact.epoch import testTimeZone
>>> from sact.epoch.interfaces import ITimeZone
>>> gsm.registerUtility(testTimeZone, ITimeZone, name='local')

Now we can test our function:

>>> clock.ts = 0
>>> what_time_is_it()

System Message: ERROR/3 (<string>, line 239)

Inconsistent literal block quoting.

1970-01-01 00:05:00+00:05

The testTimeZone used is very special and recognizable on purpose: it has a constant +5 minute offset on UTC.

Internally, call to TzLocal() has been diverted:

>>> sact.epoch.TzLocal()

System Message: ERROR/3 (<string>, line 247)

Inconsistent literal block quoting.

<TimeZone: Test>

Changelog

1.0.2 (2011-06-23)

Changes
  • Update Buildout to 1.5.2. [Sébastien Douche]
  • Updated buildout part doc so our docs directory layout

System Message: WARNING/2 (<string>, line 262)

Bullet list ends without a blank line; unexpected unindent.

remains compatible with collective.sphinx.recipe 1.0.7. [Valentin Lab]

Fix
  • Some date and time methods failed on already instancied datetime.

System Message: WARNING/2 (<string>, line 269)

Bullet list ends without a blank line; unexpected unindent.

[Guillaume Savary]

Other
  • Pkg: dev: minor and fixup to autogen.sh script. [Valentin Lab]

1.0.1 (2011-04-08)

Changes
  • Some minor rephrasing in the documentation. [Valentin Lab]
Fix
  • Minor packaging fixups, filled the description field for PyPI,

System Message: WARNING/2 (<string>, line 288)

Bullet list ends without a blank line; unexpected unindent.

corrected the licence, and remove a utf-8 char in the doc that was crashing python setup.py commands. [Valentin Lab]

1.0.0 (2011-04-08)

New
  • New .aslocal and .strftime_local() shortcuts in Time

System Message: WARNING/2 (<string>, line 298)

Bullet list ends without a blank line; unexpected unindent.

object. [Valentin Lab]

Changes
  • Renamed INSTALL and README to <name>.rst for github.

System Message: WARNING/2 (<string>, line 304)

Bullet list ends without a blank line; unexpected unindent.

[Valentin Lab]

  • buildout.cfg and bootstrap.py is cleaned from local

System Message: WARNING/2 (<string>, line 307)

Bullet list ends without a blank line; unexpected unindent.

configuration. [Valentin Lab]

  • Prepare for autogen.sh pre-release script. [Valentin Lab]
  • Added a small doc on the Clock.wait() method. [Valentin Lab]
  • Moved all docs into docs/source, written a full overview, updated conf

System Message: WARNING/2 (<string>, line 314)

Bullet list ends without a blank line; unexpected unindent.

and changelog. [Valentin Lab]

  • Prepared setup.py for release on github and pypi. [Valentin Lab]
  • More doc, better doc. [Valentin Lab]
  • Added a default repr for System and Test TimeZone objects.

System Message: WARNING/2 (<string>, line 321)

Bullet list ends without a blank line; unexpected unindent.

[Valentin Lab]

  • Removed dependency towards sact.test. [Valentin Lab]

0.6.0 (2010-10-29)

Fix
  • Make tests about time more stable. [Jonathan Ballet]

This test was asserting that two consecutives calls of the ts property return different result, the first call being lower than the second call. But the value returned by ts is a floating point number expressed in seconds, and it seems that, sometimes, Python's so fast that the assertion fails. Using the test command with --repeat 1000, it seems that I have 2% runs which are failing with this test on my computer. The fix should be sufficient, since each doctest lines are reinterpreted by Doctest, and I guess it should have a sufficient cost so that it now passes at 100%.

0.5.0 (2010-09-17)

Fix
  • Round_date now rounds microseconds as well as seconds. [Pascal Varet]
  • Updated package repository URL. [Pascal Varet]

0.4.0 (2010-07-27)

  • Compute the version of the package using current date instead of the

System Message: WARNING/2 (<string>, line 357)

Bullet list ends without a blank line; unexpected unindent.

Mercurial revision. [Jonathan Ballet]

  • Package is now versioned with the current date instead of the current

System Message: WARNING/2 (<string>, line 360)

Bullet list ends without a blank line; unexpected unindent.

Mercurial revision. [Jonathan Ballet]

0.3.0 (2010-06-03)

  • Add a default manageable clock (for tests). [Guillaume (GS) Savary]
  • Change the Time object human representation. [Guillaume (GS) Savary]
  • Uniformisation of buildout.cfg. [Valentin Lab]

0.2.0 (2010-03-09)

  • Add method to show a local time without time zone. [Guillaume (GS)

System Message: WARNING/2 (<string>, line 375)

Bullet list ends without a blank line; unexpected unindent.

Savary]

0.1.0 (2010-02-11)

  • Api: __add__ and __sub__ method in Time(). [Guillaume (GS) Savary]
  • Add a timestamp property to the Time object. [Guillaume (GS) Savary]
  • Time object now inherits from datetime object. [Jonathan Ballet]
  • Some more static method to Time object for convenience. [Valentin Lab]
  • New function to help convertion towards UTC ts. [Valentin Lab]
  • New time/clock lib. [Valentin Lab]

Subscribe to package updates

Last updated Jun 24th, 2011

Download Stats

Last month:1

What does the lock icon mean?

Builds marked with a lock icon are only available via PyPM to users with a current ActivePython Business Edition subscription.

Need custom builds or support?

ActivePython Enterprise Edition guarantees priority access to technical support, indemnification, expert consulting and quality-assured language builds.

Plan on re-distributing ActivePython?

Get re-distribution rights and eliminate legal risks with ActivePython OEM Edition.