A blank page or raw stack trace on a search error tells users nothing actionable and exposes internal implementation details — error messages containing TypeError: Cannot read property of undefined or Prisma stack traces reveal your ORM, schema, and query structure. Under ISO 25010:2011 reliability, an application that silently drops into an empty state on network failure or backend error leaves users unable to distinguish "no results" from "broken search" — and they'll assume the latter, blame the product, and leave.
Medium because the failure degrades user trust and leaks implementation details without constituting a direct data breach or service outage.
Wrap the search fetch in try/catch and render a non-technical error message when the request fails. In components/SearchInput.tsx:
try {
const res = await fetch(`/api/listings?q=${encodeURIComponent(query)}`)
if (!res.ok) throw new Error('non-2xx')
const data = await res.json()
setResults(data.listings)
} catch {
setError('Search is temporarily unavailable. Please try again.')
}
// In render:
{error && (
<div role="alert" className="bg-red-50 border border-red-200 p-4 rounded">
{error}
</div>
)}
Log the original error to the server (not to the client). Never render err.message directly — it will contain stack traces or ORM internals.
ID: directory-search-discovery.pagination-url.error-handling
Severity: medium
What to look for: Enumerate all relevant files and Intentionally trigger a search error (if possible — e.g., search for a term that causes a backend error, or simulate a network failure in dev tools). Check whether the UI displays a user-friendly error message (e.g., "Search temporarily unavailable. Please try again.") instead of showing nothing, a blank page, or a technical error stack trace.
Pass criteria: At least 1 conforming pattern must exist. Search errors result in a clear, user-friendly error message (not a stack trace or empty list). A suggestion to retry or try different terms may be provided.
Fail criteria: Search errors show a blank page, technical stack trace, or raw error message.
Skip (N/A) when: Search is not implemented or error states are not testable. Signal: no search functionality found.
Detail on fail: "Search error causes blank page with no error message." or "Raw API error shown to user: 'TypeError: Cannot read property of undefined'."
Remediation: Wrap search API calls in error handling:
// components/SearchInput.tsx
const handleSearch = async (query) => {
setLoading(true)
setError(null)
try {
const res = await fetch(`/api/listings?q=${encodeURIComponent(query)}`)
if (!res.ok) throw new Error('Search failed')
const data = await res.json()
setResults(data.listings)
} catch (err) {
setError('Search is temporarily unavailable. Please try again.')
console.error('Search error:', err) // log for debugging
} finally {
setLoading(false)
}
}
// In render:
{error && (
<div className="bg-red-50 border border-red-200 p-4 rounded">
{error}
</div>
)}