Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

BF: use time.time (no timezone offset) while checking expiration for AWS credentials #4927

Merged
merged 2 commits into from Sep 17, 2020

Conversation

yarikoptic
Copy link
Member

with time.localtime() we are getting local time without any time zone, calendar.timegm
then produces seconds since epoch for that in GMT thus again - no zone.
With time.time() we seems to be getting seconds since epoch properly.

I kept running into S3 downloads failing while credential reported to
be expiring in some hours to come

Copy link
Collaborator

@kyleam kyleam left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

with time.localtime() we are getting local time without any time zone, calendar.timegm
then produces seconds since epoch for that in GMT thus again - no zone.

Hmm, I don't think that's correct. There is a time zone there:

$ python -c 'import time; print(time.localtime().tm_zone)'
EDT

It's just that calendar.timegm expects the time tuple to be in GMT, according to its docstring and implementation:

def timegm(tuple):
    """Unrelated but handy function to calculate Unix timestamp from GMT."""
    year, month, day, hour, minute, second = tuple[:6]
    days = datetime.date(year, month, 1).toordinal() - _EPOCH_ORD + day - 1
    hours = days*24 + hour
    minutes = hours*60 + minute
    seconds = minutes*60 + second
    return seconds

But either way...

With time.time() we seems to be getting seconds since epoch properly.

... I think the switch to time.time is good.

@@ -212,7 +211,7 @@ def is_expired(self):
if not exp:
return True
exp_epoch = iso8601_to_epoch(exp)
expire_in = (exp_epoch - calendar.timegm(time.localtime())) / 3600.
expire_in = (exp_epoch - time.time()) / 3600.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you expect that the expiration field will be in something other than UTC? If so, iso8601_to_epoch suffers from the same issue and the calculation can still be off.

def iso8601_to_epoch(datestr):
    """Given ISO 8601 date/time format, return in seconds since epoch

    iso8601 is used to parse properly the time zone information, which
    can't be parsed with standard datetime strptime
    """
    return calendar.timegm(iso8601.parse_date(datestr).timetuple())

I'd say that should use utctimetuple:

diff --git a/datalad/support/network.py b/datalad/support/network.py
index bc9211f08..b291ebbfa 100644
--- a/datalad/support/network.py
+++ b/datalad/support/network.py
@@ -202,7 +202,7 @@ def iso8601_to_epoch(datestr):
     iso8601 is used to parse properly the time zone information, which
     can't be parsed with standard datetime strptime
     """
-    return calendar.timegm(iso8601.parse_date(datestr).timetuple())
+    return calendar.timegm(iso8601.parse_date(datestr).utctimetuple())


 def __urlopen_requests(url):
diff --git a/datalad/support/tests/test_network.py b/datalad/support/tests/test_network.py
index f585f3d8a..49237f44a 100644
--- a/datalad/support/tests/test_network.py
+++ b/datalad/support/tests/test_network.py
@@ -529,8 +529,8 @@ def test_is_ssh():
 def test_iso8601_to_epoch():
     epoch = 1467901515
     eq_(iso8601_to_epoch('2016-07-07T14:25:15+00:00'), epoch)
-    # zone information is actually not used
-    eq_(iso8601_to_epoch('2016-07-07T14:25:15+11:00'), epoch)
+    eq_(iso8601_to_epoch('2016-07-07T14:25:15+11:00'),
+        epoch - 11 * 60 * 60)
     eq_(iso8601_to_epoch('2016-07-07T14:25:15Z'), epoch)
     eq_(iso8601_to_epoch('2016-07-07T14:25:15'), epoch)

@yarikoptic
Copy link
Member Author

oh hoh -- thank you @kyleam for the detailed review! I will tune it up tomorrow following your recommendations -- indeed we should use zone information!

…AWS S3 credential

calendar.timegm expects the time tuple to be in GMT time tuple.
time.localtime() has time zone information but it is not part of the time tuple.

calendar.timegm then produced seconds since epoch for that in GMT thus
zone information was not used.

With time.time() we seems to be getting seconds since epoch properly.

I kept running into S3 downloads failing while credential reported to
be expiring in some hours to come
@yarikoptic
Copy link
Member Author

ok, forced pushed tuneup to initial commit message + your patch. thanks again @kyleam

Copy link
Collaborator

@kyleam kyleam left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the updates.

@codecov
Copy link

codecov bot commented Sep 17, 2020

Codecov Report

Merging #4927 into maint will decrease coverage by 0.01%.
The diff coverage is 66.66%.

Impacted file tree graph

@@            Coverage Diff             @@
##            maint    #4927      +/-   ##
==========================================
- Coverage   89.69%   89.67%   -0.02%     
==========================================
  Files         289      289              
  Lines       40477    40477              
==========================================
- Hits        36305    36297       -8     
- Misses       4172     4180       +8     
Impacted Files Coverage Δ
datalad/downloaders/credentials.py 81.76% <0.00%> (-0.12%) ⬇️
datalad/support/network.py 86.95% <100.00%> (ø)
datalad/support/tests/test_network.py 100.00% <100.00%> (ø)
datalad/downloaders/tests/test_http.py 89.92% <0.00%> (-1.23%) ⬇️
datalad/downloaders/http.py 84.55% <0.00%> (-0.39%) ⬇️
datalad/downloaders/base.py 78.57% <0.00%> (-0.36%) ⬇️
datalad/support/gitrepo.py 90.37% <0.00%> (-0.08%) ⬇️
datalad/customremotes/base.py 83.92% <0.00%> (+0.05%) ⬆️

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 213a169...3a85e9a. Read the comment docs.

@yarikoptic
Copy link
Member Author

look -- even containers is green now ;) merging!

@yarikoptic yarikoptic merged commit 0d27a8e into datalad:maint Sep 17, 2020
2 checks passed
@yarikoptic yarikoptic deleted the bf-s3-expire branch October 7, 2020 15:38
@yarikoptic yarikoptic added this to the 0.13.5 milestone Dec 12, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants