Repository: huggingface/transformers
Pull request: Fix MusicGen generation config

# What does this PR do?

Some audio models have their own `generate()` which doesn't call `prepare_generation_config`. We need to call `prepare_generation_config` to update values to prev defaults

Also, I added a small deprecation warning preparing us and users to passing either generation config of `kwargs`, only one. We will anyway have to support it for a long time, it is a common pattern among users

Changed files:
filename: src/transformers/generation/utils.py
patch: @@ -1772,9 +1772,9 @@ def _prepare_generation_config(
         """
         # parameterization priority:
         # user-defined kwargs or `generation_config` > `self.generation_config` > global default values
-        # TODO: (raushan) doesn't make sense to allow kwargs and `generation_config`. Should be mutually exclusive!
         # TODO (joao): per-model generation config classes.
 
+        generation_config_provided = generation_config is not None
         if generation_config is None:
             # Users may modify `model.config` to control generation. This is a legacy behavior and is not supported anymore
             if len(self.config._get_generation_parameters()) > 0:
@@ -1810,6 +1810,16 @@ def _prepare_generation_config(
         if generation_config.cache_implementation == "hybrid":
             generation_config.cache_implementation = None
 
+        # It doesn't make sense to allow kwargs and `generation_config`, that should be mutually exclusive
+        if generation_config_provided is not None and set(kwargs.keys()) - set(model_kwargs.keys()):
+            generation_kwargs = set(kwargs.keys()) - set(model_kwargs.keys())
+            logger.warning_once(
+                f"Passing `generation_config` together with generation-related "
+                f"arguments=({generation_kwargs}) is deprecated and will be removed in future versions. "
+                "Please pass either a `generation_config` object OR all generation "
+                "parameters explicitly, but not both.",
+            )
+
         # Finally keep output_xxx args in `model_kwargs` so it can be passed to `forward`
         output_attentions = generation_config.output_attentions
         output_hidden_states = generation_config.output_hidden_states

filename: src/transformers/models/musicgen_melody/modeling_musicgen_melody.py
patch: @@ -13,7 +13,6 @@
 # limitations under the License.
 """PyTorch Musicgen Melody model."""
 
-import copy
 import inspect
 import math
 import random
@@ -1102,12 +1101,7 @@ def generate(
                     - [`~generation.GenerateBeamEncoderDecoderOutput`]
         """
         # 1. Handle `generation_config` and kwargs that might update it, and validate the resulting objects
-        if generation_config is None:
-            generation_config = self.generation_config
-
-        generation_config = copy.deepcopy(generation_config)
-        model_kwargs = generation_config.update(**kwargs)  # All unused kwargs must be model kwargs
-        generation_config.validate()
+        generation_config, model_kwargs = self._prepare_generation_config(generation_config, **kwargs)
         self._validate_model_kwargs(model_kwargs.copy())
 
         # 2. Set generation parameters if not already defined
@@ -2043,12 +2037,7 @@ def generate(
                     - [`~generation.GenerateBeamEncoderDecoderOutput`]
         """
         # 1. Handle `generation_config` and kwargs that might update it, and validate the resulting objects
-        if generation_config is None:
-            generation_config = self.generation_config
-
-        generation_config = copy.deepcopy(generation_config)
-        model_kwargs = generation_config.update(**kwargs)  # All unused kwargs must be model kwargs
-        generation_config.validate()
+        generation_config, model_kwargs = self._prepare_generation_config(generation_config, **kwargs)
         self._validate_model_kwargs(model_kwargs.copy())
 
         # 2. Set generation parameters if not already defined

filename: src/transformers/models/whisper/generation_whisper.py
patch: @@ -647,7 +647,6 @@ def generate(
 
         """
         # 1. prepare generation config
-        generation_config = self.generation_config if generation_config is None else generation_config
         generation_config, kwargs = self._prepare_generation_config(generation_config, **kwargs)
 
         # 2. set global generate variables