diff options
-rw-r--r-- | CHANGELOG | 3 | ||||
-rw-r--r-- | bs4/__init__.py | 12 | ||||
-rw-r--r-- | bs4/element.py | 33 | ||||
-rw-r--r-- | bs4/tests/__init__.py | 6 | ||||
-rw-r--r-- | bs4/tests/test_navigablestring.py | 4 | ||||
-rw-r--r-- | bs4/tests/test_tree.py | 23 |
6 files changed, 58 insertions, 23 deletions
@@ -23,7 +23,8 @@ Python 2 was revision 605. methods was renamed to the more accurate "string." But this supposed "renaming" didn't make it into important places like the method signatures or the docstrings. That's corrected in this - version. ("text" still works, but don't use it.) [bug=1947038] + version. "text" still works, but will give a deprecation + warning. [bug=1947038] = 4.10.0 (20210907) diff --git a/bs4/__init__.py b/bs4/__init__.py index 2a436d3..2cdfed5 100644 --- a/bs4/__init__.py +++ b/bs4/__init__.py @@ -207,10 +207,10 @@ class BeautifulSoup(Tag): if old_name in kwargs: warnings.warn( 'The "%s" argument to the BeautifulSoup constructor ' - 'has been renamed to "%s."' % (old_name, new_name)) - value = kwargs[old_name] - del kwargs[old_name] - return value + 'has been renamed to "%s."' % (old_name, new_name), + DeprecationWarning + ) + return kwargs.pop(old_name) return None parse_only = parse_only or deprecated_argument( @@ -782,7 +782,9 @@ class BeautifulStoneSoup(BeautifulSoup): kwargs['features'] = 'xml' warnings.warn( 'The BeautifulStoneSoup class is deprecated. Instead of using ' - 'it, pass features="xml" into the BeautifulSoup constructor.') + 'it, pass features="xml" into the BeautifulSoup constructor.', + DeprecationWarning + ) super(BeautifulStoneSoup, self).__init__(*args, **kwargs) diff --git a/bs4/element.py b/bs4/element.py index 418b3e4..3383621 100644 --- a/bs4/element.py +++ b/bs4/element.py @@ -781,6 +781,10 @@ class PageElement(object): if string is None and 'text' in kwargs: string = kwargs.pop('text') + warnings.warn( + "The 'text' argument to find()-type methods is deprecated. Use 'string' instead.", + DeprecationWarning + ) if isinstance(name, SoupStrainer): strainer = name @@ -1548,7 +1552,8 @@ class Tag(PageElement): warnings.warn( '.%(name)sTag is deprecated, use .find("%(name)s") instead. If you really were looking for a tag called %(name)sTag, use .find("%(name)sTag")' % dict( name=tag_name - ) + ), + DeprecationWarning ) return self.find(tag_name) # We special case contents to avoid recursion. @@ -1974,8 +1979,10 @@ class Tag(PageElement): has_key() is gone in Python 3, anyway. """ - warnings.warn('has_key is deprecated. Use has_attr("%s") instead.' % ( - key)) + warnings.warn( + 'has_key is deprecated. Use has_attr("%s") instead.' % key, + DeprecationWarning + ) return self.has_attr(key) # Next, a couple classes to represent queries and their results. @@ -2003,6 +2010,11 @@ class SoupStrainer(object): """ if string is None and 'text' in kwargs: string = kwargs.pop('text') + warnings.warn( + "The 'text' argument to the SoupStrainer constructor is deprecated. Use 'string' instead.", + DeprecationWarning + ) + self.name = self._normalize_search_value(name) if not isinstance(attrs, dict): # Treat a non-dict value for attrs as a search for the 'class' @@ -2027,7 +2039,10 @@ class SoupStrainer(object): normalized_attrs[key] = self._normalize_search_value(value) self.attrs = normalized_attrs - self.text = self._normalize_search_value(string) + self.string = self._normalize_search_value(string) + + # DEPRECATED but just in case someone is checking this. + self.text = self.string def _normalize_search_value(self, value): # Leave it alone if it's a Unicode string, a callable, a @@ -2061,8 +2076,8 @@ class SoupStrainer(object): def __str__(self): """A human-readable representation of this SoupStrainer.""" - if self.text: - return self.text + if self.string: + return self.string else: return "%s|%s" % (self.name, self.attrs) @@ -2122,7 +2137,7 @@ class SoupStrainer(object): found = markup else: found = markup_name - if found and self.text and not self._matches(found.string, self.text): + if found and self.string and not self._matches(found.string, self.string): found = None return found @@ -2150,12 +2165,12 @@ class SoupStrainer(object): # If it's a Tag, make sure its name or attributes match. # Don't bother with Tags if we're searching for text. elif isinstance(markup, Tag): - if not self.text or self.name or self.attrs: + if not self.string or self.name or self.attrs: found = self.search_tag(markup) # If it's text, make sure the text matches. elif isinstance(markup, NavigableString) or \ isinstance(markup, str): - if not self.name and not self.attrs and self._matches(markup, self.text): + if not self.name and not self.attrs and self._matches(markup, self.string): found = markup else: raise Exception( diff --git a/bs4/tests/__init__.py b/bs4/tests/__init__.py index 5147f0e..224c9d8 100644 --- a/bs4/tests/__init__.py +++ b/bs4/tests/__init__.py @@ -510,13 +510,13 @@ Hello, world! self.assert_soup(markup) soup = self.soup(markup) - comment = soup.find(text="foobar") + comment = soup.find(string="foobar") assert comment.__class__ == Comment # The comment is properly integrated into the tree. - foo = soup.find(text="foo") + foo = soup.find(string="foo") assert comment == foo.next_element - baz = soup.find(text="baz") + baz = soup.find(string="baz") assert comment == baz.previous_element def test_preserved_whitespace_in_pre_and_textarea(self): diff --git a/bs4/tests/test_navigablestring.py b/bs4/tests/test_navigablestring.py index 649acc0..e4c179e 100644 --- a/bs4/tests/test_navigablestring.py +++ b/bs4/tests/test_navigablestring.py @@ -64,7 +64,7 @@ class TestNavigableStringSubclasses(SoupTest): cdata = CData("foo") soup.insert(1, cdata) assert str(soup) == "<![CDATA[foo]]>" - assert soup.find(text="foo") == "foo" + assert soup.find(string="foo") == "foo" assert soup.contents[0] == "foo" def test_cdata_is_never_formatted(self): @@ -103,7 +103,7 @@ class TestNavigableStringSubclasses(SoupTest): "<div>text</div><script>text</script><style>text</style>" ) assert [NavigableString, Script, Stylesheet] == [ - x.__class__ for x in soup.find_all(text=True) + x.__class__ for x in soup.find_all(string=True) ] # The TemplateString is a little unusual because it's generally found diff --git a/bs4/tests/test_tree.py b/bs4/tests/test_tree.py index 9d3ac4a..bfd6826 100644 --- a/bs4/tests/test_tree.py +++ b/bs4/tests/test_tree.py @@ -76,9 +76,7 @@ class TestFindAll(SoupTest): # Exact match. assert soup.find_all(string="bar") == ["bar"] - # 'text' is a deprecated alias for 'string'. - assert soup.find_all(text="bar") == ["bar"] - + # Match any of a number of strings. assert soup.find_all(string=["Foo", "bar"]) == ["Foo", "bar"] # Match a regular expression. @@ -1271,3 +1269,22 @@ class TestTreeModification(SoupTest): soup.a.string = cdata assert isinstance(soup.a.string, CData) + +class TestDeprecatedArguments(SoupTest): + + def test_find_type_method_string(self): + soup = self.soup("<a>some</a><b>markup</b>") + with warnings.catch_warnings(record=True) as w: + [result] = soup.find_all(text='markup') + assert result == 'markup' + assert result.parent.name == 'b' + msg = str(w[0].message) + assert msg == "The 'text' argument to find()-type methods is deprecated. Use 'string' instead." + + def test_soupstrainer_constructor_string(self): + with warnings.catch_warnings(record=True) as w: + strainer = SoupStrainer(text="text") + assert strainer.text == 'text' + msg = str(w[0].message) + assert msg == "The 'text' argument to the SoupStrainer constructor is deprecated. Use 'string' instead." + |