Skip to content

fix(core): index images inside Portable Text gallery blocks for media usage - #3096

Open
dchaudhari7177 wants to merge 1 commit into
emdash-cms:mainfrom
dchaudhari7177:fix/2872-media-usage-gallery-images
Open

fix(core): index images inside Portable Text gallery blocks for media usage#3096
dchaudhari7177 wants to merge 1 commit into
emdash-cms:mainfrom
dchaudhari7177:fix/2872-media-usage-gallery-images

Conversation

@dchaudhari7177

Copy link
Copy Markdown
Contributor

What does this PR do?

The media usage extractor only looked at top-level _type: "image" Portable Text blocks, so images inside a core gallery block (content[n].images[i].asset) were never indexed. A media item used only in galleries showed an empty "Used in" list with coverage complete, and so looked safe to delete.

extractPortableTextOccurrences now also walks gallery blocks. Each image's asset goes through the same ref handling as an image block (factored into addPortableTextAssetOccurrence): _ref or id, provider, MIME and the external-URL skip all behave identically. I took the second option from the issue: the existing portable_text_image reference type, with a field_path pointing into the gallery (body[1].images[0].asset._ref). That needs no change to the reference-type enum, the API schema or normalizeMediaUsageReferenceType.

Closes #2872

One question for you. Sites that already built their usage index keep their old rows until the affected content is refreshed, so gallery-only media stays "unused" there until then. CONTENT_SOURCE_SCHEMA_VERSION looks like the switch that marks scopes stale, but it is the content-source schema version, and I didn't want to bump a shared version just for an extractor change. Happy to add whatever re-index trigger you prefer.

Type of change

  • Bug fix

Checklist

  • I have read CONTRIBUTING.md
  • pnpm typecheck passes: not run as tsgo; the change is confined to extractor.ts types already in use
  • pnpm lint passes: oxlint --deny-warnings on the touched files
  • pnpm test passes (or targeted tests for my change)
  • pnpm format has been run: oxfmt
  • I have added/updated tests for my changes (if applicable)
  • User-visible strings in the admin UI are wrapped for translation: n/a
  • I have added and reviewed the user-facing changeset
  • New features link to an approved Discussion: n/a, bug fix
  • I have included screenshots below if this PR changes the UI: n/a

AI-generated code disclosure

  • This PR includes AI-generated code — model/tool: Claude Opus 5 (Claude Code)

Screenshots / test output

Not applicable (indexer). New cases in packages/core/tests/unit/media/usage-extractor.test.ts:

  • a gallery with a local _ref image, a Cloudflare Images id image, an external-URL image, an image with no asset, and a non-object entry, plus a second gallery whose images is malformed. Only the two real references come out, with paths body[1].images[0].asset._ref and body[1].images[1].asset.id;
  • an image used both as an image block and in a gallery counts as two uses.
main:  2 failed | 9 passed
head:  11 passed

tests/unit/media plus media-usage-content-refresh and media-usage-read-repository integration tests: 18 files, 182 passed.

… usage

The media usage extractor read only top-level image blocks in Portable
Text, so the images in a core gallery block (content[n].images[i].asset)
were never indexed. A media item used only in galleries showed an empty
"Used in" list and a complete coverage state, and looked unused.

Gallery images now produce portable_text_image occurrences whose field path
points into the gallery, through the same asset-ref handling as image
blocks.

Closes emdash-cms#2872
@changeset-bot

changeset-bot Bot commented Sep 13, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 1d1a4d0

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 18 packages
Name Type
emdash Patch
@emdash-cms/cloudflare Patch
@emdash-cms/plugin-test Patch
@emdash-cms/sandbox-workerd Patch
@emdash-cms/fixture-perf-site Patch
@emdash-cms/perf-demo-site Patch
@emdash-cms/cache-demo-site Patch
@emdash-cms/do-demo-site Patch
@emdash-cms/do-solo-demo-site Patch
@emdash-cms/admin Patch
@emdash-cms/auth Patch
@emdash-cms/blocks Patch
create-emdash Patch
@emdash-cms/gutenberg-to-portable-text Patch
@emdash-cms/x402 Patch
@emdash-cms/auth-atproto Patch
@emdash-cms/release-service Patch
@emdash-cms/plugin-embeds Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@github-actions github-actions Bot added area/core size/M review/needs-review No maintainer or bot review yet labels Sep 13, 2026
@pkg-pr-new

pkg-pr-new Bot commented Sep 13, 2026

Copy link
Copy Markdown

Open in StackBlitz

@emdash-cms/admin

npm i https://pkg.pr.new/@emdash-cms/admin@3096

@emdash-cms/auth

npm i https://pkg.pr.new/@emdash-cms/auth@3096

@emdash-cms/auth-atproto

npm i https://pkg.pr.new/@emdash-cms/auth-atproto@3096

@emdash-cms/blocks

npm i https://pkg.pr.new/@emdash-cms/blocks@3096

@emdash-cms/cloudflare

npm i https://pkg.pr.new/@emdash-cms/cloudflare@3096

@emdash-cms/contentful-to-portable-text

npm i https://pkg.pr.new/@emdash-cms/contentful-to-portable-text@3096

emdash

npm i https://pkg.pr.new/emdash@3096

create-emdash

npm i https://pkg.pr.new/create-emdash@3096

@emdash-cms/gutenberg-to-portable-text

npm i https://pkg.pr.new/@emdash-cms/gutenberg-to-portable-text@3096

@emdash-cms/plugin-cli

npm i https://pkg.pr.new/@emdash-cms/plugin-cli@3096

@emdash-cms/plugin-test

npm i https://pkg.pr.new/@emdash-cms/plugin-test@3096

@emdash-cms/plugin-types

npm i https://pkg.pr.new/@emdash-cms/plugin-types@3096

@emdash-cms/registry-client

npm i https://pkg.pr.new/@emdash-cms/registry-client@3096

@emdash-cms/registry-lexicons

npm i https://pkg.pr.new/@emdash-cms/registry-lexicons@3096

@emdash-cms/registry-moderation

npm i https://pkg.pr.new/@emdash-cms/registry-moderation@3096

@emdash-cms/registry-verification

npm i https://pkg.pr.new/@emdash-cms/registry-verification@3096

@emdash-cms/sandbox-workerd

npm i https://pkg.pr.new/@emdash-cms/sandbox-workerd@3096

@emdash-cms/x402

npm i https://pkg.pr.new/@emdash-cms/x402@3096

@emdash-cms/plugin-ai-moderation

npm i https://pkg.pr.new/@emdash-cms/plugin-ai-moderation@3096

@emdash-cms/plugin-atproto

npm i https://pkg.pr.new/@emdash-cms/plugin-atproto@3096

@emdash-cms/plugin-audit-log

npm i https://pkg.pr.new/@emdash-cms/plugin-audit-log@3096

@emdash-cms/plugin-color

npm i https://pkg.pr.new/@emdash-cms/plugin-color@3096

@emdash-cms/plugin-embeds

npm i https://pkg.pr.new/@emdash-cms/plugin-embeds@3096

@emdash-cms/plugin-field-kit

npm i https://pkg.pr.new/@emdash-cms/plugin-field-kit@3096

@emdash-cms/plugin-forms

npm i https://pkg.pr.new/@emdash-cms/plugin-forms@3096

@emdash-cms/plugin-webhook-notifier

npm i https://pkg.pr.new/@emdash-cms/plugin-webhook-notifier@3096

commit: 1d1a4d0

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area/core review/needs-review No maintainer or bot review yet size/M

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Media usage tracking does not index images inside gallery blocks

1 participant