diff --git a/Dockerfile b/Dockerfile index 7ea6ac0d..cb70cbc6 100644 --- a/Dockerfile +++ b/Dockerfile @@ -92,6 +92,14 @@ COPY --from=builder --chown=oxicloud:oxicloud /app/static-dist /app/static # Create storage directory with proper permissions RUN mkdir -p /app/storage && chown -R oxicloud:oxicloud /app/storage +# Allocator tuning — make RSS track the live working set. +# mimalloc retains freed pages by default, so process RSS clamps at the peak +# even after the in-memory caches (file content, thumbnails, transcode) expire +# by TTL. Purging immediately returns those pages to the kernel at no throughput +# cost. Measured on this musl/aarch64 image: a 400 MB alloc→free spike returns +# 0 MB by default vs ~400 MB with this set (idle RSS back to a few MB). +ENV MIMALLOC_PURGE_DELAY=0 + # Set working directory WORKDIR /app diff --git a/docker-compose.yml b/docker-compose.yml index 241a4422..f140be85 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -21,6 +21,14 @@ services: oxicloud: image: diocrafts/oxicloud:latest restart: always + environment: + # Return freed heap pages to the OS promptly. mimalloc retains them by + # default, so idle RSS clamps at the peak even after the in-memory caches + # expire; purging immediately makes RSS track the live working set + # (benchmarked: ~400 MB reclaimed on musl/aarch64) at no throughput cost. + # Also baked into the Dockerfile; set here so it applies to the prebuilt + # image too. + MIMALLOC_PURGE_DELAY: "0" build: context: . dockerfile: Dockerfile diff --git a/frontend/src/lib/components/AppShell.svelte b/frontend/src/lib/components/AppShell.svelte index 6de09319..14028301 100644 --- a/frontend/src/lib/components/AppShell.svelte +++ b/frontend/src/lib/components/AppShell.svelte @@ -261,7 +261,7 @@ @@ -526,7 +526,19 @@
- {Math.round(storagePct)}% {t('storage.used', 'used')} + {#if session.user.storage_quota_bytes > 0} + {t( + 'storage.used', + { + percentage: Math.round(storagePct), + used: formatBytes(session.user.storage_used_bytes), + total: formatBytes(session.user.storage_quota_bytes) + }, + '{{percentage}}% used ({{used}} / {{total}})' + )} + {:else} + {formatBytes(session.user.storage_used_bytes)} + {/if}
{/if} @@ -661,7 +673,7 @@
e.target === e.currentTarget && (aboutOpen = false)}>