Skip to content

🚧 Motion Photo facet [demonstrator, not ready for review] - #1

Closed
dschmidt wants to merge 8 commits into
refactor/search-mappingfrom
demo/motion-photo
Closed

🚧 Motion Photo facet [demonstrator, not ready for review]#1
dschmidt wants to merge 8 commits into
refactor/search-mappingfrom
demo/motion-photo

Conversation

@dschmidt

@dschmidt dschmidt commented Jul 6, 2026

Copy link
Copy Markdown
Owner

🚧 NOT READY FOR REVIEW 🚧

This is a demonstrator, not a review request. It stacks on top of the
search-mapping refactor (targets that branch) and exists only to show the
Motion Photo feature working end to end. Please do not review or merge.

What this shows

Google Motion Photo support wired through the whole stack:

  • Extraction (services/search): reads the Google Motion Photo XMP
    (Camera:/Container: keys) that the patched Tika (TIKA-4773) exposes, and
    builds a motionPhoto facet. The Tika extractors are split per facet
    (tika_image.go, tika_audio.go, ..., tika_motion_photo.go).
  • Persistence + Graph: the facet is written back to storage metadata
    (libre.graph.motionPhoto.*) and exposed on the Graph DriveItem.
  • PROPFIND (vendored reva/v2 demo patch): emits <oc:motionPhoto> so the web
    client, which lists folders via PROPFIND and not Graph, actually receives it.
  • Video presence validation: the facet is only exposed when the file really
    contains the embedded video. Sharing a photo via photos.google.com strips the
    appended video but keeps the XMP; we do a ranged read at fileSize - videoSize
    and require an MP4 ftyp box before exposing the facet.

Caveats (why this is a demonstrator)

  • Requires a patched Tika. Motion photo now comes only from the Tika key path
    (TIKA-4773, merged to Tika main, so far only in 4.0.0-SNAPSHOT, no stable
    release yet). The dev stack pins
    apache/tika:4.0.0-SNAPSHOT@sha256:b2faa4d53479225c42533d7b70e310fbdebc2036b983179a6cbf3b8c5b974397.
    There is no direct-XMP fallback anymore, so stock Tika 3.x yields no motion photo.
  • The reva change is a vendored patch, not a real dependency bump. It has to
    be upstreamed as a proper reva/v2 PR; a go mod vendor would overwrite it.
  • The libre-graph-api bump points at an unmerged upstream PR (Rebrand activitylog opencloud-eu/opencloud#36); the web
    MotionPhoto type is an interim shim.
  • No acceptance tests, no config/documentation, no upstream coordination yet.

Base: refactor/search-mapping (the search-mapping refactor PR).

dschmidt added 8 commits July 6, 2026 16:30
Adds the generated MotionPhoto model + DriveItem.LibreGraphMotionPhoto (libre-graph-api#36).
Extracts Google Motion Photo metadata (GCamera XMP) via Tika and plumbs
the @libre.graph.motionPhoto facet through the index, search results and
the graph DriveItem (libre-graph-api#36).
Vendored patch to reva/v2 ocdav propfind, mirroring the
audio/photo/location/image facets, so the web client (which lists
folders via PROPFIND, not Graph) receives <oc:motionPhoto>.
Demonstrator only: to be upstreamed as a proper reva PR. A
`go mod vendor` would overwrite this.
The facet was derived purely from XMP. Sharing a photo via
photos.google.com strips the appended video but keeps the XMP, which
produced an unplayable motionPhoto facet. Before exposing it, validate
the trailing bytes: a ranged read at fileSize-videoSize must start with
an MP4 ftyp box. Adds Retriever.RetrieveRange (cs3 + mock) and gates the
facet in Tika.Extract.
Keep tika.go focused on the generic Tika extraction. All Google Motion
Photo specifics (XMP parsing, video-size resolution, the ftyp video
presence check and helpers) move to motionphoto.go. Extract keeps only
the orchestration calls. No behavior change.
The fallback read the Google Motion Photo XMP straight from the buffered
file head because stock Tika dropped the vendor namespace. With the
patched Tika (TIKA-4773, in 4.0.0-SNAPSHOT) exposing the Camera:/Container:
keys, the Tika-key path (getMotionPhoto) covers it, so the fallback,
extractXMPPacket and the head buffering are removed. The video-presence
validation (motionPhotoHasVideo) is independent and stays.
Each facet extractor now lives in its own file next to the Tika core:
tika_image.go, tika_location.go, tika_photo.go, tika_audio.go and
tika_motion_photo.go (renamed from motionphoto.go). tika.go keeps only
the Tika type, its constructor and the Extract orchestration.

getFirstValue is now variadic (returns the first value present among the
given keys), absorbing the motion-photo multi-key lookup, so there is one
metadata helper instead of two.
In Extract, getMotionPhoto now runs last in the per-metadata loop so it
sits right before the post-loop video-presence check, instead of being
separated by the audio handling. Drop the redundant comment on the check
(motionPhotoHasVideo and its own doc comment already say what and why).
@dschmidt
dschmidt force-pushed the refactor/search-mapping branch from 8c6a3b6 to 429a9c0 Compare July 16, 2026 00:23
@dschmidt

Copy link
Copy Markdown
Owner Author

Proper PR at opencloud-eu#3200

@dschmidt dschmidt closed this Jul 29, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant