Knio / dominate

Dominate is a Python library for creating and manipulating HTML documents using an elegant DOM API. It allows you to write HTML pages in pure Python very concisely, which eliminate the need to learn another template language, and to take advantage of the more powerful features of Python.
GNU Lesser General Public License v3.0
1.72k stars 108 forks source link

Suppress rendering of boolean attributes when the value is False #111

Closed golightlyb closed 5 years ago

golightlyb commented 5 years ago

The values "true" and "false" are not allowed on boolean attributes. To represent a false value, the attribute has to be omitted altogether.

HTML 5.2, W3C Recommendation, 14 December 2017 https://www.w3.org/TR/html5/infrastructure.html#boolean-attribute

Expected behaviour is demonstrated by the included test case:

def test_boolean_attributes():
  assert input(type="checkbox", checked=True).render() == \
      '<input checked="checked" type="checkbox">'
  assert input(type="checkbox", checked=False).render() == \
      '<input type="checkbox">'
coveralls commented 5 years ago

Coverage Status

Coverage increased (+0.2%) to 96.86% when pulling 074cde6e64ba32a241cf08111a5bf3ba7cc3d996 on golightlyb:fix-boolean-attributes into f24945f0cbc7259f1ba02a722458fc231a9bc961 on Knio:master.

Knio commented 5 years ago

Thanks for finding this bug.

I am a bit hesitant about this PR, as some time in the future I'm going to receive a bug report about tag['data-foo'] = False not correctly rendering as <tag data-foo="false">. There is no easy way to fix this without maintaining a whitelist of tags and their boolean attributes.

However, since I'm already special casing the True value it seems only consistent to do both (and I can see the value where you just want to pass a boolean and have it render correctly without having to make your own conditionals), and since this is clearly a bug in more common tags, it seems like a good idea.

golightlyb commented 5 years ago

Thanks for the review - I have made those changes.

RE: tag['data-foo'] = False not correctly rendering as <tag data-foo="false">

I'd suggest, if that's what someone wants, do explicitly: tag['data-foo'] = "false"

Edit

As an aside, for example:this is what you would have to do for example with the spellcheck attribute, which is uniquely weird and is the only attribute that I know of that takes only the strings "true" or "false" (and nothing else)

golightlyb commented 5 years ago

You might be interested in this project I made that handles the various boolean and boolean-enumeration types:

Strictdom is a strictly typed wrapper over Dominate