Improve aspect of zone page, ensure long domains doesn't extend display

This commit is contained in:
nemunaire 2025-04-22 12:32:22 +02:00
parent dad3e411cd
commit 9be4b48676
8 changed files with 189 additions and 141 deletions

View file

@ -390,8 +390,8 @@
"exporting": "Please wait while we export your zone…", "exporting": "Please wait while we export your zone…",
"formating": "Please wait while we format your zone…", "formating": "Please wait while we format your zone…",
"importing": "Please wait while we are importing your domain…", "importing": "Please wait while we are importing your domain…",
"loading": "Loading the domain…", "loading": "Loading domain's services …",
"loading-account": "Loading your account …", "loading-account": "Loading your account…",
"loading-record": "Loading records…", "loading-record": "Loading records…",
"retrieving-setting": "Retrieving host settings' form...", "retrieving-setting": "Retrieving host settings' form...",
"updating": "Updating your domain name host", "updating": "Updating your domain name host",

View file

@ -354,9 +354,9 @@
"exporting": "Veuillez patienter pendant l'export de votre domaine…", "exporting": "Veuillez patienter pendant l'export de votre domaine…",
"formating": "Veuillez patienter pendant le formattage de votre zone…", "formating": "Veuillez patienter pendant le formattage de votre zone…",
"importing": "Veuillez patienter pendant l'import de votre domaine…", "importing": "Veuillez patienter pendant l'import de votre domaine…",
"loading": "Chargement du domaine", "loading": "Chargement des services du domaine.",
"loading-account": "Chargement de votre compte", "loading-account": "Chargement de votre compte.",
"loading-record": "Chargement des enregistrements", "loading-record": "Chargement des enregistrements.",
"retrieving-setting": "Récupération du formulaire de paramètrage de l'hôte...", "retrieving-setting": "Récupération du formulaire de paramètrage de l'hôte...",
"updating": "Mise à jour de l'hôte de votre domaine", "updating": "Mise à jour de l'hôte de votre domaine",
"validating": "Validation du domaine…", "validating": "Validation du domaine…",

View file

@ -183,7 +183,7 @@
<Icon name="chevron-left" /> <Icon name="chevron-left" />
Retour à la zone Retour à la zone
</Button> </Button>
{:else if $sortedDomains && $sortedDomainsWithIntermediate} {:else}
<div class="d-flex gap-2 pb-2 sticky-top" style="padding-top: 10px"> <div class="d-flex gap-2 pb-2 sticky-top" style="padding-top: 10px">
<Button <Button
type="button" type="button"
@ -191,6 +191,7 @@
outline outline
size="sm" size="sm"
class="flex-fill" class="flex-fill"
disabled={!$sortedDomains}
on:click={() => ctrlNewSubdomain.Open()} on:click={() => ctrlNewSubdomain.Open()}
> >
<Icon name="server" /> <Icon name="server" />
@ -215,7 +216,7 @@
{$t("domains.actions.audit")} {$t("domains.actions.audit")}
</DropdownItem> </DropdownItem>
<DropdownItem divider /> <DropdownItem divider />
<DropdownItem on:click={viewZone}> <DropdownItem on:click={viewZone} disabled={!$sortedDomains}>
{$t("domains.actions.view")} {$t("domains.actions.view")}
</DropdownItem> </DropdownItem>
<DropdownItem on:click={retrieveZone}> <DropdownItem on:click={retrieveZone}>
@ -243,7 +244,8 @@
</DropdownMenu> </DropdownMenu>
</ButtonDropdown> </ButtonDropdown>
</div> </div>
<div style="min-height:0; overflow-y: auto;"> <div style="min-height:0; overflow-y: auto;" class="placeholder-glow">
{#if $sortedDomains && $thisZone.id == selectedHistory}
{#if isReverseZone(data.domain.domain)} {#if isReverseZone(data.domain.domain)}
<SubdomainListTiny domains={$sortedDomains} origin={data.domain} /> <SubdomainListTiny domains={$sortedDomains} origin={data.domain} />
{:else} {:else}
@ -252,13 +254,32 @@
origin={data.domain} origin={data.domain}
/> />
{/if} {/if}
{:else}
<span class="d-block text-truncate font-monospace text-muted">
{data.domain.domain}
</span>
<span class="d-block placeholder ms-3 mb-1">
{data.domain.domain}
</span>
<span class="d-block placeholder ms-3 mb-1">
{data.domain.domain}
</span>
<span class="d-block placeholder ms-4 mb-1">
{data.domain.domain}
</span>
<span class="d-block placeholder ms-4 mb-1">
{data.domain.domain}
</span>
<span class="d-block placeholder ms-3">
{data.domain.domain}
</span>
{/if}
</div> </div>
{/if} {/if}
<div class="flex-fill" /> <div class="flex-fill" />
{#if $page.data.isZonePage && data.domain.zone_history && $domains_idx[selectedDomain] && data.domain.id === $domains_idx[selectedDomain].id} {#if !($page.data.isZonePage && data.domain.zone_history && $domains_idx[selectedDomain] && data.domain.id === $domains_idx[selectedDomain].id && $sortedDomainsWithIntermediate)}
{#if !$sortedDomainsWithIntermediate}
<Button <Button
color="danger" color="danger"
class="mt-3" class="mt-3"
@ -333,7 +354,6 @@
{/await} {/await}
</p> </p>
{/if} {/if}
{/if}
{:else} {:else}
<div class="mt-4 text-center"> <div class="mt-4 text-center">
<Spinner color="primary" /> <Spinner color="primary" />

View file

@ -51,7 +51,7 @@
</script> </script>
<Modal {isOpen} size="lg" {toggle}> <Modal {isOpen} size="lg" {toggle}>
<ModalHeader {toggle}>{$t("domains.removal")}</ModalHeader> <ModalHeader class="bg-danger-subtle" {toggle}>{$t("domains.removal")}</ModalHeader>
<ModalBody> <ModalBody>
{$t("domains.alert.remove")} {$t("domains.alert.remove")}
</ModalBody> </ModalBody>

View file

@ -24,7 +24,7 @@
<script lang="ts"> <script lang="ts">
import { goto } from "$app/navigation"; import { goto } from "$app/navigation";
import { page } from "$app/stores"; import { page } from "$app/stores";
import { onDestroy } from 'svelte'; import { onDestroy } from "svelte";
import { Spinner } from "@sveltestrap/sveltestrap"; import { Spinner } from "@sveltestrap/sveltestrap";
@ -59,7 +59,10 @@
const unsubscribe = thisZone.subscribe(async (zone) => { const unsubscribe = thisZone.subscribe(async (zone) => {
if (zone != null && zone.id != selectedHistory) { if (zone != null && zone.id != selectedHistory) {
if ($domains_idx[selectedDomain].zone_history.indexOf(zone.id) == -1) { if (
!$domains_idx[selectedDomain] ||
$domains_idx[selectedDomain].zone_history.indexOf(zone.id) == -1
) {
await refreshDomains(); await refreshDomains();
} }
selectedHistory = zone.id; selectedHistory = zone.id;
@ -73,18 +76,25 @@
{#if $thisZone && $thisZone.id == selectedHistory} {#if $thisZone && $thisZone.id == selectedHistory}
<slot /> <slot />
{:else}
<div class="mt-5 text-center flex-fill">
<Spinner label="Spinning" />
<p>{$t("wait.loading")}</p>
</div>
{/if}
{#if $thisZone}
<NewServicePath origin={data.domain} zone={$thisZone} /> <NewServicePath origin={data.domain} zone={$thisZone} />
<ServiceModal <ServiceModal
origin={data.domain} origin={data.domain}
zone={$thisZone} zone={$thisZone}
on:update-zone-services={(event) => thisZone.set(event.detail)} on:update-zone-services={(event) => thisZone.set(event.detail)}
/> />
{:else}
<div class="flex-fill d-flex flex-column">
<h2 class="d-flex align-items-center">
<Spinner label="Spinning" type="grow" />
<span class="ms-2 mt-1 font-monospace">
{data.domain.domain}
</span>
</h2>
<div class="mt-4 text-center flex-fill">
<Spinner label="Spinning" />
<p>{$t("wait.loading")}</p>
</div>
</div>
{/if} {/if}

View file

@ -29,11 +29,7 @@
import type { Zone } from "$lib/model/zone"; import type { Zone } from "$lib/model/zone";
import { domains_idx } from "$lib/stores/domains"; import { domains_idx } from "$lib/stores/domains";
import { servicesSpecs, refreshServicesSpecs } from "$lib/stores/services"; import { servicesSpecs, refreshServicesSpecs } from "$lib/stores/services";
import { import { sortedDomains, sortedDomainsWithIntermediate, thisZone } from "$lib/stores/thiszone";
sortedDomains,
sortedDomainsWithIntermediate,
thisZone,
} from "$lib/stores/thiszone";
import { t } from "$lib/translations"; import { t } from "$lib/translations";
if (!$servicesSpecs) refreshServicesSpecs(); if (!$servicesSpecs) refreshServicesSpecs();

View file

@ -80,8 +80,8 @@
{#if services.length === 0} {#if services.length === 0}
<div id={dn}> <div id={dn}>
{#if !reverseZone} {#if !reverseZone}
<h2 class="sticky-top bg-light" style="z-index: 1"> <h2 class="sticky-top bg-light d-flex align-items-center" style="z-index: 1">
<span style="white-space: nowrap"> <span class="text-truncate text-muted">
<Icon name="plus-square-dotted" title="Intermediate domain with no service" /> <Icon name="plus-square-dotted" title="Intermediate domain with no service" />
<span class="font-monospace" title={fqdn(dn, origin.domain)}> <span class="font-monospace" title={fqdn(dn, origin.domain)}>
{#if reverseZone} {#if reverseZone}
@ -91,23 +91,24 @@
{/if} {/if}
</span> </span>
</span> </span>
<div class="flex-fill"></div>
<Button <Button
type="button" type="button"
color="primary" color="primary"
size="sm" size="sm"
class="ml-2" class="ms-2"
title={$t("service.add")}
on:click={() => dispatch("new-service")} on:click={() => dispatch("new-service")}
> >
<Icon name="plus" /> <Icon name="plus" />
{$t("service.add")}
</Button> </Button>
</h2> </h2>
{/if} {/if}
</div> </div>
{:else if isCNAME(services) || isPTR(services)} {:else if isCNAME(services) || isPTR(services)}
<div id={dn}> <div id={dn}>
<h2 class="sticky-top bg-light" style="z-index: 1"> <h2 class="sticky-top bg-light d-flex align-items-center" style="z-index: 1">
<span style="white-space: nowrap"> <span class="text-truncate">
{#if isPTR(services)} {#if isPTR(services)}
<Icon name="signpost" title="PTR" /> <Icon name="signpost" title="PTR" />
{:else} {:else}
@ -121,32 +122,23 @@
{/if} {/if}
</span> </span>
</span> </span>
<span style="white-space: nowrap"> <span class="text-truncate">
<Icon name="arrow-right" /> <Icon name="arrow-right" />
<span class="font-monospace"> <span class="font-monospace" title={services[0].Service.Target}>
{services[0].Service.Target} {services[0].Service.Target}
</span> </span>
</span> </span>
<Button <div class="flex-fill"></div>
type="button"
color="primary"
size="sm"
class="ml-2"
on:click={() => dispatch("new-service")}
>
<Icon name="plus" />
{$t("service.add")}
</Button>
<Button <Button
type="button" type="button"
color="info" color="info"
outline outline
size="sm" size="sm"
class="ml-2" class="ms-2"
title={$t("domains.edit-target")}
on:click={() => showServiceModal(services[0])} on:click={() => showServiceModal(services[0])}
> >
<Icon name="pencil" /> <Icon name="pencil" />
{$t("domains.edit-target")}
</Button> </Button>
<Button <Button
type="button" type="button"
@ -154,7 +146,8 @@
disabled={deleteServiceInProgress} disabled={deleteServiceInProgress}
outline outline
size="sm" size="sm"
class="ml-2" class="ms-2"
title={isPTR(services) ? $t("domains.drop-pointer") : $t("domains.drop-alias")}
on:click={deleteCNAME} on:click={deleteCNAME}
> >
{#if deleteServiceInProgress} {#if deleteServiceInProgress}
@ -162,11 +155,16 @@
{:else} {:else}
<Icon name="x-circle" /> <Icon name="x-circle" />
{/if} {/if}
{#if isPTR(services)} </Button>
{$t("domains.drop-pointer")} <Button
{:else} type="button"
{$t("domains.drop-alias")} color="primary"
{/if} size="sm"
class="ms-2"
title={$t("service.add")}
on:click={() => dispatch("new-service")}
>
<Icon name="plus" />
</Button> </Button>
</h2> </h2>
</div> </div>
@ -226,15 +224,16 @@
{/each} {/each}
</Popover> </Popover>
{/if} {/if}
<div class="flex-fill"></div>
{#if !showResources || ($userSession && $userSession.settings.zoneview !== ZoneViewGrid)} {#if !showResources || ($userSession && $userSession.settings.zoneview !== ZoneViewGrid)}
<Button <Button
type="button" type="button"
color="primary" color="primary"
size="sm" size="sm"
title={$t("domains.add-a-service")}
on:click={() => dispatch("new-service")} on:click={() => dispatch("new-service")}
> >
<Icon name="plus" /> <Icon name="plus" />
{$t("domains.add-a-service")}
</Button> </Button>
{/if} {/if}
{#if showResources} {#if showResources}
@ -243,10 +242,10 @@
color="primary" color="primary"
outline outline
size="sm" size="sm"
title={$t("domains.add-an-alias")}
on:click={() => dispatch("new-alias")} on:click={() => dispatch("new-alias")}
> >
<Icon name="link" /> <Icon name="link" />
{$t("domains.add-an-alias")}
</Button> </Button>
{/if} {/if}
</div> </div>

View file

@ -41,16 +41,39 @@
); );
</script> </script>
<div class="mt-4 text-center flex-fill"> {#await rz}
{#await rz} <div class="flex-fill d-flex flex-column">
<h2 class="d-flex align-items-center">
<Spinner label="Spinning" type="grow" />
<span class="ms-2 mt-1 font-monospace">
{data.domain.domain}
</span>
</h2>
<div class="mt-4 text-center flex-fill">
<Spinner label={$t("common.spinning")} /> <Spinner label={$t("common.spinning")} />
<p>{$t("wait.importing")}</p> <p>{$t("wait.importing")}</p>
{:then} </div>
</div>
{:then}
<div class="flex-fill d-flex flex-column">
<h2 class="d-flex align-items-center">
<Spinner label="Spinning" type="grow" />
<span class="ms-2 mt-1 font-monospace">
{data.domain.domain}
</span>
</h2>
<div class="mt-4 text-center flex-fill">
<Spinner label={$t("common.spinning")} />
<p>{$t("wait.wait")}</p> <p>{$t("wait.wait")}</p>
{:catch main_error} </div>
</div>
{:catch main_error}
<div class="mt-4 text-center flex-fill">
<Alert color="danger" fade={false}> <Alert color="danger" fade={false}>
<strong>{$t("errors.domain-import")}</strong> <strong>{$t("errors.domain-import")}</strong>
{main_error} {main_error}
</Alert> </Alert>
{/await} </div>
</div> {/await}