Jinja Control Structure: Conditional Filtering in Loops
n
nn
n
How It Works
nThe conditional expression is added at the end of the `for` loop’s declaration using the `if` keyword. The expression is evaluated for each item in the sequence, and only those items for which the condition is `true` will be included in the loop’s iteration. This is a significant advantage because it ensures that special loop variables like `loop.index` and `loop.length` will accurately reflect the items being iterated over, rather than counting the items that were skipped.n
Syntax
n
{% for item in sequence if condition %}n <!-- Code to render for items that meet the condition -->n{% endfor %}
nn
nn
n
Demonstration with Code Samples
nHere are some practical examples of how to use conditional filtering to control your loop’s behavior.n
1. Skipping Hidden Users
nThis is a classic use case for conditional filtering, as it allows you to easily display a list of users while hiding those with a specific property.nnJinja2 Templaten
{% set users = [n {'username': 'Alice', 'hidden': false},n {'username': 'Bob', 'hidden': true},n {'username': 'Charlie', 'hidden': false}n] %}n<ul>n{% for user in users if not user.hidden %}n <li>{{ loop.index }}. {{ user.username|e }}</li>n{% endfor %}n</ul>
nExplanation: The loop is set to only iterate over users where `user.hidden` is not true. This means “Bob” is skipped, and the loop processes “Alice” and “Charlie.” Crucially, the `loop.index` for “Charlie” will be `2`, as the loop correctly only counts the items it renders.nn
nn
n
2. Displaying Only In-Stock Products
nThis example demonstrates how to filter a list of products to display only those that are currently in stock, which is useful for an e-commerce website.nnJinja2 Templaten
{% set products = [n {'name': 'Laptop', 'in_stock': true},n {'name': 'Mouse', 'in_stock': false},n {'name': 'Keyboard', 'in_stock': true}n] %}n<table>n <thead><tr><th>#</th><th>Product Name</th></tr></thead>n <tbody>n {% for product in products if product.in_stock %}n <tr>n <td>{{ loop.index }}</td>n <td>{{ product.name|e }}</td>n </tr>n {% endfor %}n </tbody>n</table>
nExplanation: The loop only processes products where `in_stock` is true. The `Mouse` product is skipped, and the table correctly displays the `Laptop` as row 1 and the `Keyboard` as row 2. The `loop.index` variable is automatically correct for the filtered list.nn
n
