Update prettier settings
This commit is contained in:
@@ -1,8 +1,8 @@
|
||||
<script>
|
||||
import { page } from '$app/stores';
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
const title = 'OwlBoard - Error';
|
||||
import { page } from "$app/stores";
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
const title = "OwlBoard - Error";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -10,16 +10,16 @@
|
||||
<h1>{$page.status}: {$page?.error?.message}</h1>
|
||||
|
||||
{#if $page.status === 404}
|
||||
<p>This is not the page you're looking for.</p>
|
||||
<p>The page you are looking for doesn't exist, use the tabs below to find another page.</p>
|
||||
<p>This is not the page you're looking for.</p>
|
||||
<p>The page you are looking for doesn't exist, use the tabs below to find another page.</p>
|
||||
{:else if $page.status === 500}
|
||||
<p>
|
||||
Something went wrong loading the app.<br />
|
||||
Try going <a href="/">home</a> and try again.
|
||||
</p>
|
||||
<p>If the problem persists, you can report an issue from the 'More' menu.</p>
|
||||
<p>
|
||||
Something went wrong loading the app.<br />
|
||||
Try going <a href="/">home</a> and try again.
|
||||
</p>
|
||||
<p>If the problem persists, you can report an issue from the 'More' menu.</p>
|
||||
{:else}
|
||||
<p>Not sure what went wrong, please try again later or report an issue from the 'More' menu.</p>
|
||||
<p>Not sure what went wrong, please try again later or report an issue from the 'More' menu.</p>
|
||||
{/if}
|
||||
|
||||
<Nav />
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
<script>
|
||||
import '$lib/themes.css';
|
||||
import '$lib/main.css';
|
||||
import { dev } from '$app/environment';
|
||||
import DevBanner from '$lib/DevBanner.svelte';
|
||||
import { page } from '$app/stores';
|
||||
import "$lib/themes.css";
|
||||
import "$lib/main.css";
|
||||
import { dev } from "$app/environment";
|
||||
import DevBanner from "$lib/DevBanner.svelte";
|
||||
import { page } from "$app/stores";
|
||||
</script>
|
||||
|
||||
<svelte:head>
|
||||
<!--
|
||||
<!--
|
||||
___ _ ___ _
|
||||
/ _ \__ __ _| | _ ) ___ __ _ _ _ __| |
|
||||
| (_) \ V V / | _ \/ _ \/ _` | '_/ _` |
|
||||
@@ -16,21 +16,21 @@
|
||||
It's easier to read there
|
||||
-->
|
||||
|
||||
<meta name="application-name" content="OwlBoard" />
|
||||
<meta name="author" content="Frederick Boniface" />
|
||||
<meta
|
||||
name="description"
|
||||
content="Get instant access to live train data, PIS codes, and location reference codes. Built by railway staff, for railway staff – your fastest route to accurate information."
|
||||
/>
|
||||
<meta name="viewport" content="width=device-width" />
|
||||
<meta name="theme-color" content="#00b7b7" />
|
||||
<link rel="canonical" href="https://owlboard.info{$page.url.pathname}" />
|
||||
<link rel="icon" href="/images/icon.svg" type="image/svg+xml" />
|
||||
<link rel="apple-touch-icon" href="/images/app-icons/any/apple-192.png" />
|
||||
<link rel="manifest" href="/manifest.json" />
|
||||
<title>OwlBoard</title>
|
||||
<meta name="application-name" content="OwlBoard" />
|
||||
<meta name="author" content="Frederick Boniface" />
|
||||
<meta
|
||||
name="description"
|
||||
content="Get instant access to live train data, PIS codes, and location reference codes. Built by railway staff, for railway staff – your fastest route to accurate information."
|
||||
/>
|
||||
<meta name="viewport" content="width=device-width" />
|
||||
<meta name="theme-color" content="#00b7b7" />
|
||||
<link rel="canonical" href="https://owlboard.info{$page.url.pathname}" />
|
||||
<link rel="icon" href="/images/icon.svg" type="image/svg+xml" />
|
||||
<link rel="apple-touch-icon" href="/images/app-icons/any/apple-192.png" />
|
||||
<link rel="manifest" href="/manifest.json" />
|
||||
<title>OwlBoard</title>
|
||||
</svelte:head>
|
||||
{#if dev}
|
||||
<DevBanner />
|
||||
<DevBanner />
|
||||
{/if}
|
||||
<slot />
|
||||
|
||||
@@ -1,36 +1,36 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import InputIsland from '$lib/islands/input-island-form.svelte';
|
||||
import QuickLinkIsland from '$lib/islands/quick-link-island.svelte';
|
||||
import Welcome from '$lib/overlays/welcome.svelte';
|
||||
import { welcome } from '$lib/stores/welcome';
|
||||
import { version, showWelcome } from '$lib/stores/version';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import InputIsland from "$lib/islands/input-island-form.svelte";
|
||||
import QuickLinkIsland from "$lib/islands/quick-link-island.svelte";
|
||||
import Welcome from "$lib/overlays/welcome.svelte";
|
||||
import { welcome } from "$lib/stores/welcome";
|
||||
import { version, showWelcome } from "$lib/stores/version";
|
||||
|
||||
const title = 'OwlBoard';
|
||||
const inputIslands = [
|
||||
{
|
||||
title: 'Live Departure Boards',
|
||||
action: '/ldb',
|
||||
placeholder: 'Enter CRS/TIPLOC',
|
||||
queryName: 'station'
|
||||
},
|
||||
{
|
||||
title: 'Train Details & PIS',
|
||||
action: '/train',
|
||||
placeholder: 'Enter Headcode',
|
||||
queryName: 'headcode'
|
||||
}
|
||||
];
|
||||
const title = "OwlBoard";
|
||||
const inputIslands = [
|
||||
{
|
||||
title: "Live Departure Boards",
|
||||
action: "/ldb",
|
||||
placeholder: "Enter CRS/TIPLOC",
|
||||
queryName: "station"
|
||||
},
|
||||
{
|
||||
title: "Train Details & PIS",
|
||||
action: "/train",
|
||||
placeholder: "Enter Headcode",
|
||||
queryName: "headcode"
|
||||
}
|
||||
];
|
||||
</script>
|
||||
|
||||
{#if showWelcome && ($welcome === 'null' || !$welcome || parseInt($welcome.replace(/\./g, '')) < parseInt(version.replace(/\./g, '')))}
|
||||
<Welcome />
|
||||
{#if showWelcome && ($welcome === "null" || !$welcome || parseInt($welcome.replace(/\./g, "")) < parseInt(version.replace(/\./g, "")))}
|
||||
<Welcome />
|
||||
{/if}
|
||||
<Header {title} />
|
||||
|
||||
{#each inputIslands as variables}
|
||||
<InputIsland {variables} />
|
||||
<InputIsland {variables} />
|
||||
{/each}
|
||||
|
||||
<QuickLinkIsland />
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script lang="ts">
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
|
||||
const title = '404 - Not Found';
|
||||
const title = "404 - Not Found";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -14,10 +14,10 @@
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
.heading {
|
||||
color: var(--second-text-color);
|
||||
}
|
||||
.err_code {
|
||||
color: white;
|
||||
}
|
||||
.heading {
|
||||
color: var(--second-text-color);
|
||||
}
|
||||
.err_code {
|
||||
color: white;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script lang="ts">
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
|
||||
const title = '50x - Server Error';
|
||||
const title = "50x - Server Error";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -14,10 +14,10 @@
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
.heading {
|
||||
color: var(--second-text-color);
|
||||
}
|
||||
.err_code {
|
||||
color: white;
|
||||
}
|
||||
.heading {
|
||||
color: var(--second-text-color);
|
||||
}
|
||||
.err_code {
|
||||
color: white;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,42 +1,42 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav-ldb.svelte';
|
||||
import PublicLdb from '$lib/ldb/public-ldb.svelte';
|
||||
import StaffLdb from '$lib/ldb/staff/staff-ldb.svelte';
|
||||
import { uuid } from '$lib/stores/uuid.js';
|
||||
import { onMount } from 'svelte';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav-ldb.svelte";
|
||||
import PublicLdb from "$lib/ldb/public-ldb.svelte";
|
||||
import StaffLdb from "$lib/ldb/staff/staff-ldb.svelte";
|
||||
import { uuid } from "$lib/stores/uuid.js";
|
||||
import { onMount } from "svelte";
|
||||
|
||||
let title = 'Loading';
|
||||
let title = "Loading";
|
||||
|
||||
async function getHeadcode() {
|
||||
return new URLSearchParams(window.location.search).get('station');
|
||||
}
|
||||
|
||||
let station = '';
|
||||
let staff = false;
|
||||
let uuidValue = '';
|
||||
|
||||
$: uuidValue = $uuid;
|
||||
|
||||
onMount(async () => {
|
||||
station = (await getHeadcode()) || '';
|
||||
if (uuidValue !== null && uuidValue !== '' && uuidValue !== 'null') {
|
||||
staff = true;
|
||||
title = 'Staff Board';
|
||||
} else {
|
||||
title = 'Public Board';
|
||||
async function getHeadcode() {
|
||||
return new URLSearchParams(window.location.search).get("station");
|
||||
}
|
||||
});
|
||||
|
||||
let station = "";
|
||||
let staff = false;
|
||||
let uuidValue = "";
|
||||
|
||||
$: uuidValue = $uuid;
|
||||
|
||||
onMount(async () => {
|
||||
station = (await getHeadcode()) || "";
|
||||
if (uuidValue !== null && uuidValue !== "" && uuidValue !== "null") {
|
||||
staff = true;
|
||||
title = "Staff Board";
|
||||
} else {
|
||||
title = "Public Board";
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
<!-- If 'uuid' exists in store then load StaffLdb else load PublicLdb -->
|
||||
{#if !staff}
|
||||
<PublicLdb {station} bind:title />
|
||||
<PublicLdb {station} bind:title />
|
||||
{:else}
|
||||
<StaffLdb {station} bind:title />
|
||||
<!--<StaffLdb {station} bind:title={title} /> -- Temporary, Disable StaffLdb - it isn't implemented -->
|
||||
<StaffLdb {station} bind:title />
|
||||
<!--<StaffLdb {station} bind:title={title} /> -- Temporary, Disable StaffLdb - it isn't implemented -->
|
||||
{/if}
|
||||
|
||||
<Nav />
|
||||
|
||||
@@ -1,77 +1,89 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { IconCode, IconHelp, IconInfoCircle, IconLocation, IconMessageCode, IconNumber, IconSettings, IconSpy, IconUser, IconUserPlus, IconVersions } from '@tabler/icons-svelte';
|
||||
const title = 'More';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import {
|
||||
IconCode,
|
||||
IconHelp,
|
||||
IconInfoCircle,
|
||||
IconLocation,
|
||||
IconMessageCode,
|
||||
IconNumber,
|
||||
IconSettings,
|
||||
IconSpy,
|
||||
IconUser,
|
||||
IconUserPlus,
|
||||
IconVersions
|
||||
} from "@tabler/icons-svelte";
|
||||
const title = "More";
|
||||
|
||||
const links = [
|
||||
{ title: 'Your Data', path: '/more/data', icon: IconUser },
|
||||
{ title: 'Registration', path: '/more/reg', icon: IconUserPlus },
|
||||
{ title: 'Settings', path: '/more/settings', icon: IconSettings },
|
||||
{ title: 'Help', path: '/more/help', icon: IconHelp },
|
||||
{ title: 'About', path: '/more/about', icon: IconInfoCircle },
|
||||
{ title: 'Location Reference Code Lookup', path: '/more/corpus', icon: IconLocation },
|
||||
{ title: 'Reason Code Lookup', path: '/more/reasons', icon: IconMessageCode },
|
||||
{ title: 'Privacy Policy', path: '/more/privacy', icon: IconSpy },
|
||||
{ title: 'Component Versions', path: '/more/versions', icon: IconVersions },
|
||||
{ title: 'Statistics', path: '/more/statistics', icon: IconNumber }
|
||||
];
|
||||
const links = [
|
||||
{ title: "Your Data", path: "/more/data", icon: IconUser },
|
||||
{ title: "Registration", path: "/more/reg", icon: IconUserPlus },
|
||||
{ title: "Settings", path: "/more/settings", icon: IconSettings },
|
||||
{ title: "Help", path: "/more/help", icon: IconHelp },
|
||||
{ title: "About", path: "/more/about", icon: IconInfoCircle },
|
||||
{ title: "Location Reference Code Lookup", path: "/more/corpus", icon: IconLocation },
|
||||
{ title: "Reason Code Lookup", path: "/more/reasons", icon: IconMessageCode },
|
||||
{ title: "Privacy Policy", path: "/more/privacy", icon: IconSpy },
|
||||
{ title: "Component Versions", path: "/more/versions", icon: IconVersions },
|
||||
{ title: "Statistics", path: "/more/statistics", icon: IconNumber }
|
||||
];
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#each links as item}
|
||||
<a href={item.path}>
|
||||
<div>
|
||||
<svelte:component this={item.icon} />
|
||||
<p>{item.title}</p>
|
||||
</div>
|
||||
</a>
|
||||
<a href={item.path}>
|
||||
<div>
|
||||
<svelte:component this={item.icon} />
|
||||
<p>{item.title}</p>
|
||||
</div>
|
||||
</a>
|
||||
{/each}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
div {
|
||||
width: 100%;
|
||||
background: rgba(0, 0, 0, 0.226);
|
||||
border-color: aliceblue;
|
||||
border-width: 1px;
|
||||
border-style: solid;
|
||||
border-left: none;
|
||||
padding-left: 0.5rem;
|
||||
overflow-x: hidden;
|
||||
border-right: none;
|
||||
height: 50px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin-bottom: 0.5rem;
|
||||
}
|
||||
a {
|
||||
text-decoration: none;
|
||||
height: 100%;
|
||||
vertical-align: middle;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
p {
|
||||
color: white;
|
||||
margin: 0;
|
||||
padding-left: 10px;
|
||||
text-align: left;
|
||||
line-height: 50px;
|
||||
vertical-align: middle;
|
||||
font-weight: 600;
|
||||
font-size: 20px;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
p {
|
||||
text-align: center;
|
||||
div {
|
||||
width: 100%;
|
||||
background: rgba(0, 0, 0, 0.226);
|
||||
border-color: aliceblue;
|
||||
border-width: 1px;
|
||||
border-style: solid;
|
||||
border-left: none;
|
||||
padding-left: 0.5rem;
|
||||
overflow-x: hidden;
|
||||
border-right: none;
|
||||
height: 50px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin-bottom: 0.5rem;
|
||||
}
|
||||
}
|
||||
@media (max-width: 380px) {
|
||||
p {
|
||||
font-size: 16px;
|
||||
a {
|
||||
text-decoration: none;
|
||||
height: 100%;
|
||||
vertical-align: middle;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
p {
|
||||
color: white;
|
||||
margin: 0;
|
||||
padding-left: 10px;
|
||||
text-align: left;
|
||||
line-height: 50px;
|
||||
vertical-align: middle;
|
||||
font-weight: 600;
|
||||
font-size: 20px;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
p {
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
@media (max-width: 380px) {
|
||||
p {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
<script>
|
||||
import LargeLogo from '$lib/images/large-logo.svelte';
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import LargeLogo from "$lib/images/large-logo.svelte";
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
|
||||
const title = 'About';
|
||||
const title = "About";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -13,19 +13,19 @@
|
||||
<p>I developed OwlBoard in 2022 with the aim of providing fast and easy access to the information we need on a daily basis.</p>
|
||||
<p>Data is sourced from National Rail Enquiries, the OwlBoard Project, and Network Rail.</p>
|
||||
<p>
|
||||
OwlBoard components are available under various Open Source licenses. Please refer to the
|
||||
<a href="https://git.fjla.uk/OwlBoard" target="_blank">code repository</a>
|
||||
for more detailed information.
|
||||
OwlBoard components are available under various Open Source licenses. Please refer to the
|
||||
<a href="https://git.fjla.uk/OwlBoard" target="_blank">code repository</a>
|
||||
for more detailed information.
|
||||
</p>
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
.neg {
|
||||
margin-top: -40px;
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
.neg {
|
||||
margin-top: -40px;
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,78 +1,78 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
const title = 'Location Codes';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
const title = "Location Codes";
|
||||
|
||||
let val = {
|
||||
crs: '',
|
||||
tiploc: '',
|
||||
stanox: '',
|
||||
nlc: '',
|
||||
name: '',
|
||||
uic: ''
|
||||
};
|
||||
|
||||
let isLoading = false;
|
||||
|
||||
async function getData(type = '', value = '') {
|
||||
const url = `${getApiUrl()}/api/v2/ref/locationCode/${type}/${value}`;
|
||||
const res = await fetch(url);
|
||||
const data = await res.json();
|
||||
isLoading = false;
|
||||
return data;
|
||||
}
|
||||
|
||||
async function processData(data) {
|
||||
//console.log("data",JSON.stringify(data))
|
||||
if (data.ERROR == 'Offline') {
|
||||
return;
|
||||
}
|
||||
val = {
|
||||
crs: data[0]['3ALPHA'] || 'None',
|
||||
tiploc: data[0]['TIPLOC'] || 'None',
|
||||
stanox: data[0]['STANOX'] || 'None',
|
||||
nlc: data[0]['NLC'] || 'None',
|
||||
name: data[0]['NLCDESC'] || 'None',
|
||||
uic: data[0]['UIC'] || 'None'
|
||||
let val = {
|
||||
crs: "",
|
||||
tiploc: "",
|
||||
stanox: "",
|
||||
nlc: "",
|
||||
name: "",
|
||||
uic: ""
|
||||
};
|
||||
//console.log("val",JSON.stringify(val));
|
||||
}
|
||||
|
||||
async function submit() {
|
||||
isLoading = true;
|
||||
let data = [];
|
||||
if (val?.crs) {
|
||||
data = await getData('crs', val.crs);
|
||||
} else if (val?.tiploc) {
|
||||
data = await getData('tiploc', val.tiploc);
|
||||
} else if (val?.stanox) {
|
||||
data = await getData('stanox', val.stanox);
|
||||
} else if (val?.nlc) {
|
||||
data = await getData('nlc', val.nlc);
|
||||
} else {
|
||||
return;
|
||||
let isLoading = false;
|
||||
|
||||
async function getData(type = "", value = "") {
|
||||
const url = `${getApiUrl()}/api/v2/ref/locationCode/${type}/${value}`;
|
||||
const res = await fetch(url);
|
||||
const data = await res.json();
|
||||
isLoading = false;
|
||||
return data;
|
||||
}
|
||||
processData(data);
|
||||
}
|
||||
|
||||
async function reset() {
|
||||
val = {
|
||||
crs: '',
|
||||
tiploc: '',
|
||||
stanox: '',
|
||||
nlc: '',
|
||||
name: '',
|
||||
uic: ''
|
||||
};
|
||||
}
|
||||
async function processData(data) {
|
||||
//console.log("data",JSON.stringify(data))
|
||||
if (data.ERROR == "Offline") {
|
||||
return;
|
||||
}
|
||||
val = {
|
||||
crs: data[0]["3ALPHA"] || "None",
|
||||
tiploc: data[0]["TIPLOC"] || "None",
|
||||
stanox: data[0]["STANOX"] || "None",
|
||||
nlc: data[0]["NLC"] || "None",
|
||||
name: data[0]["NLCDESC"] || "None",
|
||||
uic: data[0]["UIC"] || "None"
|
||||
};
|
||||
//console.log("val",JSON.stringify(val));
|
||||
}
|
||||
|
||||
async function submit() {
|
||||
isLoading = true;
|
||||
let data = [];
|
||||
if (val?.crs) {
|
||||
data = await getData("crs", val.crs);
|
||||
} else if (val?.tiploc) {
|
||||
data = await getData("tiploc", val.tiploc);
|
||||
} else if (val?.stanox) {
|
||||
data = await getData("stanox", val.stanox);
|
||||
} else if (val?.nlc) {
|
||||
data = await getData("nlc", val.nlc);
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
processData(data);
|
||||
}
|
||||
|
||||
async function reset() {
|
||||
val = {
|
||||
crs: "",
|
||||
tiploc: "",
|
||||
stanox: "",
|
||||
nlc: "",
|
||||
name: "",
|
||||
uic: ""
|
||||
};
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{/if}
|
||||
|
||||
<p>Enter one of the codes below and press submit.</p>
|
||||
@@ -80,59 +80,59 @@
|
||||
<p class="desc">Some locations only have some applicable location codes.</p>
|
||||
|
||||
<div class="inputs">
|
||||
<form on:submit={submit}>
|
||||
<input type="text" readonly placeholder="Name" bind:value={val.name} />
|
||||
<br />
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="CRS/3ALPHA" bind:value={val.crs} />
|
||||
<br />
|
||||
<input type="text" maxlength="7" autocomplete="off" placeholder="TIPLOC" bind:value={val.tiploc} />
|
||||
<br />
|
||||
<input type="text" maxlength="10" autocomplete="off" placeholder="STANOX" bind:value={val.stanox} />
|
||||
<br />
|
||||
<input type="number" maxlength="6" min="0" autocomplete="off" placeholder="NLC" bind:value={val.nlc} />
|
||||
<br />
|
||||
<input type="text" readonly autocomplete="off" placeholder="UIC" bind:value={val.uic} />
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
<button type="reset" on:click={reset}>Reset</button>
|
||||
</form>
|
||||
<form on:submit={submit}>
|
||||
<input type="text" readonly placeholder="Name" bind:value={val.name} />
|
||||
<br />
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="CRS/3ALPHA" bind:value={val.crs} />
|
||||
<br />
|
||||
<input type="text" maxlength="7" autocomplete="off" placeholder="TIPLOC" bind:value={val.tiploc} />
|
||||
<br />
|
||||
<input type="text" maxlength="10" autocomplete="off" placeholder="STANOX" bind:value={val.stanox} />
|
||||
<br />
|
||||
<input type="number" maxlength="6" min="0" autocomplete="off" placeholder="NLC" bind:value={val.nlc} />
|
||||
<br />
|
||||
<input type="text" readonly autocomplete="off" placeholder="UIC" bind:value={val.uic} />
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
<button type="reset" on:click={reset}>Reset</button>
|
||||
</form>
|
||||
</div>
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin: 10px;
|
||||
}
|
||||
input {
|
||||
font-family: urwgothic, sans-serif;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
width: 60%;
|
||||
max-width: 200px;
|
||||
min-width: 130px;
|
||||
height: 30px;
|
||||
margin-bottom: 10px;
|
||||
text-transform: uppercase;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
background-color: var(--island-bg-color);
|
||||
border: none;
|
||||
color: white;
|
||||
height: 30px;
|
||||
width: 20%;
|
||||
max-width: 100px;
|
||||
min-width: 75px;
|
||||
font-size: 18px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
.desc {
|
||||
color: white;
|
||||
}
|
||||
input {
|
||||
text-align: center;
|
||||
}
|
||||
p {
|
||||
margin: 10px;
|
||||
}
|
||||
input {
|
||||
font-family: urwgothic, sans-serif;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
width: 60%;
|
||||
max-width: 200px;
|
||||
min-width: 130px;
|
||||
height: 30px;
|
||||
margin-bottom: 10px;
|
||||
text-transform: uppercase;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
background-color: var(--island-bg-color);
|
||||
border: none;
|
||||
color: white;
|
||||
height: 30px;
|
||||
width: 20%;
|
||||
max-width: 100px;
|
||||
min-width: 75px;
|
||||
font-size: 18px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
.desc {
|
||||
color: white;
|
||||
}
|
||||
input {
|
||||
text-align: center;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,38 +1,38 @@
|
||||
<script>
|
||||
import LogoutButton from '$lib/navigation/LogoutButton.svelte';
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import { uuid } from '$lib/stores/uuid.js';
|
||||
import { onMount } from 'svelte';
|
||||
const title = 'Your Data';
|
||||
import LogoutButton from "$lib/navigation/LogoutButton.svelte";
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
import { uuid } from "$lib/stores/uuid.js";
|
||||
import { onMount } from "svelte";
|
||||
const title = "Your Data";
|
||||
|
||||
let data = [
|
||||
{
|
||||
domain: 'User not Found',
|
||||
atime: 'User not Found'
|
||||
let data = [
|
||||
{
|
||||
domain: "User not Found",
|
||||
atime: "User not Found"
|
||||
}
|
||||
];
|
||||
|
||||
let isLoading = false;
|
||||
|
||||
async function fetchData() {
|
||||
if ($uuid != "null") {
|
||||
const url = `${getApiUrl()}/api/v2/user/${$uuid}`;
|
||||
const res = await fetch(url);
|
||||
const json = await res.json();
|
||||
if (json.length) {
|
||||
data = json;
|
||||
}
|
||||
}
|
||||
}
|
||||
];
|
||||
|
||||
let isLoading = false;
|
||||
|
||||
async function fetchData() {
|
||||
if ($uuid != 'null') {
|
||||
const url = `${getApiUrl()}/api/v2/user/${$uuid}`;
|
||||
const res = await fetch(url);
|
||||
const json = await res.json();
|
||||
if (json.length) {
|
||||
data = json;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onMount(async () => {
|
||||
isLoading = true;
|
||||
await fetchData();
|
||||
isLoading = false;
|
||||
});
|
||||
onMount(async () => {
|
||||
isLoading = true;
|
||||
await fetchData();
|
||||
isLoading = false;
|
||||
});
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -43,26 +43,26 @@
|
||||
<br /><br />
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
{:else if data[0].domain != 'User not Found'}
|
||||
<p class="api_response">Registration Domain: {data[0]['domain']}</p>
|
||||
<p class="api_response">Access Time: {data[0]['atime']}</p>
|
||||
<LogoutButton />
|
||||
<p>
|
||||
Clicking the logout button will delete your data from your browser. You will then be able to make a new account, your old account will remain inactive and be deleted after 90
|
||||
days.
|
||||
</p>
|
||||
<Loading />
|
||||
{:else if data[0].domain != "User not Found"}
|
||||
<p class="api_response">Registration Domain: {data[0]["domain"]}</p>
|
||||
<p class="api_response">Access Time: {data[0]["atime"]}</p>
|
||||
<LogoutButton />
|
||||
<p>
|
||||
Clicking the logout button will delete your data from your browser. You will then be able to make a new account, your old account will remain inactive and be deleted after
|
||||
90 days.
|
||||
</p>
|
||||
{:else}
|
||||
<p class="api_response">You are not registered, we don't have any data stored.</p>
|
||||
<p class="api_response">You are not registered, we don't have any data stored.</p>
|
||||
{/if}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin: 10px;
|
||||
}
|
||||
.api_response {
|
||||
color: white;
|
||||
}
|
||||
p {
|
||||
margin: 10px;
|
||||
}
|
||||
.api_response {
|
||||
color: white;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,16 +1,16 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
</script>
|
||||
|
||||
<Header title={'Help'} />
|
||||
<Header title={"Help"} />
|
||||
<Nav />
|
||||
<br /><br />
|
||||
<p>
|
||||
You can find extensive help and documentation at <a href="https://docs.owlboard.info">the documentation site</a>.
|
||||
You can find extensive help and documentation at <a href="https://docs.owlboard.info">the documentation site</a>.
|
||||
</p>
|
||||
<p>
|
||||
You can also use the <a href="https://www.facebook.com/owlboard.support">OwlBoard Support</a> page on Facebook.
|
||||
You can also use the <a href="https://www.facebook.com/owlboard.support">OwlBoard Support</a> page on Facebook.
|
||||
</p>
|
||||
<br /><br />
|
||||
|
||||
|
||||
@@ -1,57 +1,57 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
const title = 'Privacy Policy';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
const title = "Privacy Policy";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
<div>
|
||||
<p>
|
||||
OwlBoard stores the minimum amount of data necessary to provide its functions for your use. No personal data is stored unless you report an issue. To review the specific data
|
||||
that we store, please visit <a href="/more/data">My Data</a>.
|
||||
</p>
|
||||
<p>OwlBoard does not utilize any cookies. IP addresses and browser fingerprints are not logged.</p>
|
||||
<h2>If You Do Not Sign Up</h2>
|
||||
<p>
|
||||
If you choose not to sign up, no personal data will be processed or stored unless you report an issue. Any personal settings are stored locally in your browser and do not leave
|
||||
your device.
|
||||
</p>
|
||||
<h2>If You Sign Up</h2>
|
||||
<p>
|
||||
If you sign up for the rail staff version of OwlBoard, we do require the storage of some data. However, none of this data can be used to personally identify you. Any personal
|
||||
settings are stored locally in your browser and do not leave your device.
|
||||
</p>
|
||||
<p>
|
||||
During the sign-up process, you will be asked to provide a work email address, which will be checked to confirm its origin from a railway company. Once confirmed, an email
|
||||
containing a registration link will be sent to you. At this point, the username portion of your email address is discarded. For example, if your email address is
|
||||
'a-user@owlboard.info', only 'owlboard.info' will be stored. This host portion of your email address is stored to filter and display relevant results prominently.
|
||||
</p>
|
||||
<p>The email server may store the address and message content as part of its regular operation, and your consent to this is implied when you sign up.</p>
|
||||
<p>In addition to the host portion of your email address, a randomly generated UUID is stored for the purpose of authorizing access to the rail staff data.</p>
|
||||
<h2>Reporting an Issue</h2>
|
||||
<p>When you report an issue, certain data is collected, including your browser's User Agent string and the size of the window in which you are viewing the website.</p>
|
||||
<p>
|
||||
Any data submitted when reporting an issue will be publicly viewable alongside the <a href="https://git.fjla.uk/owlboard/backend/issues" target="_blank"
|
||||
>OwlBoard/backend git repository</a
|
||||
>.
|
||||
</p>
|
||||
<p>
|
||||
OwlBoard stores the minimum amount of data necessary to provide its functions for your use. No personal data is stored unless you report an issue. To review the specific
|
||||
data that we store, please visit <a href="/more/data">My Data</a>.
|
||||
</p>
|
||||
<p>OwlBoard does not utilize any cookies. IP addresses and browser fingerprints are not logged.</p>
|
||||
<h2>If You Do Not Sign Up</h2>
|
||||
<p>
|
||||
If you choose not to sign up, no personal data will be processed or stored unless you report an issue. Any personal settings are stored locally in your browser and do not
|
||||
leave your device.
|
||||
</p>
|
||||
<h2>If You Sign Up</h2>
|
||||
<p>
|
||||
If you sign up for the rail staff version of OwlBoard, we do require the storage of some data. However, none of this data can be used to personally identify you. Any
|
||||
personal settings are stored locally in your browser and do not leave your device.
|
||||
</p>
|
||||
<p>
|
||||
During the sign-up process, you will be asked to provide a work email address, which will be checked to confirm its origin from a railway company. Once confirmed, an email
|
||||
containing a registration link will be sent to you. At this point, the username portion of your email address is discarded. For example, if your email address is
|
||||
'a-user@owlboard.info', only 'owlboard.info' will be stored. This host portion of your email address is stored to filter and display relevant results prominently.
|
||||
</p>
|
||||
<p>The email server may store the address and message content as part of its regular operation, and your consent to this is implied when you sign up.</p>
|
||||
<p>In addition to the host portion of your email address, a randomly generated UUID is stored for the purpose of authorizing access to the rail staff data.</p>
|
||||
<h2>Reporting an Issue</h2>
|
||||
<p>When you report an issue, certain data is collected, including your browser's User Agent string and the size of the window in which you are viewing the website.</p>
|
||||
<p>
|
||||
Any data submitted when reporting an issue will be publicly viewable alongside the <a href="https://git.fjla.uk/owlboard/backend/issues" target="_blank"
|
||||
>OwlBoard/backend git repository</a
|
||||
>.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
div {
|
||||
text-align: left;
|
||||
}
|
||||
div {
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
h2 {
|
||||
color: var(--second-text-color);
|
||||
margin: 10px;
|
||||
padding-top: 20px;
|
||||
}
|
||||
h2 {
|
||||
color: var(--second-text-color);
|
||||
margin: 10px;
|
||||
padding-top: 20px;
|
||||
}
|
||||
|
||||
p {
|
||||
color: white;
|
||||
margin: 10px;
|
||||
}
|
||||
p {
|
||||
color: white;
|
||||
margin: 10px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,121 +1,121 @@
|
||||
<script>
|
||||
import { onMount } from 'svelte';
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import ResultIsland from '$lib/islands/result-island.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import { onMount } from "svelte";
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import ResultIsland from "$lib/islands/result-island.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
|
||||
const title = 'Reason Codes';
|
||||
let isLoading = false;
|
||||
let inputValue = '';
|
||||
let resultObject = {
|
||||
results: false,
|
||||
title: '',
|
||||
resultLines: []
|
||||
};
|
||||
|
||||
function load() {
|
||||
isLoading = true;
|
||||
resultObject.results = false;
|
||||
getData().then((result) => {
|
||||
handleData(result);
|
||||
isLoading = false;
|
||||
});
|
||||
}
|
||||
|
||||
async function getData() {
|
||||
if (inputValue) {
|
||||
const url = `${getApiUrl()}/api/v2/ref/reasonCode/${inputValue}`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
} else {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
async function handleData(data) {
|
||||
let resultLines = [];
|
||||
if (data.length) {
|
||||
resultObject.title = data[0]['code'];
|
||||
resultLines = [data[0]['lateReason'], data[0]['cancReason']];
|
||||
} else {
|
||||
resultObject = {
|
||||
const title = "Reason Codes";
|
||||
let isLoading = false;
|
||||
let inputValue = "";
|
||||
let resultObject = {
|
||||
results: false,
|
||||
title: 'Not Found',
|
||||
title: "",
|
||||
resultLines: []
|
||||
};
|
||||
};
|
||||
|
||||
function load() {
|
||||
isLoading = true;
|
||||
resultObject.results = false;
|
||||
getData().then((result) => {
|
||||
handleData(result);
|
||||
isLoading = false;
|
||||
});
|
||||
}
|
||||
resultObject.resultLines = resultLines;
|
||||
resultObject.results = true;
|
||||
}
|
||||
|
||||
onMount(() => {
|
||||
isLoading = false;
|
||||
});
|
||||
async function getData() {
|
||||
if (inputValue) {
|
||||
const url = `${getApiUrl()}/api/v2/ref/reasonCode/${inputValue}`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
} else {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
function handleInput(event) {
|
||||
inputValue = event.target.value;
|
||||
}
|
||||
async function handleData(data) {
|
||||
let resultLines = [];
|
||||
if (data.length) {
|
||||
resultObject.title = data[0]["code"];
|
||||
resultLines = [data[0]["lateReason"], data[0]["cancReason"]];
|
||||
} else {
|
||||
resultObject = {
|
||||
results: false,
|
||||
title: "Not Found",
|
||||
resultLines: []
|
||||
};
|
||||
}
|
||||
resultObject.resultLines = resultLines;
|
||||
resultObject.results = true;
|
||||
}
|
||||
|
||||
function handleSubmit(event) {
|
||||
event.preventDefault();
|
||||
load();
|
||||
}
|
||||
onMount(() => {
|
||||
isLoading = false;
|
||||
});
|
||||
|
||||
function handleInput(event) {
|
||||
inputValue = event.target.value;
|
||||
}
|
||||
|
||||
function handleSubmit(event) {
|
||||
event.preventDefault();
|
||||
load();
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
<p>A reason code is a three digit number that maps to a reason for a delay or cancellation</p>
|
||||
<form on:submit={handleSubmit}>
|
||||
<input type="text" placeholder="Enter Code" autocomplete="off" bind:value={inputValue} on:input={handleInput} />
|
||||
<input type="text" placeholder="Enter Code" autocomplete="off" bind:value={inputValue} on:input={handleInput} />
|
||||
|
||||
<br />
|
||||
<br />
|
||||
|
||||
<button type="submit">Submit</button>
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{/if}
|
||||
|
||||
{#if resultObject.results}
|
||||
<ResultIsland {resultObject} />
|
||||
<ResultIsland {resultObject} />
|
||||
{/if}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin: 10px;
|
||||
margin-top: 20px;
|
||||
}
|
||||
input {
|
||||
width: 25%;
|
||||
min-width: 150px;
|
||||
height: 32px;
|
||||
margin-top: 10px;
|
||||
margin-bottom: 5px;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
text-align: center;
|
||||
font-family: urwgothic, 'Lucida Sans', 'Lucida Sans Regular', 'Lucida Grande', 'Lucida Sans Unicode', Geneva, Verdana, sans-serif;
|
||||
text-transform: uppercase;
|
||||
font-size: 15px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
width: 15%;
|
||||
min-width: 100px;
|
||||
margin-bottom: 5px;
|
||||
margin-top: 5px;
|
||||
border: none;
|
||||
border-radius: 20px;
|
||||
padding: 5px;
|
||||
font-family: urwgothic, 'Lucida Sans', 'Lucida Sans Regular', 'Lucida Grande', 'Lucida Sans Unicode', Geneva, Verdana, sans-serif;
|
||||
font-size: 16px;
|
||||
font-weight: 400;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
p {
|
||||
margin: 10px;
|
||||
margin-top: 20px;
|
||||
}
|
||||
input {
|
||||
width: 25%;
|
||||
min-width: 150px;
|
||||
height: 32px;
|
||||
margin-top: 10px;
|
||||
margin-bottom: 5px;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
text-align: center;
|
||||
font-family: urwgothic, "Lucida Sans", "Lucida Sans Regular", "Lucida Grande", "Lucida Sans Unicode", Geneva, Verdana, sans-serif;
|
||||
text-transform: uppercase;
|
||||
font-size: 15px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
width: 15%;
|
||||
min-width: 100px;
|
||||
margin-bottom: 5px;
|
||||
margin-top: 5px;
|
||||
border: none;
|
||||
border-radius: 20px;
|
||||
padding: 5px;
|
||||
font-family: urwgothic, "Lucida Sans", "Lucida Sans Regular", "Lucida Grande", "Lucida Sans Unicode", Geneva, Verdana, sans-serif;
|
||||
font-size: 16px;
|
||||
font-weight: 400;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,144 +1,144 @@
|
||||
<script lang="ts">
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import { onMount } from 'svelte';
|
||||
import { checkAuth } from '$lib/libauth';
|
||||
import LogoutButton from '$lib/navigation/LogoutButton.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import { onMount } from "svelte";
|
||||
import { checkAuth } from "$lib/libauth";
|
||||
import LogoutButton from "$lib/navigation/LogoutButton.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
|
||||
const title = 'Register';
|
||||
const title = "Register";
|
||||
|
||||
let state = 'unreg';
|
||||
let isLoading = true;
|
||||
let inputValue = '';
|
||||
let state = "unreg";
|
||||
let isLoading = true;
|
||||
let inputValue = "";
|
||||
|
||||
function handleInput(event: KeyboardEvent) {
|
||||
inputValue = event?.target?.value;
|
||||
}
|
||||
|
||||
async function request() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/user/request`;
|
||||
const request = {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
},
|
||||
body: JSON.stringify({
|
||||
email: inputValue
|
||||
})
|
||||
};
|
||||
const res = await fetch(url, request);
|
||||
if (res.status == 400 || res.status == 403) {
|
||||
state = 'unauth';
|
||||
} else if (res.status == 201) {
|
||||
state = 'sent';
|
||||
} else {
|
||||
state = 'error';
|
||||
function handleInput(event: KeyboardEvent) {
|
||||
inputValue = event?.target?.value;
|
||||
}
|
||||
isLoading = false;
|
||||
}
|
||||
|
||||
onMount(async () => {
|
||||
const auth = await checkAuth();
|
||||
if (auth.uuidPresent === false) {
|
||||
state = 'unreg';
|
||||
} else if (auth.uuidPresent === true) {
|
||||
state = 'reg';
|
||||
async function request() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/user/request`;
|
||||
const request = {
|
||||
method: "POST",
|
||||
headers: {
|
||||
"Content-Type": "application/json"
|
||||
},
|
||||
body: JSON.stringify({
|
||||
email: inputValue
|
||||
})
|
||||
};
|
||||
const res = await fetch(url, request);
|
||||
if (res.status == 400 || res.status == 403) {
|
||||
state = "unauth";
|
||||
} else if (res.status == 201) {
|
||||
state = "sent";
|
||||
} else {
|
||||
state = "error";
|
||||
}
|
||||
isLoading = false;
|
||||
}
|
||||
isLoading = false;
|
||||
});
|
||||
|
||||
onMount(async () => {
|
||||
const auth = await checkAuth();
|
||||
if (auth.uuidPresent === false) {
|
||||
state = "unreg";
|
||||
} else if (auth.uuidPresent === true) {
|
||||
state = "reg";
|
||||
}
|
||||
isLoading = false;
|
||||
});
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
<section class="content">
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
{:else if state == 'unreg'}
|
||||
<p>To register, you will need to enter a work email address to receive a confirmation email</p>
|
||||
<p class="bold">Already have a registration code? <a href="/more/reg/submit">enter it here</a></p>
|
||||
<form on:submit={request}>
|
||||
<input type="text" autocomplete="email" placeholder="Enter work email" bind:value={inputValue} on:input={handleInput} /><br />
|
||||
<label for="checkbox">
|
||||
I have read and accept the terms of the <a href="/more/privacy">Privacy Policy</a><br />
|
||||
<input id="checkbox" type="checkbox" required />
|
||||
</label><br />
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
<br />
|
||||
<p class="bold">What do you get?</p>
|
||||
<li>Access to Train details</li>
|
||||
<li>Access to PIS Codes</li>
|
||||
<li>ECS Movements on departure boards</li>
|
||||
<li>Non-Public trains on departure boards</li>
|
||||
<li>Hidden platform numbers on departure boards</li>
|
||||
<li>See up to the next 40 trains departing a station over the next two hours</li>
|
||||
{:else if state == 'sent'}
|
||||
<p>An email has been sent, enter the code in the email to activate your profile.</p>
|
||||
<p class="bold"><a href="/more/reg/submit">Ready to enter your code?</a></p>
|
||||
<p>If you use multiple browsers, you will only be logged in using the browser you open the link with.</p>
|
||||
<p>You will be able to register again using the same email address</p>
|
||||
{:else if state == 'unauth'}
|
||||
<p>The email address you entered does not belong to an authorised business.</p>
|
||||
<p>If you think this is an error, you can get help on <a href="/more/help">the help page</a>.</p>
|
||||
{:else if state == 'error'}
|
||||
<p>There was an error processing your request.</p>
|
||||
<p>Check that the email you entered was correct or try again later.</p>
|
||||
{:else if state == 'reg'}
|
||||
<p>
|
||||
You are already registered for OwlBoard. If you've recently logged out or updated, you may need to refresh this page to register as old data could still be stored in your
|
||||
browser.
|
||||
</p>
|
||||
<LogoutButton />
|
||||
{/if}
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
{:else if state == "unreg"}
|
||||
<p>To register, you will need to enter a work email address to receive a confirmation email</p>
|
||||
<p class="bold">Already have a registration code? <a href="/more/reg/submit">enter it here</a></p>
|
||||
<form on:submit={request}>
|
||||
<input type="text" autocomplete="email" placeholder="Enter work email" bind:value={inputValue} on:input={handleInput} /><br />
|
||||
<label for="checkbox">
|
||||
I have read and accept the terms of the <a href="/more/privacy">Privacy Policy</a><br />
|
||||
<input id="checkbox" type="checkbox" required />
|
||||
</label><br />
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
<br />
|
||||
<p class="bold">What do you get?</p>
|
||||
<li>Access to Train details</li>
|
||||
<li>Access to PIS Codes</li>
|
||||
<li>ECS Movements on departure boards</li>
|
||||
<li>Non-Public trains on departure boards</li>
|
||||
<li>Hidden platform numbers on departure boards</li>
|
||||
<li>See up to the next 40 trains departing a station over the next two hours</li>
|
||||
{:else if state == "sent"}
|
||||
<p>An email has been sent, enter the code in the email to activate your profile.</p>
|
||||
<p class="bold"><a href="/more/reg/submit">Ready to enter your code?</a></p>
|
||||
<p>If you use multiple browsers, you will only be logged in using the browser you open the link with.</p>
|
||||
<p>You will be able to register again using the same email address</p>
|
||||
{:else if state == "unauth"}
|
||||
<p>The email address you entered does not belong to an authorised business.</p>
|
||||
<p>If you think this is an error, you can get help on <a href="/more/help">the help page</a>.</p>
|
||||
{:else if state == "error"}
|
||||
<p>There was an error processing your request.</p>
|
||||
<p>Check that the email you entered was correct or try again later.</p>
|
||||
{:else if state == "reg"}
|
||||
<p>
|
||||
You are already registered for OwlBoard. If you've recently logged out or updated, you may need to refresh this page to register as old data could still be stored in
|
||||
your browser.
|
||||
</p>
|
||||
<LogoutButton />
|
||||
{/if}
|
||||
</section>
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
.bold {
|
||||
font-weight: 800;
|
||||
}
|
||||
.content {
|
||||
margin-top: 30px;
|
||||
}
|
||||
p {
|
||||
margin: 10px;
|
||||
margin-left: 20px;
|
||||
margin-right: 20px;
|
||||
}
|
||||
li {
|
||||
text-align: center;
|
||||
font-size: 14px;
|
||||
color: white;
|
||||
margin-top: 5px;
|
||||
margin-left: 15px;
|
||||
margin-right: 15px;
|
||||
list-style-type: none;
|
||||
}
|
||||
input {
|
||||
height: 40px;
|
||||
width: 80%;
|
||||
max-width: 375px;
|
||||
font-family: urwgothic, 'Franklin Gothic Medium', 'Arial Narrow', Arial, sans-serif;
|
||||
text-align: center;
|
||||
font-size: 20px;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
#checkbox {
|
||||
height: 30px;
|
||||
width: 30px;
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
width: 35%;
|
||||
height: 30px;
|
||||
border-radius: 50px;
|
||||
font-size: 18px;
|
||||
}
|
||||
.bold {
|
||||
font-weight: 800;
|
||||
}
|
||||
.content {
|
||||
margin-top: 30px;
|
||||
}
|
||||
p {
|
||||
margin: 10px;
|
||||
margin-left: 20px;
|
||||
margin-right: 20px;
|
||||
}
|
||||
li {
|
||||
text-align: center;
|
||||
font-size: 14px;
|
||||
color: white;
|
||||
margin-top: 5px;
|
||||
margin-left: 15px;
|
||||
margin-right: 15px;
|
||||
list-style-type: none;
|
||||
}
|
||||
input {
|
||||
height: 40px;
|
||||
width: 80%;
|
||||
max-width: 375px;
|
||||
font-family: urwgothic, "Franklin Gothic Medium", "Arial Narrow", Arial, sans-serif;
|
||||
text-align: center;
|
||||
font-size: 20px;
|
||||
border-radius: 50px;
|
||||
border: none;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
#checkbox {
|
||||
height: 30px;
|
||||
width: 30px;
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
width: 35%;
|
||||
height: 30px;
|
||||
border-radius: 50px;
|
||||
font-size: 18px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,128 +1,128 @@
|
||||
<script lang="ts">
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import { uuid } from '$lib/stores/uuid';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
import { uuid } from "$lib/stores/uuid";
|
||||
|
||||
const title = 'Submit Registration';
|
||||
let state = false;
|
||||
let status: string;
|
||||
const title = "Submit Registration";
|
||||
let state = false;
|
||||
let status: string;
|
||||
|
||||
let inputs: { id: string; value: string }[] = [
|
||||
{ id: '1', value: '' },
|
||||
{ id: '2', value: '' },
|
||||
{ id: '3', value: '' },
|
||||
{ id: '4', value: '' },
|
||||
{ id: '5', value: '' },
|
||||
{ id: '6', value: '' }
|
||||
];
|
||||
let inputs: { id: string; value: string }[] = [
|
||||
{ id: "1", value: "" },
|
||||
{ id: "2", value: "" },
|
||||
{ id: "3", value: "" },
|
||||
{ id: "4", value: "" },
|
||||
{ id: "5", value: "" },
|
||||
{ id: "6", value: "" }
|
||||
];
|
||||
|
||||
function handleInput(index: number, event: KeyboardEvent): void {
|
||||
if (event.key === 'Backspace' && index > 0 && inputs[index].value === '') {
|
||||
const prevInput = document.getElementById(`input-${index}`);
|
||||
if (prevInput) {
|
||||
prevInput.focus();
|
||||
}
|
||||
} else if (inputs[index].value.length === 1) {
|
||||
const nextInput = document.getElementById(`input-${index + 2}`);
|
||||
if (nextInput) {
|
||||
nextInput.focus();
|
||||
}
|
||||
function handleInput(index: number, event: KeyboardEvent): void {
|
||||
if (event.key === "Backspace" && index > 0 && inputs[index].value === "") {
|
||||
const prevInput = document.getElementById(`input-${index}`);
|
||||
if (prevInput) {
|
||||
prevInput.focus();
|
||||
}
|
||||
} else if (inputs[index].value.length === 1) {
|
||||
const nextInput = document.getElementById(`input-${index + 2}`);
|
||||
if (nextInput) {
|
||||
nextInput.focus();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function handleSubmit() {
|
||||
let submitString: string = '';
|
||||
for (const input of inputs) {
|
||||
submitString += input.value.toUpperCase();
|
||||
async function handleSubmit() {
|
||||
let submitString: string = "";
|
||||
for (const input of inputs) {
|
||||
submitString += input.value.toUpperCase();
|
||||
}
|
||||
console.log(`Code: ${submitString}`);
|
||||
const res = await submit(submitString);
|
||||
console.log(`Registration Status: ${res}`);
|
||||
if (res == 201) {
|
||||
status = "okay";
|
||||
} else if (res == 401) {
|
||||
status = "fail";
|
||||
} else {
|
||||
console.error("Unable to register: ", status);
|
||||
}
|
||||
state = true;
|
||||
}
|
||||
console.log(`Code: ${submitString}`);
|
||||
const res = await submit(submitString);
|
||||
console.log(`Registration Status: ${res}`);
|
||||
if (res == 201) {
|
||||
status = 'okay';
|
||||
} else if (res == 401) {
|
||||
status = 'fail';
|
||||
} else {
|
||||
console.error('Unable to register: ', status);
|
||||
}
|
||||
state = true;
|
||||
}
|
||||
|
||||
async function submit(id: string): Promise<number> {
|
||||
const url = `${getApiUrl()}/api/v2/user/register`;
|
||||
const request = {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
},
|
||||
body: JSON.stringify({
|
||||
uuid: id
|
||||
})
|
||||
};
|
||||
const res = await fetch(url, request);
|
||||
const body = await res.json();
|
||||
if (body.api_key) {
|
||||
uuid.set(body.api_key);
|
||||
return 201;
|
||||
} else {
|
||||
return res.status;
|
||||
async function submit(id: string): Promise<number> {
|
||||
const url = `${getApiUrl()}/api/v2/user/register`;
|
||||
const request = {
|
||||
method: "POST",
|
||||
headers: {
|
||||
"Content-Type": "application/json"
|
||||
},
|
||||
body: JSON.stringify({
|
||||
uuid: id
|
||||
})
|
||||
};
|
||||
const res = await fetch(url, request);
|
||||
const body = await res.json();
|
||||
if (body.api_key) {
|
||||
uuid.set(body.api_key);
|
||||
return 201;
|
||||
} else {
|
||||
return res.status;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#if state}
|
||||
{#if status == 'okay'}
|
||||
<p class="title-ish">You are now registered</p>
|
||||
<p>Your secret key will be stored in your browser.</p>
|
||||
<p>If you change browsers, change device or clear your browsing data, you may have to register again.</p>
|
||||
{:else if status == 'fail'}
|
||||
<p class="title-ish">Your code was not accepted</p>
|
||||
<p>The code expires after 1 hour, you can check the code and enter it again or request a <a href="/more/reg">new code</a>.</p>
|
||||
{/if}
|
||||
{#if status == "okay"}
|
||||
<p class="title-ish">You are now registered</p>
|
||||
<p>Your secret key will be stored in your browser.</p>
|
||||
<p>If you change browsers, change device or clear your browsing data, you may have to register again.</p>
|
||||
{:else if status == "fail"}
|
||||
<p class="title-ish">Your code was not accepted</p>
|
||||
<p>The code expires after 1 hour, you can check the code and enter it again or request a <a href="/more/reg">new code</a>.</p>
|
||||
{/if}
|
||||
{:else}
|
||||
<p class="title-ish">Enter your registration code below</p>
|
||||
<form on:submit={handleSubmit} id="codeInputForm">
|
||||
{#each inputs as input, index}
|
||||
<input class="code-in" bind:value={input.value} id={`input-${input.id}`} maxlength="1" autocomplete="off" on:keydown={(event) => handleInput(index, event)} />
|
||||
{/each}
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
<p class="title-ish">Enter your registration code below</p>
|
||||
<form on:submit={handleSubmit} id="codeInputForm">
|
||||
{#each inputs as input, index}
|
||||
<input class="code-in" bind:value={input.value} id={`input-${input.id}`} maxlength="1" autocomplete="off" on:keydown={(event) => handleInput(index, event)} />
|
||||
{/each}
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
{/if}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
.title-ish {
|
||||
font-size: 20px;
|
||||
}
|
||||
.code-in {
|
||||
margin: 3px;
|
||||
margin-bottom: 20px;
|
||||
width: 29px;
|
||||
height: 39px;
|
||||
font-size: 30px;
|
||||
text-align: center;
|
||||
text-transform: uppercase;
|
||||
border-radius: 10px;
|
||||
border: none;
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
width: 35%;
|
||||
min-width: 95px;
|
||||
max-width: 231px;
|
||||
height: 30px;
|
||||
border-radius: 50px;
|
||||
font-size: 18px;
|
||||
}
|
||||
p {
|
||||
margin-left: 40px;
|
||||
margin-right: 40px;
|
||||
}
|
||||
.title-ish {
|
||||
font-size: 20px;
|
||||
}
|
||||
.code-in {
|
||||
margin: 3px;
|
||||
margin-bottom: 20px;
|
||||
width: 29px;
|
||||
height: 39px;
|
||||
font-size: 30px;
|
||||
text-align: center;
|
||||
text-transform: uppercase;
|
||||
border-radius: 10px;
|
||||
border: none;
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
width: 35%;
|
||||
min-width: 95px;
|
||||
max-width: 231px;
|
||||
height: 30px;
|
||||
border-radius: 50px;
|
||||
font-size: 18px;
|
||||
}
|
||||
p {
|
||||
margin-left: 40px;
|
||||
margin-right: 40px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,188 +1,188 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Island from '$lib/islands/island.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { onMount } from 'svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Done from '$lib/navigation/done.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Island from "$lib/islands/island.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { onMount } from "svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Done from "$lib/navigation/done.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
|
||||
const title = 'Report Issue';
|
||||
let isLoading = false;
|
||||
let isDone = false;
|
||||
let isError = false;
|
||||
const title = "Report Issue";
|
||||
let isLoading = false;
|
||||
let isDone = false;
|
||||
let isError = false;
|
||||
|
||||
let reportType = '',
|
||||
reportSubject = '',
|
||||
reportMsg = '',
|
||||
reportCollected;
|
||||
onMount(async () => {
|
||||
reportCollected = {
|
||||
userAgent: navigator.userAgent,
|
||||
browser: navigator.appName,
|
||||
version: navigator.appVersion,
|
||||
platform: navigator.platform,
|
||||
viewport: `${window.innerWidth} x ${window.innerHeight}`
|
||||
};
|
||||
});
|
||||
|
||||
let preFlight = false;
|
||||
|
||||
async function submit() {
|
||||
console.log(reportType, reportSubject, reportMsg);
|
||||
preFlight = true;
|
||||
}
|
||||
|
||||
async function send() {
|
||||
console.log('SEND DATA REQUESTED');
|
||||
isLoading = true;
|
||||
const formData = JSON.stringify({
|
||||
label: reportType,
|
||||
subject: reportSubject,
|
||||
msg:
|
||||
`User Agent: ${reportCollected.userAgent}\n` +
|
||||
`Browser: ${reportCollected.browser}\n` +
|
||||
`BrowserVersion: ${reportCollected.version}\n` +
|
||||
`Platform: ${reportCollected.platform}\n` +
|
||||
`Viewport: ${reportCollected.viewport}\n\n\n` +
|
||||
`User Message:\n` +
|
||||
`${reportMsg}`
|
||||
let reportType = "",
|
||||
reportSubject = "",
|
||||
reportMsg = "",
|
||||
reportCollected;
|
||||
onMount(async () => {
|
||||
reportCollected = {
|
||||
userAgent: navigator.userAgent,
|
||||
browser: navigator.appName,
|
||||
version: navigator.appVersion,
|
||||
platform: navigator.platform,
|
||||
viewport: `${window.innerWidth} x ${window.innerHeight}`
|
||||
};
|
||||
});
|
||||
const url = `${getApiUrl()}/misc/issue`;
|
||||
const options = {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
},
|
||||
body: formData
|
||||
};
|
||||
const res = await fetch(url, options);
|
||||
if (res.status == 200) {
|
||||
isLoading = false;
|
||||
isDone = true;
|
||||
await new Promise((r) => setTimeout(r, 2000));
|
||||
window.location.href = '/';
|
||||
} else {
|
||||
isLoading = false;
|
||||
isError = true;
|
||||
}
|
||||
}
|
||||
|
||||
async function cancel() {
|
||||
preFlight = false;
|
||||
isLoading = false;
|
||||
isDone = false;
|
||||
isError = false;
|
||||
}
|
||||
let preFlight = false;
|
||||
|
||||
async function submit() {
|
||||
console.log(reportType, reportSubject, reportMsg);
|
||||
preFlight = true;
|
||||
}
|
||||
|
||||
async function send() {
|
||||
console.log("SEND DATA REQUESTED");
|
||||
isLoading = true;
|
||||
const formData = JSON.stringify({
|
||||
label: reportType,
|
||||
subject: reportSubject,
|
||||
msg:
|
||||
`User Agent: ${reportCollected.userAgent}\n` +
|
||||
`Browser: ${reportCollected.browser}\n` +
|
||||
`BrowserVersion: ${reportCollected.version}\n` +
|
||||
`Platform: ${reportCollected.platform}\n` +
|
||||
`Viewport: ${reportCollected.viewport}\n\n\n` +
|
||||
`User Message:\n` +
|
||||
`${reportMsg}`
|
||||
});
|
||||
const url = `${getApiUrl()}/misc/issue`;
|
||||
const options = {
|
||||
method: "POST",
|
||||
headers: {
|
||||
"Content-Type": "application/json"
|
||||
},
|
||||
body: formData
|
||||
};
|
||||
const res = await fetch(url, options);
|
||||
if (res.status == 200) {
|
||||
isLoading = false;
|
||||
isDone = true;
|
||||
await new Promise((r) => setTimeout(r, 2000));
|
||||
window.location.href = "/";
|
||||
} else {
|
||||
isLoading = false;
|
||||
isError = true;
|
||||
}
|
||||
}
|
||||
|
||||
async function cancel() {
|
||||
preFlight = false;
|
||||
isLoading = false;
|
||||
isDone = false;
|
||||
isError = false;
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{/if}
|
||||
|
||||
{#if isDone}
|
||||
<Done />
|
||||
<Done />
|
||||
{/if}
|
||||
|
||||
{#if !preFlight && !isDone}
|
||||
<p>Get help on the <a href="https://www.facebook.com/owlboard.support">OwlBoard Support Facebook Page</a></p>
|
||||
<p>
|
||||
Or submit an issue, you can check for existing reports
|
||||
<a href="https://git.fjla.uk/OwlBoard/backend/issues" target="_blank">here</a>
|
||||
before submitting a new issue.
|
||||
</p>
|
||||
<p>You will be shown all of the collected data before the form is submitted.</p>
|
||||
<form on:submit={submit}>
|
||||
<select class="formInputs" name="type" bind:value={reportType} placeholder="Choose Category">
|
||||
<option value="" disabled selected>Choose an Issue Type</option>
|
||||
<option value="bug">Problem</option>
|
||||
<option value="enhancement">Feature Request</option>
|
||||
<option value="question">Question</option>
|
||||
<option value="user-support">Unable to sign up</option>
|
||||
</select>
|
||||
<br />
|
||||
<input class="formInputs" type="text" bind:value={reportSubject} placeholder="Subject" />
|
||||
<br />
|
||||
<textarea class="formInputs" bind:value={reportMsg} placeholder="Enter your message..." />
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
<button type="reset">Reset</button>
|
||||
</form>
|
||||
{:else}
|
||||
<Island>
|
||||
<h2>Device Data:</h2>
|
||||
<p><span class="dataType">User Agent: </span>{reportCollected.userAgent}</p>
|
||||
<p>Get help on the <a href="https://www.facebook.com/owlboard.support">OwlBoard Support Facebook Page</a></p>
|
||||
<p>
|
||||
<span class="dataType">Browser: </span>{reportCollected.browser} - {reportCollected.version}
|
||||
Or submit an issue, you can check for existing reports
|
||||
<a href="https://git.fjla.uk/OwlBoard/backend/issues" target="_blank">here</a>
|
||||
before submitting a new issue.
|
||||
</p>
|
||||
<p><span class="dataType">Platform: </span>{reportCollected.platform}</p>
|
||||
<p><span class="dataType">Viewport: </span> {reportCollected.viewport}</p>
|
||||
<h2>Reported Data:</h2>
|
||||
<p><span class="dataType">Report Type: </span>{reportType}</p>
|
||||
<p>{reportSubject}</p>
|
||||
<p>{reportMsg}</p>
|
||||
<button class="overlayButtons" on:click={send}>Send</button>
|
||||
<button class="overlayButtons" on:click={cancel}>Cancel</button>
|
||||
</Island>
|
||||
<p>You will be shown all of the collected data before the form is submitted.</p>
|
||||
<form on:submit={submit}>
|
||||
<select class="formInputs" name="type" bind:value={reportType} placeholder="Choose Category">
|
||||
<option value="" disabled selected>Choose an Issue Type</option>
|
||||
<option value="bug">Problem</option>
|
||||
<option value="enhancement">Feature Request</option>
|
||||
<option value="question">Question</option>
|
||||
<option value="user-support">Unable to sign up</option>
|
||||
</select>
|
||||
<br />
|
||||
<input class="formInputs" type="text" bind:value={reportSubject} placeholder="Subject" />
|
||||
<br />
|
||||
<textarea class="formInputs" bind:value={reportMsg} placeholder="Enter your message..." />
|
||||
<br />
|
||||
<button type="submit">Submit</button>
|
||||
<button type="reset">Reset</button>
|
||||
</form>
|
||||
{:else}
|
||||
<Island>
|
||||
<h2>Device Data:</h2>
|
||||
<p><span class="dataType">User Agent: </span>{reportCollected.userAgent}</p>
|
||||
<p>
|
||||
<span class="dataType">Browser: </span>{reportCollected.browser} - {reportCollected.version}
|
||||
</p>
|
||||
<p><span class="dataType">Platform: </span>{reportCollected.platform}</p>
|
||||
<p><span class="dataType">Viewport: </span> {reportCollected.viewport}</p>
|
||||
<h2>Reported Data:</h2>
|
||||
<p><span class="dataType">Report Type: </span>{reportType}</p>
|
||||
<p>{reportSubject}</p>
|
||||
<p>{reportMsg}</p>
|
||||
<button class="overlayButtons" on:click={send}>Send</button>
|
||||
<button class="overlayButtons" on:click={cancel}>Cancel</button>
|
||||
</Island>
|
||||
{/if}
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
select {
|
||||
text-align: center;
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
height: 30px;
|
||||
background-color: white;
|
||||
}
|
||||
.formInputs {
|
||||
margin: 10px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
font-size: 16px;
|
||||
border: none;
|
||||
width: 50%;
|
||||
max-width: 450px;
|
||||
min-width: 250px;
|
||||
}
|
||||
input {
|
||||
text-align: center;
|
||||
border-radius: 50px;
|
||||
height: 30px;
|
||||
}
|
||||
textarea {
|
||||
text-align: left;
|
||||
border-radius: 10px;
|
||||
padding-left: 5px;
|
||||
padding-right: 5px;
|
||||
height: 30vh;
|
||||
min-height: 150px;
|
||||
max-height: 400px;
|
||||
}
|
||||
button {
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
font-family: urwgothic, sans-serif;
|
||||
font-size: 16px;
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
width: 25%;
|
||||
height: 30px;
|
||||
max-width: 100px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
h2 {
|
||||
color: white;
|
||||
}
|
||||
.dataType {
|
||||
color: white;
|
||||
}
|
||||
.overlayButtons {
|
||||
background-color: var(--main-bg-color);
|
||||
}
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
select {
|
||||
text-align: center;
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
height: 30px;
|
||||
background-color: white;
|
||||
}
|
||||
.formInputs {
|
||||
margin: 10px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
font-size: 16px;
|
||||
border: none;
|
||||
width: 50%;
|
||||
max-width: 450px;
|
||||
min-width: 250px;
|
||||
}
|
||||
input {
|
||||
text-align: center;
|
||||
border-radius: 50px;
|
||||
height: 30px;
|
||||
}
|
||||
textarea {
|
||||
text-align: left;
|
||||
border-radius: 10px;
|
||||
padding-left: 5px;
|
||||
padding-right: 5px;
|
||||
height: 30vh;
|
||||
min-height: 150px;
|
||||
max-height: 400px;
|
||||
}
|
||||
button {
|
||||
background-color: var(--island-bg-color);
|
||||
color: var(--main-text-color);
|
||||
font-family: urwgothic, sans-serif;
|
||||
font-size: 16px;
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
width: 25%;
|
||||
height: 30px;
|
||||
max-width: 100px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
h2 {
|
||||
color: white;
|
||||
}
|
||||
.dataType {
|
||||
color: white;
|
||||
}
|
||||
.overlayButtons {
|
||||
background-color: var(--main-bg-color);
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import QlSet from '$lib/islands/quick-link-set-island.svelte';
|
||||
const title = 'Settings';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import QlSet from "$lib/islands/quick-link-set-island.svelte";
|
||||
const title = "Settings";
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
@@ -1,79 +1,79 @@
|
||||
<script>
|
||||
import Island from '$lib/islands/island.svelte';
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
const title = 'Statistics';
|
||||
import Island from "$lib/islands/island.svelte";
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
const title = "Statistics";
|
||||
|
||||
async function getData() {
|
||||
const url = `${getApiUrl()}/misc/server/stats`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
}
|
||||
|
||||
function U2L(input) {
|
||||
try {
|
||||
const datetime = new Date(input * 1000);
|
||||
return datetime.toLocaleString();
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
return false;
|
||||
async function getData() {
|
||||
const url = `${getApiUrl()}/misc/server/stats`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
}
|
||||
|
||||
function U2L(input) {
|
||||
try {
|
||||
const datetime = new Date(input * 1000);
|
||||
return datetime.toLocaleString();
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#await getData()}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{:then data}
|
||||
<br />
|
||||
<p>API Server:<br /><span>{data?.hostname}</span></p>
|
||||
<p>Runtime Mode: <span>{data?.runtimeMode}</span></p>
|
||||
<p>Stats Reset: <span>{U2L(data?.reset) || 'Unknown'}</span></p>
|
||||
<h2>Last Update</h2>
|
||||
<p>Timetable: <span>{U2L(data?.updateTimes?.timetable)}</span></p>
|
||||
<p>Location Ref: <span>{U2L(data?.updateTimes?.corpus)}</span></p>
|
||||
<p>PIS Codes: <span>{U2L(data?.updateTimes?.pis)}</span></p>
|
||||
<p>Reason Codes: <span>{U2L(data?.updateTimes?.reasonCodes)}</span></p>
|
||||
<br />
|
||||
<p>API Server:<br /><span>{data?.hostname}</span></p>
|
||||
<p>Runtime Mode: <span>{data?.runtimeMode}</span></p>
|
||||
<p>Stats Reset: <span>{U2L(data?.reset) || "Unknown"}</span></p>
|
||||
<h2>Last Update</h2>
|
||||
<p>Timetable: <span>{U2L(data?.updateTimes?.timetable)}</span></p>
|
||||
<p>Location Ref: <span>{U2L(data?.updateTimes?.corpus)}</span></p>
|
||||
<p>PIS Codes: <span>{U2L(data?.updateTimes?.pis)}</span></p>
|
||||
<p>Reason Codes: <span>{U2L(data?.updateTimes?.reasonCodes)}</span></p>
|
||||
|
||||
<h2>Request Counts</h2>
|
||||
<p>LDBWS API: <span>{data?.requestCounts?.ldbws_api}</span></p>
|
||||
<p>LDBSVWS API: <span>{data?.requestCounts?.lsbsvws_api}</span></p>
|
||||
<p>Location Reference API: <span>{data?.requestCounts?.corpus_api}</span></p>
|
||||
<p>Timetable: <span>{data?.requestCounts?.timetable_db}</span></p>
|
||||
<p>PIS: <span>{data?.requestCounts?.pis_db}</span></p>
|
||||
<p>Location Reference: <span>{data?.requestCounts?.corpus_db}</span></p>
|
||||
<p>Stations: <span>{data?.requestCounts?.stations_db}</span></p>
|
||||
<h2>Request Counts</h2>
|
||||
<p>LDBWS API: <span>{data?.requestCounts?.ldbws_api}</span></p>
|
||||
<p>LDBSVWS API: <span>{data?.requestCounts?.lsbsvws_api}</span></p>
|
||||
<p>Location Reference API: <span>{data?.requestCounts?.corpus_api}</span></p>
|
||||
<p>Timetable: <span>{data?.requestCounts?.timetable_db}</span></p>
|
||||
<p>PIS: <span>{data?.requestCounts?.pis_db}</span></p>
|
||||
<p>Location Reference: <span>{data?.requestCounts?.corpus_db}</span></p>
|
||||
<p>Stations: <span>{data?.requestCounts?.stations_db}</span></p>
|
||||
|
||||
<h2>Database Lengths</h2>
|
||||
<p>Users: <span>{data?.dbLengths?.users}</span></p>
|
||||
<p>Pending Registrations: <span>{data?.dbLengths?.registrations}</span></p>
|
||||
<p>CORPUS: <span>{data?.dbLengths?.corpus}</span></p>
|
||||
<p>Stations: <span>{data?.dbLengths?.stations}</span></p>
|
||||
<p>PIS: <span>{data?.dbLengths?.pis}</span></p>
|
||||
<p>Timetable: <span>{data?.dbLengths?.timetable}</span></p>
|
||||
<p>Reason Codes: <span>{data?.dbLengths?.reasonCodes}</span></p>
|
||||
<h2>Database Lengths</h2>
|
||||
<p>Users: <span>{data?.dbLengths?.users}</span></p>
|
||||
<p>Pending Registrations: <span>{data?.dbLengths?.registrations}</span></p>
|
||||
<p>CORPUS: <span>{data?.dbLengths?.corpus}</span></p>
|
||||
<p>Stations: <span>{data?.dbLengths?.stations}</span></p>
|
||||
<p>PIS: <span>{data?.dbLengths?.pis}</span></p>
|
||||
<p>Timetable: <span>{data?.dbLengths?.timetable}</span></p>
|
||||
<p>Reason Codes: <span>{data?.dbLengths?.reasonCodes}</span></p>
|
||||
{:catch}
|
||||
<Island>
|
||||
<p style="font-weight:600">Unable to connect to server</p>
|
||||
</Island>
|
||||
<Island>
|
||||
<p style="font-weight:600">Unable to connect to server</p>
|
||||
</Island>
|
||||
{/await}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
span {
|
||||
color: white;
|
||||
}
|
||||
p {
|
||||
margin: 0;
|
||||
color: lightgray;
|
||||
}
|
||||
h2 {
|
||||
font-family: urwgothic, sans-serif;
|
||||
margin-bottom: 2px;
|
||||
margin-top: 8px;
|
||||
}
|
||||
span {
|
||||
color: white;
|
||||
}
|
||||
p {
|
||||
margin: 0;
|
||||
color: lightgray;
|
||||
}
|
||||
h2 {
|
||||
font-family: urwgothic, sans-serif;
|
||||
margin-bottom: 2px;
|
||||
margin-top: 8px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,20 +1,20 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Island from '$lib/islands/island.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import LargeLogo from '$lib/images/large-logo.svelte';
|
||||
import { version, versionTag } from '$lib/stores/version';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import { IconBrandGolang, IconBrandJavascript, IconBrandNodejs, IconBrandPython, IconBrandSvelte, IconBrandTypescript, IconFileTypeSql } from '@tabler/icons-svelte';
|
||||
import Tooltip from '$lib/Tooltip.svelte';
|
||||
const title = 'Versions';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Island from "$lib/islands/island.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import LargeLogo from "$lib/images/large-logo.svelte";
|
||||
import { version, versionTag } from "$lib/stores/version";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
import { IconBrandGolang, IconBrandJavascript, IconBrandNodejs, IconBrandPython, IconBrandSvelte, IconBrandTypescript, IconFileTypeSql } from "@tabler/icons-svelte";
|
||||
import Tooltip from "$lib/Tooltip.svelte";
|
||||
const title = "Versions";
|
||||
|
||||
async function getData() {
|
||||
const url = `${getApiUrl()}/misc/server/versions`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
}
|
||||
async function getData() {
|
||||
const url = `${getApiUrl()}/misc/server/versions`;
|
||||
const res = await fetch(url);
|
||||
return await res.json();
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
@@ -22,58 +22,60 @@
|
||||
<LargeLogo />
|
||||
|
||||
{#await getData()}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{:then data}
|
||||
<Island>
|
||||
<p>
|
||||
<Tooltip text="Svelte"><IconBrandSvelte /></Tooltip>
|
||||
<Tooltip text="Javascript"><IconBrandJavascript /></Tooltip>
|
||||
<Tooltip text="Typescript"><IconBrandTypescript /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/owlboard-svelte" target="_blank"
|
||||
>Web-app version<br /><span class="data"
|
||||
>{version}{#if versionTag}-{versionTag}{/if}</span
|
||||
></a
|
||||
>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="NodeJS"><IconBrandNodejs /></Tooltip>
|
||||
<Tooltip text="Javascript"><IconBrandJavascript /></Tooltip>
|
||||
<Tooltip text="Typescript"><IconBrandTypescript /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/backend" target="_blank">API Server version<br /><span class="data">{data?.backend || 'Unknown'}</span></a>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="Python"><IconBrandPython /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/db-manager" target="_blank">DB Manager version<br /><span class="data">{data?.['db-manager'] || 'Unknown'}</span></a>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="Go"><IconBrandGolang /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/mq-client" target="_blank">MQ Client version<br /><span class="data">{data?.['mq-client'] || 'Not installed'}</span></a>
|
||||
</p>
|
||||
</Island>
|
||||
<Island>
|
||||
<p>
|
||||
<Tooltip text="Svelte"><IconBrandSvelte /></Tooltip>
|
||||
<Tooltip text="Javascript"><IconBrandJavascript /></Tooltip>
|
||||
<Tooltip text="Typescript"><IconBrandTypescript /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/owlboard-svelte" target="_blank"
|
||||
>Web-app version<br /><span class="data"
|
||||
>{version}{#if versionTag}-{versionTag}{/if}</span
|
||||
></a
|
||||
>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="NodeJS"><IconBrandNodejs /></Tooltip>
|
||||
<Tooltip text="Javascript"><IconBrandJavascript /></Tooltip>
|
||||
<Tooltip text="Typescript"><IconBrandTypescript /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/backend" target="_blank">API Server version<br /><span class="data">{data?.backend || "Unknown"}</span></a>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="Python"><IconBrandPython /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/db-manager" target="_blank">DB Manager version<br /><span class="data">{data?.["db-manager"] || "Unknown"}</span></a>
|
||||
</p>
|
||||
<p>
|
||||
<Tooltip text="Go"><IconBrandGolang /></Tooltip>
|
||||
<br />
|
||||
<a class="data" href="https://git.fjla.uk/owlboard/mq-client" target="_blank"
|
||||
>MQ Client version<br /><span class="data">{data?.["mq-client"] || "Not installed"}</span></a
|
||||
>
|
||||
</p>
|
||||
</Island>
|
||||
{:catch}
|
||||
<Island>
|
||||
<p>
|
||||
<IconBrandSvelte /><IconBrandJavascript /><IconBrandTypescript /><br />
|
||||
Web-app Version<br /><span class="data"
|
||||
>{version}{#if versionTag}-{versionTag}{/if}</span
|
||||
>
|
||||
</p>
|
||||
<p>Unable to fetch server application versions</p>
|
||||
</Island>
|
||||
<Island>
|
||||
<p>
|
||||
<IconBrandSvelte /><IconBrandJavascript /><IconBrandTypescript /><br />
|
||||
Web-app Version<br /><span class="data"
|
||||
>{version}{#if versionTag}-{versionTag}{/if}</span
|
||||
>
|
||||
</p>
|
||||
<p>Unable to fetch server application versions</p>
|
||||
</Island>
|
||||
{/await}
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
text-decoration: none;
|
||||
padding: 15px;
|
||||
}
|
||||
.data {
|
||||
color: white;
|
||||
text-decoration: none;
|
||||
}
|
||||
p {
|
||||
text-decoration: none;
|
||||
padding: 15px;
|
||||
}
|
||||
.data {
|
||||
color: white;
|
||||
text-decoration: none;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,109 +1,109 @@
|
||||
<script>
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import Island from '$lib/islands/island.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import { uuid } from '$lib/stores/uuid';
|
||||
import StylesToc from '$lib/train/styles-toc.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import Island from "$lib/islands/island.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import { uuid } from "$lib/stores/uuid";
|
||||
import StylesToc from "$lib/train/styles-toc.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
|
||||
const title = 'PIS Finder';
|
||||
const variables = { title: 'Results' };
|
||||
let entryPIS = '';
|
||||
let entryStartCRS = '';
|
||||
let entryEndCRS = '';
|
||||
let data = [];
|
||||
let error = false;
|
||||
let errMsg = 'Unknown Error';
|
||||
let isLoading = false;
|
||||
const title = "PIS Finder";
|
||||
const variables = { title: "Results" };
|
||||
let entryPIS = "";
|
||||
let entryStartCRS = "";
|
||||
let entryEndCRS = "";
|
||||
let data = [];
|
||||
let error = false;
|
||||
let errMsg = "Unknown Error";
|
||||
let isLoading = false;
|
||||
|
||||
async function findByStartEnd() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/pis/byStartEnd/${entryStartCRS}/${entryEndCRS}`;
|
||||
await fetchData(url);
|
||||
isLoading = false;
|
||||
}
|
||||
|
||||
async function findByPis() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/pis/byCode/${entryPIS}`;
|
||||
await fetchData(url);
|
||||
isLoading = false;
|
||||
}
|
||||
|
||||
async function fetchData(url) {
|
||||
const options = {
|
||||
method: 'GET',
|
||||
headers: {
|
||||
uuid: $uuid
|
||||
}
|
||||
};
|
||||
const res = await fetch(url, options); // Enable Auth
|
||||
if (res.status == 401) {
|
||||
errMsg = 'You must be logged in to the staff version';
|
||||
error = true;
|
||||
return false;
|
||||
} else if (res.status == 500) {
|
||||
errMsg = 'Server Error, try again later';
|
||||
error = true;
|
||||
return false;
|
||||
async function findByStartEnd() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/pis/byStartEnd/${entryStartCRS}/${entryEndCRS}`;
|
||||
await fetchData(url);
|
||||
isLoading = false;
|
||||
}
|
||||
const jsonData = await res.json();
|
||||
if (jsonData.ERROR == 'offline') {
|
||||
errMsg = 'Connection error, check your internet connection and try again';
|
||||
error = true;
|
||||
return false;
|
||||
}
|
||||
data = jsonData;
|
||||
}
|
||||
|
||||
async function reset() {
|
||||
data = [];
|
||||
error = false;
|
||||
entryPIS = '';
|
||||
entryStartCRS = '';
|
||||
entryEndCRS = '';
|
||||
}
|
||||
async function findByPis() {
|
||||
isLoading = true;
|
||||
const url = `${getApiUrl()}/api/v2/pis/byCode/${entryPIS}`;
|
||||
await fetchData(url);
|
||||
isLoading = false;
|
||||
}
|
||||
|
||||
async function fetchData(url) {
|
||||
const options = {
|
||||
method: "GET",
|
||||
headers: {
|
||||
uuid: $uuid
|
||||
}
|
||||
};
|
||||
const res = await fetch(url, options); // Enable Auth
|
||||
if (res.status == 401) {
|
||||
errMsg = "You must be logged in to the staff version";
|
||||
error = true;
|
||||
return false;
|
||||
} else if (res.status == 500) {
|
||||
errMsg = "Server Error, try again later";
|
||||
error = true;
|
||||
return false;
|
||||
}
|
||||
const jsonData = await res.json();
|
||||
if (jsonData.ERROR == "offline") {
|
||||
errMsg = "Connection error, check your internet connection and try again";
|
||||
error = true;
|
||||
return false;
|
||||
}
|
||||
data = jsonData;
|
||||
}
|
||||
|
||||
async function reset() {
|
||||
data = [];
|
||||
error = false;
|
||||
entryPIS = "";
|
||||
entryStartCRS = "";
|
||||
entryEndCRS = "";
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{/if}
|
||||
|
||||
{#if error}
|
||||
<Island {variables}>
|
||||
<p class="error">{errMsg}</p>
|
||||
</Island>
|
||||
<Island {variables}>
|
||||
<p class="error">{errMsg}</p>
|
||||
</Island>
|
||||
{:else if data.length}
|
||||
<Island {variables}>
|
||||
<table>
|
||||
<tr>
|
||||
<th class="toc">TOC</th>
|
||||
<th class="code">Code</th>
|
||||
<th class="stops">Stops</th>
|
||||
</tr>
|
||||
{#each data as item}
|
||||
<tr>
|
||||
<td class="toc toc-data"><StylesToc toc={item.toc || '-'} /></td>
|
||||
<td class="code">{item.code}</td>
|
||||
<td class="stops stops-data">{item.stops.join(' ')}</td>
|
||||
</tr>
|
||||
{/each}
|
||||
</table>
|
||||
</Island>
|
||||
<Island {variables}>
|
||||
<table>
|
||||
<tr>
|
||||
<th class="toc">TOC</th>
|
||||
<th class="code">Code</th>
|
||||
<th class="stops">Stops</th>
|
||||
</tr>
|
||||
{#each data as item}
|
||||
<tr>
|
||||
<td class="toc toc-data"><StylesToc toc={item.toc || "-"} /></td>
|
||||
<td class="code">{item.code}</td>
|
||||
<td class="stops stops-data">{item.stops.join(" ")}</td>
|
||||
</tr>
|
||||
{/each}
|
||||
</table>
|
||||
</Island>
|
||||
{:else}
|
||||
<p>To search by headcode use the Train Finder on the homepage</p>
|
||||
<p>This feature now supports all GWR Services</p>
|
||||
<p class="label">Find By Start/End CRS:</p>
|
||||
<form on:submit={findByStartEnd}>
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="Start" bind:value={entryStartCRS} />
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="End" bind:value={entryEndCRS} />
|
||||
<br />
|
||||
<button type="submit">Search</button>
|
||||
</form>
|
||||
<!-- FIND BY PIS CODE NOT WORKING AT PRESENT
|
||||
<p>To search by headcode use the Train Finder on the homepage</p>
|
||||
<p>This feature now supports all GWR Services</p>
|
||||
<p class="label">Find By Start/End CRS:</p>
|
||||
<form on:submit={findByStartEnd}>
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="Start" bind:value={entryStartCRS} />
|
||||
<input type="text" maxlength="3" autocomplete="off" placeholder="End" bind:value={entryEndCRS} />
|
||||
<br />
|
||||
<button type="submit">Search</button>
|
||||
</form>
|
||||
<!-- FIND BY PIS CODE NOT WORKING AT PRESENT
|
||||
<p class="label">Find By PIS Code:</p>
|
||||
<form on:submit={findByPis}>
|
||||
<input type="number" max="9999" autocomplete="off" placeholder="PIS" bind:value={entryPIS} />
|
||||
@@ -116,69 +116,69 @@
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
.label {
|
||||
font-weight: 600;
|
||||
color: var(--main-text-color);
|
||||
}
|
||||
input {
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
text-align: center;
|
||||
text-transform: uppercase;
|
||||
width: 30%;
|
||||
max-width: 250px;
|
||||
height: 30px;
|
||||
font-size: 16px;
|
||||
margin-bottom: 15px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
width: 25%;
|
||||
max-width: 175px;
|
||||
margin: 0px;
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
height: 30px;
|
||||
background-color: var(--island-bg-color);
|
||||
color: white;
|
||||
font-size: 16px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
table {
|
||||
width: 100%;
|
||||
margin: auto;
|
||||
color: white;
|
||||
}
|
||||
td {
|
||||
padding-top: 5px;
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
.toc {
|
||||
width: 15%;
|
||||
}
|
||||
.code {
|
||||
width: 20%;
|
||||
}
|
||||
.toc-data {
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.stops-data {
|
||||
text-align: left;
|
||||
font-family: firamono, monospace;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.error {
|
||||
color: white;
|
||||
}
|
||||
#reset {
|
||||
margin: 25px;
|
||||
}
|
||||
p {
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
.label {
|
||||
font-weight: 600;
|
||||
color: var(--main-text-color);
|
||||
}
|
||||
input {
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
text-align: center;
|
||||
text-transform: uppercase;
|
||||
width: 30%;
|
||||
max-width: 250px;
|
||||
height: 30px;
|
||||
font-size: 16px;
|
||||
margin-bottom: 15px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
button {
|
||||
border: none;
|
||||
border-radius: 50px;
|
||||
font-family: urwgothic, sans-serif;
|
||||
width: 25%;
|
||||
max-width: 175px;
|
||||
margin: 0px;
|
||||
margin-left: 10px;
|
||||
margin-right: 10px;
|
||||
height: 30px;
|
||||
background-color: var(--island-bg-color);
|
||||
color: white;
|
||||
font-size: 16px;
|
||||
box-shadow: var(--box-shadow);
|
||||
}
|
||||
table {
|
||||
width: 100%;
|
||||
margin: auto;
|
||||
color: white;
|
||||
}
|
||||
td {
|
||||
padding-top: 5px;
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
.toc {
|
||||
width: 15%;
|
||||
}
|
||||
.code {
|
||||
width: 20%;
|
||||
}
|
||||
.toc-data {
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.stops-data {
|
||||
text-align: left;
|
||||
font-family: firamono, monospace;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
.error {
|
||||
color: white;
|
||||
}
|
||||
#reset {
|
||||
margin: 25px;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,106 +1,106 @@
|
||||
<script lang="ts">
|
||||
import Header from '$lib/navigation/header.svelte';
|
||||
import Loading from '$lib/navigation/loading.svelte';
|
||||
import Island from '$lib/islands/island.svelte';
|
||||
import Nav from '$lib/navigation/nav.svelte';
|
||||
import { uuid } from '$lib/stores/uuid';
|
||||
import Header from "$lib/navigation/header.svelte";
|
||||
import Loading from "$lib/navigation/loading.svelte";
|
||||
import Island from "$lib/islands/island.svelte";
|
||||
import Nav from "$lib/navigation/nav.svelte";
|
||||
import { uuid } from "$lib/stores/uuid";
|
||||
|
||||
import { onMount } from 'svelte';
|
||||
import TrainDetail from '$lib/train/train-detail.svelte';
|
||||
import { getApiUrl } from '$lib/scripts/upstream';
|
||||
import { onMount } from "svelte";
|
||||
import TrainDetail from "$lib/train/train-detail.svelte";
|
||||
import { getApiUrl } from "$lib/scripts/upstream";
|
||||
|
||||
let title = 'Timetable Results';
|
||||
let id = '';
|
||||
let data = [];
|
||||
let isLoading = true;
|
||||
let error = false;
|
||||
let errMsg = '';
|
||||
let title = "Timetable Results";
|
||||
let id = "";
|
||||
let data = [];
|
||||
let isLoading = true;
|
||||
let error = false;
|
||||
let errMsg = "";
|
||||
|
||||
$: {
|
||||
if (id) {
|
||||
title = id.toUpperCase();
|
||||
} else {
|
||||
title = 'Querying Timetable';
|
||||
$: {
|
||||
if (id) {
|
||||
title = id.toUpperCase();
|
||||
} else {
|
||||
title = "Querying Timetable";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function getHeadcode() {
|
||||
return new URLSearchParams(window.location.search).get('headcode');
|
||||
}
|
||||
|
||||
onMount(async () => {
|
||||
isLoading = true;
|
||||
id = (await getHeadcode()) || '';
|
||||
const res = await fetchData(id);
|
||||
if (res) {
|
||||
data = res;
|
||||
if (!data.length) {
|
||||
error = true;
|
||||
errMsg = 'No services found';
|
||||
}
|
||||
async function getHeadcode() {
|
||||
return new URLSearchParams(window.location.search).get("headcode");
|
||||
}
|
||||
isLoading = false;
|
||||
});
|
||||
|
||||
async function fetchData(id = '') {
|
||||
const date = 'now';
|
||||
const searchType = 'headcode';
|
||||
const options = {
|
||||
method: 'GET',
|
||||
headers: {
|
||||
uuid: $uuid
|
||||
}
|
||||
};
|
||||
const url = `${getApiUrl()}/api/v2/timetable/train/${date}/${searchType}/${id}`;
|
||||
try {
|
||||
const res = await fetch(url, options);
|
||||
if (res.status == 200) {
|
||||
return await res.json();
|
||||
} else if (res.status === 401) {
|
||||
error = true;
|
||||
errMsg = 'You must be logged into the staff version for this feature';
|
||||
return false;
|
||||
} else {
|
||||
error = true;
|
||||
errMsg = 'Unable to connect, check your connection and try again';
|
||||
return false;
|
||||
}
|
||||
} catch (err) {
|
||||
error = true;
|
||||
errMsg = 'Connection error, try again later';
|
||||
onMount(async () => {
|
||||
isLoading = true;
|
||||
id = (await getHeadcode()) || "";
|
||||
const res = await fetchData(id);
|
||||
if (res) {
|
||||
data = res;
|
||||
if (!data.length) {
|
||||
error = true;
|
||||
errMsg = "No services found";
|
||||
}
|
||||
}
|
||||
isLoading = false;
|
||||
});
|
||||
|
||||
async function fetchData(id = "") {
|
||||
const date = "now";
|
||||
const searchType = "headcode";
|
||||
const options = {
|
||||
method: "GET",
|
||||
headers: {
|
||||
uuid: $uuid
|
||||
}
|
||||
};
|
||||
const url = `${getApiUrl()}/api/v2/timetable/train/${date}/${searchType}/${id}`;
|
||||
try {
|
||||
const res = await fetch(url, options);
|
||||
if (res.status == 200) {
|
||||
return await res.json();
|
||||
} else if (res.status === 401) {
|
||||
error = true;
|
||||
errMsg = "You must be logged into the staff version for this feature";
|
||||
return false;
|
||||
} else {
|
||||
error = true;
|
||||
errMsg = "Unable to connect, check your connection and try again";
|
||||
return false;
|
||||
}
|
||||
} catch (err) {
|
||||
error = true;
|
||||
errMsg = "Connection error, try again later";
|
||||
}
|
||||
isLoading = false;
|
||||
}
|
||||
isLoading = false;
|
||||
}
|
||||
</script>
|
||||
|
||||
<Header {title} />
|
||||
<div id="whitespace" />
|
||||
|
||||
{#if error}
|
||||
<Island>
|
||||
<p style="font-weight:600">{errMsg}</p>
|
||||
</Island>
|
||||
<Island>
|
||||
<p style="font-weight:600">{errMsg}</p>
|
||||
</Island>
|
||||
{/if}
|
||||
|
||||
{#if isLoading}
|
||||
<Loading />
|
||||
<Loading />
|
||||
{/if}
|
||||
|
||||
{#each data as service}
|
||||
{#if service}
|
||||
<TrainDetail {service} />
|
||||
{/if}
|
||||
{#if service}
|
||||
<TrainDetail {service} />
|
||||
{/if}
|
||||
{/each}
|
||||
|
||||
<Nav />
|
||||
|
||||
<style>
|
||||
#whitespace {
|
||||
height: 15px;
|
||||
}
|
||||
p {
|
||||
color: white;
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
}
|
||||
#whitespace {
|
||||
height: 15px;
|
||||
}
|
||||
p {
|
||||
color: white;
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
}
|
||||
</style>
|
||||
|
||||
Reference in New Issue
Block a user