beetbox / beets

music library manager and MusicBrainz tagger
http://beets.io/
MIT License
12.57k stars 1.8k forks source link

Beet edit doesn't show custom tags #5317

Open AlexChalk opened 2 weeks ago

AlexChalk commented 2 weeks ago

Thanks for all your work on this project.

Problem

I have a plugin that writes a custom album_sort tag to sort albums by year:

class AlbumSortPlugin(BeetsPlugin):
    def __init__(self, *args, **kwargs):
        album_sort_field = mediafile.MediaField(
            mediafile.MP3StorageStyle(u"TSOA"),
            mediafile.MP4StorageStyle(u"soal"),
            mediafile.StorageStyle(u"Album Sort")
        )
        self.add_media_field("album_sort", album_sort_field)
        self.register_listener("write", self.write)
        super().__init__(*args, **kwargs)

    def write(self, item, path, tags):
        if tags['original_year'] == 0:
            tag_year = tags['year']
        else:
            tag_year = tags['original_year']

        if not tags.get("album_sort", None):
            tags["album_sort"] = f"{tag_year} {tags['album']}"

This successfully writes the custom tags to my mp3s—they show up in e.g. mp3tag. However, when I run beet edit against the imported files, even with -f album_sort, they are not displayed.

I took a look at the docs, and beet update seemed like it would fix this, however it raised the following exception:

Traceback (most recent call last):
  File "/home/me/.local/bin/beet", line 8, in <module>
    sys.exit(main())
             ^^^^^^
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/ui/__init__.py", line 1865, in main
    _raw_main(args)
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/ui/__init__.py", line 1852, in _raw_main
    subcommand.func(lib, suboptions, subargs)
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/ui/commands.py", line 1742, in update_func
    update_items(
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/ui/commands.py", line 1694, in update_items
    item.store(fields=item_fields)
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/library.py", line 395, in store
    super().store(fields)
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/dbcore/db.py", line 585, in store
    tx.mutate(query, subvars)
  File "/home/me/.local/share/pipx/venvs/beets/lib/python3.11/site-packages/beets/dbcore/db.py", line 962, in mutate
    cursor = self.db._connection().execute(statement, subvals)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
sqlite3.OperationalError: no such column: album_sort

This suggests the new tag was never written to musiclibrary.db.

n.b. beet info does show the field (perhaps because it's reading the metadata directly).

Possible Solutions

Ideally, musiclibrary.db would store tags added by plugin write methods. If that's not possible

Setup

I'm running linux, beet --version output:

beets version 2.0.0
Python version 3.11.9
plugins: albumsort, badfiles, bandcamp, convert, duplicates, edit, embedart, fetchart, ftintitle, info, inline, replaygain, scrub

Thanks!