Troubleshooting
Common issues and how to fix them
Troubleshooting
Common issues you might encounter and their solutions.
Styles not applying
Check the class name
First, verify the class name is being applied:
function Button() {
return <button className={button('base')}>Click me</button>;
}
Open DevTools and check that the element has the expected class:
<!-- Should see something like this -->
<button class="button-base">Click me</button>
If no class is present:
- Check that the component is actually rendering
- Verify the style definition is being imported
- Ensure no JavaScript errors are preventing execution
If class is present but styles don't apply:
- Check the computed styles in DevTools
- Verify no other CSS is overriding your styles
- Look for CSS specificity issues
Check CSS injection
Styles are injected lazily. Open DevTools and look for a <style> tag with typestyles:
<head>
<style id="typestyles">
.button-base {
padding: 8px 16px;
}
</style>
</head>
If the style tag is missing:
- Ensure typestyles is actually being imported
- Check that components using the styles are rendering
- Verify no bundler issues (check console for errors)
If styles are in the tag but not applied:
- Check for CSS syntax errors
- Verify the class name in HTML matches the CSS selector
- Look for ad blockers that might be removing styles
Duplicate namespace warnings
What it means
Style namespace "button" is also used in /path/to/other/file.ts.
Duplicate namespaces cause class name collisions.
This means you've created two different styles with the same namespace:
// File A
const button = styles.create('button', { ... });
// File B
const button = styles.create('button', { ... }); // Same namespace!
How to fix
Use unique, descriptive namespaces:
// ✅ Good - descriptive names
const iconButton = styles.create('icon-button', { ... });
const textButton = styles.create('text-button', { ... });
const submitButton = styles.create('submit-button', { ... });
// ❌ Bad - generic names that collide
const button = styles.create('button', { ... });
const button2 = styles.create('button', { ... }); // Collision!
TypeScript errors
"Property does not exist"
Property 'tertiary' does not exist on type '{ primary: string; secondary: string; }'
You're trying to access a token that doesn't exist:
const color = tokens.create('color', {
primary: '#0066ff',
secondary: '#6b7280',
});
color.tertiary; // Error! This token doesn't exist
Fix: Add the missing token or use an existing one.
"No overload matches this call"
No overload matches this call.
The last overload gave the following error.
Argument of type 'string' is not assignable to parameter of type...
You're passing an invalid variant:
const button = styles.create('button', {
base: { ... },
primary: { ... },
});
button('base', 'secondary'); // Error! 'secondary' is not a valid variant
Fix: Use only defined variants.
Cannot find module 'typestyles'
Cannot find module 'typestyles' or its corresponding type declarations.
Fix:
Make sure typestyles is installed:
bashnpm install typestylesCheck your import path:
ts// ✅ Correct import { styles } from 'typestyles'; // ❌ Incorrect import { styles } from './typestyles';Restart TypeScript server in your editor
SSR issues
Styles not included in SSR output
Symptom: Page renders without styles, then styles appear after hydration (flash of unstyled content).
Cause: Not using collectStyles() during render.
Fix:
import { collectStyles } from 'typestyles/server';
import { renderToString } from 'react-dom/server';
// ❌ Wrong
const html = renderToString(<App />);
// ✅ Correct
const { html, css } = collectStyles(() => renderToString(<App />));
// Include css in your HTML response
For Next.js, follow the SSR guide and use @typestyles/next (getRegisteredCss, TypestylesStylesheet, or @typestyles/next/server helpers) so the document matches what App Router streams.
Hydration mismatch
Symptom: React warning about hydration mismatch or styles appearing twice.
Cause: Mismatch between server and client CSS injection.
Fix:
Ensure the style tag ID matches:
html<!-- Server --> <style id="typestyles"> ${css} </style> <!-- Client looks for this ID -->Don't manually create the style tag on client:
tsx// ❌ Don't do this on client document.head.innerHTML += `<style id="typestyles">...</style>`; // ✅ TypeStyles handles this automatically
Empty CSS in SSR
Symptom: css string is empty.
Cause: Styles aren't being created during the render pass.
Fix: Make sure components with typestyles are actually rendered inside collectStyles():
// ❌ Wrong - App doesn't use typestyles components
const { css } = collectStyles(() => renderToString(<App />));
// css is empty because App doesn't use styles
// ✅ Correct - Components with styles are rendered
const { css } = collectStyles(() =>
renderToString(
<App>
<Button /> {/* Button uses typestyles */}
</App>
)
);
Build issues
Bundler errors
ESM/CJS issues:
If you get errors about ES modules:
// package.json
{
"type": "module"
}
Or use .mjs extension for your files.
Webpack issues:
If using webpack, ensure it can handle ES modules:
// webpack.config.js
module.exports = {
resolve: {
fullySpecified: false,
},
};
Missing dependencies
If you see errors about missing dependencies, ensure you've installed typestyles:
npm install typestyles
# If using Vite plugin
npm install -D @typestyles/vite
Runtime errors
"Cannot read property 'create' of undefined"
TypeError: Cannot read property 'create' of undefined
Cause: Importing incorrectly.
Fix:
// ✅ Correct
import { styles } from 'typestyles';
// ❌ Incorrect
import styles from 'typestyles'; // Wrong! Use named import
"insertRule is not a function"
TypeError: sheet.insertRule is not a function
Cause: Running in an environment without a real DOM (like jsdom with some configurations).
Fix: Mock the CSSOM APIs in your test setup:
// test-setup.ts
Object.defineProperty(document, 'styleSheets', {
value: [
{
insertRule: jest.fn(),
cssRules: [],
},
],
});
Or use a real browser for testing (Playwright, Cypress).
Styling issues
Specificity problems
Your styles are being overridden by other CSS:
/* Your typestyles class */
.button-base {
color: blue;
}
/* Other CSS overrides it */
button {
color: red;
} /* Higher specificity or loaded later */
Fixes:
Use more specific selectors:
tsconst button = styles.create('button', { base: { color: 'blue', // Increase specificity '&.button-base': { color: 'blue', }, }, });Load typestyles CSS after other CSS
Use
!important(not recommended):tsbase: { color: 'blue !important', }
Cascade issues
Styles from parent components affecting children:
const parent = styles.create('parent', {
base: {
'& button': { color: 'red' }, // Affects ALL buttons inside
},
});
Fix: Be more specific or avoid nesting:
const parent = styles.create('parent', {
base: {
// Don't use & button, style specific class instead
},
});
const childButton = styles.create('child-button', {
base: {
color: 'red',
},
});
Media queries not working
const responsive = styles.create('responsive', {
base: {
'@media (max-width: 768px)': {
display: 'none',
},
},
});
Check:
- Viewport is actually below 768px
- No syntax errors in the media query
- Check DevTools to see if the media query CSS was generated
Theme issues
Theme not applying
const darkTheme = tokens.createTheme('dark', {
color: {
primary: '#66b3ff',
},
});
<div className={darkTheme}>Content</div>;
Check:
The theme class is applied (check DevTools)
Tokens are being used in styles (not hardcoded values)
The token namespace matches:
ts// Creating const color = tokens.create('color', { ... }); // Overriding tokens.createTheme('dark', { color: { ... } // Must match 'color' namespace });
Theme flashing on load
Cause: Theme is applied after initial render.
Fix: Apply theme class before first paint:
<head>
<script>
// Set theme immediately
const theme = localStorage.getItem('theme');
if (theme === 'dark') {
document.documentElement.classList.add('theme-dark');
}
</script>
</head>
Vite plugin issues
HMR not working
Check that the plugin is installed and configured:
ts// vite.config.ts import typestyles from '@typestyles/vite'; export default { plugins: [typestyles()], };Ensure files import from
'typestyles'(not relative paths)Check browser console for HMR-related errors
"typestyles is not defined"
Cause: Plugin isn't transforming the file.
Fix: Make sure files import from 'typestyles':
// ✅ This file will be transformed
import { styles } from 'typestyles';
// ❌ This file won't be transformed
import { styles } from '../path/to/typestyles';
Performance issues
Slow initial render
Check for:
- Too many style definitions at once
- Creating styles inside components
- Very large CSS rules
Fixes:
- Code split your styles
- Move style definitions to module level
- Simplify complex selectors
Memory leaks
Symptoms: App gets slower over time, memory usage grows.
Common causes:
- Creating styles in event handlers or components
- Dynamic style values generating infinite variations
Fix:
// ❌ Never do this
function Component() {
const styles = createStyles(); // Creates on every render
}
// ✅ Do this instead
const styles = createStyles(); // Create once at module level
function Component() {
// Use existing styles
}
Inspecting registered CSS
To verify what the runtime has registered (for example in a route handler or test), call getRegisteredCss() from typestyles. For SSR-specific collection, use collectStyles() from typestyles/server as described in the SSR guide.
Getting help
If you're still stuck:
- Check the documentation: Review the relevant guide for your use case
- Search issues: Look for similar problems in GitHub issues
- Create a minimal reproduction:
- Create the smallest possible example that shows the issue
- Share the code and expected vs actual behavior
- Open an issue: Include:
- TypeScript version
- Bundler (Vite, webpack, etc.)
- Browser
- Minimal reproduction code
Quick checklist
When something isn't working, check:
- Is typestyles installed?
- Are imports correct (named imports, not default)?
- Are styles defined at module level (not in components)?
- Are namespaces unique?
- Is the component actually rendering?
- Are there any JavaScript errors in console?
- Are the class names in HTML what you expect?
- Is the CSS present in the DOM (DevTools)?
- For SSR: Is
collectStyles()being used? - For themes: Are tokens being used (not hardcoded values)?