mirror of
https://github.com/rajnandan1/kener.git
synced 2026-01-04 00:19:39 -06:00
chore(i18n): code clean up
This commit is contained in:
@@ -33,4 +33,9 @@ footerHTML: |
|
||||
Kener
|
||||
</a>
|
||||
an open source status page system built with Svelte and TailwindCSS.
|
||||
i18n:
|
||||
defaultLocale: "en"
|
||||
locales:
|
||||
en: "English"
|
||||
hi: "Hindi"
|
||||
|
||||
@@ -25,7 +25,7 @@
|
||||
"status_ok": "स्थिति ठीक है",
|
||||
"status_x_hour_y_minute": "%hours घंटा %minutes मिनट के लिए %status",
|
||||
"status_x_minute": "%minute मिनट के लिए %status",
|
||||
"status_x_minutes": "%minute मिनट के लिए %status",
|
||||
"status_x_minutes": "%minutes मिनट के लिए %status",
|
||||
"theme": "थीम",
|
||||
"theme_dark": "डार्क",
|
||||
"theme_light": "लाइट",
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
import { Badge } from "$lib/components/ui/badge";
|
||||
import { ChevronDown } from "lucide-svelte";
|
||||
import * as Collapsible from "$lib/components/ui/collapsible";
|
||||
import { l } from '$lib/i18n/client';
|
||||
import axios from "axios";
|
||||
import { Skeleton } from "$lib/components/ui/skeleton";
|
||||
export let incident;
|
||||
@@ -102,15 +103,15 @@
|
||||
<p class="mt-2 leading-8">
|
||||
{#if incident.labels.includes("identified")}
|
||||
<span class="mt-1 text-xs font-semibold me-2 px-2.5 py-1 uppercase leading-3 inline-block rounded tag-indetified">
|
||||
Identified
|
||||
{l(lang,'incident.identified')}
|
||||
</span>
|
||||
{/if} {#if incident.labels.includes("resolved")}
|
||||
<span class=" text-xs font-semibold me-2 px-2.5 py-1 leading-3 inline-block rounded uppercase tag-resolved">
|
||||
Resolved
|
||||
{l(lang,'incident.resolved')}
|
||||
</span>
|
||||
{/if} {#if incident.labels.includes("maintenance")}
|
||||
<span class="text-xs font-semibold me-2 px-2.5 py-1 leading-3 inline-block rounded uppercase tag-maintenance">
|
||||
Maintenance
|
||||
{l(lang,'incident.maintenance')}
|
||||
</span>
|
||||
{/if}
|
||||
</p>
|
||||
|
||||
@@ -1,34 +1,42 @@
|
||||
<script>
|
||||
import * as Card from "$lib/components/ui/card";
|
||||
import { Badge } from "$lib/components/ui/badge";
|
||||
import * as Popover from "$lib/components/ui/popover";
|
||||
import { Separator } from "$lib/components/ui/separator";
|
||||
import { onMount } from "svelte";
|
||||
import { Button } from "$lib/components/ui/button";
|
||||
import { ArrowRight, Share2, Info, Link, CopyCheck, Code, TrendingUp, Percent } from "lucide-svelte";
|
||||
import {
|
||||
ArrowRight,
|
||||
Share2,
|
||||
Info,
|
||||
Link,
|
||||
CopyCheck,
|
||||
Code,
|
||||
TrendingUp,
|
||||
Percent,
|
||||
} from "lucide-svelte";
|
||||
import { buttonVariants } from "$lib/components/ui/button";
|
||||
import { Skeleton } from "$lib/components/ui/skeleton";
|
||||
import { createEventDispatcher } from "svelte";
|
||||
import { beforeUpdate, afterUpdate } from "svelte";
|
||||
import { afterUpdate } from "svelte";
|
||||
import * as RadioGroup from "$lib/components/ui/radio-group";
|
||||
import { Label } from "$lib/components/ui/label";
|
||||
import axios from "axios";
|
||||
import { l, summaryTime, n, ampm } from '$lib/i18n/client';
|
||||
import axios from "axios";
|
||||
import { l, summaryTime, n, ampm } from "$lib/i18n/client";
|
||||
const dispatch = createEventDispatcher();
|
||||
|
||||
|
||||
/**
|
||||
* @type {{ pageData: { _90Day: any; uptime0Day: any; uptime90Day: any; }; tag: string; embed: undefined; image: any; name: any; description: any; folderName: any; }}
|
||||
*/
|
||||
export let monitor;
|
||||
/**
|
||||
* @type {any}
|
||||
*/
|
||||
export let localTz;
|
||||
export let lang;
|
||||
|
||||
|
||||
let _0Day = {};
|
||||
let _90Day = monitor.pageData._90Day;
|
||||
let uptime0Day = monitor.pageData.uptime0Day;
|
||||
let uptime90Day = monitor.pageData.uptime90Day;
|
||||
let dailyUps = monitor.pageData.dailyUps;
|
||||
let dailyDown = monitor.pageData.dailyDown;
|
||||
let dailyDegraded = monitor.pageData.dailyDegraded;
|
||||
let theme = "light";
|
||||
let embedType = "js";
|
||||
let todayDD = Object.keys(_90Day)[Object.keys(_90Day).length - 1];
|
||||
@@ -39,7 +47,6 @@
|
||||
let copiedBadgeUptime = false;
|
||||
|
||||
function copyLinkToClipboard() {
|
||||
let link = window.location.href;
|
||||
//get domain with port number
|
||||
let domain = window.location.host;
|
||||
//get protocol
|
||||
@@ -52,7 +59,6 @@
|
||||
}, 1500);
|
||||
}
|
||||
function copyUptimeBadge() {
|
||||
let link = window.location.href;
|
||||
let domain = window.location.host;
|
||||
let protocol = window.location.protocol;
|
||||
let path = `/badge/${monitor.tag}/uptime`;
|
||||
@@ -63,7 +69,6 @@
|
||||
}, 1500);
|
||||
}
|
||||
function copyStatusBadge() {
|
||||
let link = window.location.href;
|
||||
let domain = window.location.host;
|
||||
let protocol = window.location.protocol;
|
||||
let path = `/badge/${monitor.tag}/status`;
|
||||
@@ -75,13 +80,14 @@
|
||||
}
|
||||
|
||||
function copyScriptTagToClipboard() {
|
||||
let link = window.location.href;
|
||||
//get domain with port number
|
||||
let domain = window.location.host;
|
||||
//get protocol
|
||||
let protocol = window.location.protocol;
|
||||
let path = "/embed-" + monitor.tag;
|
||||
let scriptTag = `<script async src="${protocol + "//" + domain + path}/js?theme=${theme}&monitor=${protocol + "//" + domain + path}"><` + "/script>";
|
||||
let scriptTag =
|
||||
`<script async src="${protocol + "//" + domain + path}/js?theme=${theme}&monitor=${protocol + "//" + domain + path}"><` +
|
||||
"/script>";
|
||||
|
||||
if (embedType == "iframe") {
|
||||
scriptTag = `<iframe src="${protocol + "//" + domain + path}?theme=${theme}" width="100%" height="200" allowfullscreen="allowfullscreen" allowpaymentrequest frameborder="0"></iframe>`;
|
||||
@@ -139,189 +145,373 @@
|
||||
dispatch("heightChange", {});
|
||||
});
|
||||
</script>
|
||||
|
||||
<div class="grid grid-cols-12 gap-4 w-full monitor pb-4 md:w-[890px]">
|
||||
{#if monitor.embed === undefined}
|
||||
<div class="col-span-12 md:col-span-4">
|
||||
<div class="pt-1">
|
||||
<div class="scroll-m-20 text-2xl font-semibold tracking-tight">
|
||||
{#if monitor.image}
|
||||
<img src="{monitor.image}" class="w-6 h-6 inline" alt="{monitor.name}" srcset="" />
|
||||
{/if}
|
||||
<span> {monitor.name} </span>
|
||||
<br />
|
||||
{#if monitor.description}
|
||||
<Popover.Root>
|
||||
<Popover.Trigger>
|
||||
<span class="pt-0 pl-1 menu-monitor pr-0 pb-0 {buttonVariants({ variant: 'link' })}">
|
||||
<Info size="{12}" class="text-muted-foreground" />
|
||||
</span>
|
||||
</Popover.Trigger>
|
||||
<Popover.Content class="text-sm">
|
||||
<h2 class="mb-2 text-lg font-semibold">{monitor.name}</h2>
|
||||
<span class="text-muted-foreground text-sm"> {@html monitor.description} </span>
|
||||
</Popover.Content>
|
||||
</Popover.Root>
|
||||
{/if}
|
||||
<Popover.Root>
|
||||
<Popover.Trigger>
|
||||
<span class="pt-0 pl-1 pb-0 menu-monitor pr-0 {buttonVariants({ variant: 'link' })}">
|
||||
<Share2 size="{12}" class="text-muted-foreground" />
|
||||
</span>
|
||||
</Popover.Trigger>
|
||||
<Popover.Content class="pl-1 pr-1 pb-1 w-[375px] max-w-full">
|
||||
<h2 class="mb-1 text-lg font-semibold px-2">{l(lang,'monitor.share')}</h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">{l(lang,'monitor.share_desc')}</p>
|
||||
<Button class="ml-2" variant="secondary" on:click="{copyLinkToClipboard}">
|
||||
{#if !copiedLink}
|
||||
<Link class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.cp_link')} </span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.cpd_link')} </span>
|
||||
{/if}
|
||||
</Button>
|
||||
<h2 class="mb-2 mt-4 text-lg font-semibold px-2">{l(lang,'monitor.embed')}</h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">{l(lang,'monitor.embed_desc')}</p>
|
||||
<div class="grid grid-cols-2 gap-2">
|
||||
<div class="col-span-1 pl-4">
|
||||
<h3 class="text-sm mb-2 text-muted-foreground">{l(lang,'monitor.theme')}</h3>
|
||||
<RadioGroup.Root bind:value="{theme}">
|
||||
<div class="flex items-center space-x-2">
|
||||
<RadioGroup.Item value="light" id="light-theme" />
|
||||
<Label for="light-theme">{l(lang,'monitor.theme_light')}</Label>
|
||||
</div>
|
||||
<div class="flex items-center space-x-2">
|
||||
<RadioGroup.Item value="dark" id="dark-theme" />
|
||||
<Label for="dark-theme">{l(lang,'monitor.theme_dark')}</Label>
|
||||
</div>
|
||||
<RadioGroup.Input name="theme" />
|
||||
</RadioGroup.Root>
|
||||
<div class="col-span-12 md:col-span-4">
|
||||
<div class="pt-1">
|
||||
<div class="scroll-m-20 text-2xl font-semibold tracking-tight">
|
||||
{#if monitor.image}
|
||||
<img
|
||||
src={monitor.image}
|
||||
class="w-6 h-6 inline"
|
||||
alt={monitor.name}
|
||||
srcset=""
|
||||
/>
|
||||
{/if}
|
||||
<span> {monitor.name} </span>
|
||||
<br />
|
||||
{#if monitor.description}
|
||||
<Popover.Root>
|
||||
<Popover.Trigger>
|
||||
<span
|
||||
class="pt-0 pl-1 menu-monitor pr-0 pb-0 {buttonVariants(
|
||||
{ variant: 'link' },
|
||||
)}"
|
||||
>
|
||||
<Info
|
||||
size={12}
|
||||
class="text-muted-foreground"
|
||||
/>
|
||||
</span>
|
||||
</Popover.Trigger>
|
||||
<Popover.Content class="text-sm">
|
||||
<h2 class="mb-2 text-lg font-semibold">
|
||||
{monitor.name}
|
||||
</h2>
|
||||
<span class="text-muted-foreground text-sm">
|
||||
{@html monitor.description}
|
||||
</span>
|
||||
</Popover.Content>
|
||||
</Popover.Root>
|
||||
{/if}
|
||||
<Popover.Root>
|
||||
<Popover.Trigger>
|
||||
<span
|
||||
class="pt-0 pl-1 pb-0 menu-monitor pr-0 {buttonVariants(
|
||||
{ variant: 'link' },
|
||||
)}"
|
||||
>
|
||||
<Share2
|
||||
size={12}
|
||||
class="text-muted-foreground"
|
||||
/>
|
||||
</span>
|
||||
</Popover.Trigger>
|
||||
<Popover.Content
|
||||
class="pl-1 pr-1 pb-1 w-[375px] max-w-full"
|
||||
>
|
||||
<h2 class="mb-1 text-lg font-semibold px-2">
|
||||
{l(lang, "monitor.share")}
|
||||
</h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">
|
||||
{l(lang, "monitor.share_desc")}
|
||||
</p>
|
||||
<Button
|
||||
class="ml-2"
|
||||
variant="secondary"
|
||||
on:click={copyLinkToClipboard}
|
||||
>
|
||||
{#if !copiedLink}
|
||||
<Link class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.cp_link")}
|
||||
</span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.cpd_link")}
|
||||
</span>
|
||||
{/if}
|
||||
</Button>
|
||||
<h2 class="mb-2 mt-4 text-lg font-semibold px-2">
|
||||
{l(lang, "monitor.embed")}
|
||||
</h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">
|
||||
{l(lang, "monitor.embed_desc")}
|
||||
</p>
|
||||
<div class="grid grid-cols-2 gap-2">
|
||||
<div class="col-span-1 pl-4">
|
||||
<h3
|
||||
class="text-sm mb-2 text-muted-foreground"
|
||||
>
|
||||
{l(lang, "monitor.theme")}
|
||||
</h3>
|
||||
<RadioGroup.Root bind:value={theme}>
|
||||
<div
|
||||
class="flex items-center space-x-2"
|
||||
>
|
||||
<RadioGroup.Item
|
||||
value="light"
|
||||
id="light-theme"
|
||||
/>
|
||||
<Label for="light-theme"
|
||||
>{l(
|
||||
lang,
|
||||
"monitor.theme_light",
|
||||
)}</Label
|
||||
>
|
||||
</div>
|
||||
<div
|
||||
class="flex items-center space-x-2"
|
||||
>
|
||||
<RadioGroup.Item
|
||||
value="dark"
|
||||
id="dark-theme"
|
||||
/>
|
||||
<Label for="dark-theme"
|
||||
>{l(
|
||||
lang,
|
||||
"monitor.theme_dark",
|
||||
)}</Label
|
||||
>
|
||||
</div>
|
||||
<RadioGroup.Input name="theme" />
|
||||
</RadioGroup.Root>
|
||||
</div>
|
||||
<div class="col-span-1 pl-2">
|
||||
<h3
|
||||
class="text-sm mb-2 text-muted-foreground"
|
||||
>
|
||||
{l(lang, "monitor.mode")}
|
||||
</h3>
|
||||
<RadioGroup.Root bind:value={embedType}>
|
||||
<div
|
||||
class="flex items-center space-x-2"
|
||||
>
|
||||
<RadioGroup.Item
|
||||
value="js"
|
||||
id="js-embed"
|
||||
/>
|
||||
<Label for="js-embed"
|
||||
><script></Label
|
||||
>
|
||||
</div>
|
||||
<div
|
||||
class="flex items-center space-x-2"
|
||||
>
|
||||
<RadioGroup.Item
|
||||
value="iframe"
|
||||
id="iframe-embed"
|
||||
/>
|
||||
<Label for="iframe-embed"
|
||||
><iframe></Label
|
||||
>
|
||||
</div>
|
||||
<RadioGroup.Input name="embed" />
|
||||
</RadioGroup.Root>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-span-1 pl-2">
|
||||
<h3 class="text-sm mb-2 text-muted-foreground">{l(lang,'monitor.mode')}</h3>
|
||||
<RadioGroup.Root bind:value="{embedType}">
|
||||
<div class="flex items-center space-x-2">
|
||||
<RadioGroup.Item value="js" id="js-embed" />
|
||||
<Label for="js-embed"><script></Label>
|
||||
</div>
|
||||
<div class="flex items-center space-x-2">
|
||||
<RadioGroup.Item value="iframe" id="iframe-embed" />
|
||||
<Label for="iframe-embed"><iframe></Label>
|
||||
</div>
|
||||
<RadioGroup.Input name="embed" />
|
||||
</RadioGroup.Root>
|
||||
</div>
|
||||
</div>
|
||||
<Button class="mb-2 mt-4 ml-2" variant="secondary" on:click="{copyScriptTagToClipboard}">
|
||||
{#if !copiedEmbed}
|
||||
<Code class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.cp_code')} </span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.cpd_code')} </span>
|
||||
{/if}
|
||||
</Button>
|
||||
<h2 class="mb-2 mt-2 text-lg font-semibold px-2">{l(lang,'monitor.badge')} </h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">{l(lang,'monitor.badge_desc')}</p>
|
||||
<Button class="mb-2 mt-2 ml-2" variant="secondary" on:click="{copyStatusBadge}">
|
||||
{#if !copiedBadgeStatus}
|
||||
<TrendingUp class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.status')} {l(lang,'monitor.badge')}</span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.copied')} {l(lang,'monitor.badge')} </span>
|
||||
{/if}
|
||||
</Button>
|
||||
<Button class="mb-2 mt-2 ml-2" variant="secondary" on:click="{copyUptimeBadge}">
|
||||
{#if !copiedBadgeUptime}
|
||||
<Percent class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.uptime')} {l(lang,'monitor.badge')} </span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size="{12}" />
|
||||
<span class="text-sm font-medium"> {l(lang,'monitor.copied')} {l(lang,'monitor.badge')} </span>
|
||||
{/if}
|
||||
</Button>
|
||||
</Popover.Content>
|
||||
</Popover.Root>
|
||||
<Button
|
||||
class="mb-2 mt-4 ml-2"
|
||||
variant="secondary"
|
||||
on:click={copyScriptTagToClipboard}
|
||||
>
|
||||
{#if !copiedEmbed}
|
||||
<Code class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.cp_code")}
|
||||
</span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.cpd_code")}
|
||||
</span>
|
||||
{/if}
|
||||
</Button>
|
||||
<h2 class="mb-2 mt-2 text-lg font-semibold px-2">
|
||||
{l(lang, "monitor.badge")}
|
||||
</h2>
|
||||
<p class="pl-2 mb-2 text-muted-foreground text-sm">
|
||||
{l(lang, "monitor.badge_desc")}
|
||||
</p>
|
||||
<Button
|
||||
class="mb-2 mt-2 ml-2"
|
||||
variant="secondary"
|
||||
on:click={copyStatusBadge}
|
||||
>
|
||||
{#if !copiedBadgeStatus}
|
||||
<TrendingUp class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.status")}
|
||||
{l(lang, "monitor.badge")}</span
|
||||
>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.copied")}
|
||||
{l(lang, "monitor.badge")}
|
||||
</span>
|
||||
{/if}
|
||||
</Button>
|
||||
<Button
|
||||
class="mb-2 mt-2 ml-2"
|
||||
variant="secondary"
|
||||
on:click={copyUptimeBadge}
|
||||
>
|
||||
{#if !copiedBadgeUptime}
|
||||
<Percent class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.uptime")}
|
||||
{l(lang, "monitor.badge")}
|
||||
</span>
|
||||
{:else}
|
||||
<CopyCheck class="inline mr-2" size={12} />
|
||||
<span class="text-sm font-medium">
|
||||
{l(lang, "monitor.copied")}
|
||||
{l(lang, "monitor.badge")}
|
||||
</span>
|
||||
{/if}
|
||||
</Button>
|
||||
</Popover.Content>
|
||||
</Popover.Root>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="">
|
||||
<div class="grid grid-cols-2 gap-0">
|
||||
<div class="col-span-1 -mt-2">
|
||||
<a href="/incident/{monitor.folderName}#past_incident" class="pt-0 pl-0 pb-0 text-indigo-500 text-left {buttonVariants({ variant: 'link' })}">
|
||||
{l(lang,'root.recent_incidents')} <ArrowRight size="{16}" />
|
||||
</a>
|
||||
<div class="">
|
||||
<div class="grid grid-cols-2 gap-0">
|
||||
<div class="col-span-1 -mt-2">
|
||||
<a
|
||||
href="/incident/{monitor.folderName}#past_incident"
|
||||
class="pt-0 pl-0 pb-0 text-indigo-500 text-left {buttonVariants(
|
||||
{ variant: 'link' },
|
||||
)}"
|
||||
>
|
||||
{l(lang, "root.recent_incidents")}
|
||||
<ArrowRight size={16} />
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
<div class="col-span-12 md:w-[546px] {monitor.embed === undefined ? 'md:col-span-8': 'overflow-hidden'} pt-2 ">
|
||||
|
||||
<div
|
||||
class="col-span-12 md:w-[546px] {monitor.embed === undefined
|
||||
? 'md:col-span-8'
|
||||
: 'overflow-hidden'} pt-2"
|
||||
>
|
||||
<div class="col-span-12">
|
||||
<div class="grid grid-cols-12">
|
||||
<div class="{monitor.embed === undefined ? 'col-span-12': 'col-span-8'} md:col-span-8 h-[32px]">
|
||||
<button class="inline-block" on:click="{(e) => {switchView('90day')}}">
|
||||
<Badge variant="{view != '90day' ? 'outline' : ''}"> {l(lang,'monitor.90_day')} ► {n(lang, uptime90Day)}% </Badge>
|
||||
</button>
|
||||
<button on:click="{(e) => {switchView('0day')}}">
|
||||
<Badge variant="{view != '0day' ? 'outline' : ''}"> {l(lang,'monitor.today')} ► {n(lang, uptime0Day)}% </Badge>
|
||||
</button>
|
||||
</div>
|
||||
<div class="{monitor.embed === undefined ? 'col-span-12': 'col-span-4'} md:col-span-4 text-right h-[32px]">
|
||||
{#if _90Day[todayDD]}
|
||||
<div class="text-api-up text-sm truncate font-semibold mt-[4px] text-{_90Day[todayDD].cssClass}" title="{_90Day[todayDD].message}">
|
||||
{summaryTime(lang, _90Day[todayDD].message)}
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
<div class="grid grid-cols-12">
|
||||
<div
|
||||
class="{monitor.embed === undefined
|
||||
? 'col-span-12'
|
||||
: 'col-span-8'} md:col-span-8 h-[32px]"
|
||||
>
|
||||
<button
|
||||
class="inline-block"
|
||||
on:click={(e) => {
|
||||
switchView("90day");
|
||||
}}
|
||||
>
|
||||
<Badge variant={view != "90day" ? "outline" : ""}>
|
||||
{l(lang, "monitor.90_day")} ► {n(
|
||||
lang,
|
||||
uptime90Day,
|
||||
)}%
|
||||
</Badge>
|
||||
</button>
|
||||
<button
|
||||
on:click={(e) => {
|
||||
switchView("0day");
|
||||
}}
|
||||
>
|
||||
<Badge variant={view != "0day" ? "outline" : ""}>
|
||||
{l(lang, "monitor.today")} ► {n(lang, uptime0Day)}%
|
||||
</Badge>
|
||||
</button>
|
||||
</div>
|
||||
<div
|
||||
class="{monitor.embed === undefined
|
||||
? 'col-span-12'
|
||||
: 'col-span-4'} md:col-span-4 text-right h-[32px]"
|
||||
>
|
||||
{#if _90Day[todayDD]}
|
||||
<div
|
||||
class="text-api-up text-sm truncate font-semibold mt-[4px] text-{_90Day[
|
||||
todayDD
|
||||
].cssClass}"
|
||||
title={_90Day[todayDD].message}
|
||||
>
|
||||
{summaryTime(lang, _90Day[todayDD].message)}
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
{#if view == "90day"}
|
||||
<div class="chart-status relative mt-1 col-span-12">
|
||||
<div class="flex overflow-x-auto daygrid90 overflow-y-hidden py-1">
|
||||
{#each Object.entries(_90Day) as [ts, bar]}
|
||||
<div class="h-[30px] w-[6px] rounded-sm oneline">
|
||||
<div class="h-[30px] bg-{bar.cssClass} w-[4px] rounded-sm mr-[2px]"></div>
|
||||
<div class="chart-status relative mt-1 col-span-12">
|
||||
<div
|
||||
class="flex overflow-x-auto daygrid90 overflow-y-hidden py-1"
|
||||
>
|
||||
{#each Object.entries(_90Day) as [ts, bar]}
|
||||
<div class="h-[30px] w-[6px] rounded-sm oneline">
|
||||
<div
|
||||
class="h-[30px] bg-{bar.cssClass} w-[4px] rounded-sm mr-[2px]"
|
||||
></div>
|
||||
</div>
|
||||
<div
|
||||
class="absolute show-hover text-sm bg-background"
|
||||
>
|
||||
<div class="text-{bar.cssClass} font-semibold">
|
||||
● {n(
|
||||
lang,
|
||||
new Date(
|
||||
bar.timestamp * 1000,
|
||||
).toLocaleDateString(),
|
||||
)}
|
||||
{summaryTime(lang, bar.message)}
|
||||
</div>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
<div class="absolute show-hover text-sm bg-background">
|
||||
<div class="text-{bar.cssClass} font-semibold">
|
||||
● {n(lang, new Date(bar.timestamp * 1000).toLocaleDateString())} {summaryTime(lang, bar.message)}
|
||||
</div>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
</div>
|
||||
{:else}
|
||||
<div class="chart-status relative mt-1 mb-4 col-span-12">
|
||||
<div class="flex flex-wrap today-sq-div">
|
||||
{#if Object.keys(_0Day).length == 0}
|
||||
<Skeleton class="md:w-[546px] w-full h-[20px] mr-1 rounded-full" />
|
||||
{/if} {#each Object.entries(_0Day) as [ts, bar] }
|
||||
<div data-index="{bar.index}" class="h-[10px] bg-{bar.cssClass} w-[10px] today-sq m-[1px]"></div>
|
||||
<div class="hiddenx relative">
|
||||
<div data-index="{ts.index}" class="p-2 text-sm rounded font-semibold message bg-black text-white border">
|
||||
<p>
|
||||
<span class="text-{bar.cssClass}">
|
||||
●
|
||||
</span>
|
||||
{ampm(lang, n(lang, new Date(bar.timestamp * 1000).toLocaleTimeString()))}
|
||||
</p>
|
||||
{#if bar.status != 'NO_DATA'}
|
||||
<p class="pl-4">
|
||||
{l(lang,'statuses.' + bar.status)}
|
||||
</p>
|
||||
{:else}
|
||||
<p class="pl-4">-</p>
|
||||
{/if}
|
||||
</div>
|
||||
<div class="chart-status relative mt-1 mb-4 col-span-12">
|
||||
<div class="flex flex-wrap today-sq-div">
|
||||
{#if Object.keys(_0Day).length == 0}
|
||||
<Skeleton
|
||||
class="md:w-[546px] w-full h-[20px] mr-1 rounded-full"
|
||||
/>
|
||||
{/if}
|
||||
{#each Object.entries(_0Day) as [ts, bar]}
|
||||
<div
|
||||
data-index={bar.index}
|
||||
class="h-[10px] bg-{bar.cssClass} w-[10px] today-sq m-[1px]"
|
||||
></div>
|
||||
<div class="hiddenx relative">
|
||||
<div
|
||||
data-index={ts.index}
|
||||
class="p-2 text-sm rounded font-semibold message bg-black text-white border"
|
||||
>
|
||||
<p>
|
||||
<span class="text-{bar.cssClass}">
|
||||
●
|
||||
</span>
|
||||
{ampm(
|
||||
lang,
|
||||
n(
|
||||
lang,
|
||||
new Date(
|
||||
bar.timestamp * 1000,
|
||||
).toLocaleTimeString(),
|
||||
),
|
||||
)}
|
||||
</p>
|
||||
{#if bar.status != "NO_DATA"}
|
||||
<p class="pl-4">
|
||||
{l(lang, "statuses." + bar.status)}
|
||||
</p>
|
||||
{:else}
|
||||
<p class="pl-4">-</p>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<style>
|
||||
.daygrid90 {
|
||||
-ms-overflow-style: none; /* Internet Explorer 10+ */
|
||||
@@ -363,7 +553,9 @@
|
||||
}
|
||||
.today-sq:hover {
|
||||
/* transform: scale(1.1); */
|
||||
box-shadow: rgba(50, 50, 105, 0.15) 0px 2px 5px 0px, rgba(0, 0, 0, 0.05) 0px 1px 1px 0px;
|
||||
box-shadow:
|
||||
rgba(50, 50, 105, 0.15) 0px 2px 5px 0px,
|
||||
rgba(0, 0, 0, 0.05) 0px 1px 1px 0px;
|
||||
opacity: 0.75;
|
||||
transition: all 0.1s ease-in;
|
||||
cursor: pointer;
|
||||
|
||||
@@ -1,62 +1,87 @@
|
||||
<script>
|
||||
import { Button } from "$lib/components/ui/button";
|
||||
import { buttonVariants } from "$lib/components/ui/button";
|
||||
import * as DropdownMenu from "$lib/components/ui/dropdown-menu";
|
||||
import { Languages } from "lucide-svelte";
|
||||
import * as DropdownMenu from "$lib/components/ui/dropdown-menu";
|
||||
import { Languages } from "lucide-svelte";
|
||||
|
||||
export let data;
|
||||
let defaultLocaleKey = data.selectedLang;
|
||||
const allLocales = data.site.i18n?.locales;
|
||||
let defaultLocaleKey = data.selectedLang;
|
||||
const allLocales = data.site.i18n?.locales;
|
||||
|
||||
let defaultLocaleValue;
|
||||
if (!allLocales) {
|
||||
defaultLocaleValue = "English";
|
||||
} else {
|
||||
defaultLocaleValue = allLocales[defaultLocaleKey];
|
||||
}
|
||||
function setLanguage(locale) {
|
||||
document.cookie = `localLang=${locale};max-age=${60 * 60 * 24 * 365 * 30}`;
|
||||
if (locale === defaultLocaleKey) return;
|
||||
defaultLocaleValue = allLocales[locale];
|
||||
location.reload();
|
||||
}
|
||||
/**
|
||||
* @type {string}
|
||||
*/
|
||||
let defaultLocaleValue;
|
||||
if (!allLocales) {
|
||||
defaultLocaleValue = "English";
|
||||
} else {
|
||||
defaultLocaleValue = allLocales[defaultLocaleKey];
|
||||
}
|
||||
/**
|
||||
* @param {string} locale
|
||||
*/
|
||||
function setLanguage(locale) {
|
||||
document.cookie = `localLang=${locale};max-age=${60 * 60 * 24 * 365 * 30}`;
|
||||
if (locale === defaultLocaleKey) return;
|
||||
defaultLocaleValue = allLocales[locale];
|
||||
location.reload();
|
||||
}
|
||||
</script>
|
||||
|
||||
<div class="one"></div>
|
||||
|
||||
<header class="relative z-50 w-full">
|
||||
<div class="container flex h-14 items-center ">
|
||||
<div class="container flex h-14 items-center">
|
||||
<div class="mr-4 flex blurry-bg w-full justify-between">
|
||||
<a href="{data.site.home ? data.site.home:'/'}" class="mr-6 flex items-center space-x-2">
|
||||
<a
|
||||
href={data.site.home ? data.site.home : "/"}
|
||||
class="mr-6 flex items-center space-x-2"
|
||||
>
|
||||
{#if data.site.logo}
|
||||
<img src="{data.site.logo}" class="h-8" alt="{data.site.title}" srcset="" />
|
||||
{/if}
|
||||
{#if data.site.title}
|
||||
<span class="hidden font-bold md:inline-block text-[15px] lg:text-base"> {data.site.title} </span>
|
||||
{/if}
|
||||
<img
|
||||
src={data.site.logo}
|
||||
class="h-8"
|
||||
alt={data.site.title}
|
||||
srcset=""
|
||||
/>
|
||||
{/if}
|
||||
{#if data.site.title}
|
||||
<span
|
||||
class="hidden font-bold md:inline-block text-[15px] lg:text-base"
|
||||
>
|
||||
{data.site.title}
|
||||
</span>
|
||||
{/if}
|
||||
</a>
|
||||
{#if data.site.nav}
|
||||
<nav class="flex flex-wrap items-center space-x-6 text-sm font-medium">
|
||||
{#each data.site.nav as navItem}
|
||||
<a href="{navItem.url}"> {navItem.name} </a>
|
||||
{/each}
|
||||
{#if data.site.i18n && data.site.i18n.locales && Object.keys(data.site.i18n.locales).length > 1}
|
||||
<DropdownMenu.Root>
|
||||
<DropdownMenu.Trigger>
|
||||
<Button variant="outline" size="sm">
|
||||
<Languages size="{14}" class="mr-2" /> {defaultLocaleValue}
|
||||
</Button>
|
||||
</DropdownMenu.Trigger>
|
||||
<DropdownMenu.Content>
|
||||
<DropdownMenu.Group>
|
||||
{#each Object.entries(allLocales) as [key, value]}
|
||||
<DropdownMenu.Item on:click="{(e) => {setLanguage(key)}}">{value}</DropdownMenu.Item>
|
||||
{/each}
|
||||
</DropdownMenu.Group>
|
||||
</DropdownMenu.Content>
|
||||
</DropdownMenu.Root>
|
||||
{/if}
|
||||
</nav>
|
||||
{/if}
|
||||
{#if data.site.nav}
|
||||
<nav
|
||||
class="flex flex-wrap items-center space-x-6 text-sm font-medium"
|
||||
>
|
||||
{#each data.site.nav as navItem}
|
||||
<a href={navItem.url}> {navItem.name} </a>
|
||||
{/each}
|
||||
{#if data.site.i18n && data.site.i18n.locales && Object.keys(data.site.i18n.locales).length > 1}
|
||||
<DropdownMenu.Root>
|
||||
<DropdownMenu.Trigger>
|
||||
<Button variant="outline" size="sm">
|
||||
<Languages size={14} class="mr-2" />
|
||||
{defaultLocaleValue}
|
||||
</Button>
|
||||
</DropdownMenu.Trigger>
|
||||
<DropdownMenu.Content>
|
||||
<DropdownMenu.Group>
|
||||
{#each Object.entries(allLocales) as [key, value]}
|
||||
<DropdownMenu.Item
|
||||
on:click={(e) => {
|
||||
setLanguage(key);
|
||||
}}>{value}</DropdownMenu.Item
|
||||
>
|
||||
{/each}
|
||||
</DropdownMenu.Group>
|
||||
</DropdownMenu.Content>
|
||||
</DropdownMenu.Root>
|
||||
{/if}
|
||||
</nav>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
</header>
|
||||
</header>
|
||||
|
||||
Reference in New Issue
Block a user