There are plenty of sites that get dark mode / theming right: Stack Overflow, GitHub, Google, etc. but it isn’t universal.
And here are some examples:
Twitch’s mobile site
The Twitch desktop site is fine, but there is an initial flash of the wrong theme with the mobile site.
On a repeat visit, the issue doesn’t persist because a cookie is set for the theme and the second page visit includes the proper styling.
Youtube’s mobile site
Like Twitch, the desktop site is fine. On mobile however, there is a flash of the wrong theme.
The issue in this case is that the site loads with the background set to a light color via inlined css. Then a CSS file that defines the theme background color loads and overrides the initial color with the correct theme.
Sentry shows an initial static page while the JS of the app loads in, this static page doesn’t have theming, so it results in a mismatch when the dashboard loads.
Stripe API docs
The Stripe API docs don’t have the proper theme on initial load. Future loads result in the correct theme due to a cookie being set.
Pretty much the same setup as Sentry, there is an initial static page that is shown while the JS loads, and it doesn’t have proper theming. Their mobile app has a similar issue.
Apollo GraphQL docs
The Apollo docs look pretty buggy! The server returns html with a dark mode css
class name set, then on load the class name switches to light, before quickly
switching back to dark. I think the issue is that there is a
transition-property: background-color on the
<body>, so the switch is delayed
transition-duration: var(--chakra-transition-duration-normal); which is
Initial load is important, be careful when implementing theming.