fix(search): announce asynchronous empty results - #1636
Conversation
Add a focused asynchronous loading-to-empty regression on the current Search owner. The unchanged owner source lacks a status live region for the empty result, so this commit is the source-order RED. Signed-off-by: Seongho Bae <me@seonghobae.me>
Keep the existing loading status and make the post-search empty result a polite status live region. This is the minimal source repair for the focused loading-to-empty regression and changes no visual styling or Search domain behavior. Signed-off-by: Seongho Bae <me@seonghobae.me>
|
Warning Review limit reachedNext included review available in 41 minutes. View limit detailsLimit details: You’ve used the included review currently available. You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository. Review configuration: ⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Advanced Run ID: 📒 Files selected for processing (2)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
The generated #1633 SearchLayout blob was based on protected develop and reverted valid #1603 customer-copy semantics when overlaid directly. Restore the exact #1603 source while retaining only the focused live-region RED test. Keep this branch RED-only until the one-line semantic fix is applied without replacing owner content. Signed-off-by: Seongho Bae <me@seonghobae.me>
Isolate only the generated SearchLayout live-region change on protected-develop ancestry so Git can perform an ordinary three-way integration into the active Search owner without copying stale generated customer-copy source. Signed-off-by: Seongho Bae <me@seonghobae.me>
Ordinary three-way integration of the one-line live-region change into the active #1603 successor. Preserve the focused RED test and all existing Search customer-copy/evidence source.
|
@coderabbitai review Review current exact head |
🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='b1ee9b2d86916a5c29bcd7be1de09c6a6fb4e98c'
search_file='frontend/src/components/SearchLayout.tsx'
test_file='frontend/src/components/SearchLayout.empty-live-region.test.tsx'
git cat-file -e "${base}^{commit}"
git cat-file -e "${head}^{commit}"
printf '%s\n' '=== exact-range name-status ==='
git diff --name-status "$base" "$head"
printf '%s\n' '=== exact-range stat ==='
git diff --stat "$base" "$head"
printf '%s\n' '=== exact-range scoped patch ==='
git diff --find-renames --find-copies --no-ext-diff "$base" "$head" -- "$search_file" "$test_file"
printf '%s\n' '=== SearchLayout symbols at head ==='
git show "${head}:${search_file}" | ast-grep outline /dev/stdin --lang tsx --items all 2>/dev/null || true
printf '%s\n' '=== SearchLayout at base ==='
git show "${base}:${search_file}" | cat -n
printf '%s\n' '=== SearchLayout at head ==='
git show "${head}:${search_file}" | cat -n
printf '%s\n' '=== focused test at head ==='
git show "${head}:${test_file}" | cat -n
printf '%s\n' '=== test/tooling manifests ==='
fd -HI '^(package\.json|vite\.config\..*|vitest\.config\..*)$' . -x sh -c 'echo "=== $1 ==="; sed -n "1,220p" "$1"' sh {} \;Length of output: 114897 🏁 Script executed: #!/bin/bash
set -euo pipefail
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='b1ee9b2d86916a5c29bcd7be1de09c6a6fb4e98c'
overlay='d99d88ab2d67c80fc1042f6ebbb2e8627214d5b4'
search_file='frontend/src/components/SearchLayout.tsx'
printf '%s\n' '=== api-client outline and relevant implementation ==='
ast-grep outline frontend/src/lib/api-client.ts --items all
sed -n '1,260p' frontend/src/lib/api-client.ts
printf '%s\n' '=== Vitest setup ==='
sed -n '1,260p' frontend/src/test/setup.ts
printf '%s\n' '=== exact commit ancestry ==='
git merge-base --is-ancestor "$base" "$head" && echo 'base is an ancestor of head'
git merge-base "$base" "$head"
git show -s --format='head=%H%nparents=%P%nsubject=%s' "$head"
printf '%s\n' '=== normalized SearchLayout equality ==='
git show "${base}:${search_file}" > /tmp/search-base.tsx
git show "${head}:${search_file}" > /tmp/search-head.tsx
sed 's/ role="status" aria-live="polite" className=/ className=/' /tmp/search-head.tsx > /tmp/search-head-normalized.tsx
cmp -s /tmp/search-base.tsx /tmp/search-head-normalized.tsx \
&& echo 'head equals base after removing only the intended attributes' \
|| { echo 'unexpected source difference'; diff -u /tmp/search-base.tsx /tmp/search-head-normalized.tsx; }
printf '%s\n' '=== generated-overlay availability and scoped comparison ==='
if git cat-file -e "${overlay}^{commit}" 2>/dev/null; then
git show -s --format='overlay=%H%nparents=%P%nsubject=%s' "$overlay"
git diff --no-ext-diff "$base" "$overlay" -- "$search_file"
else
echo 'overlay commit is not available in the local object database'
fiLength of output: 18297
No source-level findings in the requested scope.
I did not perform browser, keyboard, assistive-technology, or hosted exact-head validation. Those delivery-gate items remain outside this source review.
|
Make the async loading-to-empty contract deterministic by resolving and flushing the controlled response chain inside React act instead of polling real zero-delay timers. Preserve the exact one-line Search source delta. Signed-off-by: Seongho Bae <me@seonghobae.me>
|
@coderabbitai review Re-review current exact head |
🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='e64a1181c234c9213774bcd5c2d4c4288bb889b2'
overlay='d99d88ab2d67c80fc1042f6ebbb2e8627214d5b4'
search_file='frontend/src/components/SearchLayout.tsx'
test_file='frontend/src/components/SearchLayout.empty-live-region.test.tsx'
git cat-file -e "${base}^{commit}"
git cat-file -e "${head}^{commit}"
echo '=== Commit and ancestry ==='
git merge-base --is-ancestor "$base" "$head" && echo 'base-is-ancestor=yes'
git show -s --format='base=%H%nhead=%H%nparents=%P%nsubject=%s' "$base" "$head"
echo '=== Exact-range files and stat ==='
git diff --name-status "$base" "$head"
git diff --stat "$base" "$head"
echo '=== Exact-range scoped patch ==='
git diff --no-ext-diff --find-renames --find-copies "$base" "$head" -- "$search_file" "$test_file"
echo '=== Base SearchLayout ==='
git show "${base}:${search_file}" | cat -n
echo '=== Head SearchLayout ==='
git show "${head}:${search_file}" | cat -n
echo '=== Head focused regression ==='
git show "${head}:${test_file}" | cat -n
echo '=== SearchLayout imports and API implementation ==='
ast-grep outline frontend/src/components/SearchLayout.tsx --items all
ast-grep outline frontend/src/lib/api-client.ts --items all
sed -n '1,280p' frontend/src/lib/api-client.ts
echo '=== Test setup and test configuration candidates ==='
fd -HI '^(setup\.(ts|tsx|js|jsx)|vitest\.config\..*|vite\.config\..*|package\.json)$' frontend . \
-E node_modules -E dist -E build \
-x sh -c 'echo "=== $1 ==="; sed -n "1,260p" "$1"' sh {} \;
echo '=== Normalized source equality ==='
git show "${base}:${search_file}" > /tmp/search-base.tsx
git show "${head}:${search_file}" > /tmp/search-head.tsx
sed 's/ role="status" aria-live="polite" className=/ className=/' \
/tmp/search-head.tsx > /tmp/search-head-normalized.tsx
if cmp -s /tmp/search-base.tsx /tmp/search-head-normalized.tsx; then
echo 'only-live-region-attributes=yes'
else
echo 'only-live-region-attributes=no'
diff -u /tmp/search-base.tsx /tmp/search-head-normalized.tsx || true
fi
echo '=== Stale overlay comparison ==='
if git cat-file -e "${overlay}^{commit}" 2>/dev/null; then
git show -s --format='overlay=%H%nparents=%P%nsubject=%s' "$overlay"
git diff --no-ext-diff "$base" "$overlay" -- "$search_file"
else
echo 'overlay-object=unavailable'
fi
echo '=== Focused test timer and async patterns ==='
git show "${head}:${test_file}" |
rg -n -C 3 'setTimeout|setInterval|waitFor|act\s*\(|resolve|fetch|api/search|role|aria-live|loading|결과가 없습니다' || trueLength of output: 140220
No source-level findings exist in the requested scope.
This review did not include hosted execution or browser, keyboard, or assistive-technology validation.
|
|
@coderabbitai review 현재 exact head |
🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='e64a1181c234c9213774bcd5c2d4c4288bb889b2'
search_file='frontend/src/components/SearchLayout.tsx'
test_file='frontend/src/components/SearchLayout.empty-live-region.test.tsx'
git cat-file -e "${base}^{commit}"
git cat-file -e "${head}^{commit}"
printf '%s\n' '=== ancestry and commit identity ==='
git merge-base --is-ancestor "$base" "$head" && echo 'base-is-ancestor=yes'
git show -s --format='base=%H%nhead=%H%nhead-parents=%P%nhead-subject=%s' "$base" "$head"
printf '%s\n' '=== exact-range changed files ==='
git diff --name-status "$base" "$head"
git diff --stat "$base" "$head"
printf '%s\n' '=== exact-range patch, requested scope ==='
git diff --no-ext-diff --find-renames --find-copies "$base" "$head" -- "$search_file" "$test_file"
printf '%s\n' '=== SearchLayout outline at exact head ==='
git show "${head}:${search_file}" >/tmp/SearchLayout.tsx
ast-grep outline /tmp/SearchLayout.tsx --lang tsx --items all
printf '%s\n' '=== SearchLayout base ==='
git show "${base}:${search_file}" | cat -n
printf '%s\n' '=== SearchLayout exact head ==='
git show "${head}:${search_file}" | cat -n
printf '%s\n' '=== focused regression at exact head ==='
git show "${head}:${test_file}" | cat -n
printf '%s\n' '=== source equality after removing only intended attributes ==='
git show "${base}:${search_file}" >/tmp/search-base.tsx
git show "${head}:${search_file}" |
sed 's/ role="status" aria-live="polite" className=/ className=/' >/tmp/search-head-normalized.tsx
if cmp -s /tmp/search-base.tsx /tmp/search-head-normalized.tsx; then
echo 'only-live-region-attributes=yes'
else
echo 'only-live-region-attributes=no'
diff -u /tmp/search-base.tsx /tmp/search-head-normalized.tsx || true
fi
printf '%s\n' '=== focused async and timing constructs ==='
git show "${head}:${test_file}" |
rg -n -C 4 'act\s*\(|setTimeout|setInterval|waitFor|vi\.(useFakeTimers|advanceTimers)|Promise|resolve|fetch|/api/search|loading|role|aria-live|결과가 없습니다' || true
printf '%s\n' '=== all live-region and alert occurrences in SearchLayout at head ==='
rg -n -C 3 'role="(status|alert)"|aria-live=|결과가 없습니다|오류|error' /tmp/SearchLayout.tsxLength of output: 123448 🏁 Script executed: #!/bin/bash
set -euo pipefail
api_file='frontend/src/lib/api-client.ts'
printf '%s\n' '=== API client outline ==='
ast-grep outline "$api_file" --items all
printf '%s\n' '=== API client fetch and JSON handling ==='
rg -n -C 12 '(^|[[:space:]])(async )?(post|get|request)[[:space:]]*<|fetch\s*\(|\.json\s*\(|Response|Api' "$api_file"
printf '%s\n' '=== structural post-method candidates ==='
ast-grep run --lang typescript \
--pattern 'async post<$T>($$$) { $$$ }' \
"$api_file" || true
printf '%s\n' '=== exact range without external comparison utility ==='
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='e64a1181c234c9213774bcd5c2d4c4288bb889b2'
git diff --no-ext-diff --unified=0 "$base" "$head" -- frontend/src/components/SearchLayout.tsxLength of output: 7634
요청 범위에서 source-level finding은 없습니다.
Hosted execution, 브라우저, 키보드, 또는 assistive-technology 검증은 수행하지 않았습니다.
|
|
@codex review Please review only exact |
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
|
@coderabbitai review Current exact head advanced to |
|
@codex review Review only exact |
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
base='8348772f8bb92dc25605e8b1ef9e85c8196bf939'
head='8ca8767c09810945a1348bdb1c4b862df1a87f96'
search_file='frontend/src/components/SearchLayout.tsx'
test_file='frontend/src/components/SearchLayout.empty-live-region.test.tsx'
api_file='frontend/src/lib/api-client.ts'
git cat-file -e "${base}^{commit}"
git cat-file -e "${head}^{commit}"
printf '%s\n' '=== exact commit identity and ancestry ==='
git merge-base --is-ancestor "$base" "$head" && echo 'base-is-ancestor=yes'
git show -s --format='base=%H%nhead=%H%nhead-parents=%P%nhead-subject=%s' "$base" "$head"
printf '%s\n' '=== exact-range changed files and stat ==='
git diff --name-status "$base" "$head"
git diff --stat "$base" "$head"
printf '%s\n' '=== exact-range scoped patch ==='
git diff --no-ext-diff --find-renames --find-copies "$base" "$head" -- \
"$search_file" "$test_file"
printf '%s\n' '=== base SearchLayout ==='
git show "${base}:${search_file}" | cat -n
printf '%s\n' '=== head SearchLayout ==='
git show "${head}:${search_file}" | cat -n
printf '%s\n' '=== head focused test ==='
git show "${head}:${test_file}" | cat -n
printf '%s\n' '=== API client outline and response-body handling ==='
ast-grep outline "$api_file" --items all
rg -n -C 14 '\bpost\s*<|\bpost\s*\(|fetch\s*\(|\.json\s*\(|Response' "$api_file"
printf '%s\n' '=== normalized product-source equality ==='
git show "${base}:${search_file}" >/tmp/search-base.tsx
git show "${head}:${search_file}" |
sed 's/ role="status" aria-live="polite" className=/ className=/' \
>/tmp/search-head-normalized.tsx
if cmp -s /tmp/search-base.tsx /tmp/search-head-normalized.tsx; then
echo 'only-live-region-attributes=yes'
else
echo 'only-live-region-attributes=no'
diff -u /tmp/search-base.tsx /tmp/search-head-normalized.tsx || true
fi
printf '%s\n' '=== focused async and accessibility constructs ==='
git show "${head}:${test_file}" |
rg -n -C 5 'Response|json\s*:|Promise|resolve|act\s*\(|fetch|/api/search|loading|role|aria-live|결과가 없습니다|setTimeout|setInterval|waitFor|advanceTimers' || true
printf '%s\n' '=== product live-region, error, and customer-copy branches ==='
rg -n -C 5 'role="(status|alert)"|aria-live=|결과가 없습니다|관계|근거|error|Error' \
/tmp/search-head-normalized.tsxLength of output: 144358
No source-level findings exist in the requested scope.
The focused test is deterministic at the response-body boundary.
I did not run hosted execution or browser, keyboard, or assistive-technology validation.
|
Current authority — 2026-09-10
#1603@8348772f8bb92dc25605e8b1ef9e85c8196bf93947c53b15d83b299777002f320c46578fce93ac96d99d88ab2d67c80fc1042f6ebbb2e8627214d5b4da2c9f8e27d60b5c6b826f4a73bad3baa62d99d9b1ee9b2d86916a5c29bcd7be1de09c6a6fb4e98ce64a1181c234c9213774bcd5c2d4c4288bb889b28ca8767c09810945a1348bdb1c4b862df1a87f96SearchLayout.tsx; fresh compare is ahead-only (behind_by=0).Generated #1633 identified a valid Search empty-state announcement gap but its full
SearchLayout.tsxblob was based on protecteddevelop. Direct overlay was proven unsafe because it reverted valid #1603 customer-facing relationship/evidence copy. The branch was repaired non-destructively, then only the generated one-line semantic patch was isolated on protected-develop ancestry and integrated through ordinary Git three-way merge (#1637). No generated.julesmetadata, dependency source, Today source, or stale Search customer-copy source is effective here.The regression holds
/api/searchpending, verifies the existing loading status, and requires맥락 검색 결과가 없습니다.to become a polite status live region only after the asynchronous search actually completes.Test-harness finding and repair
Static re-inspection of
e64a118...found an evidence defect in the test itself. The test constructed a nativeResponsefor/api/search, while the promise it explicitly awaited asemptyBodywas a separate already-resolved promise used only to build that response.ApiClient.post()awaitsresponse.json()on its own promise, so the test body overstated that it explicitly flushed the same controlled response/body chain. This is not a product-source regression and does not justify changingSearchLayout.tsx.Exact child
8ca8767...repairs only the focused test. It uses an actualResponsewhosejson()is backed by a separately controlled body promise, resolves the HTTP response first and verifies the UI remains loading while the body is still pending, then resolves/awaits that exact body promise inside Reactactbefore asserting the loading→empty transition. Product source is unchanged by this child. The effective PR scope remains exactly two files.Exact-head evidence boundary
This feature-base stacked PR cannot currently materialize Naruon’s repository-local Application CI/Bandit through ordinary
pull_requestsynchronization because protected workflow filters name only default/release bases. Canonical fleet defect.github#2073owns the repair. Do not retarget this PR todevelop, push a dummy commit, copy central workflow source, or transfer predecessor checks.CodeRabbit review attempts on predecessor heads were either rate-limited or became stale after source-changing test repair. Codex and CodeRabbit have both been requested on the current lane, but
8ca8767...requires a fresh post-last-push independent review; no predecessor approval transfers.UI Delivery Gate: FAIL
Intentionality, content ownership, and source-level functional completeness are PASS. Exact-head hosted execution is absent because the canonical stacked-PR CI contract is still open, qualifying independent current-head review is absent, and browser/AT/keyboard evidence remains incomplete. No broad accessibility-conformance claim is authorized, and #1603/#1623 are not protected-integrated.
No force-push, destructive rebase, self-approval, historical-check transfer, source-copy across canonical owners, or gate weakening.