Transfer photos from your Mac to an Android phone — straight out of the
macOS Photos library, one album at a time.
No cloud, no account, no subscription. Your library is opened read-only and
nothing is ever deleted or overwritten.
Moving photos from a Mac to an Android phone is genuinely annoying. Google removed Android File Transfer from android.com in early 2024 and no longer maintains it; iCloud doesn't talk to Android; and re-uploading 17 GB through the cloud just to pull it down again is absurd when both devices are on the same desk with a cable between them.
The manual route works but is tedious: select the album in Photos, File → Export → Export Unmodified Originals, wait, find the folder, open a file transfer app, drag it across, then check nothing was missed.
photos2android collapses that into one step. It reads the Photos library
directly, resolves an album to its original files, pushes them over adb, and
then verifies every file landed. One album, one click.
| photos2android | OpenMTP | Google Photos | AirDroid | |
|---|---|---|---|---|
| Understands Photos albums | Yes | No | No | No |
| Needs a manual export first | No | Yes | Yes | Yes |
| Works offline / no account | Yes | Yes | No | No |
| Verifies the copy afterwards | Yes | No | No | No |
| General file browsing | No | Yes | No | Yes |
OpenMTP is an excellent MTP file
browser and the tool to reach for when you want to move arbitrary files. It
just doesn't know what a Photos album is — .photoslibrary is a sealed bundle
with a SQLite index inside, so albums aren't folders you can browse. This tool
handles that part.
git clone https://github.com/sridevsoft/photos2android.git
cd photos2android
./portalThat's it — no pip install, no virtualenv. Python 3 standard library only.
You need adb:
brew install --cask android-platform-toolsAnd on the phone: Settings → About phone → tap Build number 7 times, then Developer options → USB debugging, and tap Allow when you plug it in. The app walks you through this if it can't see your phone.
Web portal — ./portal opens http://localhost:8790
Album list with real cover thumbnails pulled from your library, live phone status with storage, a summary of exactly what will be copied, then a progress bar and a verification table.
Command line
./a2p # interactive picker
./a2p --list # list albums, exit
./a2p -a "Summer 2026" --dry-run # show what would happen
./a2p -a "Summer 2026" # do it
./a2p -a "Summer 2026" --dest /sdcard/DCIM/TripThis tool moves irreplaceable photos, so the guarantees are structural rather than best-effort:
| Guarantee | How it's enforced |
|---|---|
| Your Photos library is never modified | SQLite opened with ?mode=ro — writes are impossible, not merely avoided |
| Nothing on the phone is ever deleted | there is no delete call anywhere in the codebase |
| No file is ever overwritten | same-name files are skipped, or renamed with --rename-clashes |
| Interrupting is safe | already-copied files are skipped, so re-running resumes |
| Verified, not assumed | after copying it re-lists the phone and checks every file landed and that the files that were already there are all still present |
Photos keeps its index in Photos.sqlite inside the library bundle and the
untouched originals in originals/<hex>/<UUID>.<ext>. The album→asset join
table is renumbered between Photos versions, so the schema is discovered at
runtime rather than hardcoded. Thumbnails come from the library's own JPEG
derivatives, so nothing has to be decoded or generated.
Files are pushed in batches of 50 to amortise per-call adb overhead; if a
batch fails it retries file by file to isolate the culprit rather than failing
the whole run.
- iCloud-only photos have no local file. The tool counts them, warns, and skips them. Download the originals in Photos first to include them.
- iPhone albums are mostly HEIC/MOV. Android 10+ reads both natively.
.movand.mp4are the same underlying container, so Android indexes MOV files asvideo/mp4and treats them as ordinary videos. - Copied photos won't appear at the top of Google Photos. It sorts by capture date, so an album of May photos lands among your May photos. Use Library → Photos on device → Camera to see them by folder.
- Filenames stay as the library's UUIDs. Gallery sorting uses EXIF, so dates remain correct.
-a, --album album title (partial match ok) or its pk
-l, --list list albums and exit
--library path to a .photoslibrary bundle
--dest folder on phone (default /sdcard/DCIM/Camera)
--serial adb serial, if several devices attached
--adb path to the adb binary
--dry-run show what would happen, copy nothing
--rename-clashes copy same-named files as name_1.ext instead of skipping
-y, --yes skip the confirmation prompt
Environment: A2P_PORT (default 8790), A2P_LIBRARY (library path override).
The server binds to 127.0.0.1 only.
Connect the phone by USB with USB debugging enabled, then use a tool that speaks
MTP or adb. This one goes further and pulls the photos straight out of the
Photos app, so you skip the export step entirely.
Yes. That is exactly what this does — pick the album, and its original files are copied to the phone's camera folder.
Google removed it from android.com in early 2024 and no longer maintains it. It still runs from direct links, but it breaks on current macOS versions.
Only for photos whose originals are downloaded to the Mac. iCloud-only photos have no local file — the tool counts them, warns you, and skips them. Turn on Download Originals to this Mac in Photos settings first if you need them.
No. The Photos library is opened read-only at the SQLite level, and there is no delete call anywhere in the codebase. Same-named files on the phone are skipped rather than overwritten.
Yes, and Android 10+ reads both natively. No conversion happens.
No. Python 3 standard library only — no packages, no virtualenv.
Issues and PRs welcome. The one hard rule: no code path may delete or overwrite user data. Any PR that adds one will be declined regardless of how useful the feature is.
- Author: Sriharish Sathya
- License: MIT — see LICENSE
- System Requirements: macOS with the Photos app, Python 3.8 or higher,
adb(Android Platform Tools). No third-party Python packages — standard library only. - Repo URL: https://github.com/sridevsoft/photos2android
- Contacts: sriharishsathya@gmail.com
- LinkedIn: https://www.linkedin.com/in/sriharishs/