How to Merge or De-duplicate Multiple M3U Playlists

Short answer: M3U is plain text, so merging two playlists means combining the track lines under a single #EXTM3U header. De-duplicating means removing lines that point to the same track, which is harder than it sounds because the same song can appear under two different paths. Here's how to do both properly.


Why merging M3U files gets messy

An M3U file is nothing more than a header and a list of paths, one track per line, with an optional #EXTINF line above each one giving the duration and a label. That simplicity is exactly why merging goes wrong. Two playlists built at different times, on different machines, or by different tools rarely agree on how they reference the same file.

The usual culprits:

Relative vs absolute paths. One playlist might reference Artist/Album/track.mp3 relative to its own location, while another uses a full path like /home/user/Music/Artist/Album/track.mp3. Both can point at the same file and look nothing alike as text.

Different root folders. If playlist A was built from ~/Music and playlist B from ~/Music/NewStuff, their relative paths won't line up even for identical files, since each is relative to a different starting point.

Case and separator differences. Track.mp3 vs track.MP3, or backslashes vs forward slashes if one playlist came from Windows. Same file, different string.

Tag drift. If the label in #EXTINF comes from file tags, and one copy of the file has been retagged since the other playlist was built, the labels won't match even though the audio is identical.

This is why you can't just do a naive line-by-line duplicate check most of the time. You need to resolve what each line actually points to before you can tell what's a duplicate.

Merging by hand

If you just want to combine playlists and worry about duplicates later, this part is quick:

  1. Open each M3U file in a text editor.
  2. Keep a single #EXTM3U header at the very top of the merged file, and delete any other #EXTM3U lines you find further down.
  3. Paste the #EXTINF and path line pairs from each source file into one document, keeping each pair together.
  4. Save the result as a new .m3u file.

That gives you one file with everything in it. It does not give you a deduplicated file, and if the source playlists used relative paths against different root folders, some of the merged entries will point at nothing once you move the new file.

De-duplicating properly

To actually catch duplicates, you need to normalize the paths before comparing them:

  1. Resolve every path to an absolute path. Take each relative path and combine it with the folder the playlist file lives in, so you get one consistent, fully qualified location per track.
  2. Normalize case and separators. Lowercase everything and convert backslashes to forward slashes (or vice versa) so Track.mp3 and track.MP3 compare equal.
  3. Compare the normalized paths, not the original lines. Two lines that look different as text can now be recognized as the same file, and two lines that look similar can be revealed as different files in different folders.
  4. Keep the first occurrence and drop the rest, or write a small script to do this if you're comfortable with one. A short Python script using os.path.normpath and a set to track seen paths will handle this in a few lines for anyone used to scripting.
  5. Re-save with a single header, as in the manual merge above.

If your player supports embedded tags well, comparing on artist and title instead of file path can catch duplicates that are the same song encoded twice in different folders, which path comparison alone will miss. That's a different kind of duplicate and worth checking separately if your library has been re-ripped or re-downloaded over time.

The easier path: start from your library, not your old playlists

All of the above exists because you're trying to reconcile playlists built at different times against a library that has since moved, been retagged, or grown. There's a simpler way to sidestep it: instead of merging old exports, go back to your actual music library and build the combined playlist fresh.

This is where Emthree genuinely helps, since it scans your library directly in the browser rather than working from old playlist exports. You select the tracks you want from your current library, in whatever combination you need, and export a single clean M3U from that selection. Because you're picking real files that exist right now rather than reconciling stale references, there's no path drift to untangle and nothing to de-duplicate that wasn't duplicated in your source folder to begin with.

One thing worth knowing: Emthree writes paths as relative, and export is blocked if the tracks you've selected and the playlist don't share a common root folder. That's a deliberate guard, since relative paths only resolve correctly when everything travels together from a shared root. If you're combining tracks from folders that don't share a common parent, keep that in mind before you try to export.

Nothing you scan or select leaves your machine. Emthree runs in the browser, reads your library locally, and the free tier covers unlimited scanning and full-length export with no track cap, so rebuilding a playlist from scratch instead of merging old files costs you nothing but a folder pick and a few minutes of selecting tracks.