Skip to content

Commit a5fba63

Browse files
authored
fix(favicons): let a mounted icon retry once its failure ages out (#9501)
A failed load set per-instance state that pinned the icon to its fallback until it unmounted, so the five-minute miss window never reached an icon already on screen. The module-level miss cache is now the only failure record; a reducer only re-renders on error, so the next render after the entry expires asks again (a confirmed miss is still answered from the HTTP cache).
1 parent 79a7aa1 commit a5fba63

1 file changed

Lines changed: 8 additions & 7 deletions

File tree

‎apps/sim/components/favicon.tsx‎

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,15 @@
11
'use client'
22

3-
import { type ReactNode, useState } from 'react'
3+
import { type ReactNode, useReducer } from 'react'
44
import { cn } from '@sim/emcn'
55
import { LRUCache } from 'lru-cache'
66
import { faviconSrc } from '@/lib/favicon/url'
77

88
/**
9-
* Hosts whose icon just failed, so an icon that mounts again renders its fallback at once
10-
* instead of an empty slot first. An `<img>` can't tell no icon from a provider outage, so this
11-
* lasts only as long as the route retries an outage; a confirmed miss stays in the HTTP cache.
9+
* Hosts whose icon failed recently: the only failure record, so mounted and remounted icons
10+
* render the fallback at once instead of an empty slot. An `<img>` can't tell no icon from a
11+
* provider outage, so an entry lasts only as long as the route retries an outage; the next render
12+
* after that asks again, and a confirmed miss stays in the HTTP cache.
1213
*/
1314
const knownMisses = new LRUCache<string, true>({ max: 500, ttl: 5 * 60 * 1000 })
1415

@@ -27,8 +28,8 @@ interface FaviconProps {
2728
* of a provider's placeholder.
2829
*/
2930
export function Favicon({ host, fallback, className }: FaviconProps) {
30-
const [failedHost, setFailedHost] = useState<string | null>(null)
31-
if (!host || failedHost === host || knownMisses.has(host)) return fallback
31+
const [, rerender] = useReducer((failures: number) => failures + 1, 0)
32+
if (!host || knownMisses.has(host)) return fallback
3233
return (
3334
<img
3435
src={faviconSrc(host)}
@@ -38,7 +39,7 @@ export function Favicon({ host, fallback, className }: FaviconProps) {
3839
className={cn('rounded-sm', className)}
3940
onError={() => {
4041
knownMisses.set(host, true)
41-
setFailedHost(host)
42+
rerender()
4243
}}
4344
/>
4445
)

0 commit comments

Comments
 (0)