Font Fingerprinting: How Installed Fonts Identify Your Browser
Websites detect which fonts are installed on your system by measuring text rendering differences. Learn how font fingerprinting works in practice.
Introduction
Font fingerprinting identifies browsers by detecting which fonts are installed on the user's system. Since each operating system ships with a different set of default fonts, and users install additional fonts over time, the combination of available fonts creates a unique identifier.
Websites cannot directly enumerate installed fonts through a JavaScript API. Instead, they measure text rendering to infer font availability. By rendering text in a candidate font and comparing the dimensions against a fallback font, the script determines whether each candidate is installed.
How Font Detection Works
The technique relies on a simple principle: if a font is installed, text rendered in that font will have different dimensions than text rendered in a generic fallback.
function isFontAvailable(fontName) {
const testString = 'mmmmmmmmmmlli';
const fallbackFonts = ['monospace', 'sans-serif', 'serif'];
const span = document.createElement('span');
span.style.fontSize = '72px';
span.textContent = testString;
document.body.appendChild(span);
const fallbackWidths = fallbackFonts.map(font => {
span.style.fontFamily = font;
return span.offsetWidth;
});
span.style.fontFamily = `"${fontName}", monospace`;
const testWidth = span.offsetWidth;
document.body.removeChild(span);
return testWidth !== fallbackWidths[0];
}
By testing hundreds of font names, a fingerprinting script builds a bitmap of installed fonts that is highly unique.
Platform-Specific Font Signatures
Each operating system has a distinctive font set:
| Platform | Distinctive Fonts |
|---|---|
| Windows | Segoe UI, Calibri, Consolas, Cambria |
| macOS | San Francisco, Helvetica Neue, Apple Color Emoji |
| Linux | DejaVu Sans, Liberation Mono, Noto Sans |
| Android | Roboto, Noto Sans, Droid Sans |
The presence or absence of these fonts immediately reveals the operating system, even before considering user-installed fonts.
Text Metrics Fingerprinting
Beyond simple font detection, measureText() and getBoundingClientRect() return sub-pixel measurements that vary by platform:
- Font hinting - Windows uses ClearType, macOS uses its own approach, Linux uses FreeType with configurable hinting
- Sub-pixel positioning - Text layout differs at the fractional pixel level
- Glyph rendering - The same font renders differently on each platform's text engine
These measurements can identify the OS and even the OS version.
CJK Font Considerations
Chinese, Japanese, and Korean text rendering adds additional fingerprinting vectors. Each platform uses different CJK font families:
- Windows: Microsoft YaHei (Chinese), Meiryo (Japanese), Malgun Gothic (Korean)
- macOS: PingFang SC/TC (Chinese), Hiragino Sans (Japanese), Apple SD Gothic Neo (Korean)
- Linux: Noto Sans CJK variants
CJK text metrics differ significantly across platforms, providing strong identifying signals for sessions targeting East Asian markets.
How BotCloud Manages Font Identity
BotCloud profiles include complete font configuration:
- The profile specifies which fonts should appear as "installed"
- Text metrics match the claimed platform's rendering engine
- CJK font families align with the profile's locale settings
- Font enumeration results are consistent across multiple detection methods
This ensures that font-based fingerprinting confirms the identity presented by other profile signals (User-Agent, navigator.platform, etc.) rather than contradicting them.
Best Practices
- Ensure font signals match the profile's claimed OS - Windows fonts on a profile claiming macOS is an obvious inconsistency
- Consider locale-specific fonts when targeting regional markets
- Test with multiple font detection tools to verify consistency