Migrate Joplin notebook exports to Obsidian vaults
Project description
Joplin to Obsidian Migration Tool ๐
A Python tool to convert Joplin notebook exports (markdown + front matter format) into a format suitable for Obsidian vaults. It reorganizes resources, cleans up file names, and removes Joplin-specific metadata.
Migration Workflow
- Export from Joplin: Create an export using the "Markdown + Front Matter" format
- Process with this tool: Run the migration tool against your Joplin export
- Import to Obsidian: Import the processed files into your Obsidian vault
โ ๏ธ Important Disclaimer
This tool modifies your files and directories! Always create a backup before running. The changes are irreversible. Use --dry-run to preview changes first.
What This Tool Does
| Step | Operation | Subcommand |
|---|---|---|
| 1 | Move resources from global _resources to local folders |
move-resources |
| 2 | Remove trailing underscores/spaces from files & folders | โ |
| 3 | Remove empty _resources directories |
cleanup-files |
| 4 | Remove location data (latitude, longitude, altitude) from YAML front matter | cleanup-location |
Installation
pip
pip install joplin-to-obsidian
uv
uv tool install joplin-to-obsidian
Docker
docker pull ghcr.io/hugobatista/joplin-to-obsidian:latest
Usage
Run all steps (with confirmation prompt)
joplin-to-obsidian run /path/to/export
Preview changes (dry run)
joplin-to-obsidian --dry-run run /path/to/export
Shows exactly what would happen without modifying any files:
Step 1: Moving resources to _resources folders
would copy 3 resource(s):
- WebClipper.png
would save 1 file(s):
- Welcome!/4. Tips.md
Step 2: Removing trailing underscores
Would rename: /path/export/note_.md -> /path/export/note.md
Step 4: Removing location data from YAML front matter
Would remove location data from 5 files in Welcome!/:
- 1. Welcome to Joplin!.md
- 2. Importing and exporting notes.md
- 3. Synchronising your notes.md
- 4. Tips.md
- 5. Joplin Privacy Policy.md
Run individual steps
joplin-to-obsidian move-resources /path/to/export
joplin-to-obsidian cleanup-files /path/to/export
joplin-to-obsidian cleanup-location /path/to/export
Each subcommand also supports --dry-run:
joplin-to-obsidian --dry-run move-resources /path/to/export
Show version
joplin-to-obsidian --version
Docker
# Run all steps
docker run -it --rm -v /path/to/export:/data ghcr.io/hugobatista/joplin-to-obsidian:latest run /data
# Build from source
docker build -t joplin-to-obsidian .
docker run -it --rm -v /path/to/export:/data joplin-to-obsidian run /data
Input Structure
your-export-folder/
โโโ _resources/
โ โโโ image1.png
โ โโโ document.pdf
โ โโโ attachment.jpg
โโโ Note 1.md
โโโ Note 2.md
โโโ Subfolder/
โ โโโ Note 3.md
โ โโโ Note 4.md
โโโ ...
Output Structure
your-export-folder/
โโโ Note 1.md
โโโ _resources/
โ โโโ image1.png
โโโ Note 2.md
โโโ _resources/
โ โโโ document.pdf
โโโ Subfolder/
โ โโโ Note 3.md
โ โโโ _resources/
โ โ โโโ attachment.jpg
โ โโโ Note 4.md
โโโ ...
Technical Details
- Language: Python 3.10+
- Dependencies: Typer (for CLI), otherwise standard library
- File Encoding: UTF-8
Troubleshooting
"Resource not found" errors
Markdown files may reference resources that don't exist in the _resources directory. The tool skips these and continues.
Permission errors
Ensure you have write permissions for the directory and all its contents.
File conflicts
If cleanup creates duplicate names, the tool automatically appends numbers to avoid conflicts.
Validation
After running, verify that:
- All markdown files still open correctly
- Images and attachments are still accessible
- No important data was lost
Contributing
See CONTRIBUTING.md for guidelines.
License
MIT โ see LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file joplin_to_obsidian-0.2.0.tar.gz.
File metadata
- Download URL: joplin_to_obsidian-0.2.0.tar.gz
- Upload date:
- Size: 83.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
45ee682a13adf7343fbf83024b2f208ed706b652a1ac3801859268cb6697cabf
|
|
| MD5 |
2cad32146b6c9bcd878f33dcdd30d3f4
|
|
| BLAKE2b-256 |
c6d972d65910e4ab33904005b6012f87a7f5a437db3eb52124b08620eb6a1cd8
|
Provenance
The following attestation bundles were made for joplin_to_obsidian-0.2.0.tar.gz:
Publisher:
pypi.yml on hugobatista/joplin-to-obsidian
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
joplin_to_obsidian-0.2.0.tar.gz -
Subject digest:
45ee682a13adf7343fbf83024b2f208ed706b652a1ac3801859268cb6697cabf - Sigstore transparency entry: 2100933402
- Sigstore integration time:
-
Permalink:
hugobatista/joplin-to-obsidian@285caa2331912499c963d5e7541c917c7548fdb8 -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/hugobatista
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi.yml@285caa2331912499c963d5e7541c917c7548fdb8 -
Trigger Event:
release
-
Statement type:
File details
Details for the file joplin_to_obsidian-0.2.0-py3-none-any.whl.
File metadata
- Download URL: joplin_to_obsidian-0.2.0-py3-none-any.whl
- Upload date:
- Size: 11.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
60dd1694c8194417f5f500b7ec30d36eb245fc22f3562f0f1dbd08402cc8cff4
|
|
| MD5 |
61749551ed4e20211953a794eb5783f0
|
|
| BLAKE2b-256 |
eec31a0ab0fa2ab2393bbebd4d416ebfe4968c3670f3bbcd60fc7267b3a4624a
|
Provenance
The following attestation bundles were made for joplin_to_obsidian-0.2.0-py3-none-any.whl:
Publisher:
pypi.yml on hugobatista/joplin-to-obsidian
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
joplin_to_obsidian-0.2.0-py3-none-any.whl -
Subject digest:
60dd1694c8194417f5f500b7ec30d36eb245fc22f3562f0f1dbd08402cc8cff4 - Sigstore transparency entry: 2100933721
- Sigstore integration time:
-
Permalink:
hugobatista/joplin-to-obsidian@285caa2331912499c963d5e7541c917c7548fdb8 -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/hugobatista
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
pypi.yml@285caa2331912499c963d5e7541c917c7548fdb8 -
Trigger Event:
release
-
Statement type: