My Projects

Guitar Pro

Status: πŸ§ͺ Experimental β€” reads and writes correctly but the API may change before 1.0.

I play electric guitar and bass, so tablature is part of my daily life. Guitar Pro is the de facto format β€” nearly every tab site and every transcriber uses it β€” but it is a complex binary format with multiple undocumented versions. Understanding it required cross-referencing TuxGuitar, PyGuitarPro, and AlphaTab. And because I prefer MuseScore for notation I also needed MusicXML support, the interchange format accepted by every non-guitar-specific tool.

So I built the library I wished existed.


guitarpro is a safe, high-performance Rust library for parsing and writing music score files. It covers the full Guitar Pro family and MusicXML, exposes a unified data model, and ships both a CLI and a local web viewer.

Format support

FormatReadWrite
GP3, GP4, GP5βœ… stableβœ… stable
GP6 (.gpx)πŸ§ͺ experimentalβ€”
GP7 (.gp) via GPIF XMLπŸ§ͺ experimentalβ€”
MusicXMLπŸ§ͺ experimentalplanned

Library features

Quick start

[dependencies]
guitarpro = "0.1"
use guitarpro::model::song::Song;
use guitarpro::model::track::SongTrackOps;

let data = std::fs::read("song.gp5")?;
let mut song = Song::default();
song.read_gp5(&data);
println!("{} β€” {} tracks", song.name, song.tracks.len());

CLI: score_tool

score_tool is a full-featured command-line tool for inspecting, converting, and analysing score files.

info β€” inspect a file

Prints metadata, a track table (name, type, tuning, instrument, MIDI channel), and a timeline of tempo/key/time-signature changes, repeat signs, and section markers.

score_tool info --input song.gp5
score_tool info --input song.gp5 --json   # machine-readable output

convert β€” change format

Converts between any supported format. Works on a single file or a whole directory.

score_tool convert --input song.gp5 --output song.xml
score_tool convert --input tabs/ --output xml_tabs/ --to xml   # batch
score_tool convert --input song.gp5 --output song.gp4 --dry-run

Supported formats: gp3, gp4, gp5, gpx, gp (GP7), xml (MusicXML), score (internal JSON).

extract β€” pull out tracks

Saves a subset of tracks into a new file. Select by name (substring) or by index.

# Keep only the "Guitar" track
score_tool extract --input song.gp5 --output guitar.gp5 --tracks guitar

# Keep tracks 0 and 2 (0-based)
score_tool extract --input song.gp5 --output duo.gp5 --track-index 0,2

# Remove the drum track, keep everything else
score_tool extract --input song.gp5 --output no-drums.gp5 --tracks drums --invert

duplicates β€” find duplicate files

Scans a directory for duplicate or near-duplicate score files using a fingerprint built from MIDI pitch histograms, metadata, and measure count. Cosine similarity is computed across all pairs; files above the threshold are grouped.

score_tool duplicates --dir ~/tabs/
score_tool duplicates --dir ~/tabs/ --recursive --threshold 0.9
score_tool duplicates --dir ~/tabs/ --delete-keep-first   # prompts before deleting
score_tool duplicates --dir ~/tabs/ --json

repeats β€” analyse repeat structure

Decodes all repeat signs (|:, :|Γ—N, volta brackets) and jump directions (D.S., D.C., al Coda…) and reports the sounding bar sequence. Also detects simile marks (%, %%) per track. Optionally writes a flattened file with all marks expanded to real content.

score_tool repeats --input song.gp5
score_tool repeats --input song.gp5 --json
score_tool repeats --input song.gp5 --expand --output song-flat.gp5
score_tool repeats --input song.gp5 --track "Guitar"  # simile analysis for one track

form β€” detect musical structure

Segments the score into sections and labels them by similarity (A, B, Aβ€², C…). Uses pitch-class fingerprints and cosine similarity; segments are seeded from section markers or repeat signs, with a fixed-window fallback.

score_tool form --input song.gp5
score_tool form --input song.gp5 --threshold 0.75 --variant-threshold 0.90
score_tool form --input song.gp5 --track "Rhythm Guitar" --json

fingering β€” suggest left-hand fingering

Computes a finger assignment (index / middle / ring / pinky, barre detection, position shifts) for every fretted note in tab tracks and prints it per measure. Assignments can be written back into an annotated .score JSON.

score_tool fingering --input song.gp5
score_tool fingering --input song.gp5 --track "Lead"
score_tool fingering --input song.gp5 --annotate song-fingered.score --json

Web server: score_server

Status: 🚧 Work in progress β€” core features work, playback and polish are incomplete.

A local score viewer that runs in any browser. No Electron, no installation beyond the binary. The Rust backend (axum) parses and analyses files; the frontend renders notation and tab using alphaTab.

score_server --port 3000 --open          # starts server and opens browser
score_server --port 3000 --open song.gp5 # opens a specific file on launch

What works:

Planned:

What’s coming in the library

Repo Β· crates.io Β· lib.rs