{# Shared panel macros #} {% macro status_tag(code) -%} {%- if code is none -%}— {%- elif code >= 500 -%}{{ code }} {%- elif code >= 400 -%}{{ code }} {%- elif code >= 300 -%}{{ code }} {%- else -%}{{ code }} {%- endif -%} {%- endmacro %} {% macro level_tag(level) -%} {%- set cls = {'DEBUG': '', 'INFO': 'is-info', 'WARNING': 'is-warning', 'ERROR': 'is-danger', 'CRITICAL': 'is-danger'}.get(level, '') -%} {{ level }} {%- endmacro %} {% macro duration(ms) -%} {{ ms | lw_duration }} {%- endmacro %} {% macro time_ago(dt) -%} {%- endmacro %} {% macro tags(items) -%} {% if items %}
{% for t in items %}{{ t }}{% endfor %}
{% endif %} {%- endmacro %} {# Recursive JSON viewer with nested
, no libraries. #} {% macro json_tree(value, open=false) -%} {%- if value is mapping -%} {%- if value -%}
{ {{ value | length }} }
{%- else -%}{}{%- endif -%} {%- elif value is string -%} {%- if value | length > 120 or '\n' in value -%}
{{ value }}
{%- else -%}"{{ value }}"{%- endif -%} {%- elif value is sequence -%} {%- if value -%}
[ {{ value | length }} ]
{%- else -%}[]{%- endif -%} {%- elif value is none -%}null {%- else -%}{{ value | tojson }} {%- endif -%} {%- endmacro %} {% macro sql_block(sql) -%}
{{ sql | lw_sql }}
{%- endmacro %} {# Collapsible traceback and snippet with the line highlighted. #} {% macro traceback(frames, text) -%} {% for f in frames | reverse %}
{{ f.file }}:{{ f.line }} in {{ f.function }} {% if f.snippet %}
{% for l in f.snippet %}{{ l.line }} {{ l.code }}
{% endfor %}
{% else %}
{{ f.code }}
{% endif %}
{% endfor %}
Full traceback
{{ text }}
{%- endmacro %} {% macro pagination(older_url, newer_url) -%} {% if older_url or newer_url %} {% endif %} {%- endmacro %} {# Generic table: each type defines head() and row(e) in entries/.html; the rows come from _rows.html. Import `with context`. #} {% macro entry_table(entries, entry_type) -%} {% import "leeuwenhoek/entries/" ~ entry_type ~ ".html" as t with context %}
{{ t.head() }}{% include "leeuwenhoek/_rows.html" %}
{%- endmacro %} {# Resolve / Reopen button of an exception family (POST with the panel's CSRF token). Import `with context` so `csrf_token` is available. #} {% macro resolve_button(family_hash, resolved_at, small=false) -%} {% set action = 'reopen' if resolved_at else 'resolve' %}
{%- if resolved_at %} {%- else %} {%- endif %}
{%- endmacro %} {# Retry button of a failed Celery or RQ run (POST with the panel's CSRF token), disabled with the reason when the run can't be dispatched again. Nothing for other entries. Import `with context`. #} {% macro retry_button(entry) -%} {% if is_failed_run(entry) %} {% set reason = retry_problem(entry) %}
{%- if reason %} {%- else %} {%- endif %}
Retries of this run {% if reason %}

{{ reason }}

{% endif %}
{% endif %} {%- endmacro %} {# "Retry of" link from a run dispatched by the Retry button to the failed run it retries. #} {% macro retry_of_link(entry) -%} {%- if entry.content.retry_of %} · Retry of {{ entry.content.retry_of[:8] }}{% endif -%} {%- endmacro %}