Sign In
Sign In
  1. Home
  2. CONSTRUIR
  3. Manipulação de dados
  4. Manipulação de dados - Avançada
CONSTRUIR
49 articles
Categorias
Tradução em massa
Etapas no Flow Builder11
Iniciar Intent1
🪄 Gerar com IA4
Respostas
Carregamento de ficheiros
Transferência para chat ao vivo7
Transferência para tíquetes1
APIs
Manipulação de dados2
Manipulação de dados - Avançada
Manipulação de dados - Exemplos
Variáveis
Lógica e condições2
Entrada do utilizador
[Descontinuado] Modo de rascunho e construtor avançado10
Trace no Flow Builder
Use Cases5

Manipulação de dados - Avançada

Aprenda a sintaxe avançada de templates Jinja, filtros e acesso a atributos para manipular variáveis na etapa de Manipulação de dados.

Updated on 24 de setembro de 2026

O que é Jinja?

Jinja é um mecanismo de templates que permite formatar texto; sua sintaxe é inspirada no Django e no Python.

Os templates Jinja são simplesmente arquivos de texto... Um template contém variáveis e/ou expressões, que são substituídas por valores quando o template é renderizado; e tags, que controlam a lógica do template.

Você pode consultar a documentação oficial do Jinja: aqui

Funções básicas

Manipule entradas com instruções simples (filtros e expressões) para obter o resultado desejado.

Por exemplo, obtenha a lista de preços de todos os produtos e arredonde para 2 casas decimais.

Text
products | map(attribute='item.price') | map('round', 2) | list

Você só precisa conhecer algumas coisas:

Acesso a atributos

Você pode acessar atributos com um ponto ou colchetes (para variáveis)

Python
foo = { bar: 'hey' }
foo.bar # => 'hey'

var1 = 'bar'
foo[var1] # => 'hey'

Atribuições

As atribuições usam a tag set e podem ter vários destinos:

Python
{% set prices = products | map(attribute='item.price') | list %}
{% set navigation = [('index.html', 'Index'), ('about.html', 'About')] %}
{% set key, value = 'my_key', 'my_value' %}

Expressões

Elas funcionam de forma muito semelhante ao Python comum; mesmo que você não trabalhe com Python, deve sentir-se à vontade com isso.

  • Literais
    A forma mais simples de expressões são os literais. Literais são representações de objetos Python, como strings e números. Existem os seguintes literais:

    • "Hello World"Tudo entre duas aspas duplas ou simples é uma string. Elas são úteis sempre que você precisar de uma string no template (por exemplo, como argumentos de chamadas de funções e filtros, ou apenas para estender ou incluir um template).

    • 42 / 123_456Inteiros são números inteiros sem parte decimal. O caractere ‘_’ pode ser usado para separar grupos e facilitar a leitura.

    • 42.23 / 42.1e2 / 123_456.789Números de ponto flutuante podem ser escritos usando ‘.’ como separador decimal. Também podem ser escritos em notação científica, com ‘e’ maiúsculo ou minúsculo para indicar o expoente. O caractere ‘_’ pode separar grupos para facilitar a leitura, mas não pode ser usado na parte do expoente.

    • ['list', 'of', 'objects']Tudo entre dois colchetes é uma lista. Listas são úteis para armazenar dados sequenciais a serem iterados.

    • ('tuple', 'of', 'values')Tuplas são como listas que não podem ser modificadas (“imutáveis”). Se uma tupla tiver apenas um item, ela deverá ser seguida por uma vírgula (('1-tuple',)). Tuplas geralmente são usadas para representar itens com dois ou mais elementos. Consulte o exemplo de lista acima para obter mais detalhes.

    • {'dict': 'of', 'key': 'and', 'value': 'pairs'}Um dict em Python é uma estrutura que combina chaves e valores. As chaves devem ser únicas e sempre ter exatamente um valor.

    • true / false true é sempre verdadeiro e false é sempre falso.

      Observação: as constantes especiais true, false e none são realmente escritas em minúsculas. Como isso já causou confusão no passado (True era expandido para uma variável indefinida considerada falsa), agora as três também podem ser escritas em maiúsculas (True, False e None). No entanto, por consistência (todos os identificadores são escritos em minúsculas), você deve usar as versões minúsculas.

  • Matemática
    Permite calcular com valores. Os seguintes operadores são compatíveis:

    • +Adiciona dois objetos. Normalmente, os objetos são números, mas, se ambos forem strings ou listas, você poderá concatená-los dessa forma. No entanto, essa não é a forma preferida de concatenar strings! Para concatenação de strings, consulte o operador ~ . {{ 1 + 1 }} é 2.

    • -Subtrai o segundo número do primeiro. {{ 3 - 2 }} é 1.

    • /Divide dois números. O valor retornado será um número de ponto flutuante. {{ 1 / 2 }} é {{ 0.5 }}.

    • //Divide dois números e retorna o resultado inteiro truncado. {{ 20 // 7 }} é 2.

    • %Calcula o resto de uma divisão inteira. {{ 11 % 7 }} é 4.

    • *Multiplica o operando esquerdo pelo direito. {{ 2 * 2 }} retornaria 4. Isso também pode ser usado para repetir uma string várias vezes. {{ '=' * 80 }} imprimiria uma barra com 80 sinais de igualdade.

    • **Eleva o operando esquerdo à potência do operando direito. {{ 2**3 }} retornaria 8. Ao contrário do Python, potências encadeadas são avaliadas da esquerda para a direita. {{ 3**3**3 }} é avaliado como (3**3)**3, mas seria avaliado como 3**(3**3) no Python. Use parênteses para deixar explícita a ordem desejada.

  • Comparações

    • ==Compara dois objetos quanto à igualdade.

    • !=Compara dois objetos quanto à desigualdade.

    • > verdadeiro se o lado esquerdo for maior que o lado direito.

    • >= verdadeiro se o lado esquerdo for maior ou igual ao lado direito.

    • < verdadeiro se o lado esquerdo for menor que o lado direito.

    • <= verdadeiro se o lado esquerdo for menor ou igual ao lado direito.

  • Lógica

    • eRetorna true se o operando esquerdo e o direito forem true.

    • ouRetorna true se o operando esquerdo ou o direito for true.

    • nãonega uma instrução (veja abaixo).

    • (expr)Os parênteses agrupam uma expressão.

      Observação: os operadores é e in também permitem negação usando uma notação infixa: foo is not bar e foo not in bar em vez de not foo is bar e not foo in bar. Todas as outras expressões exigem uma notação prefixa: not (foo and bar).

  • Outros operadores
    Os seguintes operadores são muito úteis, mas não se encaixam em nenhuma das outras duas categorias:

    • inExecuta um teste de contenção de sequência/mapeamento. Retorna true se o operando esquerdo estiver contido no direito. 1 in [1, 2, 3] retornaria true, por exemplo.

    • éExecuta um teste.

    • | (barra vertical) Aplica um filtro.

    • ~ (til) Converte todos os operandos em strings e concatena-os.
      "Hello " ~ name ~ "!" retornaria Hello John!(se name == ‘John’)

    • ()Chama um objeto chamável: post.render(). Dentro dos parênteses, você pode usar argumentos posicionais e nomeados, como no Python:
      post.render(user, full=true).

    • . / []Obtém um atributo de um objeto. (Consulte Variáveis)

Filtros

As variáveis podem ser modificadas por filtros. Eles são uma biblioteca de funções auxiliares que realizam transformações para você, para que não precise fazê-lo manualmente. Os filtros são separados da variável por um símbolo de barra vertical (|) e podem ter argumentos opcionais entre parênteses. Vários filtros podem ser encadeados. A saída de um filtro é aplicada ao seguinte.
Por exemplo, name | trim | capitalize removerá todos os espaços em branco de name e colocará sua primeira letra em maiúscula.
Filtros que aceitam argumentos têm os argumentos entre parênteses, assim como uma chamada de função. Por exemplo: listx | join(', ') unirá uma lista usando vírgulas.
Você pode usar If inline com filtros 'multiple' if array | count > 1 else 'one'
Muitos filtros de listas retornam iteradores (para loops) em vez de listas; certifique-se de usar o list filtro.

Filtros integrados

  • Lista completa de filtros
    Filtros integrados do Jinja

  • Filtros usados com frequência
    5 filtros são destacados com a tag [must know]. Estes são os filtros básicos que você precisa conhecer e ajudarão na maioria das operações de manipulação de dados. Os demais também serão úteis, mas você poderá consultá-los quando precisar.

    • default
      Valor padrão se a entrada não existir

      Python
      'hey' | default('my_variable is not defined')
      => "hey"
      
      None | default('my_variable is not defined')
      => "my_variable is not defined"
    • capitalize / title / lower / upper
      Altera a capitalização de uma string

      Python
      'hello' | capitalize
      => "Hello"
      
      'arbitrary code execution' | title
      => "Arbitary Code Execution"
      
      'this is an example' | upper
      => "THIS IS AN EXAMPLE"
      
      'THIS IS AN EXAMPLE' | lower
      => "this is an example"
    • map [must know]
      Há dois usos principais:

      • Extrair atributos de objetos em uma lista

      • Aplicar filtro a todos os itens de uma lista

      Python
      products = [
      	{name: 'abc', nested: {price: 2.77}},
      	{name: 'def', nested: {price: 3.82}},
      	{name: 'ghi', nested: {price: 1.39}}
      ] 
      
      products | map(attribute='name') | map('capitalize') | list
      => ['Abc', 'Ghi', 'Def']
      
      products | map(attribute='nested.price') | map('round', 1) | list
      => [2.8, 3.8, 1.4]
    • selectattr / rejectattr [must know]
      Filtra uma lista de objetos com base nos atributos
      Recebe um atributo e um teste (consulte a seção de testes) como argumento

      Python
      users = [
      	{name: 'abc', active: True, role: 'admin'},
      	{name: 'def', active: False, role: 'admin'},
      	{name: 'ghi', active: True, role: 'builder'}
      ]
      
      users | selectattr('role', '==', 'admin') | list
      => [
      	{name: "abc", active: True, role: "admin"},
      	{name: "def", active: False, role: "admin"}
      ]
      
      users | selectattr('active') | list
      => [
      	{name: "abc", active: True, role: "admin"},
      	{name: "ghi", active: True, role: "builder"}
      ]
      
      # reverse of select
      users | rejectattr('active') | list
      => [
      	{name: "def", active: False}
      ]
      
      # with a regex
      apps = [
        {name: 'bosv1', database: 'bos-pgsql-v1'},
      	{name: 'boav1', database: 'boa-mango'},
      	{name: 'bosv2', database: 'bos-pgsql-v2'}
      ]
      apps | selectattr('database', 'search', '.*pgsql.*') | list
      => [
      	{name: 'bosv1', database: 'bos-pgsql-v1'},
      	{name: 'bosv2', database: 'bos-pgsql-v2'}
      ]
    • select / reject [must know]
      Recebe um teste (consulte a seção de testes) como argumento

      Python
      # simple selects
      numbers | select("odd")
      numbers | select("even")
      numbers | select("divisibleby", 3)
      numbers | select("lessthan", 42)
      
      # Reject is reversed of select
      numbers | reject('odd')
      
      # Fin the number of users who are admin (assuming a map of roles)
      ['admin', 'nope', 'admin'] | select("==", "admin") | list
      => ['admin', 'admin'] | count 
      => 2
      
      # filter undefined variables after a map operation
      [undefined, "hey", "oh"] | select('defined') | list
      => ["hey", "oh"]
      
      # select items containing "v1"
      ["prod-v1", "prod_v2", "item_v1"] | select("in", "v1") | list
      => ["prod-v1", "item_v1"]
      
      # with regex
      ["p-v1_lk", "c-v2", "m-v1-lk"] | select("search", ".*v1(-|_)lk") | list
      => ["p-v1_lock", "m-v1-lock"]
    • flatten [must know]
      Após um map, select ou uma manipulação de dados mais complexa, é comum terminar com listas como esta: `[[1,2], [3,4]]`
      Use flatten para mesclá-las em uma única lista

      Python
      [[1, 2], [3, 4]] | flatten
      => [1, 2, 3, 4]
    • list [must know]
      Converte um valor em uma lista. Você o usará com frequência, pois a maioria dos filtros úteis retorna iteradores em vez de listas, e é preciso convertê-los manualmente novamente em listas.

    • join

      Python
      ['abc', 'def', 'ghi'] | join(', ')
      => "abc, def, ghi"
      
      [{name: 'abc'}, {name: 'def'}] | join(', ', attribute='name')
      => "abc, def"
    • dictsort

      Python
      for key, value in mydict | dictsort
      => #sort the dict by key, case insensitive
      
      for key, value in mydict | dictsort(reverse=true)
      => #sort the dict by key, case insensitive, reverse order
      
      for key, value in mydict | dictsort(true)
      => #sort the dict by key, case sensitive
      
      for key, value in mydict | dictsort(false, 'value')
      => #sort the dict by value, case insensitive
    • format
      Formata uma string (printf)

      Python
      "%s, %s!" | format('Hello', 'world')
      Hello, world!
    • groupby

      Python
      users = [
      	{name: 'pierre', city: 'paris'},
        {name: 'leo', city: 'marseille'},
      	{name: 'lucy', city: 'paris'}
      ] 
      
      # Useful to use with for loops (for city, items in users | groupby('city'))
      users | groupby("city")
      => [
      		["marseille", [
      				{"city":"marseille", "name": "leo"}
      			]
      		],
      		["paris", [
      				{"city": "paris", "name": "pierre"},
      				{"city": "paris", "name": "lucy"}
      			]
      		]
      	]
      
      apps = [
        {name: 'bos', database: 'bos-pgsql-staging'},
      	{name: 'boa', database: 'bos-pgsql-staging'},
      	{name: 'bos', database: 'bos-pgsql-prod'},
      	{anon: true, database: 'Anon-mvp-pgsql-other'}
      ]
      
      apps | groupby("name", default: 'unknown')
      => [
      	["bos", [
      		{name: 'bos', database: 'bos-pgsql-staging'},
      		{name: 'bos', database: 'bos-pgsql-prod'},
      	],
      	["boa", [
      			{name: 'boa', database: 'bos-pgsql-staging'}
      		]
      	],
      	["unknown", [
      			{anon: true, database: 'Anon-mvp-pgsql-other'}
      		]
      	]
      ]
    • int / string

      Python
      '43' | int
      => 43
      
      'h43' | int
      => 0
      
      34 | string
      => '34'
      
      {name: 'hello'} | string
      => "{name: 'hello'}"
    • first / last

      Python
      [1, 2, 3] | first
      => 1
      
      [1, 2, 3] | last
      => 3
    • length / count

      Python
      [1, 2, 3] | length
      => 3
      
      [1, 3, 5, 10] | count # alias
      => 4
    • max / min

      Python
      [1, 2, 3] | min
      => 1
      
      [{code: 1}, {code: 2}] | max(attribute='code')
      => 2
    • random

      Python
      ['a', 'b', 'c'] | random
      => 'c' # random item of the list
    • replace

      Python
      'Hello World' | replace('Hello', 'Goodbye')
      => "Goodbye World"
      
      # Restrict to the first x occurences
      'aaaaargh' | replace('a', 'd,', 2)
      => d,d,aaargh
    • reverse

      Python
      ['a', 'b', 'c'] | reverse | list
      => ['c', 'b', 'a']
    • round

      Python
      42.55 | round
      => 43.0
      
      42.55 | round(1, 'floor')
      => 42.5
      
      42.54 | round(1, 'ceiling')
      => 42.6
    • slice

      Python
      ['a', 'b', 'c'] | slice(3) | list
      => [['a'], ['b'], ['c']]
    • sort

      Python
      ['b', 'a'] | sort | list
      => ["a", "b"]
      
      ['a', 'b'] | sort(reverse=true) | list
      => ["b", "a"]
      
      ['a', 'B', 'A'] | sort(case_sensitive=true) | list
      => ["A", "B", "a"]
      
      [{text: 'b'}, {text: 'a'}] | sort(attribute='text') | list
      => [{text: 'a'}, {text: 'b'}]
    • sum

      Python
      [22, 48] | sum
      => 70
      
      [{price: 22}, {price: 48}] | sum(attribute='price')
      => 70
    • trim

      Python
      "   hello   " | trim
      => "hello"
    • truncate

      Python
      "foo bar baz qux" | truncate(9)
      => "foo..."
      
      # Truncate regardless of words
      "foo bar baz qux" | truncate(9, True)
      => "foo ba..."
      
      # Truncate use a default leeway of 5, the fourth parameter.
      "foo bar baz qux" | truncate(11)
      => "foo bar baz qux"
      "foo bar baz qux" | truncate(11, False, '[...]', 0)
      => "foo bar[...]"
    • unique

Filtros personalizados

Estes são filtros adicionais implementados pela ViaSay.

Filtros de data

Os filtros a seguir permitem converter strings que representam data/intervalo em objetos Python datetime/timedelta.

  • to_date: Analisa uma string em um objeto datetime; recebe tzname como parâmetro.

Python
{% set departure="20230730T1028" | to_date("Europe/Paris") %}
{% set departure=departure.strftime("%H:%M:%S - %d/%m/%Y") %}
# departure will contain the following value: "10:28:00 - 30/07/2023"
  • to_timedelta: Analisa uma string de timedelta em um objeto timedelta.

Python
{% set time_before_departure="1 day, 17:02:31" | to_timedelta %}
{% set today="20230730T1028" | to_date("Europe/Paris") %}
{% set departure=today + time_before_departure %}
{% set departure=departure.strftime("%H:%M:%S - %d/%m/%Y") %}
# departure will contain the following value:  "03:30:03 - 01/08/2023"
  • timestamp_to_date: Converte um timestamp Unix (inteiro em milissegundos) em um datetime

Python
{% set departure=1691597204000 | timestamp_to_date %}
{% set departure=departure.strftime("%H:%M:%S - %d/%m/%Y") %}
# departure will contain the following value:  "16:06:44 - 09/08/2023"

Aviso: Você não pode armazenar um datetime em uma variável de saída da etapa de manipulação de dados. Isso resultará em um erro de execução. Primeiro, é necessário formatá-lo como string usando strftime como mostrado nos exemplos acima.

Testes

Além dos filtros, também estão disponíveis os chamados “testes”. Os testes podem ser usados para testar uma variável em relação a uma expressão comum. Para testar uma variável ou expressão, adicione é mais o nome do teste depois da variável. Por exemplo, para descobrir se uma variável está definida, você pode fazer name is defined, que retornará true ou false dependendo de se name está definida no contexto do modelo atual.

Os testes também podem aceitar argumentos. Se o teste aceitar apenas um argumento, você pode omitir os parênteses.

Lista de testes integrados

Métodos nativos do Python

Você pode usar a maioria dos métodos nativos dos objetos Python.

Por exemplo, você pode dividir uma string ou mesclar dicionários:

Python
"abc, def, ghi".split(', ')
=> ['abc', 'def', 'ghi']

{name: 'pierre'}.update({role: 'admin'})
=> {name: 'pierre', role: 'admin'}

Aqui estão os métodos disponíveis para os principais tipos de objetos:

  • String

  • Dicionário

  • Lista

Utilização avançada

Descrição de todos os recursos fornecidos pelo mecanismo de modelos que você pode usar no bloco de código. Isso permitirá fazer manipulações mais avançadas com loops, vários ifs, funções etc. (também conhecido como programação imperativa).

Usamos Jinja 3 para os modelos. Se precisar de referências ou de mais detalhes depois de ler este documento, consulte a documentação oficial.

Ele é derivado do Python, portanto você verá muitas semelhanças e poderá até usar alguns métodos do Python em determinados objetos.

Delimitadores

Existem alguns tipos de delimitadores. Os delimitadores padrão são configurados da seguinte forma:

  • {% ... %} para Instruções (não imprime nenhum valor)

  • {{ ... }} para Expressões (imprime na saída do modelo)

  • {# ... #} para Comentários não incluídos na saída do modelo

No bloco de código, você pode usar todos eles, mas a saída será descartada de qualquer forma. Portanto, você deverá usar instruções e comentários.

Nas saídas, os valores são envolvidos em uma expressão para manter as coisas simples.

Atribuições

As atribuições usam a tag set e podem ter vários destinos:

Python
{% **set** navigation = [('index.html', 'Index'), ('about.html', 'About')] %}
{% **set** key, value = call_something() %}
  • Comportamento de escopo
    Tenha em mente que não é possível definir variáveis dentro de um bloco (exceto if, que não introduz um escopo) e fazê-las aparecer fora dele. Isso também se aplica a loops. Como resultado, o modelo a seguir não fará o que você talvez espere:

    Python
    {% set iterated = false %}
    {% for item in seq %}
        {{ item }}
        {% set iterated = true %}
    {% endfor %}
    {% if not iterated %} did not iterate {% endif %}

    Não é possível fazer isso. Em vez disso, use construções alternativas, como o bloco else do loop ou a variável especial loop:

    Python
    {% for item in seq %}
        {{ item }}
    {% else %}
        did not iterate
    {% endfor %}

    Casos de uso mais complexos podem ser tratados usando objetos namespace, que permitem propagar alterações entre escopos:

    Python
    {% set ns = namespace(found=false) %}
    {% for item in items %}
        {% if item.check_something() %}
            {% set ns.found = true %}
        {% endif %}
        * {{ item.title }}
    {% endfor %}
    Found item having something: {{ ns.found }}

Lista de estruturas de controle

  • If / elif / else
    A instrução if é comparável à instrução if do Python. Na forma mais simples, você pode usá-la para testar se uma variável está definida, não está vazia e não é falsa:

    Python
    {% if users %}
    	{% set text = 'users' %}
    {% endif %}

    Para várias ramificações, elif e else podem ser usados como no Python. Você também pode usar Expressões mais complexas:

    Python
    {% if kenny.sick %}
        {% set text = 'Kenny is sick.' %}
    {% elif kenny.dead %}
    		{% set text = 'You killed Kenny!  You ****!!!' %}
    {% else %}
    		{% set text = 'Kenny looks okay --- so far' %}
    {% endif %}

    If também pode ser usado como uma expressão inline:

    Python
    {% set text = 'layout' if layout_template is defined else 'default' %}

    e para filtragem de loops:

    Python
    {% for user in users if not user.hidden %}
        {% do usernames.append(user) %}
    {% endfor %}
  • For

    Percorre cada item de uma sequência. Por exemplo:

    Python
    {% for user in users %}
      {% do array.append(user | trim | capitalize) %}
    {% endfor %}

    Como as variáveis nos modelos mantêm suas propriedades de objeto (do Python), é possível iterar sobre contêineres como dict:

    Python
    {% for key, value in my_dict.items() %}
    		{% array.append([key, value]) %}
    {% endfor %}

    Os dicionários do Python podem não estar na ordem em que você deseja exibi-los. Se a ordem for importante, use o filtro | dictsort.

    Python
    {% for key, value in my_dict | dictsort %}
        {% array.append([key, value]) %}
    {% endfor %}

    Dentro de um bloco for-loop, você pode acessar algumas variáveis especiais:

    Variáveis

    Descrição

    loop.index

    A iteração atual do loop. (indexada a partir de 1)

    loop.index0

    A iteração atual do loop. (indexada a partir de 0)

    loop.revindex

    O número de iterações desde o final do loop (indexado a partir de 1)

    loop.revindex0

    O número de iterações desde o final do loop (indexado a partir de 0)

    loop.first

    Verdadeiro se for a primeira iteração.

    loop.last

    Verdadeiro se for a última iteração.

    loop.length

    O número de itens na sequência.

    loop.cycle

    Uma função auxiliar para alternar entre uma lista de sequências.

    loop.depth

    Indica a profundidade atual da renderização em um loop recursivo. Começa em 1

    loop.depth0

    Indica a profundidade atual da renderização em um loop recursivo. Começa em 0

    loop.previtem

    O item da iteração anterior. Indefinido durante a primeira iteração.

    loop.nextitem

    O item da iteração seguinte. Indefinido durante a última iteração.

    loop.changed(*val)

    Verdadeiro se tiver sido chamado anteriormente com um valor diferente (ou se não tiver sido chamado).

    Dentro de um for-loop, é possível alternar entre uma lista de strings/variáveis a cada passagem pelo loop usando o auxiliar especial loop.cycle:

    Python
    {% for row in rows %}
    		{% set css_class = loop.cycle('odd', 'even') %}
        {% do array.append([css_class, row]) %}
    {% endfor %}

    Ao contrário do Python, não é possível usar break ou continue em um loop. No entanto, você pode filtrar a sequência durante a iteração, o que permite ignorar itens. O exemplo a seguir ignora todos os usuários ocultos:

    Python
    {% for user in users if not user.hidden %}
        {% do filtered_users.append(user) %}
    {% endfor %}

    A vantagem é que a variável especial loop fará a contagem corretamente; portanto, não contará os usuários sobre os quais não se iterou.

    Se nenhuma iteração ocorrer porque a sequência está vazia ou porque a filtragem removeu todos os itens da sequência, você pode renderizar um bloco padrão usando else:

    Python
    {% for user i users %}
        {% do array.append(user) %}
    {% else %}
        {% do array.append('empty') %}
    {% endfor %}

    Observe que, no Python, os blocos else são executados sempre que o loop correspondente não tiver sido interrompido por break. Como os loops não podem usar break de qualquer forma, foi escolhido um comportamento ligeiramente diferente para a palavra-chave else.

    Também é possível usar loops recursivamente. Isso é útil ao lidar com dados recursivos, como sitemaps ou RDFa. Para usar loops recursivamente, basta adicionar o modificador recursive à definição do loop e chamar a variável loop com o novo iterável no ponto em que deseja fazer a recursão.

    O exemplo a seguir implementa um sitemap com loops recursivos:

    Python
    {% for item in sitemap recursive %}
        {% set title = item.title %}</a>
        {% if item.children %}
            {% do loop(item.children) %}
        {% endif %}
    		{% do array.append(title) %}
    {% endfor %}

    A variável loop sempre se refere ao loop mais próximo (o mais interno). Se tivermos mais de um nível de loops, podemos vincular novamente a variável loop escrevendo {% set outer_loop = loop %} após o loop que queremos usar recursivamente. Então, podemos chamá-lo usando {{ outer_loop(…) }}

    Observe que as atribuições em loops serão apagadas ao final da iteração e não podem sobreviver ao escopo do loop. Consulte Atribuições, comportamento de escopo para obter mais informações sobre como lidar com isso.

    Se tudo o que você deseja fazer é verificar se algum valor mudou desde a última iteração ou mudará na próxima, você pode usar previtem e nextitem:

    Python
    {% for value in values %}
        {% if loop.previtem is defined and value > loop.previtem %}
            The value just increased!
        {% endif %}
        {{ value }}
        {% if loop.nextitem is defined and loop.nextitem > value %}
            The value will increase even more!
        {% endif %}
    {% endfor %}

    Se você só se importa em saber se o valor mudou, usar changed é ainda mais fácil:

    Python
    {% for entry in entries %}
        {% if loop.changed(entry.category) %}
            <h2>{{ entry.category }}</h2>
        {% endif %}
        <p>{{ entry.message }}</p>
    {% endfor %}

Lista de funções globais

  • range
    Retorna uma lista contendo uma progressão aritmética de inteiros. range(i, j) retorna [i, i+1, i+2, ..., j-1]; o início (!) é definido por padrão como 0. Quando step é fornecido, ele especifica o incremento (ou decremento). Por exemplo, range(4) e range(0, 4, 1) retornam [0, 1, 2, 3]. O ponto final é omitido! Esses são exatamente os índices válidos para uma lista de 4 elementos.
    Isso é útil para repetir um bloco de modelo várias vezes, por exemplo, para preencher uma lista. Imagine que você tenha 7 usuários na lista, mas queira renderizar três itens vazios para impor uma altura com CSS:

    Python
    <ul>
    {% for user in users %}
        <li>{{ user.username }}</li>
    {% endfor %}
    {% for number in range(10 - users | count) %}
        <li class="empty"><span>...</span></li>
    {% endfor %}
    </ul>
  • lipsum
    Gera um lorem ipsum para o modelo. Por padrão, são gerados cinco parágrafos de HTML, cada um com entre 20 e 100 palavras. Se html for False, será retornado texto comum. Isso é útil para gerar conteúdos simples para testes de layout.

  • dict
    Uma alternativa conveniente aos literais de dict. {'foo': 'bar'} é igual a dict(foo='bar').

  • cycler
    Percorre valores, produzindo-os um de cada vez e reiniciando quando chega ao fim.
    Semelhante a loop.cycle, mas pode ser usado fora de loops ou entre vários loops. Por exemplo, renderize uma lista de pastas e arquivos alternando entre as classes “odd” e “even”.
    Cada argumento posicional será produzido na ordem fornecida em cada ciclo.

    • propriedades

      • current
        Retorna o item atual. Equivale ao item que será retornado na próxima vez que [next()](https://jinja.palletsprojects.com/en/3.0.x/templates/#jinja-globals.cycler.next) for chamado.

      • next()
        Retorna o item atual e, em seguida, avança [current](https://jinja.palletsprojects.com/en/3.0.x/templates/#jinja-globals.cycler.current) para o próximo item.

      • reset()
        Redefine o item atual como o primeiro item.

  • joiner
    Um pequeno auxiliar que pode ser usado para “unir” várias seções. Um joiner recebe uma string e retorna essa string sempre que é chamado, exceto na primeira vez (quando retorna uma string vazia). Você pode usá-lo para unir elementos:

  • namespace
    Cria um novo contêiner que permite atribuir atributos usando a tag {% set %} :

    Python
    {% set ns = namespace() %}
    {% set ns.foo = 'bar' %}

    O principal objetivo é permitir transportar um valor de dentro do corpo de um loop para um escopo externo. Os valores iniciais podem ser fornecidos como um dict, como argumentos nomeados ou ambos (mesmo comportamento do construtor dict do Python):

    Python
    {% set ns = namespace(found=false) %}
    {% for item in items %}
        {% if item.check_something() %}
            {% set ns.found = true %}
        {% endif %}
         {{ item.title }}
    {% endfor %}
    Found item having something: {{ ns.found }}

Macros (funções)

As macros são comparáveis a funções em linguagens de programação comuns. Elas são úteis para colocar padrões frequentemente usados em funções reutilizáveis e não repetir código (“DRY”).

Veja um pequeno exemplo de uma macro que renderiza um elemento de formulário:

Python
{% set registered_users = [] %}

{% macro register_users(users, bot='', role='basic') -%}
		{% for user in users %}
		  {% do registered_users.append(user.update({role: role, bot: 'a'})) %}
		{% endfor %}
{%- endmacro %}

{% macro filter_sensitive(text, filter='[SENSITIVE]') -%}
		{# bank cards #}
		{% set filtered = text | regex_replace('^4[0-9]{12}(?:[0-9]{3})?$', filter) %}
		{# phone numbers #}
		{% set filtered = filtered | regex_replace('^[\+]?[(]?[0-9]{3}[)]?[-\s\.]?[0-9]{3}[-\s\.]?[0-9]{4,6}$', filter) %}
		
		{{ filtered }}
{%- endmacro %}

A macro pode então ser chamada como uma função no namespace:

Python
register_users([{name: 'pierre'}, {name: 'paul'}], role='admin')
register_users([{name: 'leo'}, {name: 'lucy'}], role='builder', bot='op')

=> registered_users = [
		{name: 'pierre', role: 'admin', bot=''},
		{name: 'paul', role: 'admin', bot=''},
		{name: 'leo', role: 'builder', bot='op'},
		{name: 'lucy', role: 'builder', bot='op'}
]

Dentro das macros, você tem acesso a três variáveis especiais:

  • varargs
    Se forem passados para a macro mais argumentos posicionais do que ela aceita, eles acabam na variável especial varargs como uma lista de valores.

  • kwargs
    Como varargs, mas para argumentos nomeados. Todos os argumentos nomeados não consumidos são armazenados nessa variável especial.

  • caller
    Se a macro foi chamada a partir de uma tag call, o chamador é armazenado nessa variável como uma macro chamável.

As macros também expõem alguns de seus detalhes internos. Os seguintes atributos estão disponíveis em um objeto de macro:

  • nome
    O nome da macro. {{ input.name }} imprimirá input.

  • arguments
    Uma tupla com os nomes dos argumentos aceitos pela macro.

  • catch_kwargs
    Isso é true se a macro aceitar argumentos nomeados adicionais (ou seja, acessar a variável especial kwargs).

  • catch_varargs
    Isso é true se a macro aceitar argumentos posicionais adicionais (ou seja, acessar a variável especial varargs).

  • caller
    Isso é true se a macro acessar a variável especial caller e puder ser chamada a partir de uma tag call.

Se o nome de uma macro começar com um sublinhado, ela não será exportada e não poderá ser importada.

Call

Em alguns casos, pode ser útil passar uma macro para outra macro. Para isso, você pode usar o bloco especial call.

Também é possível passar argumentos de volta para o bloco call. Isso o torna útil como substituto para loops. De modo geral, um bloco call funciona exatamente como uma macro sem nome.

Was this article helpful?

On this page
  • Acesso a atributos
  • Atribuições
  • Expressões
  • Filtros
  • Filtros integrados
  • Filtros personalizados
  • Testes
  • Métodos nativos do Python
  • Delimitadores
  • Atribuições
  • Lista de estruturas de controle
  • Lista de funções globais
  • Macros (funções)
  • Call

Made from France 💙

Categories

  • ANÁLISE
  • CONSTRUIR
  • LOUIS AI
  • INTEGRAR

🔗 Useful Links

  • Sign In
  • Website
  • Terms & Conditions

© 2026

MindsayPowered by Mindsay

Search the help center…

Search help center articles