Title: Add utility functions to test for legal XML characters and names · Issue #139489 · python/cpython · GitHub
Open Graph Title: Add utility functions to test for legal XML characters and names · Issue #139489 · python/cpython
X Title: Add utility functions to test for legal XML characters and names · Issue #139489 · python/cpython
Description: Feature or enhancement It is well known fact that some characters (such as < or &) must be escaped in XML and HTML, and that attribute values must be quoted. It is less known fact (unless you specially looked for it) that not all charact...
Open Graph Description: Feature or enhancement It is well known fact that some characters (such as < or &) must be escaped in XML and HTML, and that attribute values must be quoted. It is less known fact (unless you speci...
X Description: Feature or enhancement It is well known fact that some characters (such as < or &) must be escaped in XML and HTML, and that attribute values must be quoted. It is less known fact (unless yo...
Opengraph URL: https://github.com/python/cpython/issues/139489
X: @github
Domain: github.com
{"@context":"https://schema.org","@type":"DiscussionForumPosting","headline":"Add utility functions to test for legal XML characters and names","articleBody":"# Feature or enhancement\n\nIt is well known fact that some characters (such as `\u003c` or `\u0026`) must be escaped in XML and HTML, and that attribute values must be quoted. It is less known fact (unless you specially looked for it) that not all characters can be included in XML, even if escaped. For example, XML cannot contain the null character.\n\nThere is also restriction on names of elements and attributes. They cannot contain `\u003c`, `\u003e`, `/`, `!`, `?`, spaces and many other characters. But unlike to Python identifiers, `-`, `:`, `.`, etc are acceptable. The list of valid and invalid characters is pretty long. In the case when the user input is used for element or attribute names without validation, this can even lead to XML injection vulnerability ([CVE-2025-9375](https://nvd.nist.gov/vuln/detail/CVE-2025-9375))\n\nSo, I think that it would be useful to provide standard functions to validate XML characters and names in the stdlib. `xml.sax.saxutils` looks an appropriate place, it already has `escape()` and `quoteattr()` utilities.\n\nWe can also provide functions to \"sanitize\" XML characters, similar to `sanitize_xml()` in `Lib/test/libregrtest/utils.py`, but more general. This is similar to old issue #63014.\n\nNow, the problem is that there are two standards of XML: 1.0 and 1.1. The former is much more popular. And they have different definitions of legal characters. There are also restricted characters in XML 1.1 which cannot be used in \"well-formed\" documents and parsed entities. There is also a set of characters (version depending) using which legal but is discouraged. Should we have several functions or several parameters to specify the XML version and other options?\n\nhttps://www.w3.org/TR/xml/#charsets\nhttps://www.w3.org/TR/xml11/#charsets\n\nFortunately, the syntax for names is the same in XML 1.0 and 1.1.\n\nhttps://www.w3.org/TR/xml/#NT-Name\nhttps://www.w3.org/TR/xml11/#NT-Name\n\nWe can also add a similar set of functions for HTML.\n\n\u003c!-- gh-linked-prs --\u003e\n### Linked PRs\n* gh-139768\n* gh-149412\n* gh-149641\n* gh-149652\n\u003c!-- /gh-linked-prs --\u003e\n","author":{"url":"https://github.com/serhiy-storchaka","@type":"Person","name":"serhiy-storchaka"},"datePublished":"2025-10-02T08:44:00.000Z","interactionStatistic":{"@type":"InteractionCounter","interactionType":"https://schema.org/CommentAction","userInteractionCount":8},"url":"https://github.com/139489/cpython/issues/139489"}
| route-pattern | /_view_fragments/issues/show/:user_id/:repository/:id/issue_layout(.:format) |
| route-controller | voltron_issues_fragments |
| route-action | issue_layout |
| fetch-nonce | v2:1cbfd368-c210-e94e-e2bf-0c1d18fc05a7 |
| current-catalog-service-hash | 81bb79d38c15960b92d99bca9288a9108c7a47b18f2423d0f6438c5b7bcd2114 |
| request-id | D09A:7F3E2:205D8AF:2F07695:6A54F240 |
| html-safe-nonce | 1891c70671eb5ed7bebe713ce677daae30597edeb743155c5b49491589e01e76 |
| visitor-payload | eyJyZWZlcnJlciI6IiIsInJlcXVlc3RfaWQiOiJEMDlBOjdGM0UyOjIwNUQ4QUY6MkYwNzY5NTo2QTU0RjI0MCIsInZpc2l0b3JfaWQiOiI4NTk2NTMyOTU2MzM1NzY0MDMzIiwicmVnaW9uX2VkZ2UiOiJpYWQiLCJyZWdpb25fcmVuZGVyIjoiaWFkIn0= |
| visitor-hmac | cecff474a43cb2b7fa7c6296d614f81a70c3a0ef32b976b9d03f7e493ff4860c |
| hovercard-subject-tag | issue:3476640479 |
| github-keyboard-shortcuts | repository,issues,copilot |
| google-site-verification | Apib7-x98H0j5cPqHWwSMm6dNU4GmODRoqxLiDzdx9I |
| octolytics-url | https://collector.github.com/github/collect |
| analytics-location | / |
| fb:app_id | 1401488693436528 |
| apple-itunes-app | app-id=1477376905, app-argument=https://github.com/_view_fragments/issues/show/python/cpython/139489/issue_layout |
| twitter:image | https://opengraph.githubassets.com/bea8334c8f73abdda8a3d26ef190f30d1a276d206ee3dbdad67db5336f2c4ea4/python/cpython/issues/139489 |
| twitter:card | summary_large_image |
| og:image | https://opengraph.githubassets.com/bea8334c8f73abdda8a3d26ef190f30d1a276d206ee3dbdad67db5336f2c4ea4/python/cpython/issues/139489 |
| og:image:alt | Feature or enhancement It is well known fact that some characters (such as < or &) must be escaped in XML and HTML, and that attribute values must be quoted. It is less known fact (unless you speci... |
| og:image:width | 1200 |
| og:image:height | 600 |
| og:site_name | GitHub |
| og:type | object |
| og:author:username | serhiy-storchaka |
| hostname | github.com |
| expected-hostname | github.com |
| None | eae2aab99907699a22d2c8449aa683ca74454fca87211b98f7c7b722086b2839 |
| turbo-cache-control | no-preview |
| go-import | github.com/python/cpython git https://github.com/python/cpython.git |
| octolytics-dimension-user_id | 1525981 |
| octolytics-dimension-user_login | python |
| octolytics-dimension-repository_id | 81598961 |
| octolytics-dimension-repository_nwo | python/cpython |
| octolytics-dimension-repository_public | true |
| octolytics-dimension-repository_is_fork | false |
| octolytics-dimension-repository_network_root_id | 81598961 |
| octolytics-dimension-repository_network_root_nwo | python/cpython |
| turbo-body-classes | logged-out env-production page-responsive |
| disable-turbo | false |
| browser-stats-url | https://api.github.com/_private/browser/stats |
| browser-errors-url | https://api.github.com/_private/browser/errors |
| release | dd26d3896747463b6bd56edd5e290edb595c3cbc |
| ui-target | full |
| theme-color | #1e2327 |
| color-scheme | light dark |
Links:
Viewport: width=device-width