Skip to content

Commit 7082536

Browse files
Adebesin-Cellclaude
andcommitted
fix: track remaining packages by name and support partial expand
- useOrgPackages: derive remainingNames from a Set of loaded package names instead of positional slicing, so partial Algolia failures don't permanently skip packages on retry - useVisibleItems: onExpand can return false to signal partial load, keeping hasMore true so the user can retry Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 611ecc6 commit 7082536

File tree

2 files changed

+12
-7
lines changed

2 files changed

+12
-7
lines changed

app/composables/npm/useOrgPackages.ts

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -137,8 +137,8 @@ export function useOrgPackages(orgName: MaybeRefOrGetter<string>) {
137137

138138
/** Load all remaining packages that weren't fetched in the initial batch. */
139139
async function loadAll(): Promise<void> {
140-
const names = allNames.value
141-
if (names.length <= loadedObjects.value.length) return
140+
const loadedSet = new Set(loadedObjects.value.map(o => o.package.name))
141+
if (loadedSet.size >= allNames.value.length) return
142142

143143
// Reuse in-flight promise to prevent duplicate fetches
144144
if (loadAllPromise) {
@@ -157,10 +157,11 @@ export function useOrgPackages(orgName: MaybeRefOrGetter<string>) {
157157
async function _doLoadAll(): Promise<void> {
158158
const names = allNames.value
159159
const current = loadedObjects.value
160-
if (names.length <= current.length) return
160+
const loadedSet = new Set(current.map(o => o.package.name))
161+
const remainingNames = names.filter(n => !loadedSet.has(n))
162+
if (remainingNames.length === 0) return
161163

162164
const org = toValue(orgName)
163-
const remainingNames = names.slice(current.length)
164165

165166
let newObjects: NpmSearchResult[] = []
166167

app/composables/useVisibleItems.ts

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,10 @@ export interface UseVisibleItemsOptions {
55
/**
66
* Called when expanding. Useful for loading remaining data on demand.
77
* If it returns a promise, `isExpanding` will be `true` until it resolves.
8+
* Return `false` to signal a partial load — `showAll` stays false so
9+
* `hasMore` remains true and the user can retry.
810
*/
9-
onExpand?: () => void | Promise<void>
11+
onExpand?: () => void | boolean | Promise<void | boolean>
1012
}
1113

1214
export function useVisibleItems<T>(
@@ -30,15 +32,17 @@ export function useVisibleItems<T>(
3032

3133
const expand = async () => {
3234
if (showAll.value) return
35+
let fullyLoaded = true
3336
if (options?.onExpand) {
3437
isExpanding.value = true
3538
try {
36-
await options.onExpand()
39+
const result = await options.onExpand()
40+
if (result === false) fullyLoaded = false
3741
} finally {
3842
isExpanding.value = false
3943
}
4044
}
41-
showAll.value = true
45+
if (fullyLoaded) showAll.value = true
4246
}
4347
const collapse = () => {
4448
showAll.value = false

0 commit comments

Comments
 (0)