sablon icon indicating copy to clipboard operation
sablon copied to clipboard

Conditionals: allow string comparism

Open ChrisKaun opened this issue 4 years ago • 4 comments

We have a unique usecase for one of our customers who would like to display a string property dependent on it's value in different font-colors. This would require us to do something like this:

«car.color:if(val == 'green')»
  «=car.color» but marked in green
«car.color:elsif(val == 'red')»
  «=car.color» but marked in red
«car.color:endIf»

Of course it would be possible to create a getter method in rails that checks each color but since this is a really unique use case it wouldn't make any sense to hardcode this into our software logic.

ChrisKaun avatar Nov 27 '20 07:11 ChrisKaun

The idea behind the sablon template language is that templates should contain the least amount of knowledge possible. The reason is that they are hard to test and prone to errors when making changes. For that reason, such convenience operators are not provided. As you already deduced, the way to achieve this, would be by defining predicate methods on some object that you can check from the template.

senny avatar Nov 27 '20 08:11 senny

@ChrisKaun another good option might be to pre-process the context supplied by the user so you can streamline processing on the template side. I had several areas of complex logic and instead of trying to process that in the template I pre-processed stuff into several chunks of HTML and injected that into the document. One additional benefit of having most of the logic done outside of the template is that it lends itself to easier testing and validation.

stadelmanma avatar Nov 28 '20 00:11 stadelmanma

The idea behind the sablon template language is that templates should contain the least amount of knowledge possible. The reason is that they are hard to test and prone to errors when making changes. For that reason, such convenience operators are not provided. As you already deduced, the way to achieve this, would be by defining predicate methods on some object that you can check from the template.

The problem with his approach is that each time a new color must be added the methods must be updated.

another good option might be to pre-process the context supplied by the user so you can streamline processing on the template side. I had several areas of complex logic and instead of trying to process that in the template I pre-processed stuff into several chunks of HTML and injected that into the document. One additional benefit of having most of the logic done outside of the template is that it lends itself to easier testing and validation.

If I understand that correctly this still would require changes in the pre-process logic each time the customer of ours requires a new color, which I would love to skip.

ChrisKaun avatar Nov 30 '20 07:11 ChrisKaun

@ChrisKaun Using sablon within a rails framework, I've achieved what you're suggesting by wrapping the string in ActiveSupport::StringInquirer.

«car.color:if(green?)»
  «=car.color» but marked in green
«car.color:elsif(red?)»
  «=car.color» but marked in red
«car.color:endIf»

arvanasse avatar Dec 02 '21 01:12 arvanasse