Library / SDK
drivendataorg/cloudpathlib avatar
drivendataorg/cloudpathlib

cloudpathlib gives cloud storage the pathlib interface you already know

Python pathlib-style classes for cloud storage services such as Amazon S3, Azure Blob Storage, and Google Cloud Storage.

630 stars88 forksPythonMIT

At a glance

What is it?
cloudpathlib provides classes that mimic pathlib.Path for S3, Google Cloud Storage and Azure Blob URIs, so a file path that points at a bucket behaves like a file path, with writes, globbing and unlinking included. It also keeps a local cache, and it is deliberately thin, which is both its strength and the limit of what it can do.
Who is it for?
Adopt cloudpathlib when your code already thinks in terms of paths and you want that same code to work against object storage without rewriting it into SDK calls. Do not adopt it when you need cloud specific operations that the Path interface does not model, and do not adopt it if you cannot accept the cloud SDKs as dependencies.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository received new commits within the last day.
What is it written in?
Mainly Python, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 23, 2026, and from our analysis. They are not legal advice.

Editorial analysis

A Path that points at a bucket

The library is a set of classes that mimic `pathlib.Path`'s interface for URIs from different cloud storage services, and the promise is in the README's own words: it aims to be the meringue of file management libraries, the subtle sweetness of `pathlib` working in harmony with the ethereal lightness of the cloud.

The mechanism is dispatch on the URI scheme. You construct one `CloudPath` and it returns the right subclass:

python
with CloudPath("s3://bucket/filename.txt").open("w+") as f:
    f.write("Send my changes to the cloud!")

That single line is the whole pitch. A file opened in write mode on a URI uploads what you write, with no separate upload call and no file management step in the developer code. The README lists reading as something that just works, and says that using the `write_text`, `write_bytes` or `.open('w')` methods will all upload your changes to cloud storage without any additional file management as a developer.

The supported clouds are AWS S3, Google Cloud Storage and Azure Blob Storage, with FTP described as on the way. The supported methods table in the README also lists an `HttpsPath` column alongside `AzureBlobPath`, `GSPath` and `S3Path`, so plain HTTP paths are part of the same family.

The licence is MIT, the documentation site is cloudpathlib.drivendata.org, and the project comes from DrivenData.

Extras decide what you can actually use

The installation instructions are where the design of the package becomes clear, because cloudpathlib does not bundle the cloud SDKs. It depends on them, for example boto3, google-cloud-storage and azure-storage-blob, to communicate with their respective storage service, and if you try to use cloud paths for a cloud service for which you do not have the dependencies installed, cloudpathlib will error and tell you what you need to install.

So the SDKs are optional extras:

bash
pip install cloudpathlib[s3,gs,azure]

With some shells you may need quotes:

bash
pip install "cloudpathlib[s3,gs,azure]"

The currently supported services are `azure`, `gs` and `s3`, and there is also an `all` extra that installs all available services' dependencies. And here is the sentence to remember: if you do not specify any extras or separately install any cloud SDKs, you will only be able to develop with the base classes for rolling your own cloud path class.

The same split exists on conda, where the suffix goes into the package name:

bash
conda install cloudpathlib-s3 -c conda-forge

with the same consequence, that without a suffix only the base classes are usable. A development version is also installable straight from GitHub, again needing the extras spelled out:

bash
pip install https://github.com/drivendataorg/cloudpathlib.git#egg=cloudpathlib[all]

That is a defensible arrangement. The base classes are small and dependency free, so a project that only needs one cloud does not carry the SDKs of the other two.

The API is pathlib, and the quick usage shows the whole surface

The quick usage example in the README is a tour of the interface, and it reads like ordinary pathlib code:

python
from cloudpathlib import CloudPath

# dispatches to S3Path based on prefix
root_dir = CloudPath("s3://drivendata-public-assets/")
root_dir
#: S3Path('s3://drivendata-public-assets/')

# there's only one file, but globbing works in nested folder
for f in root_dir.glob('**/*.txt'):
    text_data = f.read_text()
    print(f)
    print(text_data)

The pattern is to construct a root, glob it, read the matched objects, and then join a new name onto the root with the division operator:

python
# use / to join paths (and, in this case, create a new file)
new_file_copy = root_dir / "nested_dir/copy_file.txt"
new_file_copy
#: S3Path('s3://drivendata-public-assets/nested_dir/copy_file.txt')

# show things work and the file does not exist yet
new_file_copy.exists()
#: False

# writing text data to the new file in the cloud
new_file_copy.write_text(text_data)
#: 6933

and then `unlink()` to remove it again, after which the glob no longer lists it.

Two details are worth pausing on. The object returned by the constructor is a different type per scheme, so `S3Path` appears in the output, which means the same calling code can be pointed at S3, GCS or Azure without branching on the cloud. And `exists()` returning False for a path you just constructed is the local cache answering, not a network round trip, which is the caching behaviour showing through in the example.

Caching is local, and you control the folder

The caching behaviour is listed as a feature and it deserves a paragraph of its own, because it is the part that changes what your program actually does.

The README describes caching as files being downloaded locally only when necessary, and adds that you can easily pass a persistent cache folder so that across processes and sessions you only re-download what is necessary.

So the model is a local mirror that is populated on demand, with an optional location that survives between runs. That is a sensible default for code that reads a few objects from a bucket in a pipeline, and it has consequences you should decide about rather than inherit. A persistent cache means disk usage that grows with the objects you read, and a cache folder shared between processes means two processes can see each other's copies.

The other side of the same feature is that reads are not always a network call. Once an object is cached, a `read_text` is a local file read, which is why the `exists()` call in the example can answer without touching S3.

The README describes most methods and properties from `pathlib.Path` as supported, except for the ones that do not make sense in a cloud context, and says there are a few additional methods or properties that relate to specific cloud services or specifically for cloud paths. The support table in the README has a column for each of `AzureBlobPath`, `GSPath`, `HttpsPath` and `S3Path`, with rows such as `absolute`, `anchor`, `as_uri`, `drive`, `exists`, `glob` and `is_absolute` marked as supported across them.

Two small classes is the price of a new cloud

The extensibility story is the most reusable idea in the library, and it is deliberately unglamorous.

The base classes do most of the work generically, so implementing two small classes, `MyPath` and `MyClient`, is all you need to add support for a new cloud storage service. The split between them is the interesting part, because a `Path` and a `Client` in this design are different kinds of object: one is the path with its operations, the other is the handle on the remote service that the path delegates to.

That is what makes the second feature, testability, possible. The README lists local filesystem implementations that can be used to easily mock cloud storage in your unit tests. A test suite that would otherwise need a real bucket and network access can point the client at a local directory instead, and the path code under test does not change.

Together, the two features answer the objection that usually sinks a facade library. A `Path` interface over a remote service is convenient until the remote service does something the interface does not model, and then you are stuck with a wrapper that hides the operations you actually need. The answer here is that the base classes do the generic work and you can subclass or bypass them for the parts that are specific, and the tests can run against a local implementation of the same interface.

The testability point is also why the library can claim a large test suite and code coverage, with a tests workflow badge and a codecov badge in the README header.

Packaging details that decide whether it fits your build

The project file is short and tells you what you are pulling in. The build backend is `flit_core` at 3.2 or newer, the project name is `cloudpathlib`, the version is 0.26.0, and `requires-python` is `>=3.10`. The only unconditional runtime dependency is `typing-extensions` for Python versions below 3.11.

The optional dependency groups are the same four as the pip extras: `azure` for azure-storage-blob and azure-storage-file-datalake at version 12 or newer, `gs` for google-cloud-storage, `s3` for boto3 at 1.34.0 or newer, and `all` for the three of them.

The tooling configuration is also visible. Black is configured with a line length of 99 and target versions from py310 through py315, and mypy is set with `allow_redefinition` and `ignore_missing_imports`. The Makefile has the usual targets, `clean`, `dist` which runs `python -m build`, `docs-setup` which regenerates the documentation pages from README.md and HISTORY.md, and separate help, test and live test targets, with a `test-live-cloud-rig` target for running against real buckets.

The `.env.example` shows what the live tests expect, and it is a good list of the credential shapes you will meet: standard AWS access key variables, an Azure storage connection string plus a separate Gen2 one for ADLS testing, Google application credentials or a project id and service account key, and a set of custom S3 variables for a service such as MinIO, with a custom endpoint and bucket. The bucket variables are named after the live test suite, so the example file doubles as a description of how the project tests itself against real clouds.

Editorial conclusion

Adopt cloudpathlib when your code already thinks in terms of paths and you want that same code to work against object storage without rewriting it into SDK calls. Do not adopt it when you need cloud specific operations that the Path interface does not model, and do not adopt it if you cannot accept the cloud SDKs as dependencies. Verify first that the extra you need is installed, since without it you only get the base classes, that the cache folder you configure is on storage big enough for the objects you read, and that the version you pin is the one you tested, with v0.26.0 from 2026-10-02 the most recent tag and the last push on 2026-10-19.

Frequently asked questions

What is cloudpathlib?

It is a Python library with classes that mimic `pathlib.Path`'s interface for URIs from different cloud storage services. CloudPath dispatches on the scheme, so `s3://` gives you an S3Path, with AWS S3, Google Cloud Storage and Azure Blob Storage implemented and FTP described as on the way.

How do I install cloudpathlib for a specific cloud?

The cloud SDKs are optional extras, so you install them with pip's extras syntax, for example `pip install cloudpathlib[s3,gs,azure]`, or with quotes around it for some shells. Without any extras you only get the base classes for writing your own cloud path class, and on conda the equivalent is a suffixed package name such as `conda install cloudpathlib-s3 -c conda-forge`.

Does cloudpathlib cache downloaded files?

Yes. The README describes caching, where files are downloaded locally only when necessary, and you can pass a persistent cache folder so that across processes and sessions you only re-download what is necessary. It also provides local filesystem implementations that can be used to mock cloud storage in unit tests.

How do I add support for a cloud that is not built in?

The base classes do most of the work generically, so the README says implementing two small classes, MyPath and MyClient, is all you need to add support for a new cloud storage service.

Official sources

  1. drivendataorg/cloudpathlib on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/drivendataorg-cloudpathlib.svg)](https://hysenlabs.com/projects/drivendataorg-cloudpathlib)

Was this useful?