diff --git a/beetsplug/substitute.py b/beetsplug/substitute.py new file mode 100644 index 000000000..120e62dfc --- /dev/null +++ b/beetsplug/substitute.py @@ -0,0 +1,54 @@ +# This file is part of beets. +# Copyright 2023, Daniele Ferone. +# +# Permission is hereby granted, free of charge, to any person obtaining +# a copy of this software and associated documentation files (the +# "Software"), to deal in the Software without restriction, including +# without limitation the rights to use, copy, modify, merge, publish, +# distribute, sublicense, and/or sell copies of the Software, and to +# permit persons to whom the Software is furnished to do so, subject to +# the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. + +"""The substitute plugin module. + +Uses user-specified substitution rules to canonicalize names for path formats. +""" + +import re +from beets.plugins import BeetsPlugin + + +class Substitute(BeetsPlugin): + """The substitute plugin class. + + Create a template field function that subsitute the given field with the + given substitution rules. ``rules`` must be a list of (pattern, + replacement) pairs. + """ + def tmpl_substitute(self, text): + """Do the actual replacing.""" + if text: + for pattern, replacement in self.substitute_rules: + if pattern.match(text.lower()): + return replacement + return text + else: + return u'' + + def __init__(self): + """Initialize the substitute plugin. + + Get the configuration, register template function and create list of + substitute rules. + """ + super(Substitute, self).__init__() + self.substitute_rules = [] + self.template_funcs['substitute'] = self.tmpl_substitute + + for key, view in self.config.items(): + value = view.as_str() + pattern = re.compile(key.lower()) + self.substitute_rules.append((pattern, value)) diff --git a/docs/changelog.rst b/docs/changelog.rst index 0aacbf03a..4ceeb1874 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -115,6 +115,10 @@ New features: * :doc:`/plugins/embyupdate`: Add handling for private users by adding ``userid`` config option. :bug:`4402` +* :doc:`/plugins/substitute`: Add the new plugin `substitute` as an alternative + to the `rewrite` plugin. The main difference between them being that + `rewrite` modifies files' metadata and `substitute` does not. + :bug:`2786` Bug fixes: diff --git a/docs/plugins/index.rst b/docs/plugins/index.rst index 96b0eb7a8..21e99e3dc 100644 --- a/docs/plugins/index.rst +++ b/docs/plugins/index.rst @@ -122,6 +122,7 @@ following to your configuration:: spotify subsonicplaylist subsonicupdate + substitute the thumbnails types @@ -240,6 +241,11 @@ Path Formats :doc:`rewrite ` Substitute values in path formats. +:doc:`substitute ` + As an alternative to :doc:`rewrite `, use this plugin. The main + difference between them is that this plugin never modifies the files + metadata. + :doc:`the ` Move patterns in path formats (i.e., move "a" and "the" to the end). diff --git a/docs/plugins/rewrite.rst b/docs/plugins/rewrite.rst index 3706d940a..41cd454bf 100644 --- a/docs/plugins/rewrite.rst +++ b/docs/plugins/rewrite.rst @@ -30,5 +30,9 @@ As a convenience, the plugin applies patterns for the ``artist`` field to the ``albumartist`` field as well. (Otherwise, you would probably want to duplicate every rule for ``artist`` and ``albumartist``.) -Note that this plugin only applies to templating; it does not modify files' -metadata tags or the values tracked by beets' library database. +A word of warning: This plugin theoretically only applies to templates and path +formats; it initially does not modify files' metadata tags or the values +tracked by beets' library database, but since it *rewrites all field lookups*, +it modifies the file's metadata anyway. See comments in issue :bug:`2786`. + +As an alternative to this plugin the :doc:`/plugins/substitute` could be used. diff --git a/docs/plugins/substitute.rst b/docs/plugins/substitute.rst new file mode 100644 index 000000000..14f3cb025 --- /dev/null +++ b/docs/plugins/substitute.rst @@ -0,0 +1,23 @@ +Substitute Plugin +================= + +The ``substitute`` plugin lets you easily substitute values in your templates and +path formats. Specifically, it is intended to let you *canonicalize* names +such as artists: For example, perhaps you want albums from The Jimi Hendrix +Experience to be sorted into the same folder as solo Hendrix albums. + +This plugin is intented as a replacement for the ``rewrite`` plugin. While +the ``rewrite`` plugin modifies the metadata, this plugin does not. + +Enable the ``substitute`` plugin (see :ref:`using-plugins`), then make a ``substitute:`` section in your config file to contain your rules. +Each rule consists of a case-insensitive regular expression pattern, and a +replacement value. For example, you might use: + + substitute: + .*jimi hendrix.*: Jimi Hendrix + + +To apply the substitution, you have to call the function ``%substitute{}`` in the paths section. For example: + + paths: + default: %substitute{$albumartist}/$year - $album%aunique{}/$track - $title \ No newline at end of file