286 lines
11 KiB
HTML
286 lines
11 KiB
HTML
<!DOCTYPE html>
|
||
|
||
<html
|
||
lang="en-US"
|
||
class="light-style customizer-hide"
|
||
>
|
||
<head>
|
||
<meta charset="utf-8" />
|
||
<meta
|
||
name="viewport"
|
||
content="width=device-width, initial-scale=1.0, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0"
|
||
/>
|
||
|
||
<title>Login - amiPro sample site </title>
|
||
|
||
<meta name="description" content="" />
|
||
|
||
<!-- Favicon -->
|
||
<link rel="icon" type="image/x-icon" href="files/favicon.ico" />
|
||
|
||
<!-- Fonts -->
|
||
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
||
<link
|
||
href="https://fonts.googleapis.com/css2?family=Public+Sans:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&display=swap"
|
||
rel="stylesheet"
|
||
/>
|
||
|
||
<!-- Icons. Uncomment required icon fonts -->
|
||
<!-- link rel="stylesheet" href="../assets/vendor/fonts/boxicons.css" / -->
|
||
|
||
<!-- Core CSS -->
|
||
<link rel="stylesheet" href="files/core.css" class="template-customizer-core-css" />
|
||
<link rel="stylesheet" href="files/theme-default.css" class="template-customizer-theme-css" />
|
||
<link rel="stylesheet" href="files/demo.css" />
|
||
|
||
<!-- Vendors CSS -->
|
||
<link rel="stylesheet" href="files/perfect-scrollbar.css" />
|
||
|
||
<!-- Page CSS -->
|
||
<!-- Page -->
|
||
<link rel="stylesheet" href="files/page-auth.css" />
|
||
<!-- Helpers -->
|
||
<script src="files/helpers.js"></script>
|
||
|
||
<!--! Template customizer & Theme config files MUST be included after core stylesheets and helpers.js in the <head> section -->
|
||
<!--? Config: Mandatory theme config file contain global vars & default theme options, Set your preferred theme option in this file. -->
|
||
<script src="files/config.js"></script>
|
||
|
||
<script src="files/popper.js"></script>
|
||
<script src="files/bootstrap.js"></script>
|
||
<script src="files/perfect-scrollbar.js"></script>
|
||
<script src="files/menu.js"></script>
|
||
<script src="files/main.js"></script>
|
||
|
||
<script src="files/amipro_utils.js?v=20260118"></script>
|
||
<script src="files/dfido2-lib.js?v=20260118"></script>
|
||
|
||
<script>
|
||
<!--
|
||
// For stand alone: 'https://local.dqj-macpro.com'
|
||
// For proxy: set 'https://mac-air-m2.dqj-home.com'
|
||
-->
|
||
setFidoServerURL('https://fido2.amipro.me'); //'https://local.dqj-macpro.com');
|
||
|
||
const i18n_messages = new Map();
|
||
|
||
var lang_map = new Map();
|
||
lang_map.set("en-US", "Welcome to amiPro sample site!");
|
||
lang_map.set("zh-CN", "欢迎来到 amiPro 示例网站!");
|
||
lang_map.set("ja", "amiPro サンプルサイトへようこそ!");
|
||
i18n_messages.set("msg_welcome", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Please sign in to your account and register your devices.");
|
||
lang_map.set("zh-CN", "请登录您的帐户并注册设备。");
|
||
lang_map.set("ja", "アカウントにサインインして、デバイスを登録してください。");
|
||
i18n_messages.set("msg_intro", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "USER ID");
|
||
lang_map.set("zh-CN", "用户ID");
|
||
lang_map.set("ja", "ユーザーID");
|
||
i18n_messages.set("msg_uid", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "PASSWORD");
|
||
lang_map.set("zh-CN", "密码");
|
||
lang_map.set("ja", "パスワード");
|
||
i18n_messages.set("msg_pw", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Any password can sign in");
|
||
lang_map.set("zh-CN", "任意密码可登录");
|
||
lang_map.set("ja", "任意のパスワードでログインできます");
|
||
i18n_messages.set("msg_pw_intro", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Sign in");
|
||
lang_map.set("zh-CN", "登录");
|
||
lang_map.set("ja", "ログイン");
|
||
i18n_messages.set("msg_sign_in", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Input User ID, please!");
|
||
lang_map.set("zh-CN", "请输入用户ID!");
|
||
lang_map.set("ja", "ユーザーIDを入力してください!");
|
||
i18n_messages.set("msg_uid_input", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Passwordless login");
|
||
lang_map.set("zh-CN", "无密码登录");
|
||
lang_map.set("ja", "パスワードレス ログイン");
|
||
i18n_messages.set("title_fido2_login", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "This sample is production-oriented.");
|
||
lang_map.set("zh-CN", "此示例面向生产环境。");
|
||
lang_map.set("ja", "このサンプルは本番指向です。");
|
||
i18n_messages.set("msg_prod_note_title", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Handles real-world browser differences");
|
||
lang_map.set("zh-CN", "处理真实世界的浏览器差异");
|
||
lang_map.set("ja", "実際のブラウザー差異に対応");
|
||
i18n_messages.set("msg_prod_note_1", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Uses recommended WebAuthn options");
|
||
lang_map.set("zh-CN", "使用推荐的 WebAuthn 选项");
|
||
lang_map.set("ja", "推奨される WebAuthn オプションを使用");
|
||
i18n_messages.set("msg_prod_note_2", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Mirrors production flow (RP ID, challenge, verification)");
|
||
lang_map.set("zh-CN", "模拟生产流程(RP ID、质询、验证)");
|
||
lang_map.set("ja", "本番フロー(RP ID、チャレンジ、検証)を再現");
|
||
i18n_messages.set("msg_prod_note_3", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "Safe to use as a starting point");
|
||
lang_map.set("zh-CN", "可安全作为起点使用");
|
||
lang_map.set("ja", "スターターとして安全に利用可能");
|
||
i18n_messages.set("msg_prod_note_4", lang_map);
|
||
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "15-minute integration guide");
|
||
lang_map.set("zh-CN", "15分钟接入指南");
|
||
lang_map.set("ja", "15分での導入ガイド");
|
||
i18n_messages.set("msg_integration_link", lang_map);
|
||
|
||
window.onload = function() {
|
||
logoutFido2UserSession();
|
||
|
||
if(canTryAutoAuthentication()){
|
||
lang_map = new Map();
|
||
lang_map.set("en-US", "If automatic login fails, enter your user ID and click Passwordless login.");
|
||
lang_map.set("zh-CN", "如果自动登录失败,请输入用户ID并点击“无密码登录”。");
|
||
lang_map.set("ja", "自動ログインに失敗した場合は、ユーザーIDを入力して「パスワードレス ログイン」をクリックしてください。");
|
||
i18n_messages.set("msg_intro", lang_map);
|
||
setI18NText(i18n_messages)
|
||
authenticate()
|
||
}else{
|
||
setI18NText(i18n_messages)
|
||
}
|
||
}
|
||
|
||
async function authenticate(){
|
||
var uid = document.getElementById('uid').value
|
||
if(uid && 0==uid.length)uid=null
|
||
|
||
const result = await authenticateFido2(uid)
|
||
|
||
if(result.status === 'ok'){
|
||
location.href = 'devices.html?uid='+result.username
|
||
}else{
|
||
errProcessFido2(result)
|
||
}
|
||
}
|
||
|
||
function checkInput(){
|
||
const uid = document.getElementById('uid').value
|
||
if(!uid || 0>=uid.length){
|
||
alert(document.getElementById('msg_uid_input').textContent)
|
||
return false;
|
||
}else return true;
|
||
}
|
||
|
||
</script>
|
||
</head>
|
||
<body>
|
||
<!-- Content -->
|
||
|
||
<div class="container-xxl">
|
||
<div class="authentication-wrapper authentication-basic container-p-y">
|
||
<div class="authentication-inner">
|
||
<!-- Register -->
|
||
<div class="card">
|
||
<div class="card-body">
|
||
<!-- Logo -->
|
||
<div class="app-brand justify-content-center">
|
||
<a href="https://www.amiPro.me/" class="app-brand-link gap-2">
|
||
<img style="width:160px;" src="files/favicon.ico"/>
|
||
</a>
|
||
</div>
|
||
<!-- /Logo -->
|
||
<h4 class="mb-2" id="msg_welcome">Welcome to amiPro sample site!</h4>
|
||
<p class="mb-4" id="msg_intro">Please sign-in to your account and start the adventure</p>
|
||
|
||
<div class="mb-4">
|
||
<p class="fw-semibold mb-2" id="msg_prod_note_title">This sample is production-oriented.</p>
|
||
<ul class="ps-3 mb-4" style="list-style: disc;">
|
||
<li id="msg_prod_note_1">Handles real-world browser differences</li>
|
||
<li id="msg_prod_note_2">Uses recommended WebAuthn options</li>
|
||
<li id="msg_prod_note_3">Mirrors production flow (RP ID, challenge, verification)</li>
|
||
<li id="msg_prod_note_4">Safe to use as a starting point</li>
|
||
</ul>
|
||
<p class="mb-4">
|
||
<a id="msg_integration_link" href="https://www.amipro.me/integration.html" target="_blank" rel="noopener">30-minute integration guide</a>
|
||
</p>
|
||
</div>
|
||
|
||
<div id="msg_uid_input" style="display:none;">Input User ID, please!</div>
|
||
|
||
<form class="mb-3" action="devices.html" method="GET" onsubmit="return checkInput();">
|
||
<div class="mb-3">
|
||
<label for="email" class="form-label" id="msg_uid" name="uid">User ID</label>
|
||
<input
|
||
type="text"
|
||
class="form-control"
|
||
id="uid"
|
||
name="uid"
|
||
placeholder="Enter your User ID"
|
||
autofocus
|
||
/>
|
||
</div>
|
||
<div class="mb-3 form-password-toggle">
|
||
<div class="d-flex justify-content-between">
|
||
<label class="form-label" for="password" id="msg_pw">Password</label>
|
||
<small id="msg_pw_intro">Any password can login</small>
|
||
</div>
|
||
<div class="input-group input-group-merge">
|
||
<input
|
||
type="password"
|
||
id="password"
|
||
class="form-control"
|
||
name="password"
|
||
placeholder="············"
|
||
aria-describedby="password"
|
||
/>
|
||
<span class="input-group-text cursor-pointer"><i class="bx bx-hide"></i></span>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="mb-3">
|
||
<button class="btn btn-primary d-grid w-100" style="background-color: #ce59d9;border-color: #ce59d9;" id="msg_sign_in">Sign in</button>
|
||
</div>
|
||
</form>
|
||
|
||
<p class="text-center" id="fido_btn">
|
||
<a href="javascript:authenticate(true);">
|
||
<span id="title_fido2_login">Passwordless login</span>
|
||
</a>
|
||
</p>
|
||
</div>
|
||
</div>
|
||
<!-- /Register -->
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- / Content -->
|
||
|
||
<!-- div class="buy-now">
|
||
<a
|
||
href="https://themeselection.com/products/sneat-bootstrap-html-admin-template/"
|
||
target="_blank"
|
||
class="btn btn-danger btn-buy-now"
|
||
>Change language</a
|
||
>
|
||
</div -->
|
||
|
||
<script async defer src="https://buttons.github.io/buttons.js"></script>
|
||
</body>
|
||
</html>
|