summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNicolas Lupien <nicolas@expedibox.com>2023-12-20 11:49:47 -0500
committerMariusz Felisiak <felisiak.mariusz@gmail.com>2023-12-22 08:27:59 +0100
commit2bf46c3825ad4ec170324791d6f3a329316ae2d4 (patch)
tree18ef6877e7fadf81f6554d5aa12142fba53effdf
parent5c6906cef4d4858bfe8d00de94eb797aa40b31fd (diff)
Fixed #34658 -- Added SimpleTestCase.assertNotInHTML().
-rw-r--r--django/test/testcases.py22
-rw-r--r--docs/releases/5.1.txt3
-rw-r--r--docs/topics/testing/tools.txt10
-rw-r--r--tests/test_utils/tests.py10
4 files changed, 37 insertions, 8 deletions
diff --git a/django/test/testcases.py b/django/test/testcases.py
index 0e887bdc0b..b5d426f75f 100644
--- a/django/test/testcases.py
+++ b/django/test/testcases.py
@@ -922,14 +922,17 @@ class SimpleTestCase(unittest.TestCase):
msg_prefix += ": "
haystack_repr = safe_repr(haystack)
if count is not None:
- self.assertEqual(
- real_count,
- count,
- (
- f"{msg_prefix}Found {real_count} instances of {needle!r} (expected "
- f"{count}) in the following response\n{haystack_repr}"
- ),
- )
+ if count == 0:
+ msg = (
+ f"{needle!r} unexpectedly found in the following response\n"
+ f"{haystack_repr}"
+ )
+ else:
+ msg = (
+ f"Found {real_count} instances of {needle!r} (expected {count}) in "
+ f"the following response\n{haystack_repr}"
+ )
+ self.assertEqual(real_count, count, f"{msg_prefix}{msg}")
else:
self.assertTrue(
real_count != 0,
@@ -939,6 +942,9 @@ class SimpleTestCase(unittest.TestCase):
),
)
+ def assertNotInHTML(self, needle, haystack, msg_prefix=""):
+ self.assertInHTML(needle, haystack, count=0, msg_prefix=msg_prefix)
+
def assertJSONEqual(self, raw, expected_data, msg=None):
"""
Assert that the JSON fragments raw and expected_data are equal.
diff --git a/docs/releases/5.1.txt b/docs/releases/5.1.txt
index fffaec21c6..cc72346eef 100644
--- a/docs/releases/5.1.txt
+++ b/docs/releases/5.1.txt
@@ -238,6 +238,9 @@ Tests
self.client.post("/items/1", query_params={"action": "delete"})
await self.async_client.post("/items/1", query_params={"action": "delete"})
+* The new :meth:`.SimpleTestCase.assertNotInHTML` assertion allows testing that
+ an HTML fragment is not contained in the given HTML haystack.
+
URLs
~~~~
diff --git a/docs/topics/testing/tools.txt b/docs/topics/testing/tools.txt
index b01dd35b8c..068e452ad0 100644
--- a/docs/topics/testing/tools.txt
+++ b/docs/topics/testing/tools.txt
@@ -1905,6 +1905,16 @@ your test suite.
In older versions, error messages didn't contain the ``haystack``.
+.. method:: SimpleTestCase.assertNotInHTML(needle, haystack, msg_prefix="")
+
+ .. versionadded:: 5.1
+
+ Asserts that the HTML fragment ``needle`` is *not* contained in the
+ ``haystack``.
+
+ Whitespace in most cases is ignored, and attribute ordering is not
+ significant. See :meth:`~SimpleTestCase.assertHTMLEqual` for more details.
+
.. method:: SimpleTestCase.assertJSONEqual(raw, expected_data, msg=None)
Asserts that the JSON fragments ``raw`` and ``expected_data`` are equal.
diff --git a/tests/test_utils/tests.py b/tests/test_utils/tests.py
index bce060f7ef..ce78ffc008 100644
--- a/tests/test_utils/tests.py
+++ b/tests/test_utils/tests.py
@@ -1053,6 +1053,16 @@ class InHTMLTests(SimpleTestCase):
with self.assertRaisesMessage(AssertionError, msg):
self.assertInHTML("<b>This</b>", haystack, 3)
+ def test_assert_not_in_html(self):
+ haystack = "<p><b>Hello</b> <span>there</span>! Hi <span>there</span>!</p>"
+ self.assertNotInHTML("<b>Hi</b>", haystack=haystack)
+ msg = (
+ "'<b>Hello</b>' unexpectedly found in the following response"
+ f"\n{haystack!r}"
+ )
+ with self.assertRaisesMessage(AssertionError, msg):
+ self.assertNotInHTML("<b>Hello</b>", haystack=haystack)
+
class JSONEqualTests(SimpleTestCase):
def test_simple_equal(self):