Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Arrow functions #874

Open
wants to merge 5 commits into
base: master
Choose a base branch
from

Conversation

antoineveldhoven
Copy link
Contributor

@antoineveldhoven antoineveldhoven commented Oct 11, 2023

Aiming to resolve #652

I'm not (yet) quite convinced if this is the way to go; would really like to get some discussion going on how to approach this and eventually get this fixed and merged.

Implementation of arrow functions in filters:

sort
filter
map
reduce

Object manipulation is not really supported; this implementation accepts a arrowFunction (Twig syntax) which is compiled and parsed as a new (runtime) template. The return values (e.g. output) of the arrowFunction are delegated to their respective JS functions.

As previously stated: this is merely a functional (read dirty) workaround; but for most of the use cases it will do the trick.

@lodewijkbovy
Copy link

Would be great to see this one merged too!

@willrowe
Copy link
Collaborator

willrowe commented Nov 7, 2023

I'm in the process of reviewing this, but I'm not sure if this approach is going to work. I think the body of the arrow function will need to be parsed as an expression. I'm trying to come up with a more general way for it to be compiled so a simple function can be called by the filters that support it.

@ericmorand
Copy link
Contributor

ericmorand commented Dec 2, 2023

I'm not sure this will work.

It is perfectly possible to register filters (and I assume functions and tests) that return promises:

import Twig from "twig";

import pkg from 'twig';
const {twig} = pkg;

Twig.extendFilter('asyncUpper', (value) => Promise.resolve(value.toUpperCase()));

const t = twig({
    data: '{{ "a"|asyncUpper}}'
});

t.renderAsync().then(console.log); // outputs "A"

How would the arrow function behave in this case?

{{ [4, 5]|sort((a, b) => a|asyncUpper < b ? -1 : 1)|join() }}

I think some tests need to be added to ensure that the arrow function support expression and async expressions specifically. The current tests suite provided by this PR is far from covering all the possible expressions that Twig accepts as the body of the arrow function. Moreso because Twig.js supports asynchronous expressions.

Note that this issue applies to every element of the language that accepts an arrow function as parameter: has every, has some, map from the top of my head.

@michaeldietiker
Copy link

Any updates on arrow function support?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Add filter, map and reduce filters with support for arrow functions
5 participants