Skip to content

fix(ObjectStorePreviewStorage): Close count stream wrapper - #63849

Merged
CarlSchwan merged 1 commit into
masterfrom
carl/close-countWrappr
Aug 31, 2026
Merged

fix(ObjectStorePreviewStorage): Close count stream wrapper#63849
CarlSchwan merged 1 commit into
masterfrom
carl/close-countWrappr

Conversation

@CarlSchwan

Copy link
Copy Markdown
Member

Summary

So that the size is finalized

TODO

  • ...

Checklist

AI (if applicable)

  • The content of this PR was partly or fully generated using AI

@CarlSchwan CarlSchwan added this to the Nextcloud 36 milestone Aug 31, 2026
@CarlSchwan CarlSchwan self-assigned this Aug 31, 2026
@CarlSchwan
CarlSchwan requested a review from a team as a code owner August 31, 2026 12:36
@CarlSchwan
CarlSchwan requested review from Altahrim, icewind1991, leftybournes and salmart-dev and removed request for a team August 31, 2026 12:36
@CarlSchwan
CarlSchwan enabled auto-merge August 31, 2026 13:33
@CarlSchwan

Copy link
Copy Markdown
Member Author

/backport to stable35

@CarlSchwan

Copy link
Copy Markdown
Member Author

/backport to stable34

@CarlSchwan

Copy link
Copy Markdown
Member Author

/backport to stable33

@jo23sh

jo23sh commented Aug 31, 2026

Copy link
Copy Markdown

Production data point in favour of backporting this to stable34.

We hit this on 34.0.2 with OpenStack Swift as primary storage. writePreview() returns $size = 0 on every call because Swift::writeObject() never closes the stream it is handed, so the CountWrapper callback never fires. savePreview() then throws Unable to write preview file even though the upload to Swift succeeded.

The impact is bigger than log noise, because the preview is never recorded in oc_previews:

  • No preview has been cached since the 34 upgrade. Last row in oc_previews is 2026-08-10 00:38, hours before we upgraded that morning — 21 days, zero new rows, against 14,781 image files.
  • Every thumbnail request regenerates from scratch, indefinitely. ~99% of the failures are GET /core/preview, and a 32×32 request still goes through getMaxPreview(), so each one fully decodes the source and builds a 4096×4096 preview.
  • Orphaned objects accumulate. The upload succeeds before the throw, so each attempt leaves an object nothing will ever read: 26,306 objects / 10.5 GB in 21 days, ~34% of all objects in the container.
  • On a small (4 GB) instance this exhausted memory and required a hard reset.

For comparison the files path gets this right — ObjectStoreStorage::writeStream() closes the count stream before reading the size:

$this->objectStore->writeObject($urn, $countStream, ...);
if (is_resource($countStream)) {
    fclose($countStream);
}
$stat['size'] = $totalWritten;

Carrying this patch locally meanwhile; it applies cleanly to 34.0.2. Happy to test a stable34 backport.

So that the size is finalized

Signed-off-by: Carl Schwan <carl@carlschwan.eu>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug]: ObjectStorePreviewStorage returns size 0 with OpenStack Swift, causing “Unable to write preview file”

5 participants