Show HN: TagLib-WASM, a TypeScript-first music tagging library

4 hours ago 2

Tests npm version npm downloads  MIT
TypeScript Built with Emscripten Built with TagLib
Deno Node.js Bun Cloudflare Workers Electron Browsers

TagLib-Wasm is the universal tagging library for TypeScript/JavaScript (TS|JS) platforms: Deno, Node.js, Bun, Cloudflare Workers, Electron, and browsers.

This project exists because the TS|JS ecosystem had no battle-tested audio tagging library that supports reading and writing music metadata to all popular audio formats. It aspires to be a universal solution for all TS|JS*-capable platforms — Deno, Node.js, Bun, Electron, Cloudflare Workers, and browsers.

TagLib-Wasm stands on the shoulders of giants, including TagLib itself, Emscripten, and Wasm (WebAssembly). TagLib itself is legendary and a core dependency of many music apps.

  • ✅ Full audio format support – Supports all audio formats supported by TagLib
  • ✅ TypeScript first – Complete type definitions and modern API
  • ✅ Wide TS/JS runtime support – Deno, Node.js, Bun, Electron, Cloudflare Workers, and browsers
  • ✅ Format abstraction – Handles container format details automagically when possible
  • ✅ Zero dependencies – Self-contained Wasm bundle
  • ✅ Production ready – Growing test suite helps ensure safety and reliability
  • ✅ Two API styles – Use the “Simple” API (3 functions), or the full “Core” API for more advanced applications
import { TagLib } from "npm:taglib-wasm";

Requirements: Node.js v22.6.0 or higher

Using with TypeScript (.ts files)

Two options for TypeScript:

  1. Node's experimental TypeScript support
# Node.js 22.6.0+ with experimental flag node --experimental-strip-types your-script.ts # Future versions may not need the flag
  1. TypeScript loader (recommended)
npm install --save-dev tsx npx tsx your-script.ts

Using with JavaScript (.js files)

// Use the pre-compiled JavaScript version import { TagLib } from "taglib-wasm"; import { applyTags, readTags } from "taglib-wasm/simple"; // Everything works the same as TypeScript const taglib = await TagLib.initialize(); const tags = await readTags("song.mp3");

Note: See our full documentation for details on Node.js experimental TypeScript support.

Works in both main and renderer processes:

// Main process import { TagLib } from "taglib-wasm"; // Renderer process (with nodeIntegration: true) const { TagLib } = require("taglib-wasm");
import { applyTags, readTags, updateTags } from "taglib-wasm/simple"; // Read tags - just one function call! const tags = await readTags("song.mp3"); console.log(tags.title, tags.artist, tags.album); // Apply tags and get modified buffer (in-memory) const modifiedBuffer = await applyTags("song.mp3", { title: "New Title", artist: "New Artist", album: "New Album", }); // Or update tags on disk (requires file path) await updateTags("song.mp3", { title: "New Title", artist: "New Artist", });
import { TagLib } from "taglib-wasm"; // Initialize taglib-wasm const taglib = await TagLib.initialize(); // Load audio file const file = await taglib.open("song.mp3"); // Read and update metadata const tag = file.tag(); tag.setTitle("New Title"); tag.setArtist("New Artist"); // Save changes file.save(); // Clean up file.dispose();
import { getCoverArt, setCoverArt } from "taglib-wasm/simple"; // Extract cover art const coverData = await getCoverArt("song.mp3"); if (coverData) { await Deno.writeFile("cover.jpg", coverData); } // Set new cover art const imageData = await Deno.readFile("new-cover.jpg"); const modifiedBuffer = await setCoverArt("song.mp3", imageData, "image/jpeg"); // Save modifiedBuffer to file if needed

📖 View Full Documentation

tag-wasm is designed to support all formats supported by TagLib:

  • .mp3 – ID3v2 and ID3v1 tags
  • .m4a/.mp4 – MPEG-4/AAC metadata for AAC and Apple Lossless audio
  • .flac – Vorbis comments and audio properties
  • .ogg – Ogg Vorbis format with full metadata support
  • .wav – INFO chunk metadata
  • Additional formats – Opus, APE, MPC, WavPack, TrueAudio, AIFF, WMA, and more

Extended Metadata Support

Beyond basic tags, taglib-wasm supports extended metadata:

import { Tags } from "taglib-wasm"; // AcoustID fingerprints file.setProperty( Tags.AcoustidFingerprint, "AQADtMmybfGO8NCNEESLnzHyXNOHeHnG...", ); // MusicBrainz IDs file.setProperty( Tags.MusicBrainzTrackId, "f4d1b6b8-8c1e-4d9a-9f2a-1234567890ab", ); // ReplayGain volume normalization file.setProperty(Tags.TrackGain, "-6.54 dB"); file.setProperty(Tags.TrackPeak, "0.987654");

View all supported tag constants →

# Prerequisites: Emscripten SDK # Install via: https://emscripten.org/docs/getting_started/downloads.html # Clone and build git clone https://github.com/CharlesWiltgen/taglib-wasm.git cd taglib-wasm # Build Wasm module npm run build:wasm # Run tests npm test

View full development guide →

taglib-wasm works across all major JavaScript runtimes:

Runtime Status Installation Notes
Deno ✅ Full npm:taglib-wasm Native TypeScript
Node.js ✅ Full npm install taglib-wasm TypeScript via tsx
Bun ✅ Full bun add taglib-wasm Native TypeScript
Browser ✅ Full Via bundler Full API support
Cloudflare Workers ✅ Full taglib-wasm/workers Memory-optimized build
Electron ✅ Full npm install taglib-wasm Main & renderer processes
  • Memory Usage – Entire file must be loaded into memory (may be an issue for very large files)
  • Concurrent Access – Not thread-safe (JavaScript single-threaded nature mitigates this)
  • Cloudflare Workers – Limited to 128MB memory per request; files larger than ~100MB may fail

Contributions are welcome! Please read our Contributing Guide for details on our code of conduct and the process for submitting pull requests.

This project uses dual licensing:

  • TypeScript/JavaScript code – MIT License (see LICENSE)
  • WebAssembly binary (taglib.wasm) – LGPL-2.1-or-later (inherited from TagLib)

The TagLib library is dual-licensed under LGPL/MPL. When compiled to WebAssembly, the resulting binary must comply with LGPL requirements. This means:

  • You can use taglib-wasm in commercial projects
  • If you modify the TagLib C++ code, you must share those changes
  • You must provide a way for users to relink with a modified TagLib

For details, see lib/taglib/COPYING.LGPL

  • TagLib – Excellent audio metadata library
  • Emscripten – WebAssembly compilation toolchain
Read Entire Article