Add space allocation on the top of the table

This commit is contained in:
Arnaud 2024-09-23 22:47:49 +02:00
parent b9da49c9fa
commit 4cabe251e3
No known key found for this signature in database
GPG Key ID: 69D6CE281FCAE663
3 changed files with 121 additions and 32 deletions

View File

@ -1,38 +1,20 @@
import { Spinner, Cell, Table } from "@codex-storage/marketplace-ui-components";
import { useQuery } from "@tanstack/react-query";
import prettyMilliseconds from "pretty-ms";
import { CodexSdk } from "../../sdk/codex";
import { Promises } from "../../utils/promises";
import { Cell, Table } from "@codex-storage/marketplace-ui-components";
import { TruncateCell } from "../TruncateCell/TruncateCell";
import { PrettyBytes } from "../../utils/bytes";
import { AvailabilityActionsCell } from "./AvailabilityActionsCell";
import { CodexAvailability } from "@codex-storage/sdk-js/async";
import { Times } from "../../utils/times";
type Props = {
// onEdit: () => void;
availabilities: CodexAvailability[];
onReservationsShow: (availability: CodexAvailability) => void;
};
export function AvailabilitiesTable({ onReservationsShow }: Props) {
const { data, isPending } = useQuery({
queryFn: () =>
CodexSdk.marketplace
.availabilities()
.then((s) => Promises.rejectOnError(s)),
queryKey: ["availabilities"],
refetchOnWindowFocus: false,
retry: false,
throwOnError: true,
});
if (isPending) {
return (
<div className="purchases-loader">
<Spinner width="3rem" />
</div>
);
}
export function AvailabilitiesTable({
availabilities,
onReservationsShow,
}: Props) {
const headers = [
"id",
"total size",
@ -42,13 +24,12 @@ export function AvailabilitiesTable({ onReservationsShow }: Props) {
"actions",
];
const sorted = [...(data || [])].reverse();
const cells =
sorted.map((a) => {
availabilities.map((a) => {
return [
<TruncateCell value={a.id} />,
<Cell value={PrettyBytes(a.totalSize)} />,
<Cell value={prettyMilliseconds(a.duration)} />,
<Cell value={Times.pretty(a.duration)} />,
<Cell value={a.minPrice.toString()} />,
<Cell value={a.maxCollateral.toString()} />,
<AvailabilityActionsCell

View File

@ -13,3 +13,72 @@
margin: auto;
display: block;
}
.availabilities-space .nodeSpaceAllocation-legendRow,
.availabilities-space .nodeSpaceAllocation-barItem {
transition: opacity 0.35s;
opacity: 0.8;
}
.table-container:has(.table-tbodyTr:first-child:hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-0,
.table-container:has(.table-tbodyTr:first-child:hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:first-child {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(2):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-1,
.table-container:has(.table-tbodyTr:nth-child(2):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(2) {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(3):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-2,
.table-container:has(.table-tbodyTr:nth-child(3):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(3) {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(4):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-3,
.table-container:has(.table-tbodyTr:nth-child(4):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(4) {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(5):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-4,
.table-container:has(.table-tbodyTr:nth-child(5):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(5) {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(6):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-5,
.table-container:has(.table-tbodyTr:nth-child(6):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(6) {
opacity: 1;
}
.table-container:has(.table-tbodyTr:nth-child(7):hover)
+ .availabilities-space
.nodeSpaceAllocation-quota-6,
.table-container:has(.table-tbodyTr:nth-child(7):hover)
+ .availabilities-space
.nodeSpaceAllocation-legendRow:nth-child(7) {
opacity: 1;
}

View File

@ -4,17 +4,43 @@ import { AvailabilitiesTable } from "../../components/Availability/Availabilitie
import { useState } from "react";
import { AvailabilityReservations } from "../../components/Availability/AvailabilityReservations";
import { CodexAvailability } from "@codex-storage/sdk-js/async";
import { CodexSdk } from "../../sdk/codex";
import { Promises } from "../../utils/promises";
import { useQuery } from "@tanstack/react-query";
import {
SpaceAllocation,
Spinner,
} from "@codex-storage/marketplace-ui-components";
import { Strings } from "../../utils/strings";
export const Route = createFileRoute("/dashboard/availabilities")({
component: () => {
const [availabilitySelected, setAvailabilitySelected] =
useState<CodexAvailability | null>(null);
const { data: availabilities = [], isPending } = useQuery({
queryFn: () =>
CodexSdk.marketplace
.availabilities()
.then((s) => Promises.rejectOnError(s))
.then((res) => res.sort((a, b) => b.totalSize - a.totalSize)),
queryKey: ["availabilities"],
refetchOnWindowFocus: false,
retry: false,
throwOnError: true,
});
const onReservationsShow = (a: CodexAvailability) =>
setAvailabilitySelected(a);
const onReservationsClose = () => setAvailabilitySelected(null);
const allocation = availabilities
.map((a) => ({
title: Strings.shortId(a.id),
size: a.totalSize,
}))
.slice(0, 7);
return (
<div className="container">
<AvailabilityReservations
@ -22,10 +48,23 @@ export const Route = createFileRoute("/dashboard/availabilities")({
onClose={onReservationsClose}
open={!!availabilitySelected}></AvailabilityReservations>
<AvailabilitiesTable
// onEdit={onOpen}
onReservationsShow={onReservationsShow}
/>
<div className="availabilities-content">
{isPending ? (
<div className="purchases-loader">
<Spinner width="3rem" />
</div>
) : (
<AvailabilitiesTable
// onEdit={onOpen}
availabilities={availabilities}
onReservationsShow={onReservationsShow}
/>
)}
<div className="availabilities-space">
<SpaceAllocation data={allocation} />
</div>
</div>
</div>
);
},