node-taglib-sharp icon indicating copy to clipboard operation
node-taglib-sharp copied to clipboard

Error setting tags for m4a files

Open Anogh297 opened this issue 1 year ago • 26 comments

I'm trying to set tags to a m4a file but I keep getting Argument null: ${name} was not provided. It occurs when calling myFile.save()

import { File } from "node-taglib-sharp";
const myFile = File.createFromPath(`${process.cwd()}\\ong_bong_chong.m4a`);

myFile.tag.title = "Ong Bong Chong";
myFile.tag.performers = ["Firoze Jong"];

myFile.save();
myFile.dispose();

this is the error I get

Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\utils.js:53
            throw new Error(`Argument null: ${name} was not provided`);
                  ^

Error: Argument null: text was not provided
    at Guards.notNullOrUndefined (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\utils.js:53:19)
    at ByteVector.fromString (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\byteVector.js:382:24)
    at get data [as data] (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\mpeg4\boxes\isoHandlerBox.js:62:173)
    at Mpeg4BoxRenderer.renderBox (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\mpeg4\mpeg4BoxRenderer.js:33:22)
    at Mpeg4BoxRenderer.renderBox (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\mpeg4\mpeg4BoxRenderer.js:29:45)
    at Mpeg4BoxRenderer.renderBox (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\mpeg4\mpeg4BoxRenderer.js:29:45)
    at Mpeg4File.save (Z:\Development\taglib\node_modules\.pnpm\[email protected]\node_modules\node-taglib-sharp\dist\mpeg4\mpeg4File.js:79:56)
    at file:///Z:/Development/taglib/index.ts:5:8
    at ModuleJob.run (node:internal/modules/esm/module_job:217:25)
    at async ModuleLoader.import (node:internal/modules/esm/loader:316:24)

Node.js v20.9.0

The file is a download from yt-dlp and does not have any tags. ong_bong_chong.zip

Anogh297 avatar Mar 08 '24 09:03 Anogh297

hot fix: https://github.com/subframe7536/node-taglib-sharp-memory/commit/04188810e92de0fdbf77243e058f8b9309654273

subframe7536 avatar Mar 08 '24 13:03 subframe7536

Thank you for your reply. Installing your version of it throws another error. Would appreciate if you could tell me what I would need to do to fix this

import taglib from "node-taglib-sharp-extend";
const { File } = taglib;
Error [ERR_PACKAGE_PATH_NOT_EXPORTED]: No "exports" main defined in Z:\Development\taglib\node_modules\node-taglib-sharp-extend\package.json imported from Z:\Development\taglib\index.js      
    at new NodeError (node:internal/errors:406:5)
    at exportsNotFound (node:internal/modules/esm/resolve:268:10)
    at packageExportsResolve (node:internal/modules/esm/resolve:542:13)
    at packageResolve (node:internal/modules/esm/resolve:772:14)
    at moduleResolve (node:internal/modules/esm/resolve:838:20)
    at defaultResolve (node:internal/modules/esm/resolve:1043:11)
    at ModuleLoader.defaultResolve (node:internal/modules/esm/loader:383:12)
    at ModuleLoader.resolve (node:internal/modules/esm/loader:352:25)
    at ModuleLoader.getModuleJob (node:internal/modules/esm/loader:228:38)
    at ModuleWrap.<anonymous> (node:internal/modules/esm/module_job:85:39) {
  code: 'ERR_PACKAGE_PATH_NOT_EXPORTED'
}

Node.js v20.9.0```

Anogh297 avatar Mar 08 '24 17:03 Anogh297

Please try

import { File } from "node-taglib-sharp-extend";

subframe7536 avatar Mar 08 '24 17:03 subframe7536

Same error.

Anogh297 avatar Mar 08 '24 19:03 Anogh297

Fixed in v0.2.7

subframe7536 avatar Mar 09 '24 06:03 subframe7536

Z:\Development\taglib>node index   
node:internal/errors:497
    ErrorCaptureStackTrace(err);
    ^

Error [ERR_MODULE_NOT_FOUND]: Cannot find module 'Z:\Development\taglib\node_modules\.pnpm\[email protected][email protected]\node_modules\node-taglib-sharp-extend\dist\taglib\byteVector' imported from Z:\Development\taglib\node_modules\.pnpm\[email protected][email protected]\node_modules\node-taglib-sharp-extend\dist\taglib\index.js
    at new NodeError (node:internal/errors:406:5)
    at finalizeResolution (node:internal/modules/esm/resolve:233:11)
    at moduleResolve (node:internal/modules/esm/resolve:845:10)
    at defaultResolve (node:internal/modules/esm/resolve:1043:11)
    at ModuleLoader.defaultResolve (node:internal/modules/esm/loader:383:12)
    at ModuleLoader.resolve (node:internal/modules/esm/loader:352:25)
    at ModuleLoader.getModuleJob (node:internal/modules/esm/loader:228:38)
    at ModuleWrap.<anonymous> (node:internal/modules/esm/module_job:85:39)
    at link (node:internal/modules/esm/module_job:84:36) {
  url: 'file:///Z:/Development/taglib/node_modules/.pnpm/[email protected][email protected]/node_modules/node-taglib-sharp-extend/dist/taglib/byteVector',
  code: 'ERR_MODULE_NOT_FOUND'
}

Node.js v20.9.0

Anogh297 avatar Mar 09 '24 17:03 Anogh297

Sorry, this package only support modern bundlers.

You can try esno

edit: after some works, everything should be OK in v0.2.8

subframe7536 avatar Mar 10 '24 01:03 subframe7536

Thank you, it works as expected. However typescript still throws this error Property 'File' does not exist on type 'typeof import("Z:/Development/taglib/node_modules/.pnpm/[email protected][email protected]/node_modules/node-taglib-sharp-extend/dist/index", { with: { "resolution-mode": "import" } })'.

import * as taglib from "node-taglib-sharp-extend";
const { File } = taglib; 

Anogh297 avatar Mar 10 '24 07:03 Anogh297

Sorry I have no idea with that. The type resolution have no error according to this site

subframe7536 avatar Mar 10 '24 08:03 subframe7536

I see. Perhaps typescript is not emitting the declaration files properly? The index.d.ts file is just export * from 'node-taglib-sharp-memory/src';

image

Anogh297 avatar Mar 10 '24 08:03 Anogh297

I found that you are right, I used the function under utils when processing files myself, and did not find the default import error. And the above inspection website also found no errors, so it was published. I think I need to export types a different way.

subframe7536 avatar Mar 10 '24 08:03 subframe7536

finally... v0.2.9

subframe7536 avatar Mar 10 '24 11:03 subframe7536

Thanks a lot! It's working fine and the intellisense works too:D Sorry to be a bother but I had a last question, when trying to add the tags the file gets corrupted. I don't think it's the library's fault but rather yt-dlp where I am getting my file from. Since the library works fine and I am only getting this issue with recently downloaded files. Can you suggest me a way of fixing it?

// myFile.corruptionReasons
[
  'Box header specified a size of 805306368 bytes but only 3478550 bytes left in the file'
]

Anogh297 avatar Mar 10 '24 14:03 Anogh297

sure, please provide a minimal reproduction and source audio file

subframe7536 avatar Mar 10 '24 14:03 subframe7536

yt-dlp executable yt-dlp https://www.youtube.com/watch?v=2SUwOgmvzK4 -f m4a

audio.zip

Anogh297 avatar Mar 10 '24 14:03 Anogh297

This seems to be an existing issue in C# implemention: https://github.com/mono/taglib-sharp/issues/306

@benrr101 @digimezzo any idea?

subframe7536 avatar Mar 12 '24 02:03 subframe7536

Sorry I haven't been able to look at this project in quite a while. I'm wrapping up another project and hope to continue with this one relatively soon-ish :tm:

benrr101 avatar Apr 04 '24 22:04 benrr101

Sorry I haven't been able to look at this project in quite a while. I'm wrapping up another project and hope to continue with this one relatively soon-ish ™️

I did some testing earlier on, got diverted somewhere else but back now on my music project. I've been setting up various tables and pages for metadata editing but wanted to ask if you feel, in particular the unified approach is stable ? I'm not doing video at this point and even my supported codecs are limited to mp3, flac, m4a, and ape.

stuartambient avatar Apr 08 '24 01:04 stuartambient

@stuartambient I think the idea of taglib (sharp or otherwise) was always to provide a unified abstraction but also provide interfaces for interacting with specific tagging formats in an advanced manner. The unified abstraction is the most documented in the wiki for this project, and I think for a lot of users this enough. Using the advanced interfaces requires some working knowledge of the tagging formats, otherwise metadata can get messed up. I mean to write more documentation on how it all works, but it'll take me time I don't have at the moment 😓

What are your thoughts?

benrr101 avatar Apr 25 '24 18:04 benrr101

I'm settled in my current strategy to use the unified approach. I have no idea what I might need more advanced methods for at this point but if things change I'll learn. My current dilemma is that in my app, I've been using Borewit/Music-metadata, maybe you're familiar with it. It's node based and only reads and parses metadata. It presents different groups of metadata, 'format', 'common', 'trackInfo' and 'native'. I mostly pull from common and format.

There are some fields from music-metadata and node-taglib-sharp that conflict in data structure, i.e. artist (string) vs performers (array). I'm considering do I write some code that after taglib writes, music-metadata can parse or do I use taglib for both. Node-taglib-sharp seems like it could easily replace my use of the aforementioned but I know little about standards and am concerned about other music software being able to read the metadata, like VLC, Foobar, Musicbee, etc.

I realize that I'll need to do testing on my own.

tldr - are the metadata data structures used in node-taglib-sharp compatible with other music players / managers. Is there a standard that all or most music software shares about metadata ?

stuartambient avatar May 01 '24 15:05 stuartambient

Ah, I see what you're saying. To answer your ultimate question, yes the tags that node-taglib-sharp stores are compatible with your favorite music software. I test things I'm unsure about against foobar2000 and vlc to make sure they behave as expected. For your specific example of artist/performers, most (if not all, I can't remember fully right now) are stored as a single tag with a delimitor between values in the array. If only only need one artist, you're always welcome to read/write a single value array, or interact with it using the First* properties.

To get more into the weeds, it does depend a lot on the tagging format that is used. For example, ASF has a single field for artist that's baked into the format. While FLAC is basically a fancy list of key/value pairs, so it's possible to store multiple key/value pairs with the same key (eg, split an array of artists over multiple pairs). Although there is precedent for the most popular tagging fields, ultimately, the tagging formats are open-ended enough that you can store tags however you want. Eg, iTunes is notorious for inventing its own fields or using tags in uncommon ways. This is why the advanced mechanisms exist - even if we can cover all "most common behavior" with configuration, having an escape hatch to do things manually is beneficial to some users.

Also, here's a wiki page I found recently for where Foobar2000 pulls its tags from. https://wiki.hydrogenaud.io/?title=Tag_Mapping

benrr101 avatar May 01 '24 16:05 benrr101

@benrr101 thank you for the reply and explanation. Very helpful and the itunes example gives me a better perspective.

stuartambient avatar May 01 '24 19:05 stuartambient

@stuartambient I made a new package music-metadata-wasm recently, which use lofty-rs and build by wasm-pack, can also read / write the tag. Would you like to have a try?

subframe7536 avatar May 01 '24 23:05 subframe7536

@subframe7536 maybe at some point. Is it fork from Borewit ?

stuartambient avatar May 02 '24 23:05 stuartambient

@stuartambient Noop, a brand new one. At lease the m4a file tag could be correctly written. Maybe have better performance

subframe7536 avatar May 03 '24 02:05 subframe7536

@stuartambient Noop, a brand new one. At lease the m4a file tag could be correctly written. Maybe have better performance

I'm not supporting m4a right now. The player uses html audio and doesn't always handle m4a well. I'll have to look at it in the future. Seems like a popular format.

stuartambient avatar May 06 '24 12:05 stuartambient