OXYGENHUB
# a22e4aec2e28 oxygenhub / templates / login.html
2.7 KiB · HTML · last changed A phone as the second factor: Keystore keys approve sign-ins by the number the browser shows, and the sudo step asks a stale session again before sensitive changes (closes #356) 3 days ago source blame history raw
1
{% extends "base.html" %}
2
{% block title %}Sign in{% endblock %}
3
{% block content %}
4
{# The mark (docs/backgrounds.md §2): brand only, no data. #}
5
<script type="application/json" id="backdrop-data">{"scene":"mark"}</script>
6
{% include "backdrop.html" %}
7
<div class="head"><h1>Sign in <small>{{ shell.site }}</small></h1></div>
8
{% if reset %}<p class="note">Your password is set. Sign in with it; every other session was signed out.</p>{% endif %}
9
{% if let Some(e) = error %}<p class="error">{{ e }}</p>{% endif %}
10
<div class="signin-layout{% if !providers.is_empty() && totp_for.is_none() %} with-providers{% endif %}">
11
<form class="card" method="post" action="/login">
12
  <input type="hidden" name="next" value="{{ next }}">
13
  {% if let Some(u) = totp_for %}
14
  <input type="hidden" name="username" value="{{ u }}">
15
  <input type="hidden" name="pending" value="{{ pending }}">
16
  {% if let Some((id, number)) = approval %}
17
  {# Waiting on the phone (oxygenhub#356): the page asks what became of it and signs in once it is approved. #}
18
  <input type="hidden" name="approval" value="{{ id }}">
19
  <div class="approve-wait" data-approval-poll="/login/approval" data-approval-id="{{ id }}" aria-live="polite">
20
    <p>Password accepted for <strong>{{ u }}</strong>. Open OxygenHub on your phone and pick</p>
21
    <p class="approve-number" aria-label="the number {{ number }}">{{ number }}</p>
22
    <p class="small mute" data-approval-status>Waiting for your phone…</p>
23
  </div>
24
  <button type="submit" name="use_code" value="1" class="small" formnovalidate>Use a code instead</button>
25
  {% else %}
26
  <p>Password accepted for <strong>{{ u }}</strong>. Enter the six-digit code from your authenticator app, or a recovery code.</p>
27
  <label for="code">Code</label><input type="text" id="code" name="code" autocomplete="one-time-code" inputmode="numeric" autofocus>
28
  {% endif %}
29
  {% else %}
30
  <label for="username">Username</label><input type="text" id="username" name="username" autocomplete="username" autofocus required>
31
  <label for="password">Password</label><input type="password" id="password" name="password" autocomplete="current-password" required>
32
  {% endif %}
33
  {% if approval.is_none() %}<button type="submit">SIGN IN</button>{% endif %}
34
  {% if totp_for.is_some() && approval.is_none() && phones %}<button type="submit" name="phone" value="1" class="small" formnovalidate>Approve on my phone instead</button>{% endif %}
35
</form>
36
{% if !providers.is_empty() && totp_for.is_none() %}<div class="signin-or" aria-hidden="true"><span>or</span></div>
37
{% let verb = "Sign in" %}{% let suffix = "" %}{% include "signin_buttons.html" %}{% endif %}
38
</div>
39
<p class="small mute"><a href="/login/reset">Forgot your password?</a> · No account? <a href="/register">Register</a>.</p>
40
{% endblock %}