Repository: marshmallow-code/marshmallow
Pull request #2762 (2025-01-12 20:25:10)

Warn when using ordered class Meta option
`ordered` has technically been deprecated since https://github.com/marshmallow-code/marshmallow/pull/1896, but now we raise an explicit warning when it's set


Patch:
diff --git a/CHANGELOG.rst b/CHANGELOG.rst
index 85105ca2..ab79c680 100644
--- a/CHANGELOG.rst
+++ b/CHANGELOG.rst
@@ -13,6 +13,12 @@ Documentation:
 
 - Various documentation improvements (:pr:`2757`, :pr:`2759`).
 
+Deprecations:
+
+- The ``ordered`` `class Meta <marshmallow.Schema.Meta>` option is deprecated (:issue:`2146`, :pr:`2762`). 
+  Field order is already preserved by default. Set `marshmallow.Schema.dict_class` to `collections.OrderedDict` 
+  to maintain the previous behavior.
+
 3.25.1 (2025-01-11)
 *******************
 
diff --git a/pyproject.toml b/pyproject.toml
index 1c8d9e9f..9974fbcb 100644
--- a/pyproject.toml
+++ b/pyproject.toml
@@ -91,7 +91,7 @@ no_implicit_optional = true
 
 [tool.pytest.ini_options]
 norecursedirs = ".git .ropeproject .tox docs env venv tests/mypy_test_cases"
-addopts = "-v --tb=short"
 filterwarnings = [
   "ignore:Returning `False` from a validator:marshmallow.warnings.ChangedInMarshmallow4Warning",
+  "ignore:The `ordered` `class Meta` option is deprecated.:marshmallow.warnings.RemovedInMarshmallow4Warning",
 ]
diff --git a/src/marshmallow/schema.py b/src/marshmallow/schema.py
index 567dfd7e..b5b238ed 100644
--- a/src/marshmallow/schema.py
+++ b/src/marshmallow/schema.py
@@ -229,6 +229,14 @@ class SchemaOpts:
         else:
             render_module = json
         self.render_module = getattr(meta, "render_module", render_module)
+        if hasattr(meta, "ordered"):
+            warnings.warn(
+                "The `ordered` `class Meta` option is deprecated. "
+                "Field order is already preserved by default. "
+                "Set `Schema.dict_class` to OrderedDict to maintain the previous behavior.",
+                RemovedInMarshmallow4Warning,
+                stacklevel=2,
+            )
         self.ordered = getattr(meta, "ordered", ordered)
         self.index_errors = getattr(meta, "index_errors", True)
         self.include = getattr(meta, "include", {})


Test patch:
diff --git a/tests/test_options.py b/tests/test_options.py
index 4200ab90..98fe4f2d 100644
--- a/tests/test_options.py
+++ b/tests/test_options.py
@@ -4,6 +4,7 @@ from collections import OrderedDict
 import pytest
 
 from marshmallow import EXCLUDE, Schema, fields
+from marshmallow.warnings import RemovedInMarshmallow4Warning
 from tests.base import User
 
 
@@ -59,6 +60,19 @@ class OrderedNestedOnly(Schema):
 
 
 class TestFieldOrdering:
+    def test_ordered_option_is_deprecate(self):
+        with pytest.warns(RemovedInMarshmallow4Warning):
+
+            class MySchema(Schema):
+                class Meta:
+                    ordered = True
+
+        with pytest.warns(RemovedInMarshmallow4Warning):
+
+            class MySchema(Schema):
+                class Meta:
+                    ordered = False
+
     @pytest.mark.parametrize("with_meta", (False, True))
     def test_ordered_option_is_inherited(self, user, with_meta):
         class ParentUnordered(Schema):