import { isVersionSmaller } from '@/react/common/semver-utils';
import { humanize } from '@/portainer/filters/filters';
import { EnvironmentId } from '@/react/portainer/environments/types';
import { useEnvironment } from '@/react/portainer/environments/queries';
import { getPlatformTypeName } from '@/react/portainer/environments/utils';
import { ProgressBar } from '@@/ProgressBar';
import { Tooltip } from '@@/Tip/Tooltip/Tooltip';
import { InlineLoader } from '@@/InlineLoader/InlineLoader';
import { useDockerStorageUsageQuery } from '../queries/useDockerStorageUsageQuery';
const MIN_AGENT_VERSION = '2.42.0';
export function DockerStorageInfo({
endpointId,
}: {
endpointId: EnvironmentId;
}) {
const environmentQuery = useEnvironment(endpointId);
const environment = environmentQuery.data;
const agentVersion = environment?.Agent.Version;
const dockerStorageUsageQuery = useDockerStorageUsageQuery(endpointId, {
enabled: !!environment,
});
const dockerStorageUsage = dockerStorageUsageQuery.data;
if (environmentQuery.isLoading || dockerStorageUsageQuery.isLoading) {
return Loading storage information...;
}
if (dockerStorageUsageQuery.isError) {
const errorMessage =
dockerStorageUsageQuery.error instanceof Error
? dockerStorageUsageQuery.error.message
: 'Unknown error';
const needsUpgrade =
environmentQuery.isFetched &&
// Empty version means a pre-2.15 agent that doesn't report its version —
// definitely predates docker-storage support.
(!agentVersion || isVersionSmaller(agentVersion, MIN_AGENT_VERSION));
const minAgentVersionMessage = `Disk usage requires agent version ${MIN_AGENT_VERSION} or later. Upgrade your agent to enable this feature.`;
return (
Not available
);
}
if (!environment) {
return (
Not available
);
}
const platformName = getPlatformTypeName(
environment.Type,
environment.ContainerEngine
);
if (dockerStorageUsage?.totalBytes === undefined) {
return (
Not available
);
}
const dockerBytes = dockerStorageUsage.dockerBytes;
const otherBytes = Math.max(
0,
dockerStorageUsage.totalBytes -
dockerStorageUsage.availableBytes -
dockerBytes
);
return (
<>
{/* The progress bar is purely visual — all data is in the text legend below */}
{humanize(dockerStorageUsage.totalBytes)}
{platformName} ({humanize(dockerBytes)})
Images
{humanize(dockerStorageUsage.imageBytes)}
Containers
{humanize(dockerStorageUsage.containerBytes)}
Volumes
{humanize(dockerStorageUsage.volumeBytes)}
Build cache
{humanize(dockerStorageUsage.buildCacheBytes)}
}
/>
Other ({humanize(otherBytes)})
Free ({humanize(dockerStorageUsage.availableBytes)})
Partition: {dockerStorageUsage.rootDir}
>
);
}