Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
33 commits
Select commit Hold shift + click to select a range
5aa17d3
feat(ui): checkmark on active highlight swatch
cameronapak Jul 20, 2026
1f25866
fix(highlights): re-prompt when a resumed pending write fails 401/403
cameronapak Jul 15, 2026
4dd2c12
docs(highlights): document intentional 5xx intent-drop on resumed writes
cameronapak Jul 15, 2026
16de729
fix(highlights): apply code-review findings across core, hooks, and ui
cameronapak Jul 16, 2026
014e797
fix(deps): pin xstate to 5.32.4 to clear the supply-chain cooldown
cameronapak Jul 16, 2026
905e592
fix(core): bind the data-exchange grant to the initiating user
cameronapak Jul 16, 2026
769c033
fix(highlights): close grant-initiator race and preserve sibling pend…
cameronapak Jul 21, 2026
70102cc
merge(main): resolve highlightsEnabled conflict with controlled mode
cameronapak Jul 22, 2026
1bbf9fa
merge(main): absorb #286 checkmark landing
cameronapak Jul 22, 2026
0efafe1
fix(highlights): preserve grants and pitch on one-shot sign-in
cameronapak Jul 22, 2026
db02cc7
fix(core): clear stale granted-permissions stash on signIn
cameronapak Jul 22, 2026
32bf66d
fix(auth): bind grant stash to OAuth state and clear stale DX initiator
cameronapak Jul 22, 2026
5faafcc
fix(core): treat empty 2xx response bodies as no data
cameronapak Jul 22, 2026
75a6651
feat(ui): launch server-backed highlights (HIGHLIGHTS_LIVE on)
cameronapak Jul 22, 2026
d71d18a
feat(ui): theme-aware highlight fills, Swift SDK parity
cameronapak Jul 22, 2026
a9af8fc
fix(ui): require accessible label on YouVersion Platform logo
cameronapak Jul 22, 2026
8662cec
refactor(core): store pending granted-permissions stash as string[]
cameronapak Jul 22, 2026
b34e9d7
docs: remove personal workflow notes from AGENTS.md
cameronapak Jul 22, 2026
00b1ff4
docs: consolidate highlights changesets into one launch changelog
cameronapak Jul 22, 2026
978dd20
feat(ui): rounded highlight fills and dark-mode swatch previews
cameronapak Jul 22, 2026
9fc94e8
chore(demo): drop the sign-in pitch message from the vite demo
cameronapak Jul 22, 2026
4ded90a
fix(ui): show popover focus ring only for keyboard focus
cameronapak Jul 22, 2026
43f759a
fix(core): accept bracket-notation granted_permissions from callbacks
cameronapak Jul 22, 2026
f81fd59
fix(auth): dedupe OAuth code exchange so duplicate callbacks can't wi…
cameronapak Jul 23, 2026
232e622
refactor(review): apply simplification pass from PR 294 review
cameronapak Jul 23, 2026
90b4716
fix(auth): share concurrent token refreshes so a losing duplicate can…
cameronapak Jul 23, 2026
ba6e5fe
fix(ui): verse label and footnote icon inherit text color over highli…
cameronapak Jul 23, 2026
2850531
fix(auth): optimistically seed requested permissions when the server …
cameronapak Jul 23, 2026
423aa6a
fix(ui): cap verse popover to viewport width with scrollable swatch row
cameronapak Jul 23, 2026
e9d0f2b
fix(ui): attach popover scroll-fade to the row's real lifecycle and t…
cameronapak Jul 23, 2026
cf6a291
feat(ui): highlight fills render at 30% opacity in light mode too (pr…
cameronapak Jul 23, 2026
959f2ca
docs(ui): fix stale checkmark comment after both-mode fill dimming
cameronapak Jul 23, 2026
7b91105
revert(ui): restore full-strength light-mode highlight fills (design …
cameronapak Jul 23, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 0 additions & 15 deletions .changeset/bible-reader-highlights-api.md

This file was deleted.

7 changes: 0 additions & 7 deletions .changeset/checkmark-active-swatch.md

This file was deleted.

7 changes: 7 additions & 0 deletions .changeset/fix-granted-permissions-bracket-notation.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
---
'@youversion/platform-core': patch
---

Fix one-shot sign-in dropping the `highlights` grant when the auth server echoes it back with PHP/Rails bracket-array notation (`granted_permissions[]=highlights`).

`parseGrantedPermissions` read only the bare `granted_permissions` key, but `URLSearchParams` treats `granted_permissions[]` (and indexed `granted_permissions[0]`) as distinct keys. The server demonstrably uses this bracket notation for the analogous outbound `requested_permissions[]` param it builds on the hosted consent redirect, so a return echo in the same shape was silently discarded — leaving the permission cache empty and re-prompting the just-in-time data-exchange consent after a completed sign-in. The parser now accepts `granted_permissions`, `granted_permissions[]`, and `granted_permissions[<index>]`, keeping it symmetric with the server's encoding. Purely additive: bare `granted_permissions` and all user/state-scoping and fail-closed protections are unchanged.
15 changes: 0 additions & 15 deletions .changeset/fix-highlights-jam-issues.md

This file was deleted.

11 changes: 0 additions & 11 deletions .changeset/highlight-auth-flow.md

This file was deleted.

24 changes: 24 additions & 0 deletions .changeset/highlights-server-backed.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
---
'@youversion/platform-core': patch
'@youversion/platform-react-hooks': minor
'@youversion/platform-react-ui': minor
---

BibleReader highlights are now real, server-backed YouVersion highlights, with a built-in sign-in and permission flow so a reader's highlights persist to their YouVersion account.

**Important: previous releases accidentally shipped a demo-only, localStorage-based highlights implementation in BibleReader. It stored highlights only in the local browser and never synced to the reader's YouVersion account. That implementation has been removed and replaced by the server-backed highlights described here.** These highlights are live in this release and enabled by default.

- Server-backed highlights in BibleReader: tap verses, pick a color, and highlights persist to the reader's YouVersion account instead of the local browser.
- Built-in sign-in dialog and just-in-time `highlights` permission flow: a highlight tap while signed out opens a sign-in dialog; a missing `highlights` permission triggers the YouVersion data-exchange consent flow, and the pending highlight is applied automatically once consent is granted (surviving the redirect round-trip).
- New `BibleReader` props `appName` and `signInPromptMessage` for the sign-in dialog (Swift SDK parity): `appName` names your app in the dialog, and `signInPromptMessage` shows an optional integrator pitch (hidden when unset).
- Optimistic UI: color taps apply and remove instantly while writes settle in the background, with automatic revert on network/5xx failures and a re-prompt on auth failures (401/403).
- Behavior change in `useHighlights`: `createHighlight` and `deleteHighlight` no longer auto-refetch. Direct consumers must now call `refetch()` themselves after their mutations settle; the BibleReader flow coordinates this for you (batching a set of verse writes into a single refetch).
- New exports: `YouVersionAuthContext` from `@youversion/platform-react-hooks` (the no-throw alternative to `useYVAuth` for components that must tolerate a missing auth provider), and a re-export of the `Highlight` type from `@youversion/platform-react-ui`.
- The active color swatch now shows a checkmark (24px `icons/check`) instead of an X, matching the Bible app; tapping it still removes the highlight.
- Highlight-flow reliability fixes surfaced by staging: the previously invisible primary button in the permission dialog now uses the correct `bg-primary` / `text-primary-foreground` pairing (it resolved to white-on-white in light mode); the optimistic overlay is retired only once a refetch actually reflects the write, so highlights no longer flicker out and back under read-after-write lag; removes now send one DELETE per verse (range DELETE is unsupported by the API), while applies still collapse contiguous verses into range USFMs; and highlight fills now fade their background color (~250ms, disabled under `prefers-reduced-motion`) instead of popping in.
- Fix: the core `ApiClient` now treats empty-body 2xx JSON responses as success with no data. Previously a successful highlight delete (a 200 with an empty body) was misread as a failure, briefly flashing the removed highlight back before it disappeared.
- Fix: duplicate processing of the same OAuth callback (e.g. the double-invoked auth init effect under React StrictMode) can no longer clear a just-granted `highlights` permission. The code-for-token exchange is now deduped by authorization code, so a repeated callback shares the one exchange instead of firing a second request whose failure would wipe the freshly seeded grant and re-prompt for permission.
- Fix: a one-shot `highlights` sign-in no longer re-prompts for permission when the auth server omits the grant echo. On the web flow the server returns no `granted_permissions` on the callback and no data-exchange scope on the token, so nothing seeded the permission cache and the flow immediately re-prompted after consent. The permissions requested at sign-in are now stashed (bound to the OAuth `state`) and seeded optimistically on return; the seed is self-correcting because a 401/403 on the first write drops the permission and re-prompts.
- Fix: concurrent token refreshes (e.g. the double-invoked auth init effect under React StrictMode) now share a single in-flight refresh, so a losing duplicate can no longer spend the single-use refresh token a second time and wipe the session on its failure.
- Fix: verse labels and footnote icons now inherit the surrounding text color over highlight fills instead of being painted with the fill color, keeping them legible on highlighted verses.
- Theme-aware highlight rendering: highlight fills render at full opacity in light mode and 30 percent opacity in dark mode, matching the Swift SDK; verse numbers over dark-mode highlights render white. Highlight fills now have subtly rounded corners, with each wrapped line fragment getting its own rounded ends so a multi-line highlight no longer cuts off square at the wrap. The verse-action popover color swatches preview the real fill: in dark mode they show the same dimmed color a highlight will apply. Opening the popover with a mouse or touch no longer flashes a focus ring on the first swatch; keyboard navigation still shows a clearly visible focus ring.
2 changes: 2 additions & 0 deletions .changeset/localization-aria-labels.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,5 @@
---

Localize BibleReader font-size/line-spacing and popover close accessibility labels via i18n.

- The YouVersion Platform logo component's accessible label is now a required prop with no hardcoded English default; the SDK's built-in usages pass localized labels.
12 changes: 0 additions & 12 deletions .changeset/xstate-highlights-flow.md

This file was deleted.

9 changes: 9 additions & 0 deletions CONTEXT.md
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,15 @@ enums — more arrive later — and the server reports the ones a user granted
back to the app via `granted_permissions` on the sign-in and data-exchange
callbacks (YPE-1034).

## Sign-in prompt message

Optional integrator-owned pitch line shown on the **sign-in dialog**
(`YouVersionPlatformConfiguration.signInPromptMessage`). Hidden when unset;
the SDK does not ship a default (Swift parity). Distinct from localized SDK
copy (`signIn.paragraph`, buttons, etc.).
_Avoid_: app message, integrator message (informal); `signIn.appMessage`
(unused Swift stub key)

## Highlight auth flow

The flow (YPE-1034) that turns a color tap into an applied highlight when the
Expand Down
Loading
Loading