You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
149 lines
4.1 KiB
149 lines
4.1 KiB
<script lang="ts">
|
|
import LogEntry from "../components/LogEntry.svelte";
|
|
import type { LogResult } from "../models/log";
|
|
import logStore from "../stores/logs";
|
|
import { addDays, endOfDay, endOfWeek, formatFormTime, formatWeekdayDate, startOfDay, startOfWeek } from "../utils/time";
|
|
import EmptyList from "../components/EmptyList.svelte";
|
|
import RefreshSelection from "../components/RefreshSelection.svelte";
|
|
import DateRangeSelect from "../components/DateRangeSelect.svelte";
|
|
import EveryMinute from "../components/EveryMinute.svelte";
|
|
import { allOffsets, RelativeDateRange } from "../utils/date-range";
|
|
|
|
const lsValue = localStorage.getItem("sl2.logspage.range")
|
|
|
|
let groupedLogs: {day: Date, text: string, logs: LogResult[]}[] = [];
|
|
let range = allOffsets.find(o => o.name === lsValue) || new RelativeDateRange(-7, "day");
|
|
let now = new Date();
|
|
let error = "";
|
|
let emptyMessage = `No logs since ${formatWeekdayDate(range.calculate(now)[0])}.`;
|
|
|
|
let min: Date;
|
|
let max: Date;
|
|
|
|
$: [min, max] = range.calculate(now);
|
|
|
|
$: localStorage.setItem("sl2.logspage.range", range.name);
|
|
|
|
$: {
|
|
error = "";
|
|
|
|
if (!Number.isNaN(min.getTime()) && !Number.isNaN(max.getTime())) {
|
|
if (min.getTime() < max.getTime()) {
|
|
if (!$logStore.loading) {
|
|
if ($logStore.stale || $logStore.filter.minTime?.getTime() != min.getTime() || $logStore.filter.maxTime?.getTime() != max.getTime()) {
|
|
logStore.load({
|
|
minTime: min,
|
|
maxTime: max,
|
|
});
|
|
}
|
|
}
|
|
} else {
|
|
error = "Time only goes one way in this universe, you should respect that."
|
|
}
|
|
} else {
|
|
error = "The dates must be valid."
|
|
}
|
|
}
|
|
|
|
$: {
|
|
if (!$logStore.loading && !$logStore.stale) {
|
|
emptyMessage = `No logs between ${formatWeekdayDate(min)} and ${formatWeekdayDate(max)}.`;
|
|
}
|
|
}
|
|
|
|
$: {
|
|
if (!$logStore.loading) {
|
|
groupedLogs = [];
|
|
|
|
if ($logStore.logs.length > 0) {
|
|
|
|
const today = new Date();
|
|
const tomorrow = addDays(today, 1);
|
|
const yesterday = addDays(today, -1);
|
|
|
|
let current = new Date($logStore.logs[0].loggedTime);
|
|
|
|
let remainingLogs = $logStore.logs;
|
|
|
|
while (remainingLogs.length > 0) {
|
|
const currentDay = startOfDay(current);
|
|
|
|
const currentLogs: LogResult[] = [];
|
|
for (const log of remainingLogs) {
|
|
if (Date.parse(log.loggedTime) >= currentDay.getTime()) {
|
|
currentLogs.push(log);
|
|
} else {
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (currentLogs.length > 0) {
|
|
remainingLogs = remainingLogs.slice(currentLogs.length);
|
|
|
|
let text = formatWeekdayDate(current);
|
|
if (current.getTime() === tomorrow.getTime()) {
|
|
text = "Tomorrow";
|
|
} else if (current.getTime() === today.getTime()) {
|
|
text = "Today";
|
|
} else if (current.getTime() === yesterday.getTime()) {
|
|
text = "Yesterday";
|
|
}
|
|
|
|
groupedLogs.push({day: current, text, logs: currentLogs});
|
|
}
|
|
|
|
current = addDays(current, -1);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<div class="page">
|
|
<DateRangeSelect label="Time Filter" noFuture styled bind:value={range} />
|
|
<div class="error">{error}</div>
|
|
<div class="log-list" class:loading={$logStore.loading}>
|
|
{#each groupedLogs as logGroup (logGroup.day.getTime())}
|
|
<h2>{logGroup.text}</h2>
|
|
{#each logGroup.logs as log (log.id)}
|
|
<LogEntry log={log} />
|
|
{/each}
|
|
{/each}
|
|
{#if groupedLogs.length === 0}
|
|
<EmptyList icon="list" text={emptyMessage} />
|
|
{/if}
|
|
</div>
|
|
</div>
|
|
<RefreshSelection />
|
|
<EveryMinute bind:now={now} />
|
|
|
|
<style>
|
|
div.error {
|
|
color: #ff4545;
|
|
text-align: center;
|
|
}
|
|
div.error:empty {
|
|
display: none;
|
|
}
|
|
|
|
div.page {
|
|
display: block;
|
|
margin: auto;
|
|
max-width: 100%;
|
|
width: 640px;
|
|
margin-top: 0;
|
|
box-sizing: border-box;
|
|
}
|
|
|
|
div.log-list.loading {
|
|
opacity: 0.75;
|
|
}
|
|
|
|
h2 {
|
|
font-size: 1.5em;
|
|
font-weight: 100;
|
|
text-align: center;
|
|
margin: 0;
|
|
margin-top: 1em;
|
|
}
|
|
</style>
|