{"action":"opened","number":2,"pull_request":{"url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2","id":188571846,"html_url":"https://github.com/woctezuma/SensCritique-Takeout/pull/2","diff_url":"https://github.com/woctezuma/SensCritique-Takeout/pull/2.diff","patch_url":"https://github.com/woctezuma/SensCritique-Takeout/pull/2.patch","issue_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/2","number":2,"state":"open","locked":false,"title":"Pin beautifulsoup4 to latest version 4.6.0","user":{"login":"pyup-bot","id":16239342,"avatar_url":"https://avatars0.githubusercontent.com/u/16239342?v=4","gravatar_id":"","url":"https://api.github.com/users/pyup-bot","html_url":"https://github.com/pyup-bot","followers_url":"https://api.github.com/users/pyup-bot/followers","following_url":"https://api.github.com/users/pyup-bot/following{/other_user}","gists_url":"https://api.github.com/users/pyup-bot/gists{/gist_id}","starred_url":"https://api.github.com/users/pyup-bot/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/pyup-bot/subscriptions","organizations_url":"https://api.github.com/users/pyup-bot/orgs","repos_url":"https://api.github.com/users/pyup-bot/repos","events_url":"https://api.github.com/users/pyup-bot/events{/privacy}","received_events_url":"https://api.github.com/users/pyup-bot/received_events","type":"User","site_admin":false},"body":"\nThis PR pins [beautifulsoup4](https://pypi.org/project/beautifulsoup4) to the latest release **4.6.0**.\n\n\n\n<details>\n  <summary>Changelog</summary>\n  \n  \n   ### 4.6.0\n   ```\n   * Added the `Tag.get_attribute_list` method, which acts like `Tag.get` for\n  getting the value of an attribute, but which always returns a list,\n  whether or not the attribute is a multi-value attribute. [bug=1678589]\n\n* It&#39;s now possible to use a tag&#39;s namespace prefix when searching,\n  e.g. soup.find(&#39;namespace:tag&#39;) [bug=1655332]\n\n* Improved the handling of empty-element tags like &lt;br&gt; when using the\n  html.parser parser. [bug=1676935]\n\n* HTML parsers treat all HTML4 and HTML5 empty element tags (aka void\n  element tags) correctly. [bug=1656909]\n\n* Namespace prefix is preserved when an XML tag is copied. Thanks\n  to Vikas for a patch and test. [bug=1685172]\n   ```\n   \n  \n  \n   ### 4.5.3\n   ```\n   * Fixed foster parenting when html5lib is the tree builder. Thanks to\n  Geoffrey Sneddon for a patch and test.\n  \n* Fixed yet another problem that caused the html5lib tree builder to\n  create a disconnected parse tree. [bug=1629825]\n   ```\n   \n  \n  \n   ### 4.5.2\n   ```\n   * Apart from the version number, this release is identical to\n  4.5.3. Due to user error, it could not be completely uploaded to\n  PyPI. Use 4.5.3 instead.\n   ```\n   \n  \n  \n   ### 4.5.1\n   ```\n   * Fixed a crash when passing Unicode markup that contained a\n  processing instruction into the lxml HTML parser on Python\n  3. [bug=1608048]\n   ```\n   \n  \n  \n   ### 4.5.0\n   ```\n   * Beautiful Soup is no longer compatible with Python 2.6. This\n  actually happened a few releases ago, but it&#39;s now official.\n\n* Beautiful Soup will now work with versions of html5lib greater than\n  0.99999999. [bug=1603299]\n\n* If a search against each individual value of a multi-valued\n  attribute fails, the search will be run one final time against the\n  complete attribute value considered as a single string. That is, if\n  a tag has class=&quot;foo bar&quot; and neither &quot;foo&quot; nor &quot;bar&quot; matches, but\n  &quot;foo bar&quot; does, the tag is now considered a match.\n\n  This happened in previous versions, but only when the value being\n  searched for was a string. Now it also works when that value is\n  a regular expression, a list of strings, etc. [bug=1476868]\n\n* Fixed a bug that deranged the tree when a whitespace element was\n  reparented into a tag that contained an identical whitespace\n  element. [bug=1505351]\n\n* Added support for CSS selector values that contain quoted spaces,\n  such as tag[style=&quot;display: foo&quot;]. [bug=1540588]\n\n* Corrected handling of XML processing instructions. [bug=1504393]\n\n* Corrected an encoding error that happened when a BeautifulSoup\n  object was copied. [bug=1554439]\n\n* The contents of &lt;textarea&gt; tags will no longer be modified when the\n  tree is prettified. [bug=1555829]\n\n* When a BeautifulSoup object is pickled but its tree builder cannot\n  be pickled, its .builder attribute is set to None instead of being\n  destroyed. This avoids a performance problem once the object is\n  unpickled. [bug=1523629]\n\n* Specify the file and line number when warning about a\n  BeautifulSoup object being instantiated without a parser being\n  specified. [bug=1574647]\n\n* The `limit` argument to `select()` now works correctly, though it&#39;s\n  not implemented very efficiently. [bug=1520530]\n\n* Fixed a Python 3 ByteWarning when a URL was passed in as though it\n  were markup. Thanks to James Salter for a patch and\n  test. [bug=1533762]\n\n* We don&#39;t run the check for a filename passed in as markup if the\n  &#39;filename&#39; contains a less-than character; the less-than character\n  indicates it&#39;s most likely a very small document. [bug=1577864]\n   ```\n   \n  \n  \n   ### 4.4.1\n   ```\n   * Fixed a bug that deranged the tree when part of it was\n  removed. Thanks to Eric Weiser for the patch and John Wiseman for a\n  test. [bug=1481520]\n\n* Fixed a parse bug with the html5lib tree-builder. Thanks to Roel\n  Kramer for the patch. [bug=1483781]\n\n* Improved the implementation of CSS selector grouping. Thanks to\n  Orangain for the patch. [bug=1484543]\n\n* Fixed the test_detect_utf8 test so that it works when chardet is\n  installed. [bug=1471359]\n\n* Corrected the output of Declaration objects. [bug=1477847]\n   ```\n   \n  \n  \n   ### 4.4.0\n   ```\n   Especially important changes:\n\n* Added a warning when you instantiate a BeautifulSoup object without\n  explicitly naming a parser. [bug=1398866]\n\n* __repr__ now returns an ASCII bytestring in Python 2, and a Unicode\n  string in Python 3, instead of a UTF8-encoded bytestring in both\n  versions. In Python 3, __str__ now returns a Unicode string instead\n  of a bytestring. [bug=1420131]\n\n* The `text` argument to the find_* methods is now called `string`,\n  which is more accurate. `text` still works, but `string` is the\n  argument described in the documentation. `text` may eventually\n  change its meaning, but not for a very long time. [bug=1366856]\n\n* Changed the way soup objects work under copy.copy(). Copying a\n  NavigableString or a Tag will give you a new NavigableString that&#39;s\n  equal to the old one but not connected to the parse tree. Patch by\n  Martijn Peters. [bug=1307490]\n\n* Started using a standard MIT license. [bug=1294662]\n\n* Added a Chinese translation of the documentation by Delong .w.\n\nNew features:\n\n* Introduced the select_one() method, which uses a CSS selector but\n  only returns the first match, instead of a list of\n  matches. [bug=1349367]\n\n* You can now create a Tag object without specifying a\n  TreeBuilder. Patch by Martijn Pieters. [bug=1307471]\n\n* You can now create a NavigableString or a subclass just by invoking\n  the constructor. [bug=1294315]\n\n* Added an `exclude_encodings` argument to UnicodeDammit and to the\n  Beautiful Soup constructor, which lets you prohibit the detection of\n  an encoding that you know is wrong. [bug=1469408]\n\n* The select() method now supports selector grouping. Patch by\n  Francisco Canas [bug=1191917]\n\nBug fixes:\n\n* Fixed yet another problem that caused the html5lib tree builder to\n  create a disconnected parse tree. [bug=1237763]\n\n* Force object_was_parsed() to keep the tree intact even when an element\n  from later in the document is moved into place. [bug=1430633]\n\n* Fixed yet another bug that caused a disconnected tree when html5lib\n  copied an element from one part of the tree to another. [bug=1270611]\n\n* Fixed a bug where Element.extract() could create an infinite loop in\n  the remaining tree.\n\n* The select() method can now find tags whose names contain\n  dashes. Patch by Francisco Canas. [bug=1276211]\n\n* The select() method can now find tags with attributes whose names\n  contain dashes. Patch by Marek Kapolka. [bug=1304007]\n\n* Improved the lxml tree builder&#39;s handling of processing\n  instructions. [bug=1294645]\n\n* Restored the helpful syntax error that happens when you try to\n  import the Python 2 edition of Beautiful Soup under Python\n  3. [bug=1213387]\n\n* In Python 3.4 and above, set the new convert_charrefs argument to\n  the html.parser constructor to avoid a warning and future\n  failures. Patch by Stefano Revera. [bug=1375721]\n\n* The warning when you pass in a filename or URL as markup will now be\n  displayed correctly even if the filename or URL is a Unicode\n  string. [bug=1268888]\n\n* If the initial &lt;html&gt; tag contains a CDATA list attribute such as\n  &#39;class&#39;, the html5lib tree builder will now turn its value into a\n  list, as it would with any other tag. [bug=1296481]\n\n* Fixed an import error in Python 3.5 caused by the removal of the\n  HTMLParseError class. [bug=1420063]\n\n* Improved docstring for encode_contents() and\n  decode_contents(). [bug=1441543]\n\n* Fixed a crash in Unicode, Dammit&#39;s encoding detector when the name\n  of the encoding itself contained invalid bytes. [bug=1360913]\n\n* Improved the exception raised when you call .unwrap() or\n  .replace_with() on an element that&#39;s not attached to a tree.\n\n* Raise a NotImplementedError whenever an unsupported CSS pseudoclass\n  is used in select(). Previously some cases did not result in a\n  NotImplementedError.\n\n* It&#39;s now possible to pickle a BeautifulSoup object no matter which\n  tree builder was used to create it. However, the only tree builder\n  that survives the pickling process is the HTMLParserTreeBuilder\n  (&#39;html.parser&#39;). If you unpickle a BeautifulSoup object created with\n  some other tree builder, soup.builder will be None. [bug=1231545]\n   ```\n   \n  \n  \n   ### 4.3.2\n   ```\n   * Fixed a bug in which short Unicode input was improperly encoded to\n  ASCII when checking whether or not it was the name of a file on\n  disk. [bug=1227016]\n\n* Fixed a crash when a short input contains data not valid in\n  filenames. [bug=1232604]\n\n* Fixed a bug that caused Unicode data put into UnicodeDammit to\n  return None instead of the original data. [bug=1214983]\n\n* Combined two tests to stop a spurious test failure when tests are\n  run by nosetests. [bug=1212445]\n   ```\n   \n  \n  \n   ### 4.3.1\n   ```\n   * Fixed yet another problem with the html5lib tree builder, caused by\n  html5lib&#39;s tendency to rearrange the tree during\n  parsing. [bug=1189267]\n\n* Fixed a bug that caused the optimized version of find_all() to\n  return nothing. [bug=1212655]\n   ```\n   \n  \n  \n   ### 4.3.0\n   ```\n   * Instead of converting incoming data to Unicode and feeding it to the\n  lxml tree builder in chunks, Beautiful Soup now makes successive\n  guesses at the encoding of the incoming data, and tells lxml to\n  parse the data as that encoding. Giving lxml more control over the\n  parsing process improves performance and avoids a number of bugs and\n  issues with the lxml parser which had previously required elaborate\n  workarounds:\n\n  - An issue in which lxml refuses to parse Unicode strings on some\n    systems. [bug=1180527]\n\n  - A returning bug that truncated documents longer than a (very\n    small) size. [bug=963880]\n\n  - A returning bug in which extra spaces were added to a document if\n    the document defined a charset other than UTF-8. [bug=972466]\n\n  This required a major overhaul of the tree builder architecture. If\n  you wrote your own tree builder and didn&#39;t tell me, you&#39;ll need to\n  modify your prepare_markup() method.\n\n* The UnicodeDammit code that makes guesses at encodings has been\n  split into its own class, EncodingDetector. A lot of apparently\n  redundant code has been removed from Unicode, Dammit, and some\n  undocumented features have also been removed.\n\n* Beautiful Soup will issue a warning if instead of markup you pass it\n  a URL or the name of a file on disk (a common beginner&#39;s mistake).\n\n* A number of optimizations improve the performance of the lxml tree\n  builder by about 33%, the html.parser tree builder by about 20%, and\n  the html5lib tree builder by about 15%.\n\n* All find_all calls should now return a ResultSet object. Patch by\n  Aaron DeVore. [bug=1194034]\n   ```\n   \n  \n  \n   ### 4.2.1\n   ```\n   * The default XML formatter will now replace ampersands even if they\n  appear to be part of entities. That is, &quot;&amp;lt;&quot; will become\n  &quot;&amp;amp;lt;&quot;. The old code was left over from Beautiful Soup 3, which\n  didn&#39;t always turn entities into Unicode characters.\n\n  If you really want the old behavior (maybe because you add new\n  strings to the tree, those strings include entities, and you want\n  the formatter to leave them alone on output), it can be found in\n  EntitySubstitution.substitute_xml_containing_entities(). [bug=1182183]\n\n* Gave new_string() the ability to create subclasses of\n  NavigableString. [bug=1181986]\n\n* Fixed another bug by which the html5lib tree builder could create a\n  disconnected tree. [bug=1182089]\n\n* The .previous_element of a BeautifulSoup object is now always None,\n  not the last element to be parsed. [bug=1182089]\n\n* Fixed test failures when lxml is not installed. [bug=1181589]\n\n* html5lib now supports Python 3. Fixed some Python 2-specific\n  code in the html5lib test suite. [bug=1181624]\n\n* The html.parser treebuilder can now handle numeric attributes in\n  text when the hexidecimal name of the attribute starts with a\n  capital X. Patch by Tim Shirley. [bug=1186242]\n   ```\n   \n  \n  \n   ### 4.2.0\n   ```\n   * The Tag.select() method now supports a much wider variety of CSS\n  selectors.\n\n - Added support for the adjacent sibling combinator (+) and the\n   general sibling combinator (~). Tests by &quot;liquider&quot;. [bug=1082144]\n\n - The combinators (&gt;, +, and ~) can now combine with any supported\n   selector, not just one that selects based on tag name.\n\n - Added limited support for the &quot;nth-of-type&quot; pseudo-class. Code\n   by Sven Slootweg. [bug=1109952]\n\n* The BeautifulSoup class is now aliased to &quot;_s&quot; and &quot;_soup&quot;, making\n  it quicker to type the import statement in an interactive session:\n\n  from bs4 import _s\n   or\n  from bs4 import _soup\n\n  The alias may change in the future, so don&#39;t use this in code you&#39;re\n  going to run more than once.\n\n* Added the &#39;diagnose&#39; submodule, which includes several useful\n  functions for reporting problems and doing tech support.\n\n  - diagnose(data) tries the given markup on every installed parser,\n    reporting exceptions and displaying successes. If a parser is not\n    installed, diagnose() mentions this fact.\n\n  - lxml_trace(data, html=True) runs the given markup through lxml&#39;s\n    XML parser or HTML parser, and prints out the parser events as\n    they happen. This helps you quickly determine whether a given\n    problem occurs in lxml code or Beautiful Soup code.\n\n  - htmlparser_trace(data) is the same thing, but for Python&#39;s\n    built-in HTMLParser class.\n\n* In an HTML document, the contents of a &lt;script&gt; or &lt;style&gt; tag will\n  no longer undergo entity substitution by default. XML documents work\n  the same way they did before. [bug=1085953]\n\n* Methods like get_text() and properties like .strings now only give\n  you strings that are visible in the document--no comments or\n  processing commands. [bug=1050164]\n\n* The prettify() method now leaves the contents of &lt;pre&gt; tags\n  alone. [bug=1095654]\n\n* Fix a bug in the html5lib treebuilder which sometimes created\n  disconnected trees. [bug=1039527]\n\n* Fix a bug in the lxml treebuilder which crashed when a tag included\n  an attribute from the predefined &quot;xml:&quot; namespace. [bug=1065617]\n\n* Fix a bug by which keyword arguments to find_parent() were not\n  being passed on. [bug=1126734]\n\n* Stop a crash when unwisely messing with a tag that&#39;s been\n  decomposed. [bug=1097699]\n\n* Now that lxml&#39;s segfault on invalid doctype has been fixed, fixed a\n  corresponding problem on the Beautiful Soup end that was previously\n  invisible. [bug=984936]\n\n* Fixed an exception when an overspecified CSS selector didn&#39;t match\n  anything. Code by Stefaan Lippens. [bug=1168167]\n   ```\n   \n  \n  \n   ### 4.1.3\n   ```\n   * Skipped a test under Python 2.6 and Python 3.1 to avoid a spurious\n  test failure caused by the lousy HTMLParser in those\n  versions. [bug=1038503]\n\n* Raise a more specific error (FeatureNotFound) when a requested\n  parser or parser feature is not installed. Raise NotImplementedError\n  instead of ValueError when the user calls insert_before() or\n  insert_after() on the BeautifulSoup object itself. Patch by Aaron\n  Devore. [bug=1038301]\n   ```\n   \n  \n  \n   ### 4.1.2\n   ```\n   * As per PEP-8, allow searching by CSS class using the &#39;class_&#39;\n  keyword argument. [bug=1037624]\n\n* Display namespace prefixes for namespaced attribute names, instead of\n  the fully-qualified names given by the lxml parser. [bug=1037597]\n\n* Fixed a crash on encoding when an attribute name contained\n  non-ASCII characters.\n\n* When sniffing encodings, if the cchardet library is installed,\n  Beautiful Soup uses it instead of chardet. cchardet is much\n  faster. [bug=1020748]\n\n* Use logging.warning() instead of warning.warn() to notify the user\n  that characters were replaced with REPLACEMENT\n  CHARACTER. [bug=1013862]\n   ```\n   \n  \n  \n   ### 4.1.1\n   ```\n   * Fixed an html5lib tree builder crash which happened when html5lib\n  moved a tag with a multivalued attribute from one part of the tree\n  to another. [bug=1019603]\n\n* Correctly display closing tags with an XML namespace declared. Patch\n  by Andreas Kostyrka. [bug=1019635]\n\n* Fixed a typo that made parsing significantly slower than it should\n  have been, and also waited too long to close tags with XML\n  namespaces. [bug=1020268]\n\n* get_text() now returns an empty Unicode string if there is no text,\n  rather than an empty bytestring. [bug=1020387]\n   ```\n   \n  \n  \n   ### 4.1.0\n   ```\n   * Added experimental support for fixing Windows-1252 characters\n  embedded in UTF-8 documents. (UnicodeDammit.detwingle())\n\n* Fixed the handling of &amp;quot; with the built-in parser. [bug=993871]\n\n* Comments, processing instructions, document type declarations, and\n  markup declarations are now treated as preformatted strings, the way\n  CData blocks are. [bug=1001025]\n\n* Fixed a bug with the lxml treebuilder that prevented the user from\n  adding attributes to a tag that didn&#39;t originally have\n  attributes. [bug=1002378] Thanks to Oliver Beattie for the patch.\n\n* Fixed some edge-case bugs having to do with inserting an element\n  into a tag it&#39;s already inside, and replacing one of a tag&#39;s\n  children with another. [bug=997529]\n\n* Added the ability to search for attribute values specified in UTF-8. [bug=1003974]\n\n  This caused a major refactoring of the search code. All the tests\n  pass, but it&#39;s possible that some searches will behave differently.\n   ```\n   \n  \n  \n   ### 4.0.5\n   ```\n   * Added a new method, wrap(), which wraps an element in a tag.\n\n* Renamed replace_with_children() to unwrap(), which is easier to\n  understand and also the jQuery name of the function.\n\n* Made encoding substitution in &lt;meta&gt; tags completely transparent (no\n  more %SOUP-ENCODING%).\n\n* Fixed a bug in decoding data that contained a byte-order mark, such\n  as data encoded in UTF-16LE. [bug=988980]\n\n* Fixed a bug that made the HTMLParser treebuilder generate XML\n  definitions ending with two question marks instead of\n  one. [bug=984258]\n\n* Upon document generation, CData objects are no longer run through\n  the formatter. [bug=988905]\n\n* The test suite now passes when lxml is not installed, whether or not\n  html5lib is installed. [bug=987004]\n\n* Print a warning on HTMLParseErrors to let people know they should\n  install a better parser library.\n   ```\n   \n  \n  \n   ### 4.0.4\n   ```\n   * Fixed a bug that sometimes created disconnected trees.\n\n* Fixed a bug with the string setter that moved a string around the\n  tree instead of copying it. [bug=983050]\n\n* Attribute values are now run through the provided output formatter.\n  Previously they were always run through the &#39;minimal&#39; formatter. In\n  the future I may make it possible to specify different formatters\n  for attribute values and strings, but for now, consistent behavior\n  is better than inconsistent behavior. [bug=980237]\n\n* Added the missing renderContents method from Beautiful Soup 3. Also\n  added an encode_contents() method to go along with decode_contents().\n\n* Give a more useful error when the user tries to run the Python 2\n  version of BS under Python 3.\n\n* UnicodeDammit can now convert Microsoft smart quotes to ASCII with\n  UnicodeDammit(markup, smart_quotes_to=&quot;ascii&quot;).\n   ```\n   \n  \n  \n   ### 4.0.3\n   ```\n   * Fixed a typo that caused some versions of Python 3 to convert the\n  Beautiful Soup codebase incorrectly.\n\n* Got rid of the 4.0.2 workaround for HTML documents--it was\n  unnecessary and the workaround was triggering a (possibly different,\n  but related) bug in lxml. [bug=972466]\n   ```\n   \n  \n  \n   ### 4.0.2\n   ```\n   * Worked around a possible bug in lxml that prevents non-tiny XML\n  documents from being parsed. [bug=963880, bug=963936]\n\n* Fixed a bug where specifying `text` while also searching for a tag\n  only worked if `text` wanted an exact string match. [bug=955942]\n   ```\n   \n  \n  \n   ### 4.0.1\n   ```\n   * This is the first official release of Beautiful Soup 4. There is no\n   ```\n   \n  \n  \n   ### 4.0.0\n   ```\n   might treat &quot;4.0.0&quot; as being an earlier version than &quot;4.0.0b10&quot;.\n\n* Brought BS up to date with the latest release of soupselect, adding\n  CSS selector support for direct descendant matches and multiple CSS\n  class matches.\n   ```\n   \n  \n  \n   ### 4.0.0b10\n   ```\n   * Added support for simple CSS selectors, taken from the soupselect project.\n\n* Fixed a crash when using html5lib. [bug=943246]\n\n* In HTML5-style &lt;meta charset=&quot;foo&quot;&gt; tags, the value of the &quot;charset&quot;\n  attribute is now replaced with the appropriate encoding on\n  output. [bug=942714]\n\n* Fixed a bug that caused calling a tag to sometimes call find_all()\n  with the wrong arguments. [bug=944426]\n\n* For backwards compatibility, brought back the BeautifulStoneSoup\n  class as a deprecated wrapper around BeautifulSoup.\n   ```\n   \n  \n  \n   ### 4.0.0b9\n   ```\n   * Fixed the string representation of DOCTYPEs that have both a public\n  ID and a system ID.\n\n* Fixed the generated XML declaration.\n\n* Renamed Tag.nsprefix to Tag.prefix, for consistency with\n  NamespacedAttribute.\n\n* Fixed a test failure that occurred on Python 3.x when chardet was\n  installed.\n\n* Made prettify() return Unicode by default, so it will look nice on\n  Python 3 when passed into print().\n   ```\n   \n  \n  \n   ### 4.0.0b8\n   ```\n   * All tree builders now preserve namespace information in the\n  documents they parse. If you use the html5lib parser or lxml&#39;s XML\n  parser, you can access the namespace URL for a tag as tag.namespace.\n\n  However, there is no special support for namespace-oriented\n  searching or tree manipulation. When you search the tree, you need\n  to use namespace prefixes exactly as they&#39;re used in the original\n  document.\n\n* The string representation of a DOCTYPE always ends in a newline.\n\n* Issue a warning if the user tries to use a SoupStrainer in\n  conjunction with the html5lib tree builder, which doesn&#39;t support\n  them.\n   ```\n   \n  \n  \n   ### 4.0.0b7\n   ```\n   * Upon decoding to string, any characters that can&#39;t be represented in\n  your chosen encoding will be converted into numeric XML entity\n  references.\n\n* Issue a warning if characters were replaced with REPLACEMENT\n  CHARACTER during Unicode conversion.\n\n* Restored compatibility with Python 2.6.\n\n* The install process no longer installs docs or auxiliary text files.\n\n* It&#39;s now possible to deepcopy a BeautifulSoup object created with\n  Python&#39;s built-in HTML parser.\n\n* About 100 unit tests that &quot;test&quot; the behavior of various parsers on\n  invalid markup have been removed. Legitimate changes to those\n  parsers caused these tests to fail, indicating that perhaps\n  Beautiful Soup should not test the behavior of foreign\n  libraries.\n\n  The problematic unit tests have been reformulated as informational\n  comparisons generated by the script\n  scripts/demonstrate_parser_differences.py.\n\n  This makes Beautiful Soup compatible with html5lib version 0.95 and\n  future versions of HTMLParser.\n   ```\n   \n  \n  \n   ### 4.0.0b6\n   ```\n   * Multi-valued attributes like &quot;class&quot; always have a list of values,\n  even if there&#39;s only one value in the list.\n\n* Added a number of multi-valued attributes defined in HTML5.\n\n* Stopped generating a space before the slash that closes an\n  empty-element tag. This may come back if I add a special XHTML mode\n  (http://www.w3.org/TR/xhtml1/C_2), but right now it&#39;s pretty\n  useless.\n\n* Passing text along with tag-specific arguments to a find* method:\n\n   find(&quot;a&quot;, text=&quot;Click here&quot;)\n\n  will find tags that contain the given text as their\n  .string. Previously, the tag-specific arguments were ignored and\n  only strings were searched.\n\n* Fixed a bug that caused the html5lib tree builder to build a\n  partially disconnected tree. Generally cleaned up the html5lib tree\n  builder.\n\n* If you restrict a multi-valued attribute like &quot;class&quot; to a string\n  that contains spaces, Beautiful Soup will only consider it a match\n  if the values correspond to that specific string.\n   ```\n   \n  \n  \n   ### 4.0.0b5\n   ```\n   * Rationalized Beautiful Soup&#39;s treatment of CSS class. A tag\n  belonging to multiple CSS classes is treated as having a list of\n  values for the &#39;class&#39; attribute. Searching for a CSS class will\n  match *any* of the CSS classes.\n\n  This actually affects all attributes that the HTML standard defines\n  as taking multiple values (class, rel, rev, archive, accept-charset,\n  and headers), but &#39;class&#39; is by far the most common. [bug=41034]\n\n* If you pass anything other than a dictionary as the second argument\n  to one of the find* methods, it&#39;ll assume you want to use that\n  object to search against a tag&#39;s CSS classes. Previously this only\n  worked if you passed in a string.\n\n* Fixed a bug that caused a crash when you passed a dictionary as an\n  attribute value (possibly because you mistyped &quot;attrs&quot;). [bug=842419]\n\n* Unicode, Dammit now detects the encoding in HTML 5-style &lt;meta&gt; tags\n  like &lt;meta charset=&quot;utf-8&quot; /&gt;. [bug=837268]\n\n* If Unicode, Dammit can&#39;t figure out a consistent encoding for a\n  page, it will try each of its guesses again, with errors=&quot;replace&quot;\n  instead of errors=&quot;strict&quot;. This may mean that some data gets\n  replaced with REPLACEMENT CHARACTER, but at least most of it will\n  get turned into Unicode. [bug=754903]\n\n* Patched over a bug in html5lib (?) that was crashing Beautiful Soup\n  on certain kinds of markup. [bug=838800]\n\n* Fixed a bug that wrecked the tree if you replaced an element with an\n  empty string. [bug=728697]\n\n* Improved Unicode, Dammit&#39;s behavior when you give it Unicode to\n  begin with.\n   ```\n   \n  \n  \n   ### 4.0.0b4\n   ```\n   * Added BeautifulSoup.new_string() to go along with BeautifulSoup.new_tag()\n\n* BeautifulSoup.new_tag() will follow the rules of whatever\n  tree-builder was used to create the original BeautifulSoup object. A\n  new &lt;p&gt; tag will look like &quot;&lt;p /&gt;&quot; if the soup object was created to\n  parse XML, but it will look like &quot;&lt;p&gt;&lt;/p&gt;&quot; if the soup object was\n  created to parse HTML.\n\n* We pass in strict=False to html.parser on Python 3, greatly\n  improving html.parser&#39;s ability to handle bad HTML.\n\n* We also monkeypatch a serious bug in html.parser that made\n  strict=False disastrous on Python 3.2.2.\n\n* Replaced the &quot;substitute_html_entities&quot; argument with the\n  more general &quot;formatter&quot; argument.\n\n* Bare ampersands and angle brackets are always converted to XML\n  entities unless the user prevents it.\n\n* Added PageElement.insert_before() and PageElement.insert_after(),\n  which let you put an element into the parse tree with respect to\n  some other element.\n\n* Raise an exception when the user tries to do something nonsensical\n  like insert a tag into itself.\n   ```\n   \n  \n  \n   ### 4.0.0b3\n   ```\n   Beautiful Soup 4 is a nearly-complete rewrite that removes Beautiful\nSoup&#39;s custom HTML parser in favor of a system that lets you write a\nlittle glue code and plug in any HTML or XML parser you want.\n\nBeautiful Soup 4.0 comes with glue code for four parsers:\n\n * Python&#39;s standard HTMLParser (html.parser in Python 3)\n * lxml&#39;s HTML and XML parsers\n * html5lib&#39;s HTML parser\n\nHTMLParser is the default, but I recommend you install lxml if you\ncan.\n\nFor complete documentation, see the Sphinx documentation in\nbs4/doc/source/. What follows is a summary of the changes from\nBeautiful Soup 3.\n\n=== The module name has changed ===\n\nPreviously you imported the BeautifulSoup class from a module also\ncalled BeautifulSoup. To save keystrokes and make it clear which\nversion of the API is in use, the module is now called &#39;bs4&#39;:\n\n    &gt;&gt;&gt; from bs4 import BeautifulSoup\n\n=== It works with Python 3 ===\n\nBeautiful Soup 3.1.0 worked with Python 3, but the parser it used was\nso bad that it barely worked at all. Beautiful Soup 4 works with\nPython 3, and since its parser is pluggable, you don&#39;t sacrifice\nquality.\n\nSpecial thanks to Thomas Kluyver and Ezio Melotti for getting Python 3\nsupport to the finish line. Ezio Melotti is also to thank for greatly\nimproving the HTML parser that comes with Python 3.2.\n\n=== CDATA sections are normal text, if they&#39;re understood at all. ===\n\nCurrently, the lxml and html5lib HTML parsers ignore CDATA sections in\nmarkup:\n\n &lt;p&gt;&lt;![CDATA[foo]]&gt;&lt;/p&gt; =&gt; &lt;p&gt;&lt;/p&gt;\n\nA future version of html5lib will turn CDATA sections into text nodes,\nbut only within tags like &lt;svg&gt; and &lt;math&gt;:\n\n &lt;svg&gt;&lt;![CDATA[foo]]&gt;&lt;/svg&gt; =&gt; &lt;p&gt;foo&lt;/p&gt;\n\nThe default XML parser (which uses lxml behind the scenes) turns CDATA\nsections into ordinary text elements:\n\n &lt;p&gt;&lt;![CDATA[foo]]&gt;&lt;/p&gt; =&gt; &lt;p&gt;foo&lt;/p&gt;\n\nIn theory it&#39;s possible to preserve the CDATA sections when using the\nXML parser, but I don&#39;t see how to get it to work in practice.\n\n=== Miscellaneous other stuff ===\n\nIf the BeautifulSoup instance has .is_xml set to True, an appropriate\nXML declaration will be emitted when the tree is transformed into a\nstring:\n\n    &lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;&gt;\n    &lt;markup&gt;\n     ...\n    &lt;/markup&gt;\n\nThe [&#39;lxml&#39;, &#39;xml&#39;] tree builder sets .is_xml to True; the other tree\nbuilders set it to False. If you want to parse XHTML with an HTML\nparser, you can set it manually.\n   ```\n   \n  \n  \n   ### 3.2\n   ```\n   to make it obvious which one you should use.\n   ```\n   \n  \n  \n  \n  \n   ### 3.1.0\n   ```\n   A hybrid version that supports 2.4 and can be automatically converted\nto run under Python 3.0. There are three backwards-incompatible\nchanges you should be aware of, but no new features or deliberate\nbehavior changes.\n\n1. str() may no longer do what you want. This is because the meaning\nof str() inverts between Python 2 and 3; in Python 2 it gives you a\nbyte string, in Python 3 it gives you a Unicode string.\n\nThe effect of this is that you can&#39;t pass an encoding to .__str__\nanymore. Use encode() to get a string and decode() to get Unicode, and\nyou&#39;ll be ready (well, readier) for Python 3.\n\n2. Beautiful Soup is now based on HTMLParser rather than SGMLParser,\nwhich is gone in Python 3. There&#39;s some bad HTML that SGMLParser\nhandled but HTMLParser doesn&#39;t, usually to do with attribute values\nthat aren&#39;t closed or have brackets inside them:\n\n  &lt;a href=&quot;foo&lt;/a&gt;, &lt;/a&gt;&lt;a href=&quot;bar&quot;&gt;baz&lt;/a&gt;\n  &lt;a b=&quot;&lt;a&gt;&quot;&gt;&#39;, &#39;&lt;a b=&quot;&amp;lt;a&amp;gt;&quot;&gt;&lt;/a&gt;&lt;a&gt;&quot;&gt;&lt;/a&gt;\n\nA later version of Beautiful Soup will allow you to plug in different\nparsers to make tradeoffs between speed and the ability to handle bad\nHTML.\n\n3. In Python 3 (but not Python 2), HTMLParser converts entities within\nattributes to the corresponding Unicode characters. In Python 2 it&#39;s\npossible to parse this string and leave the &amp;eacute; intact.\n\n &lt;a href=&quot;http://crummy.com?sacr&amp;eacute;&amp;bleu&quot;&gt;\n\nIn Python 3, the &amp;eacute; is always converted to \\xe9 during\nparsing.\n   ```\n   \n  \n  \n   ### 3.0.7\n   ```\n   Fixed a UnicodeDecodeError when unpickling documents that contain\nnon-ASCII characters.\n\nFixed a TypeError that occurred in some circumstances when a tag\ncontained no text.\n\nJump through hoops to avoid the use of chardet, which can be extremely\nslow in some circumstances. UTF-8 documents should never trigger the\nuse of chardet.\n\nWhitespace is preserved inside &lt;pre&gt; and &lt;textarea&gt; tags that contain\nnothing but whitespace.\n\nBeautiful Soup can now parse a doctype that&#39;s scoped to an XML namespace.\n   ```\n   \n  \n  \n   ### 3.0.7a\n   ```\n   Added an import that makes BS work in Python 2.3.\n   ```\n   \n  \n  \n   ### 3.0.6\n   ```\n   Got rid of a very old debug line that prevented chardet from working.\n\nAdded a Tag.decompose() method that completely disconnects a tree or a\nsubset of a tree, breaking it up into bite-sized pieces that are\neasy for the garbage collecter to collect.\n\nTag.extract() now returns the tag that was extracted.\n\nTag.findNext() now does something with the keyword arguments you pass\nit instead of dropping them on the floor.\n\nFixed a Unicode conversion bug.\n\nFixed a bug that garbled some &lt;meta&gt; tags when rewriting them.\n   ```\n   \n  \n  \n   ### 3.0.5\n   ```\n   Soup objects can now be pickled, and copied with copy.deepcopy.\n\nTag.append now works properly on existing BS objects. (It wasn&#39;t\noriginally intended for outside use, but it can be now.) (Giles\nRadford)\n\nPassing in a nonexistent encoding will no longer crash the parser on\nPython 2.4 (John Nagle).\n\nFixed an underlying bug in SGMLParser that thinks ASCII has 255\ncharacters instead of 127 (John Nagle).\n\nEntities are converted more consistently to Unicode characters.\n\nEntity references in attribute values are now converted to Unicode\ncharacters when appropriate. Numeric entities are always converted,\nbecause SGMLParser always converts them outside of attribute values.\n\nALL_ENTITIES happens to just be the XHTML entities, so I renamed it to\nXHTML_ENTITIES.\n\nThe regular expression for bare ampersands was too loose. In some\ncases ampersands were not being escaped. (Sam Ruby?)\n\nNon-breaking spaces and other special Unicode space characters are no\nlonger folded to ASCII spaces. (Robert Leftwich)\n\nInformation inside a TEXTAREA tag is now parsed literally, not as HTML\ntags. TEXTAREA now works exactly the same way as SCRIPT. (Zephyr Fang)\n   ```\n   \n  \n  \n   ### 3.0.4\n   ```\n   Fixed a bug that crashed Unicode conversion in some cases.\n\nFixed a bug that prevented UnicodeDammit from being used as a\ngeneral-purpose data scrubber.\n\nFixed some unit test failures when running against Python 2.5.\n\nWhen considering whether to convert smart quotes, UnicodeDammit now\nlooks at the original encoding in a case-insensitive way.\n   ```\n   \n  \n  \n   ### 3.0.3\n   ```\n   Beautiful Soup is now usable as a way to clean up invalid XML/HTML (be\nsure to pass in an appropriate value for convertEntities, or XML/HTML\nentities might stick around that aren&#39;t valid in HTML/XML). The result\nmay not validate, but it should be good enough to not choke a\nreal-world XML parser. Specifically, the output of a properly\nconstructed soup object should always be valid as part of an XML\ndocument, but parts may be missing if they were missing in the\noriginal. As always, if the input is valid XML, the output will also\nbe valid.\n   ```\n   \n  \n  \n   ### 3.0.2\n   ```\n   Previously, Beautiful Soup correctly handled attribute values that\ncontained embedded quotes (sometimes by escaping), but not other kinds\nof XML character. Now, it correctly handles or escapes all special XML\ncharacters in attribute values.\n\nI aliased methods to the 2.x names (fetch, find, findText, etc.) for\nbackwards compatibility purposes. Those names are deprecated and if I\never do a 4.0 I will remove them. I will, I tell you!\n\nFixed a bug where the findAll method wasn&#39;t passing along any keyword\narguments.\n\nWhen run from the command line, Beautiful Soup now acts as an HTML\npretty-printer, not an XML pretty-printer.\n   ```\n   \n  \n  \n   ### 3.0.1\n   ```\n   Reintroduced the &quot;fetch by CSS class&quot; shortcut. I thought keyword\narguments would replace it, but they don&#39;t. You can&#39;t call soup(&#39;a&#39;,\nclass=&#39;foo&#39;) because class is a Python keyword.\n\nIf Beautiful Soup encounters a meta tag that declares the encoding,\nbut a SoupStrainer tells it not to parse that tag, Beautiful Soup will\nno longer try to rewrite the meta tag to mention the new\nencoding. Basically, this makes SoupStrainers work in real-world\napplications instead of crashing the parser.\n   ```\n   \n  \n  \n   ### 3.0.0\n   ```\n   This release is not backward-compatible with previous releases. If\nyou&#39;ve got code written with a previous version of the library, go\nahead and keep using it, unless one of the features mentioned here\nreally makes your life easier. Since the library is self-contained,\nyou can include an old copy of the library in your old applications,\nand use the new version for everything else.\n\nThe documentation has been rewritten and greatly expanded with many\nmore examples.\n\nBeautiful Soup autodetects the encoding of a document (or uses the one\nyou specify), and converts it from its native encoding to\nUnicode. Internally, it only deals with Unicode strings. When you\nprint out the document, it converts to UTF-8 (or another encoding you\nspecify). [Doc reference]\n\nIt&#39;s now easy to make large-scale changes to the parse tree without\nscrewing up the navigation members. The methods are extract,\nreplaceWith, and insert. [Doc reference. See also Improving Memory\nUsage with extract]\n\nPassing True in as an attribute value gives you tags that have any\nvalue for that attribute. You don&#39;t have to create a regular\nexpression. Passing None for an attribute value gives you tags that\ndon&#39;t have that attribute at all.\n\nTag objects now know whether or not they&#39;re self-closing. This avoids\nthe problem where Beautiful Soup thought that tags like &lt;BR /&gt; were\nself-closing even in XML documents. You can customize the self-closing\ntags for a parser object by passing them in as a list of\nselfClosingTags: you don&#39;t have to subclass anymore.\n\nThere&#39;s a new built-in parser, MinimalSoup, which has most of\nBeautifulSoup&#39;s HTML-specific rules, but no tag nesting rules. [Doc\nreference]\n\nYou can use a SoupStrainer to tell Beautiful Soup to parse only part\nof a document. This saves time and memory, often making Beautiful Soup\nabout as fast as a custom-built SGMLParser subclass. [Doc reference,\nSoupStrainer reference]\n\nYou can (usually) use keyword arguments instead of passing a\ndictionary of attributes to a search method. That is, you can replace\nsoup(args={&quot;id&quot; : &quot;5&quot;}) with soup(id=&quot;5&quot;). You can still use args if\n(for instance) you need to find an attribute whose name clashes with\nthe name of an argument to findAll. [Doc reference: **kwargs attrs]\n\nThe method names have changed to the better method names used in\nRubyful Soup. Instead of find methods and fetch methods, there are\nonly find methods. Instead of a scheme where you can&#39;t remember which\nmethod finds one element and which one finds them all, we have find\nand findAll. In general, if the method name mentions All or a plural\nnoun (eg. findNextSiblings), then it finds many elements\nmethod. Otherwise, it only finds one element. [Doc reference]\n\nSome of the argument names have been renamed for clarity. For instance\navoidParserProblems is now parserMassage.\n\nBeautiful Soup no longer implements a feed method. You need to pass a\nstring or a filehandle into the soup constructor, not with feed after\nthe soup has been created. There is still a feed method, but it&#39;s the\nfeed method implemented by SGMLParser and calling it will bypass\nBeautiful Soup and cause problems.\n\nThe NavigableText class has been renamed to NavigableString. There is\nno NavigableUnicodeString anymore, because every string inside a\nBeautiful Soup parse tree is a Unicode string.\n\nfindText and fetchText are gone. Just pass a text argument into find\nor findAll.\n\nNull was more trouble than it was worth, so I got rid of it. Anything\nthat used to return Null now returns None.\n\nSpecial XML constructs like comments and CDATA now have their own\nNavigableString subclasses, instead of being treated as oddly-formed\ndata. If you parse a document that contains CDATA and write it back\nout, the CDATA will still be there.\n\nWhen you&#39;re parsing a document, you can get Beautiful Soup to convert\nXML or HTML entities into the corresponding Unicode characters. [Doc\nreference]\n   ```\n   \n  \n  \n   ### 2.1.1\n   ```\n   Fixed a serious performance bug in BeautifulStoneSoup which was\ncausing parsing to be incredibly slow.\n\nCorrected several entities that were previously being incorrectly\ntranslated from Microsoft smart-quote-like characters.\n\nFixed a bug that was breaking text fetch.\n\nFixed a bug that crashed the parser when text chunks that look like\nHTML tag names showed up within a SCRIPT tag.\n\nTHEAD, TBODY, and TFOOT tags are now nestable within TABLE\ntags. Nested tables should parse more sensibly now.\n\nBASE is now considered a self-closing tag.\n   ```\n   \n  \n  \n   ### 2.1.0\n   ```\n   Added a wide variety of new search methods which, given a starting\npoint inside the tree, follow a particular navigation member (like\nnextSibling) over and over again, looking for Tag and NavigableText\nobjects that match certain criteria. The new methods are findNext,\nfetchNext, findPrevious, fetchPrevious, findNextSibling,\nfetchNextSiblings, findPreviousSibling, fetchPreviousSiblings,\nfindParent, and fetchParents. All of these use the same basic code\nused by first and fetch, so you can pass your weird ways of matching\nthings into these methods.\n\nThe fetch method and its derivatives now accept a limit argument.\n\nYou can now pass keyword arguments when calling a Tag object as though\nit were a method.\n\nFixed a bug that caused all hand-created tags to share a single set of\nattributes.\n   ```\n   \n  \n  \n   ### 2.0.3\n   ```\n   Fixed Python 2.2 support for iterators.\n\nFixed a bug that gave the wrong representation to tags within quote\ntags like &lt;script&gt;.\n\nTook some code from Mark Pilgrim that treats CDATA declarations as\ndata instead of ignoring them.\n\nBeautiful Soup&#39;s setup.py will now do an install even if the unit\ntests fail. It won&#39;t build a source distribution if the unit tests\nfail, so I can&#39;t release a new version unless they pass.\n   ```\n   \n  \n  \n   ### 2.0.2\n   ```\n   Added the unit tests in a separate module, and packaged it with\ndistutils.\n\nFixed a bug that sometimes caused renderContents() to return a Unicode\nstring even if there was no Unicode in the original string.\n\nAdded the done() method, which closes all of the parser&#39;s open\ntags. It gets called automatically when you pass in some text to the\nconstructor of a parser class; otherwise you must call it yourself.\n\nReinstated some backwards compatibility with 1.x versions: referencing\nthe string member of a NavigableText object returns the NavigableText\nobject instead of throwing an error.\n   ```\n   \n  \n  \n   ### 2.0.1\n   ```\n   Fixed a bug that caused bad results when you tried to reference a tag\nname shorter than 3 characters as a member of a Tag, eg. tag.table.td.\n\nMade sure all Tags have the &#39;hidden&#39; attribute so that an attempt to\naccess tag.hidden doesn&#39;t spawn an attempt to find a tag named\n&#39;hidden&#39;.\n\nFixed a bug in the comparison operator.\n   ```\n   \n  \n  \n   ### 2.0\n   ```\n   This is the release to get if you want Python 1.5 compatibility.\n\nThe desired value of an attribute can now be any of the following:\n\n * A string\n * A string with SQL-style wildcards\n * A compiled RE object\n * A callable that returns None/false/empty string if the given value\n   doesn&#39;t match, and any other value otherwise.\n\nThis is much easier to use than SQL-style wildcards (see, regular\nexpressions are good for something). Because of this, I no longer\nrecommend you use SQL-style wildcards. They may go away in a future\nrelease to clean up the code.\n\nMade Beautiful Soup handle processing instructions as text instead of\nignoring them.\n\nApplied patch from Richie Hindle (richie at entrian dot com) that\nmakes tag.string a shorthand for tag.contents[0].string when the tag\nhas only one string-owning child.\n\nAdded still more nestable tags. The nestable tags thing won&#39;t work in\na lot of cases and needs to be rethought.\n\nFixed an edge case where searching for &quot;%foo&quot; would match any string\nshorter than &quot;foo&quot;.\n   ```\n   \n  \n  \n   ### 2.0.0\n   ```\n   Beautiful Soup version 1 was very useful but also pretty stupid. I\noriginally wrote it without noticing any of the problems inherent in\ntrying to build a parse tree out of ambiguous HTML tags. This version\nsolves all of those problems to my satisfaction. It also adds many new\nclever things to make up for the removal of the stupid things.\n\n== Parsing ==\n\nThe parser logic has been greatly improved, and the BeautifulSoup\nclass should much more reliably yield a parse tree that looks like\nwhat the page author intended. For a particular class of odd edge\ncases that now causes problems, there is a new class,\nICantBelieveItsBeautifulSoup.\n\nBy default, Beautiful Soup now performs some cleanup operations on\ntext before parsing it. This is to avoid common problems with bad\ndefinitions and self-closing tags that crash SGMLParser. You can\nprovide your own set of cleanup operations, or turn it off\naltogether. The cleanup operations include fixing self-closing tags\nthat don&#39;t close, and replacing Microsoft smart quotes and similar\ncharacters with their HTML entity equivalents.\n\nYou can now get a pretty-print version of parsed HTML to get a visual\npicture of how Beautiful Soup parses it, with the Tag.prettify()\nmethod.\n\n== Strings and Unicode ==\n\nThere are separate NavigableText subclasses for ASCII and Unicode\nstrings. These classes directly subclass the corresponding base data\ntypes. This means you can treat NavigableText objects as strings\ninstead of having to call methods on them to get the strings.\n\nstr() on a Tag always returns a string, and unicode() always returns\nUnicode. Previously it was inconsistent.\n\n== Tree traversal ==\n\nIn a first() or fetch() call, the tag name or the desired value of an\nattribute can now be any of the following:\n\n * A string (matches that specific tag or that specific attribute value)\n * A list of strings (matches any tag or attribute value in the list)\n * A compiled regular expression object (matches any tag or attribute\n   value that matches the regular expression)\n * A callable object that takes the Tag object or attribute value as a\n   string. It returns None/false/empty string if the given string\n   doesn&#39;t match, and any other value if it does.\n\nThis is much easier to use than SQL-style wildcards (see, regular\nexpressions are good for something). Because of this, I took out\nSQL-style wildcards. I&#39;ll put them back if someone complains, but\ntheir removal simplifies the code a lot.\n\nYou can use fetch() and first() to search for text in the parse tree,\nnot just tags. There are new alias methods fetchText() and firstText()\ndesigned for this purpose. As with searching for tags, you can pass in\na string, a regular expression object, or a method to match your text.\n\nIf you pass in something besides a map to the attrs argument of\nfetch() or first(), Beautiful Soup will assume you want to match that\nthing against the &quot;class&quot; attribute. When you&#39;re scraping\nwell-structured HTML, this makes your code a lot cleaner.\n\n1.x and 2.x both let you call a Tag object as a shorthand for\nfetch(). For instance, foo(&quot;bar&quot;) is a shorthand for\nfoo.fetch(&quot;bar&quot;). In 2.x, you can also access a specially-named member\nof a Tag object as a shorthand for first(). For instance, foo.barTag\nis a shorthand for foo.first(&quot;bar&quot;). By chaining these shortcuts you\ntraverse a tree in very little code: for header in\nsoup.bodyTag.pTag.tableTag(&#39;th&#39;):\n\nIf an element relationship (like parent or next) doesn&#39;t apply to a\ntag, it&#39;ll now show up Null instead of None. first() will also return\nNull if you ask it for a nonexistent tag. Null is an object that&#39;s\njust like None, except you can do whatever you want to it and it&#39;ll\ngive you Null instead of throwing an error.\n\nThis lets you do tree traversals like soup.htmlTag.headTag.titleTag\nwithout having to worry if the intermediate stages are actually\nthere. Previously, if there was no &#39;head&#39; tag in the document, headTag\nin that instance would have been None, and accessing its &#39;titleTag&#39;\nmember would have thrown an AttributeError. Now, you can get what you\nwant when it exists, and get Null when it doesn&#39;t, without having to\ndo a lot of conditionals checking to see if every stage is None.\n\nThere are two new relations between page elements: previousSibling and\nnextSibling. They reference the previous and next element at the same\nlevel of the parse tree. For instance, if you have HTML like this:\n\n  &lt;p&gt;&lt;ul&gt;&lt;li&gt;Foo&lt;br /&gt;&lt;li&gt;Bar&lt;/ul&gt;\n\nThe first &#39;li&#39; tag has a previousSibling of Null and its nextSibling\nis the second &#39;li&#39; tag. The second &#39;li&#39; tag has a nextSibling of Null\nand its previousSibling is the first &#39;li&#39; tag. The previousSibling of\nthe &#39;ul&#39; tag is the first &#39;p&#39; tag. The nextSibling of &#39;Foo&#39; is the\n&#39;br&#39; tag.\n\nI took out the ability to use fetch() to find tags that have a\nspecific list of contents. See, I can&#39;t even explain it well. It was\nreally difficult to use, I never used it, and I don&#39;t think anyone\nelse ever used it. To the extent anyone did, they can probably use\nfetchText() instead. If it turns out someone needs it I&#39;ll think of\nanother solution.\n\n== Tree manipulation ==\n\nYou can add new attributes to a tag, and delete attributes from a\ntag. In 1.x you could only change a tag&#39;s existing attributes.\n\n== Porting Considerations ==\n\nThere are three changes in 2.0 that break old code:\n\nIn the post-1.2 release you could pass in a function into fetch(). The\nfunction took a string, the tag name. In 2.0, the function takes the\nactual Tag object.\n\nIt&#39;s no longer to pass in SQL-style wildcards to fetch(). Use a\nregular expression instead.\n\nThe different parsing algorithm means the parse tree may not be shaped\nlike you expect. This will only actually affect you if your code uses\none of the affected parts. I haven&#39;t run into this problem yet while\nporting my code.\n   ```\n   \n  \n  \n   ### 1.2\n   ```\n   Applied patch from Ben Last (ben at benlast dot com) that made\nTag.renderContents() correctly handle Unicode.\n\nMade BeautifulStoneSoup even dumber by making it not implicitly close\na tag when another tag of the same type is encountered; only when an\nactual closing tag is encountered. This change courtesy of Fuzzy (mike\nat pcblokes dot com). BeautifulSoup still works as before.\n   ```\n   \n  \n  \n   ### 1.1\n   ```\n   Added more &#39;nestable&#39; tags. Changed popping semantics so that when a\nnestable tag is encountered, tags are popped up to the previously\nencountered nestable tag (of whatever kind). I will revert this if\nenough people complain, but it should make more people&#39;s lives easier\nthan harder. This enhancement was suggested by Anthony Baxter (anthony\nat interlink dot com dot au).\n   ```\n   \n  \n  \n   ### 1.0\n   ```\n   Initial release.\n   ```\n   \n  \n</details>\n\n\n \n\n<details>\n  <summary>Links</summary>\n  \n  - PyPI: https://pypi.org/project/beautifulsoup4\n  - Changelog: https://pyup.io/changelogs/beautifulsoup4/\n  - Homepage: http://www.crummy.com/software/BeautifulSoup/bs4/\n</details>\n\n","created_at":"2018-05-16T21:55:00Z","updated_at":"2018-05-16T21:55:00Z","closed_at":null,"merged_at":null,"merge_commit_sha":null,"assignee":null,"assignees":[],"requested_reviewers":[],"requested_teams":[],"labels":[],"milestone":null,"commits_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2/commits","review_comments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2/comments","review_comment_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/comments{/number}","comments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/2/comments","statuses_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/statuses/fae310c6c0ee7bb24d057ead121dc4ae2b3ac07f","head":{"label":"woctezuma:pyup-pin-beautifulsoup4-4.6.0","ref":"pyup-pin-beautifulsoup4-4.6.0","sha":"fae310c6c0ee7bb24d057ead121dc4ae2b3ac07f","user":{"login":"woctezuma","id":570669,"avatar_url":"https://avatars0.githubusercontent.com/u/570669?v=4","gravatar_id":"","url":"https://api.github.com/users/woctezuma","html_url":"https://github.com/woctezuma","followers_url":"https://api.github.com/users/woctezuma/followers","following_url":"https://api.github.com/users/woctezuma/following{/other_user}","gists_url":"https://api.github.com/users/woctezuma/gists{/gist_id}","starred_url":"https://api.github.com/users/woctezuma/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/woctezuma/subscriptions","organizations_url":"https://api.github.com/users/woctezuma/orgs","repos_url":"https://api.github.com/users/woctezuma/repos","events_url":"https://api.github.com/users/woctezuma/events{/privacy}","received_events_url":"https://api.github.com/users/woctezuma/received_events","type":"User","site_admin":false},"repo":{"id":133636421,"name":"SensCritique-Takeout","full_name":"woctezuma/SensCritique-Takeout","owner":{"login":"woctezuma","id":570669,"avatar_url":"https://avatars0.githubusercontent.com/u/570669?v=4","gravatar_id":"","url":"https://api.github.com/users/woctezuma","html_url":"https://github.com/woctezuma","followers_url":"https://api.github.com/users/woctezuma/followers","following_url":"https://api.github.com/users/woctezuma/following{/other_user}","gists_url":"https://api.github.com/users/woctezuma/gists{/gist_id}","starred_url":"https://api.github.com/users/woctezuma/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/woctezuma/subscriptions","organizations_url":"https://api.github.com/users/woctezuma/orgs","repos_url":"https://api.github.com/users/woctezuma/repos","events_url":"https://api.github.com/users/woctezuma/events{/privacy}","received_events_url":"https://api.github.com/users/woctezuma/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/woctezuma/SensCritique-Takeout","description":"SensCritique Takeout","fork":false,"url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout","forks_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/forks","keys_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/keys{/key_id}","collaborators_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/teams","hooks_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/hooks","issue_events_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/events{/number}","events_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/events","assignees_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/assignees{/user}","branches_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/branches{/branch}","tags_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/tags","blobs_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/refs{/sha}","trees_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/trees{/sha}","statuses_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/statuses/{sha}","languages_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/languages","stargazers_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/stargazers","contributors_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/contributors","subscribers_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/subscribers","subscription_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/subscription","commits_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/commits{/sha}","git_commits_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/commits{/sha}","comments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/comments{/number}","issue_comment_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/comments{/number}","contents_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/contents/{+path}","compare_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/compare/{base}...{head}","merges_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/merges","archive_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/downloads","issues_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues{/number}","pulls_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls{/number}","milestones_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/milestones{/number}","notifications_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/labels{/name}","releases_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/releases{/id}","deployments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/deployments","created_at":"2018-05-16T08:43:26Z","updated_at":"2018-05-16T21:54:54Z","pushed_at":"2018-05-16T21:54:59Z","git_url":"git://github.com/woctezuma/SensCritique-Takeout.git","ssh_url":"git@github.com:woctezuma/SensCritique-Takeout.git","clone_url":"https://github.com/woctezuma/SensCritique-Takeout.git","svn_url":"https://github.com/woctezuma/SensCritique-Takeout","homepage":null,"size":2,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"archived":false,"open_issues_count":1,"license":{"key":"mit","name":"MIT License","spdx_id":"MIT","url":"https://api.github.com/licenses/mit"},"forks":0,"open_issues":1,"watchers":0,"default_branch":"master"}},"base":{"label":"woctezuma:master","ref":"master","sha":"877e9ff69d4cd8a3c020cb1425d9912a646955ea","user":{"login":"woctezuma","id":570669,"avatar_url":"https://avatars0.githubusercontent.com/u/570669?v=4","gravatar_id":"","url":"https://api.github.com/users/woctezuma","html_url":"https://github.com/woctezuma","followers_url":"https://api.github.com/users/woctezuma/followers","following_url":"https://api.github.com/users/woctezuma/following{/other_user}","gists_url":"https://api.github.com/users/woctezuma/gists{/gist_id}","starred_url":"https://api.github.com/users/woctezuma/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/woctezuma/subscriptions","organizations_url":"https://api.github.com/users/woctezuma/orgs","repos_url":"https://api.github.com/users/woctezuma/repos","events_url":"https://api.github.com/users/woctezuma/events{/privacy}","received_events_url":"https://api.github.com/users/woctezuma/received_events","type":"User","site_admin":false},"repo":{"id":133636421,"name":"SensCritique-Takeout","full_name":"woctezuma/SensCritique-Takeout","owner":{"login":"woctezuma","id":570669,"avatar_url":"https://avatars0.githubusercontent.com/u/570669?v=4","gravatar_id":"","url":"https://api.github.com/users/woctezuma","html_url":"https://github.com/woctezuma","followers_url":"https://api.github.com/users/woctezuma/followers","following_url":"https://api.github.com/users/woctezuma/following{/other_user}","gists_url":"https://api.github.com/users/woctezuma/gists{/gist_id}","starred_url":"https://api.github.com/users/woctezuma/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/woctezuma/subscriptions","organizations_url":"https://api.github.com/users/woctezuma/orgs","repos_url":"https://api.github.com/users/woctezuma/repos","events_url":"https://api.github.com/users/woctezuma/events{/privacy}","received_events_url":"https://api.github.com/users/woctezuma/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/woctezuma/SensCritique-Takeout","description":"SensCritique Takeout","fork":false,"url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout","forks_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/forks","keys_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/keys{/key_id}","collaborators_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/teams","hooks_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/hooks","issue_events_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/events{/number}","events_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/events","assignees_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/assignees{/user}","branches_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/branches{/branch}","tags_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/tags","blobs_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/refs{/sha}","trees_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/trees{/sha}","statuses_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/statuses/{sha}","languages_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/languages","stargazers_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/stargazers","contributors_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/contributors","subscribers_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/subscribers","subscription_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/subscription","commits_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/commits{/sha}","git_commits_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/git/commits{/sha}","comments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/comments{/number}","issue_comment_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/comments{/number}","contents_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/contents/{+path}","compare_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/compare/{base}...{head}","merges_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/merges","archive_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/downloads","issues_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues{/number}","pulls_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls{/number}","milestones_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/milestones{/number}","notifications_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/labels{/name}","releases_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/releases{/id}","deployments_url":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/deployments","created_at":"2018-05-16T08:43:26Z","updated_at":"2018-05-16T21:54:54Z","pushed_at":"2018-05-16T21:54:59Z","git_url":"git://github.com/woctezuma/SensCritique-Takeout.git","ssh_url":"git@github.com:woctezuma/SensCritique-Takeout.git","clone_url":"https://github.com/woctezuma/SensCritique-Takeout.git","svn_url":"https://github.com/woctezuma/SensCritique-Takeout","homepage":null,"size":2,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"archived":false,"open_issues_count":1,"license":{"key":"mit","name":"MIT License","spdx_id":"MIT","url":"https://api.github.com/licenses/mit"},"forks":0,"open_issues":1,"watchers":0,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2"},"html":{"href":"https://github.com/woctezuma/SensCritique-Takeout/pull/2"},"issue":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/2"},"comments":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/issues/2/comments"},"review_comments":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2/comments"},"review_comment":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/pulls/2/commits"},"statuses":{"href":"https://api.github.com/repos/woctezuma/SensCritique-Takeout/statuses/fae310c6c0ee7bb24d057ead121dc4ae2b3ac07f"}},"author_association":"NONE","merged":false,"mergeable":null,"rebaseable":null,"mergeable_state":"unknown","merged_by":null,"comments":0,"review_comments":0,"maintainer_can_modify":false,"commits":1,"additions":1,"deletions":1,"changed_files":1}}
{"actor":{"display_login":"pyup-bot"}}