277 lines
11 KiB
Svelte
277 lines
11 KiB
Svelte
<script>
|
|
import { apikey, lang, api_endpoint, laptime_track } from "./store.js";
|
|
import isURL from "validator/lib/isURL";
|
|
import isUUID from "validator/lib/isUUID";
|
|
import axios from "axios";
|
|
import { _, locale } from "svelte-i18n";
|
|
let token;
|
|
let api_endpoint_input = "";
|
|
let track;
|
|
$: error = false;
|
|
$: errormessage = "";
|
|
$: isTokenValid =
|
|
token?.length === 44 &&
|
|
token.split(".")[0].length === 7 &&
|
|
isUUID(token.split(".")[1]);
|
|
$: isEndpointValid = isURL(api_endpoint_input);
|
|
</script>
|
|
|
|
<div class="w-full flex flex-wrap">
|
|
<!-- Login Section -->
|
|
<div class="w-full md:w-1/2 flex flex-col">
|
|
<div class="flex justify-center md:justify-start pt-12 md:pl-12 md:-mb-24">
|
|
<div class="bg-black text-white font-bold text-xl p-4">
|
|
<img src="./favicon.png" alt="" style="height: 3rem;display: inline;" />
|
|
LfK! Beamershow
|
|
</div>
|
|
</div>
|
|
|
|
<div
|
|
class="flex flex-col justify-center md:justify-start my-auto pt-8 md:pt-0 px-8 md:px-24 lg:px-32"
|
|
>
|
|
<p class="text-center text-3xl">{$_("configuration")}</p>
|
|
<p class="text-center">
|
|
<a
|
|
target="_blank"
|
|
class="underline"
|
|
href="https://docs.lauf-fuer-kaya.de/"
|
|
>{$_("see_our_configuration_guide")}</a
|
|
>
|
|
</p>
|
|
{#if error}
|
|
{#if errormessage === "invalid_token"}
|
|
<div
|
|
class="text-white px-6 py-4 border-0 rounded relative bg-red-500 mt-2"
|
|
>
|
|
<span class="inline-block align-middle">
|
|
<b class="capitalize">{$_("error")}</b><br />{$_(
|
|
"the_provided_scan_station_token_is_invalid"
|
|
)}<br />{$_("please_check_your_token_and_try_again")}
|
|
</span>
|
|
</div>
|
|
{/if}
|
|
{#if errormessage === "station_disabled"}
|
|
<div
|
|
class="text-white px-6 py-4 border-0 rounded relative bg-red-500 mt-2"
|
|
>
|
|
<span class="inline-block align-middle">
|
|
<b class="capitalize">{$_("error")}</b><br />{$_(
|
|
"the_provided_scan_station_is_disabled"
|
|
)}
|
|
</span>
|
|
</div>
|
|
{/if}
|
|
{/if}
|
|
{#if $api_endpoint && !$apikey}
|
|
<form
|
|
class="flex flex-col pt-3 md:pt-8"
|
|
onsubmit="event.preventDefault();"
|
|
on:submit={() => {
|
|
axios
|
|
.request({
|
|
method: "GET",
|
|
url: $api_endpoint + "api/stats/runners/distance",
|
|
headers: { Authorization: "Bearer " + token },
|
|
})
|
|
.then(function (response) {
|
|
error = false;
|
|
errormessage = "";
|
|
apikey.set(token);
|
|
})
|
|
.catch(function (e) {
|
|
error = true;
|
|
errormessage = e.response.data.short;
|
|
});
|
|
}}
|
|
>
|
|
<div class="flex flex-col pt-4">
|
|
<label for="token" class="text-lg">{$_("client_token")}</label>
|
|
<input
|
|
type="text"
|
|
id="token"
|
|
placeholder={$_("client_token")}
|
|
bind:value={token}
|
|
class:border-red-500={!isTokenValid}
|
|
class:border-solid={!isTokenValid}
|
|
class:border-3={!isTokenValid}
|
|
class="shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mt-1 leading-tight focus:outline-none focus:shadow-outline"
|
|
/>
|
|
</div>
|
|
{#if !isTokenValid}
|
|
<span class="text-sm"
|
|
>{$_("please_provide_a_valid_client_token")}</span
|
|
>
|
|
{/if}
|
|
<button
|
|
disabled={!isTokenValid}
|
|
class:cursor-pointer={isTokenValid}
|
|
class:opacity-50={!isTokenValid}
|
|
id="configure"
|
|
type="submit"
|
|
class="bg-black text-white font-bold text-lg hover:bg-gray-700 p-2 mt-8 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-black"
|
|
>{$_("configure")}</button
|
|
>
|
|
</form>
|
|
{:else if $api_endpoint && $apikey}
|
|
<form
|
|
class="flex flex-col pt-3 md:pt-8"
|
|
onsubmit="event.preventDefault();"
|
|
on:submit={() => {
|
|
laptime_track.set(track);
|
|
}}
|
|
>
|
|
<div class="flex flex-col pt-4">
|
|
<label for="track" class="text-lg">{$_("track_id")}</label>
|
|
<input
|
|
type="number"
|
|
id="track"
|
|
placeholder="Track"
|
|
bind:value={track}
|
|
class:border-red-500={!isTokenValid}
|
|
class:border-solid={!isTokenValid}
|
|
class:border-3={!isTokenValid}
|
|
class="shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mt-1 leading-tight focus:outline-none focus:shadow-outline"
|
|
/>
|
|
</div>
|
|
<button
|
|
disabled={!track}
|
|
class:cursor-pointer={track}
|
|
class:opacity-50={!track}
|
|
id="configure"
|
|
type="submit"
|
|
class="bg-black text-white font-bold text-lg hover:bg-gray-700 p-2 mt-8 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-black"
|
|
>{$_("configure")}</button
|
|
>
|
|
</form>
|
|
{:else}
|
|
<form
|
|
class="flex flex-col pt-3 md:pt-8"
|
|
onsubmit="event.preventDefault();"
|
|
on:submit={() => {
|
|
if (api_endpoint_input.substr(-1) !== "/") {
|
|
api_endpoint_input = api_endpoint_input + "/";
|
|
}
|
|
api_endpoint.set(api_endpoint_input);
|
|
}}
|
|
>
|
|
<div class="flex flex-col pt-4">
|
|
<label for="api_endpoint" class="text-lg"
|
|
>{$_("api_endpoint")}</label
|
|
>
|
|
<input
|
|
type="text"
|
|
id="api_endpoint"
|
|
placeholder={$_("api_endpoint")}
|
|
bind:value={api_endpoint_input}
|
|
class:border-red-500={!isEndpointValid}
|
|
class:border-solid={!isEndpointValid}
|
|
class:border-3={!isEndpointValid}
|
|
class="shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mt-1 leading-tight focus:outline-none focus:shadow-outline"
|
|
/>
|
|
</div>
|
|
{#if !isEndpointValid}
|
|
<span class="text-sm"
|
|
>{$_("please_provide_a_valid_client_api_endpoint")}</span
|
|
>
|
|
{/if}
|
|
<button
|
|
disabled={!isEndpointValid}
|
|
class:cursor-pointer={isEndpointValid}
|
|
class:opacity-50={!isEndpointValid}
|
|
id="configure"
|
|
type="submit"
|
|
class="bg-black text-white font-bold text-lg hover:bg-gray-700 p-2 mt-8 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-black"
|
|
>{$_("configure")}</button
|
|
>
|
|
</form>
|
|
{/if}
|
|
<div class="text-center pt-12 pb-12">
|
|
<p>
|
|
<svg
|
|
style="height: 1rem;display: inline;"
|
|
xmlns="http://www.w3.org/2000/svg"
|
|
fill="none"
|
|
stroke="currentColor"
|
|
stroke-width="2"
|
|
stroke-linecap="round"
|
|
stroke-linejoin="round"
|
|
class="feather feather-zap"
|
|
viewBox="0 0 24 24"
|
|
>
|
|
<path d="M13 2L3 14h9l-1 8 10-12h-9l1-8z" />
|
|
</svg><span
|
|
>powered by <a
|
|
href="https://odit.services"
|
|
target="_blank"
|
|
class="underline">ODIT.Services</a
|
|
>.</span
|
|
>
|
|
</p>
|
|
</div>
|
|
</div>
|
|
<div class="w-full p-3">
|
|
<div class="inline-block mr-2 mt-2">
|
|
<button
|
|
on:click={() => {
|
|
lang.set("de-DE");
|
|
locale.set("de-DE");
|
|
}}
|
|
type="button"
|
|
class="bg-black focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-black text-white text-sm py-2.5 px-5 rounded-md hover:bg-blue-700"
|
|
>Deutsch
|
|
<svg
|
|
class="h-4 inline"
|
|
xmlns="http://www.w3.org/2000/svg"
|
|
viewBox="0 0 512 512"
|
|
><path
|
|
d="M15.923 345.043C52.094 442.527 145.929 512 256 512s203.906-69.473 240.077-166.957L256 322.783l-240.077 22.26z"
|
|
fill="#ffda44"
|
|
/><path
|
|
d="M256 0C145.929 0 52.094 69.472 15.923 166.957L256 189.217l240.077-22.261C459.906 69.472 366.071 0 256 0z"
|
|
/><path
|
|
d="M15.923 166.957C5.633 194.69 0 224.686 0 256s5.633 61.31 15.923 89.043h480.155C506.368 317.31 512 287.314 512 256s-5.632-61.31-15.923-89.043H15.923z"
|
|
fill="#d80027"
|
|
/></svg
|
|
></button
|
|
>
|
|
</div>
|
|
<div class="inline-block mr-2 mt-2">
|
|
<button
|
|
on:click={() => {
|
|
lang.set("en-US");
|
|
locale.set("en-US");
|
|
}}
|
|
type="button"
|
|
class="bg-black focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-black text-white text-sm py-2.5 px-5 rounded-md hover:bg-blue-700"
|
|
>English
|
|
<svg
|
|
class="h-4 inline"
|
|
xmlns="http://www.w3.org/2000/svg"
|
|
viewBox="0 0 512 512"
|
|
>
|
|
<circle cx="256" cy="256" r="256" fill="#f0f0f0" />
|
|
<g fill="#d80027">
|
|
<path
|
|
d="M244.87 256H512c0-23.106-3.08-45.49-8.819-66.783H244.87V256zM244.87 122.435h229.556a257.35 257.35 0 00-59.07-66.783H244.87v66.783zM256 512c60.249 0 115.626-20.824 159.356-55.652H96.644C140.374 491.176 195.751 512 256 512zM37.574 389.565h436.852a254.474 254.474 0 0028.755-66.783H8.819a254.474 254.474 0 0028.755 66.783z"
|
|
/>
|
|
</g>
|
|
<path
|
|
d="M118.584 39.978h23.329l-21.7 15.765 8.289 25.509-21.699-15.765-21.699 15.765 7.16-22.037a257.407 257.407 0 00-49.652 55.337h7.475l-13.813 10.035a255.58 255.58 0 00-6.194 10.938l6.596 20.301-12.306-8.941a253.567 253.567 0 00-8.372 19.873l7.267 22.368h26.822l-21.7 15.765 8.289 25.509-21.699-15.765-12.998 9.444A258.468 258.468 0 000 256h256V0c-50.572 0-97.715 14.67-137.416 39.978zm9.918 190.422l-21.699-15.765L85.104 230.4l8.289-25.509-21.7-15.765h26.822l8.288-25.509 8.288 25.509h26.822l-21.7 15.765 8.289 25.509zm-8.289-100.083l8.289 25.509-21.699-15.765-21.699 15.765 8.289-25.509-21.7-15.765h26.822l8.288-25.509 8.288 25.509h26.822l-21.7 15.765zM220.328 230.4l-21.699-15.765L176.93 230.4l8.289-25.509-21.7-15.765h26.822l8.288-25.509 8.288 25.509h26.822l-21.7 15.765 8.289 25.509zm-8.289-100.083l8.289 25.509-21.699-15.765-21.699 15.765 8.289-25.509-21.7-15.765h26.822l8.288-25.509 8.288 25.509h26.822l-21.7 15.765zm0-74.574l8.289 25.509-21.699-15.765-21.699 15.765 8.289-25.509-21.7-15.765h26.822l8.288-25.509 8.288 25.509h26.822l-21.7 15.765z"
|
|
fill="#0052b4"
|
|
/>
|
|
</svg></button
|
|
>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Image Section -->
|
|
<div class="w-1/2 shadow-2xl">
|
|
<img
|
|
alt=""
|
|
class="object-cover w-full h-screen hidden md:block"
|
|
src="https://source.unsplash.com/IXUM4cJynP0"
|
|
/>
|
|
</div>
|
|
</div>
|