Skip to content

Notification Templates

Keystone issues automated notifications regarding changes to user accounts and resource allocations. Administrators can customize these notifications using templates to reflect organization-specific branding and messaging.

Overriding Templates

Keystone generates notifications using HTML templates and the Jinja2 templating engine. The location of custom templates is configurable via application settings.

When a notification is triggered, Keystone first checks for a custom template file. If no custom template is available, Keystone falls back to an internal default. The selected template is then rendered using the context data outlined below.

For security reasons, data is sanitized before being injected into the template. Certain Jinja features — such as access to application internals — are also disabled.

Base Template

Template file: base.html

The base template serves as the parent layout for all notification content, providing top-level styling and structure. The template defines two content blocks that child templates override to inject content.

Block Name Description
main Main body content of the email notification.
footer Footer content displayed at the bottom of the message.
Default Template Content
<!doctype html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Keystone User Notification</title>
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <style>
    body {
      font-family: Helvetica, sans-serif;
      font-size: 16px;
      line-height: 1.4;
      background-color: #f5f5f5;
      margin: 0;
      padding: 0;
    }

    table.body {
      width: 100%;
    }

    table.main {
      width: 100%;
      background-color: #ffffff;
      border: 1px solid #eaeaea;
      border-radius: 0;
    }

    table.footer {
      width: 100%;
      text-align: center;
      padding-top: 24px;
      padding-bottom: 24px;
    }

    td.container {
      width: 600px;
      padding-top: 24px;
    }

    td.wrapper {
      padding: 24px;
    }

    td.footer-text {
      color: #a1a1a1;
      font-size: 11px;
    }
  </style>
</head>
<body>
<table role="presentation" class="body">
  <tr>
    <td>&nbsp;</td>
    <td class="container">
      <table role="presentation" class="main">
        <tr>
          <td class="wrapper">
            {% block main %}{% endblock %}
          </td>
        </tr>
      </table>
      <table role="presentation" class="footer">
        <tr>
          <td class="footer-text">
            {% block footer %}
              The Keystone HPC Utility <br> &copy; Better HPC
            {% endblock %}
          </td>
        </tr>
      </table>
    </td>
    <td>&nbsp;</td>
  </tr>
</table>
</body>
</html>

Upcoming Resource Expiration

Template file: upcoming_expiration.html

The upcoming expiration notification alerts users that one or more of their active resource allocations is nearing its expiration date.

Default Template Content
{% extends "base.html" %}

{% block main %}
  {% if user.first_name and user.last_name %}
    <p>Dear {{ user.first_name }} {{ user.last_name }},</p>
  {% else %}
    <p>Dear {{ user.username }},</p>
  {% endif %}
  <p>
    This notification is to remind you your HPC compute allocation <strong>"{{ request.title }}"</strong>
    is set to expire in {{ days_to_expire }} days on {{ request.expire.isoformat() }}.
  </p>
  <p>Sincerely,</p>
  <p>The keystone HPC utility</p>
{% endblock %}

Expired Resource Allocation

Template file: past_expiration.html

The past expiration notification alerts users that one or more of their active resource allocations has expired and that the resources granted under that allocation are no longer availible for use.

Default Template Content
{% extends "base.html" %}

{% block main %}
  {% if user.first_name and user.last_name %}
    <p>Dear {{ user.first_name }} {{ user.last_name }},</p>
  {% else %}
    <p>Dear {{ user.username }},</p>
  {% endif %}
  <p>
    This notification is to alert you your HPC compute allocation <strong>"{{ request.title }}"</strong>
    expired on {{ request.expire.isoformat() }}. You will no longer be able to use the resources awarded
    to you under this allocation when submitting new jobs.
  </p>
  <p>Sincerely,</p>
  <p>The keystone HPC utility</p>
{% endblock %}