taglib-wasm 0.2.8 β 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +147 -107
- package/build/taglib.js +1 -1
- package/build/taglib.wasm +0 -0
- package/index.ts +4 -0
- package/package.json +7 -9
- package/src/mod.ts +14 -3
- package/src/simple.ts +5 -6
- package/src/taglib.ts +29 -1
- package/src/wasm-workers.ts +9 -1
- package/src/wasm.ts +30 -0
- package/src/workers.ts +50 -29
- package/src/simple-jsr.ts +0 -204
- package/src/taglib-jsr.ts +0 -48
- package/src/wasm-jsr.ts +0 -13
package/README.md
CHANGED
|
@@ -26,7 +26,7 @@ Because thereβs nothing like it. [`mp3tag.js`](https://mp3tag.js.org/) is matu
|
|
|
26
26
|
### Deno
|
|
27
27
|
|
|
28
28
|
```typescript
|
|
29
|
-
import { TagLib } from "
|
|
29
|
+
import { TagLib } from "npm:taglib-wasm";
|
|
30
30
|
```
|
|
31
31
|
|
|
32
32
|
### Node.js
|
|
@@ -78,13 +78,13 @@ console.log(`Duration: ${props.length}s, Bitrate: ${props.bitrate} kbps`);
|
|
|
78
78
|
Full control when you need it:
|
|
79
79
|
|
|
80
80
|
```typescript
|
|
81
|
-
import { TagLib } from "
|
|
81
|
+
import { TagLib } from "taglib-wasm";
|
|
82
82
|
|
|
83
83
|
// Initialize taglib-wasm
|
|
84
84
|
const taglib = await TagLib.initialize();
|
|
85
85
|
|
|
86
86
|
// Load audio file from buffer
|
|
87
|
-
const audioData = await
|
|
87
|
+
const audioData = await readFile("song.mp3"); // Node.js/Bun: fs.readFile, Deno: Deno.readFile
|
|
88
88
|
const file = taglib.openFile(audioData);
|
|
89
89
|
|
|
90
90
|
// Read metadata
|
|
@@ -97,16 +97,15 @@ console.log(`Duration: ${props.length}s`);
|
|
|
97
97
|
console.log(`Bitrate: ${props.bitrate} kbps`);
|
|
98
98
|
|
|
99
99
|
// Write metadata
|
|
100
|
-
file.
|
|
101
|
-
|
|
102
|
-
|
|
100
|
+
const tag = file.tag();
|
|
101
|
+
tag.setTitle("New Title");
|
|
102
|
+
tag.setArtist("New Artist");
|
|
103
|
+
tag.setAlbum("New Album");
|
|
103
104
|
|
|
104
|
-
|
|
105
|
+
// Save changes
|
|
106
|
+
file.save();
|
|
105
107
|
|
|
106
|
-
|
|
107
|
-
file.setAcoustidFingerprint("AQADtMmybfGO8NCNEESLnzHyXNOHeHnG...");
|
|
108
|
-
file.setAcoustidId("e7359e88-f1f7-41ed-b9f6-16e58e906997");
|
|
109
|
-
file.setMusicBrainzTrackId("f4d1b6b8-8c1e-4d9a-9f2a-1234567890ab");
|
|
108
|
+
console.log("Updated tags:", file.tag());
|
|
110
109
|
|
|
111
110
|
// Clean up
|
|
112
111
|
file.dispose();
|
|
@@ -137,16 +136,15 @@ console.log(`Duration: ${props.length}s`);
|
|
|
137
136
|
console.log(`Bitrate: ${props.bitrate} kbps`);
|
|
138
137
|
|
|
139
138
|
// Write metadata
|
|
140
|
-
file.
|
|
141
|
-
|
|
142
|
-
|
|
139
|
+
const tag = file.tag();
|
|
140
|
+
tag.setTitle("New Title");
|
|
141
|
+
tag.setArtist("New Artist");
|
|
142
|
+
tag.setAlbum("New Album");
|
|
143
143
|
|
|
144
|
-
|
|
144
|
+
// Save changes
|
|
145
|
+
file.save();
|
|
145
146
|
|
|
146
|
-
|
|
147
|
-
file.setAcoustidFingerprint("AQADtMmybfGO8NCNEESLnzHyXNOHeHnG...");
|
|
148
|
-
file.setAcoustidId("e7359e88-f1f7-41ed-b9f6-16e58e906997");
|
|
149
|
-
file.setMusicBrainzTrackId("f4d1b6b8-8c1e-4d9a-9f2a-1234567890ab");
|
|
147
|
+
console.log("Updated tags:", file.tag());
|
|
150
148
|
|
|
151
149
|
// Clean up
|
|
152
150
|
file.dispose();
|
|
@@ -174,16 +172,15 @@ console.log(`Duration: ${props.length}s`);
|
|
|
174
172
|
console.log(`Bitrate: ${props.bitrate} kbps`);
|
|
175
173
|
|
|
176
174
|
// Write metadata
|
|
177
|
-
file.
|
|
178
|
-
|
|
179
|
-
|
|
175
|
+
const tag = file.tag();
|
|
176
|
+
tag.setTitle("New Title");
|
|
177
|
+
tag.setArtist("New Artist");
|
|
178
|
+
tag.setAlbum("New Album");
|
|
180
179
|
|
|
181
|
-
|
|
180
|
+
// Save changes
|
|
181
|
+
file.save();
|
|
182
182
|
|
|
183
|
-
|
|
184
|
-
file.setAcoustidFingerprint("AQADtMmybfGO8NCNEESLnzHyXNOHeHnG...");
|
|
185
|
-
file.setAcoustidId("e7359e88-f1f7-41ed-b9f6-16e58e906997");
|
|
186
|
-
file.setMusicBrainzTrackId("f4d1b6b8-8c1e-4d9a-9f2a-1234567890ab");
|
|
183
|
+
console.log("Updated tags:", file.tag());
|
|
187
184
|
|
|
188
185
|
// Clean up
|
|
189
186
|
file.dispose();
|
|
@@ -213,16 +210,51 @@ console.log(`Duration: ${props.length}s`);
|
|
|
213
210
|
console.log(`Bitrate: ${props.bitrate} kbps`);
|
|
214
211
|
|
|
215
212
|
// Write metadata
|
|
216
|
-
file.
|
|
217
|
-
|
|
218
|
-
|
|
213
|
+
const tag = file.tag();
|
|
214
|
+
tag.setTitle("New Title");
|
|
215
|
+
tag.setArtist("New Artist");
|
|
216
|
+
tag.setAlbum("New Album");
|
|
217
|
+
|
|
218
|
+
// Save changes
|
|
219
|
+
file.save();
|
|
219
220
|
|
|
220
221
|
console.log("Updated tags:", file.tag());
|
|
221
222
|
|
|
222
|
-
//
|
|
223
|
-
file.
|
|
224
|
-
|
|
225
|
-
|
|
223
|
+
// Clean up
|
|
224
|
+
file.dispose();
|
|
225
|
+
```
|
|
226
|
+
|
|
227
|
+
### Deno
|
|
228
|
+
|
|
229
|
+
```typescript
|
|
230
|
+
import { TagLib } from "npm:taglib-wasm";
|
|
231
|
+
|
|
232
|
+
// Initialize taglib-wasm
|
|
233
|
+
const taglib = await TagLib.initialize();
|
|
234
|
+
|
|
235
|
+
// Load audio file from filesystem
|
|
236
|
+
const audioData = await Deno.readFile("song.mp3");
|
|
237
|
+
const file = taglib.openFile(audioData);
|
|
238
|
+
|
|
239
|
+
// Read metadata
|
|
240
|
+
const tags = file.tag();
|
|
241
|
+
const props = file.audioProperties();
|
|
242
|
+
|
|
243
|
+
console.log(`Title: ${tags.title}`);
|
|
244
|
+
console.log(`Artist: ${tags.artist}`);
|
|
245
|
+
console.log(`Duration: ${props.length}s`);
|
|
246
|
+
console.log(`Bitrate: ${props.bitrate} kbps`);
|
|
247
|
+
|
|
248
|
+
// Write metadata
|
|
249
|
+
const tag = file.tag();
|
|
250
|
+
tag.setTitle("New Title");
|
|
251
|
+
tag.setArtist("New Artist");
|
|
252
|
+
tag.setAlbum("New Album");
|
|
253
|
+
|
|
254
|
+
// Save changes
|
|
255
|
+
file.save();
|
|
256
|
+
|
|
257
|
+
console.log("Updated tags:", file.tag());
|
|
226
258
|
|
|
227
259
|
// Clean up
|
|
228
260
|
file.dispose();
|
|
@@ -293,63 +325,62 @@ export default {
|
|
|
293
325
|
- β
**.wav** β INFO chunk metadata
|
|
294
326
|
- β
**Legacy formats**: Opus, APE, MPC, WavPack, TrueAudio, and more
|
|
295
327
|
|
|
296
|
-
## π―
|
|
328
|
+
## π― Extended Metadata with PropertyMap
|
|
297
329
|
|
|
298
|
-
`taglib-wasm`
|
|
330
|
+
`taglib-wasm` provides a **PropertyMap API** for accessing extended metadata beyond the basic tags. This allows you to read and write format-specific fields and custom metadata.
|
|
299
331
|
|
|
300
332
|
### AcoustID example
|
|
301
333
|
|
|
302
334
|
```typescript
|
|
303
|
-
//
|
|
304
|
-
file.
|
|
305
|
-
file.
|
|
306
|
-
|
|
307
|
-
//
|
|
308
|
-
//
|
|
309
|
-
//
|
|
310
|
-
// β’ MP4: ----:com.apple.iTunes:Acoustid... freeform atoms
|
|
335
|
+
// Using PropertyMap API to set extended metadata
|
|
336
|
+
file.setProperty("ACOUSTID_FINGERPRINT", "AQADtMmybfGO8NCNEESLnzHyXNOHeHnG...");
|
|
337
|
+
file.setProperty("ACOUSTID_ID", "e7359e88-f1f7-41ed-b9f6-16e58e906997");
|
|
338
|
+
|
|
339
|
+
// Note: Property keys may vary by format
|
|
340
|
+
// Use file.properties() to see all available properties
|
|
341
|
+
file.save(); // Don't forget to save!
|
|
311
342
|
```
|
|
312
343
|
|
|
313
344
|
### MusicBrainz example
|
|
314
345
|
|
|
315
346
|
```typescript
|
|
316
|
-
//
|
|
317
|
-
file.
|
|
318
|
-
file.
|
|
319
|
-
file.
|
|
347
|
+
// MusicBrainz metadata using PropertyMap
|
|
348
|
+
file.setProperty("MUSICBRAINZ_TRACKID", "f4d1b6b8-8c1e-4d9a-9f2a-1234567890ab");
|
|
349
|
+
file.setProperty("MUSICBRAINZ_ALBUMID", "a1b2c3d4-e5f6-7890-abcd-ef1234567890");
|
|
350
|
+
file.setProperty("MUSICBRAINZ_ARTISTID", "12345678-90ab-cdef-1234-567890abcdef");
|
|
320
351
|
```
|
|
321
352
|
|
|
322
353
|
### Volume example
|
|
323
354
|
|
|
324
355
|
```typescript
|
|
325
|
-
// ReplayGain
|
|
326
|
-
file.
|
|
327
|
-
file.
|
|
328
|
-
file.
|
|
329
|
-
file.
|
|
330
|
-
|
|
331
|
-
// Apple Sound Check support
|
|
332
|
-
file.setAppleSoundCheck("00000150 00000150 00000150 00000150...");
|
|
356
|
+
// ReplayGain volume normalization
|
|
357
|
+
file.setProperty("REPLAYGAIN_TRACK_GAIN", "-6.54 dB");
|
|
358
|
+
file.setProperty("REPLAYGAIN_TRACK_PEAK", "0.987654");
|
|
359
|
+
file.setProperty("REPLAYGAIN_ALBUM_GAIN", "-8.12 dB");
|
|
360
|
+
file.setProperty("REPLAYGAIN_ALBUM_PEAK", "0.995432");
|
|
333
361
|
```
|
|
334
362
|
|
|
335
363
|
### Extended fields
|
|
336
364
|
|
|
337
365
|
```typescript
|
|
338
|
-
//
|
|
339
|
-
file.
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
366
|
+
// Using PropertyMap to set multiple properties at once
|
|
367
|
+
const properties = file.properties(); // Get current properties
|
|
368
|
+
|
|
369
|
+
// Set extended metadata
|
|
370
|
+
file.setProperties({
|
|
371
|
+
ALBUMARTIST: ["Various Artists"],
|
|
372
|
+
COMPOSER: ["Composer Name"],
|
|
373
|
+
BPM: ["120"],
|
|
374
|
+
COMPILATION: ["1"],
|
|
375
|
+
DISCNUMBER: ["1"],
|
|
376
|
+
TRACKTOTAL: ["12"],
|
|
377
|
+
// Note: Property keys vary by format
|
|
349
378
|
});
|
|
350
|
-
```
|
|
351
379
|
|
|
352
|
-
|
|
380
|
+
// Or set individual properties
|
|
381
|
+
file.setProperty("ALBUMARTIST", "Various Artists");
|
|
382
|
+
file.setProperty("COMPOSER", "Composer Name");
|
|
383
|
+
```
|
|
353
384
|
|
|
354
385
|
## ποΈ Development
|
|
355
386
|
|
|
@@ -384,8 +415,7 @@ build/
|
|
|
384
415
|
βββ taglib.js # Generated Emscripten JavaScript
|
|
385
416
|
βββ taglib.wasm # Compiled WebAssembly module
|
|
386
417
|
|
|
387
|
-
tests/ # Test
|
|
388
|
-
tests/ # Test suite
|
|
418
|
+
tests/ # Test suite and sample audio files
|
|
389
419
|
examples/ # Usage examples for different runtimes
|
|
390
420
|
βββ deno/ # Deno-specific examples
|
|
391
421
|
βββ bun/ # Bun-specific examples
|
|
@@ -449,53 +479,63 @@ class TagLib {
|
|
|
449
479
|
class AudioFile {
|
|
450
480
|
// Validation
|
|
451
481
|
isValid(): boolean;
|
|
452
|
-
|
|
482
|
+
getFormat(): string;
|
|
453
483
|
|
|
454
484
|
// Properties
|
|
455
485
|
audioProperties(): AudioProperties;
|
|
456
|
-
tag(): TagData;
|
|
457
486
|
|
|
458
|
-
// Tag
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
487
|
+
// Tag Access (returns Tag object with getters and setters)
|
|
488
|
+
tag(): Tag;
|
|
489
|
+
|
|
490
|
+
// PropertyMap API for extended metadata
|
|
491
|
+
properties(): PropertyMap;
|
|
492
|
+
setProperties(properties: PropertyMap): void;
|
|
493
|
+
getProperty(key: string): string | undefined;
|
|
494
|
+
setProperty(key: string, value: string): void;
|
|
495
|
+
|
|
496
|
+
// MP4-specific methods
|
|
497
|
+
isMP4(): boolean;
|
|
498
|
+
getMP4Item(key: string): string | undefined;
|
|
499
|
+
setMP4Item(key: string, value: string): void;
|
|
500
|
+
removeMP4Item(key: string): void;
|
|
466
501
|
|
|
467
502
|
// File Operations
|
|
468
503
|
save(): boolean;
|
|
504
|
+
getFileBuffer(): Uint8Array;
|
|
469
505
|
dispose(): void;
|
|
506
|
+
}
|
|
507
|
+
```
|
|
470
508
|
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
//
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
setReplayGainAlbumPeak(peak: string): void;
|
|
493
|
-
getReplayGainAlbumPeak(): string | undefined;
|
|
494
|
-
setAppleSoundCheck(iTunNORM: string): void;
|
|
495
|
-
getAppleSoundCheck(): string | undefined;
|
|
509
|
+
### Tag interface
|
|
510
|
+
|
|
511
|
+
```typescript
|
|
512
|
+
interface Tag {
|
|
513
|
+
// Basic metadata (getters)
|
|
514
|
+
title: string;
|
|
515
|
+
artist: string;
|
|
516
|
+
album: string;
|
|
517
|
+
comment: string;
|
|
518
|
+
genre: string;
|
|
519
|
+
year: number;
|
|
520
|
+
track: number;
|
|
521
|
+
|
|
522
|
+
// Setters
|
|
523
|
+
setTitle(value: string): void;
|
|
524
|
+
setArtist(value: string): void;
|
|
525
|
+
setAlbum(value: string): void;
|
|
526
|
+
setComment(value: string): void;
|
|
527
|
+
setGenre(value: string): void;
|
|
528
|
+
setYear(value: number): void;
|
|
529
|
+
setTrack(value: number): void;
|
|
496
530
|
}
|
|
497
531
|
```
|
|
498
532
|
|
|
533
|
+
### PropertyMap type
|
|
534
|
+
|
|
535
|
+
```typescript
|
|
536
|
+
type PropertyMap = { [key: string]: string[] };
|
|
537
|
+
```
|
|
538
|
+
|
|
499
539
|
## ποΈ Configuration
|
|
500
540
|
|
|
501
541
|
```typescript
|
|
@@ -514,7 +554,7 @@ interface TagLibConfig {
|
|
|
514
554
|
|
|
515
555
|
| Runtime | Status | Installation | Performance | TypeScript |
|
|
516
556
|
| ----------- | ------- | --------------------------------- | ----------- | ---------- |
|
|
517
|
-
| **Deno** | β
Full | `
|
|
557
|
+
| **Deno** | β
Full | `npm:taglib-wasm` | Excellent | Native |
|
|
518
558
|
| **Bun** | β
Full | `bun add taglib-wasm` | Excellent | Native |
|
|
519
559
|
| **Node.js** | β
Full | `npm install taglib-wasm` | Good | Via loader |
|
|
520
560
|
| **Browser** | β
Full | CDN/bundler | Good | Via build |
|