Skip to content

fix: replace deprecated datetime.utcfromtimestamp#70

Merged
shcheklein merged 2 commits into
fsspec:mainfrom
mixilchenko:fix/deprecated-utcfromtimestamp
Jul 24, 2026
Merged

fix: replace deprecated datetime.utcfromtimestamp#70
shcheklein merged 2 commits into
fsspec:mainfrom
mixilchenko:fix/deprecated-utcfromtimestamp

Conversation

@mixilchenko

@mixilchenko mixilchenko commented Jul 9, 2026

Copy link
Copy Markdown
Contributor

datetime.utcfromtimestamp() is deprecated since Python 3.12 and slated for removal. SSHFileSystem._decode_attributes() used it to decode SFTP atime/mtime, so every info()/ls(detail=True)/modified() call emits a DeprecationWarning on modern Python and will break outright once the function is removed.

This PR replaces it with datetime.fromtimestamp(ts, tz=timezone.utc).

Behavior changes (⚠️ for downstream consumers):

  • info()["time"], info()["mtime"] and modified() now return timezone-aware UTC datetimes instead of naive ones. The instant represented is identical; only tzinfo changed. This aligns sshfs with fsspec's own LocalFileSystem and sftp implementations. Code that compares these values against naive datetimes will now raise TypeError and should switch to aware datetimes (e.g. datetime.now(timezone.utc)).
  • atime/mtime missing from the server response now yield None instead of raising TypeError (SFTPAttrs fields are optional).

Tests:

  • info() timestamps are asserted to be tz-aware UTC, locking in the new contract.
  • _decode_attributes() with SFTPAttrs(atime=None, mtime=None) returns None for both fields.

datetime.utcfromtimestamp is deprecated and slated for removal. Route
both timestamps through a _naive_utc helper that uses
datetime.fromtimestamp(ts, timezone.utc) and strips tzinfo, preserving
the existing naive-UTC values returned in info dicts.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Pull request overview

Updates timestamp handling in SSHFileSystem to avoid the deprecated datetime.utcfromtimestamp() while preserving the existing behavior of returning naive UTC datetime objects in info() dictionaries.

Changes:

  • Import timezone and introduce a private _naive_utc() helper that converts POSIX timestamps via datetime.fromtimestamp(..., timezone.utc) and strips tzinfo.
  • Route SFTP attribute atime/mtime decoding through _naive_utc() to maintain prior naive-UTC outputs.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread sshfs/spec.py Outdated

@shcheklein shcheklein left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Thanks for the PR!

  • We need tests for this
  • Let's review and do a change that is aligned with fsspec.implementations.sftp and LocalFileSystem. I think they do tz-aware UTC datetimes fromtimestamp(ts, tz=timezone.utc
  • Helper probably should disappear
  • Pre-existing: SFTPAttrs.atime/mtime are Optional - worth fixing it here (don't try to convert - just return None)

@mixilchenko
mixilchenko requested a review from shcheklein July 24, 2026 08:36
@shcheklein

Copy link
Copy Markdown
Collaborator

@mixilchenko thanks! could you please update the PR description?

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Pull request overview

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

Comments suppressed due to low confidence (1)

sshfs/spec.py:158

  • The PR description says the goal is to preserve the existing naive UTC semantics of datetime.utcfromtimestamp(...) by stripping tzinfo, but the new implementation returns tz-aware datetimes (tz=timezone.utc). That’s a behavior/API change for info()/ls(detail=True) and may break callers which expect naive UTC datetimes.

Consider routing both timestamps through a small helper which returns naive-UTC (i.e., fromtimestamp(..., tz=UTC) then replace(tzinfo=None)), matching the PR’s stated intent while also handling None safely.

            "time": (
                datetime.fromtimestamp(attributes.atime, tz=timezone.utc)
                if attributes.atime is not None
                else None
            ),

Comment thread tests/test_sshfs.py
@shcheklein shcheklein closed this Jul 24, 2026
@shcheklein shcheklein reopened this Jul 24, 2026
@codecov-commenter

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 93.41%. Comparing base (15aac74) to head (cfa621b).
⚠️ Report is 9 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff             @@
##             main      #70      +/-   ##
==========================================
- Coverage   94.30%   93.41%   -0.89%     
==========================================
  Files          13       12       -1     
  Lines         738      775      +37     
==========================================
+ Hits          696      724      +28     
- Misses         42       51       +9     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@shcheklein
shcheklein merged commit 01cdf6f into fsspec:main Jul 24, 2026
14 checks passed
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.

4 participants