Skip to content
This repository was archived by the owner on Jun 25, 2024. It is now read-only.

Commit 3ee2d8f

Browse files
author
Billy Clark
committed
users with U2F MFA could not utilize material theme yet.
1 parent ecaf754 commit 3ee2d8f

File tree

7 files changed

+931
-2
lines changed

7 files changed

+931
-2
lines changed

dictionaries/mfa.definition.json

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,24 @@
6060
"fr": "TODO",
6161
"ko": "TODO"
6262
},
63+
"u2f_header": {
64+
"en": "Security key",
65+
"es": "TODO",
66+
"fr": "TODO",
67+
"ko": "TODO"
68+
},
69+
"u2f_icon": {
70+
"en": "USB key icon",
71+
"es": "TODO",
72+
"fr": "TODO",
73+
"ko": "TODO"
74+
},
75+
"u2f_instructions": {
76+
"en": "You may now insert your security key and press its button.",
77+
"es": "TODO",
78+
"fr": "TODO",
79+
"ko": "TODO"
80+
},
6381
"shield_icon": {
6482
"en": "Shield icon",
6583
"es": "TODO",
@@ -120,6 +138,12 @@
120138
"fr": "TODO",
121139
"ko": "TODO"
122140
},
141+
"button_try_again": {
142+
"en": "Try again",
143+
"es": "TODO",
144+
"fr": "TODO",
145+
"ko": "TODO"
146+
},
123147
"remember_this": {
124148
"en": "Remember this computer for 30 days",
125149
"es": "TODO",

themes/material/mfa/prompt-for-mfa-backupcode.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@
6868
</div>
6969

7070
<script>
71-
ga('send','event','error','backupcode', <?= $message ?>');
71+
ga('send','event','error','backupcode', '<?= $message ?>');
7272
</script>
7373
<?php
7474
}

themes/material/mfa/prompt-for-mfa-totp.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@
6868
</div>
6969

7070
<script>
71-
ga('send','event','error','totp', <?= $message ?>');
71+
ga('send','event','error','totp', '<?= $message ?>');
7272
</script>
7373
<?php
7474
}
Lines changed: 149 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,149 @@
1+
<!DOCTYPE html>
2+
<html>
3+
<head>
4+
<title><?= $this->t('{material:mfa:title}') ?></title>
5+
6+
<?php include __DIR__ . '/../common-head-elements.php' ?>
7+
8+
<script src="/module.php/material/mfa-u2f-api.js"></script>
9+
<script>
10+
function verifyU2f() {
11+
// TODO: need feature sniff and error handling
12+
var u2fSignRequest = <?= json_encode($this->data['mfaOption']['data']) ?> || {};
13+
14+
u2f.sign(u2fSignRequest.appId, u2fSignRequest.challenge, [u2fSignRequest],
15+
handleU2fResponse);
16+
}
17+
18+
function handleU2fResponse(u2fResponse) {
19+
if (u2fResponse.errorCode && u2fResponse.errorCode != 0) {
20+
return handleError(u2fResponse);
21+
}
22+
23+
submitForm(u2fResponse);
24+
}
25+
26+
function handleError(u2fResponse) {
27+
var message = u2fResponse.errorMessage ||
28+
Object.keys(u2f.ErrorCodes)[u2fResponse.errorCode];
29+
30+
var errorNode = document.querySelector('p.error');
31+
32+
errorNode.classList.add('show');
33+
errorNode.querySelector('span').textContent = message;
34+
35+
offerRetry();
36+
}
37+
38+
function offerRetry() {
39+
var retryButton = document.querySelector('.mdl-button.mdl-color-text--red');
40+
41+
retryButton.classList.add('show');
42+
}
43+
44+
function submitForm(u2fResponse) {
45+
var form = document.querySelector('form');
46+
var submissionInput = createHiddenInput('submitMfa');
47+
var u2fResponseInput = createHiddenInput('mfaSubmission');
48+
49+
u2fResponseInput.value = JSON.stringify(u2fResponse);
50+
51+
form.appendChild(submissionInput);
52+
form.appendChild(u2fResponseInput);
53+
54+
form.submit();
55+
}
56+
57+
function createHiddenInput(name) {
58+
var input = document.createElement('input');
59+
60+
input.type = 'hidden';
61+
input.name = name;
62+
63+
return input;
64+
}
65+
</script>
66+
</head>
67+
<body class="gradient-bg" onload="verifyU2f()">
68+
<div class="mdl-layout mdl-layout--fixed-header fill-viewport">
69+
<header class="mdl-layout__header">
70+
<div class="mdl-layout__header-row">
71+
<span class="mdl-layout-title">
72+
<?= $this->t('{material:mfa:header}') ?>
73+
</span>
74+
</div>
75+
</header>
76+
<main class="mdl-layout__content" layout-children="column">
77+
<form layout-children="column" method="POST">
78+
<?php
79+
foreach ($this->data['formData'] as $name => $value) {
80+
?>
81+
<input type="hidden" name="<?= htmlentities($name); ?>"
82+
value="<?= htmlentities($value); ?>"/>
83+
<?php
84+
}
85+
?>
86+
<div class="mdl-card mdl-shadow--8dp">
87+
<div class="mdl-card__media white-bg margin" layout-children="column">
88+
<img src="/module.php/material/mfa-u2f.png"
89+
alt="<?= $this->t('{material:mfa:u2f_icon}') ?>">
90+
</div>
91+
92+
<div class="mdl-card__title center">
93+
<h1 class="mdl-card__title-text">
94+
<?= $this->t('{material:mfa:u2f_header}') ?>
95+
</h1>
96+
</div>
97+
98+
<div class="mdl-card__title center" >
99+
<p class="mdl-card__subtitle-text">
100+
<?= $this->t('{material:mfa:u2f_instructions}') ?>
101+
</p>
102+
</div>
103+
104+
<?php
105+
$message = $this->data['errorMessage'];
106+
107+
if (! empty($message)) {
108+
?>
109+
<script>
110+
ga('send','event','error','u2f', '<?= $message ?>');
111+
</script>
112+
<?php
113+
}
114+
?>
115+
<div class="mdl-card__supporting-text"
116+
layout-children="column">
117+
<p class="mdl-color-text--red error <?= empty($message) ? 'hide' : 'show' ?>">
118+
<i class="material-icons">error</i>
119+
120+
<span class="mdl-typography--caption">
121+
<?= htmlentities($message) ?>
122+
</span>
123+
</p>
124+
</div>
125+
126+
<div class="mdl-card__actions" layout-children="row">
127+
<span flex></span>
128+
<!-- used input instead of button to avoid form submission on click -->
129+
<input type="button" onclick="verifyU2f()"
130+
class="mdl-button mdl-color-text--red hide"
131+
value="<?= $this->t('{material:mfa:button_try_again}') ?>">
132+
133+
</div>
134+
</div>
135+
136+
<div>
137+
<label class="mdl-checkbox mdl-js-checkbox mdl-js-ripple-effect">
138+
<span class="mdl-checkbox__label">
139+
<?= $this->t('{material:mfa:remember_this}') ?>
140+
</span>
141+
<input type="checkbox" name="rememberMe" value="true" checked
142+
class="mdl-checkbox__input"/>
143+
</label>
144+
</div>
145+
</form>
146+
</main>
147+
</div>
148+
</body>
149+
</html>

0 commit comments

Comments
 (0)