Closed talamus closed 5 years ago
Short answer: suuuuuuure, but not really
Long answer: I feel like this would be better handled outside of chevron. Before today, chevron could almost do this with just a simple custom datatype, but I needed to add just a few lines of code in order to get custom falsy data types to output as something besides empty strings.
Here's an example of how to do this outside of chevron
#!/usr/bin/env python
import chevron
class CustomData(dict):
class LowercaseBool:
_CHEVRON_return_scope_when_falsy = True
def __init__(self, value):
self.value = value
def __bool__(self):
return self.value
__nonzero__ = __bool__
def __str__(self):
if self.value:
return 'true'
return 'false'
def __getitem__(self, key):
item = dict.__getitem__(self, key)
if isinstance(item, dict):
return CustomData(item)
if isinstance(item, bool):
return self.LowercaseBool(item)
return item
data = {
'truthy': True,
'falsy': False,
}
template = '''\
{{# truthy}}
Truthy is {{ truthy }} and Falsy is {{ falsy }}
{{/ truthy}}
{{# falsy }}
This will never print {{.}}
{{/ falsy }}
'''
print(chevron.render(template, CustomData(data)))
# Truthy is true and Falsy is false
You should be able to convert datetime objects in a similar fashion too, all of this with no extra logic inside of chevron, and no (well, very little, I had to add those lines in) overhead unless you want to do this.
I hope this does what you need it to, if not let me know. I'm not opposed to chevron becoming better, I just want to make sure chevron stays spec compliant, compatible with old versions of python, and fast.
I'll release a version with this soonish, I want to checkout some of the other issues and PRs first (If I don't, just comment here or email me and yell at me).
Excellent! Much better idea that I was going to hack together.
(I had a small worry about the truthiness of the "false" string, but then I read your code sample with open eyes. The value and the string representation are separated in there.)
Hey talamus,
This is works except for the looping over lists, just have to expand CustomData a bit... https://gist.github.com/noahmorrison/4810ee5cf33f694da2449952b9205809
(please let me know if you got this email, not 100% sure it'll get to you)
Noah
On Fri, Aug 24, 2018 at 8:28 AM, Tero Niemi notifications@github.com wrote:
Now when I think about this -- there is a possibility this approach can create a small problem, because the "false" (a string) is actually True.
Consider some JSON data:
{ "entities": [ { "type": "dog", "mythical": false },{ "type": "kerberos", "mythical": true } ], "this_is_null": null }
And a template:
{{#entities}} type: {{type}} mythical: {{mythical}} {{#mythical}} "A truly mythical creature!" {{/mythical}} {{^mythical}} "An ordinary animal" {{/mythical}} {{/entities}}
The desired output would be:
type: dog mythical: false "An ordinary animal" type: kerberos mythical: true "A truly mythical creature!"
Note the small case "true" and "false" combined with working boolean logic. (The same thing would happen if someone would like to output None as "null".)
I think we are going to need a separate getValue() and toString(), so to speak...
— You are receiving this because you modified the open/close state. Reply to this email directly, view it on GitHub https://github.com/noahmorrison/chevron/issues/35#issuecomment-415744145, or mute the thread https://github.com/notifications/unsubscribe-auth/AHEujWaez3TYicuu2rjQRKu0XI1ZXLFfks5uT_FZgaJpZM4WJm7m .
Hello, Could it be possible to have an optional replacer function for the values, like the one in JSON.stringify()?
Our problem is that our booleans are getting written out as "True" and "False" when the template we are writing them expects them to be in "true" and "false" format.
Of course -- the same thing could be used to convert datetime objects into some specific format, like these beautifully ugly "/Date(1239018869048)/" .Net things.