swc-plugin-source-tracker
v0.1.1
Published
SWC plugin that injects data-source attributes with file:line:col into JSX DOM elements. Replaces React 19's removed __debugSource. Works with Next.js 15/16 + Turbopack.
Maintainers
Readme
swc-plugin-source-tracker
SWC plugin that injects data-source attributes into JSX DOM elements at compile time.
Each attribute contains the file path, line number, and column where the element was defined in source code.
<!-- Before -->
<div className="card">
<h2>Title</h2>
<p>Content</p>
</div>
<!-- After -->
<div className="card" data-source="app/page.tsx:12:5">
<h2 data-source="app/page.tsx:13:7">Title</h2>
<p data-source="app/page.tsx:14:7">Content</p>
</div>Why?
React 19 removed fiber._debugSource, breaking all click-to-source tools (react-dev-inspector, LocatorJS, click-to-component, etc.).
This plugin provides a build-time alternative that works with Next.js 15, 16, Turbopack, and standalone @swc/core.
Install
npm install swc-plugin-source-trackerUsage with Next.js
// next.config.mjs
import { withSourceTracker } from "swc-plugin-source-tracker";
const nextConfig = {
experimental: {
swcPlugins: [withSourceTracker()],
},
};
export default nextConfig;That's it. The plugin auto-detects your Next.js version and selects the compatible WASM binary.
Dev-only
You probably want this in development only:
// next.config.mjs
import { withSourceTracker } from "swc-plugin-source-tracker";
const nextConfig = {
experimental: {
swcPlugins: [
...(process.env.NODE_ENV === "development" ? [withSourceTracker()] : []),
],
},
};
export default nextConfig;Options
withSourceTracker(
// Plugin config (passed to SWC)
{ attr: "data-source" }, // Custom attribute name (default: "data-source")
// JS options
{ version: "v54" }, // Force specific swc_core version: "v35" | "v54"
);Usage with @swc/core (standalone)
import { getWasmPath } from "swc-plugin-source-tracker";
const result = await swc.transform(code, {
filename: "src/App.tsx",
jsc: {
parser: { syntax: "typescript", tsx: true },
experimental: {
plugins: [[getWasmPath(), {}]],
},
},
});Compatibility
| WASM | swc_core | Next.js | Bundler | |------|----------|---------|---------| | v35 | 35.0.0 | 15.x | Webpack | | v54 | 54.0.0 | 16.x | Turbopack |
withSourceTracker() auto-selects the correct version based on your installed Next.js.
How it works
- An SWC WASM plugin visits every JSX opening element during compilation
- For intrinsic DOM elements (
div,span,button, etc.), it injects adata-sourceattribute - The value contains
filename:line:columnresolved from SWC's source map - Custom components (
<MyComponent>) are skipped — they render DOM elements that get annotated
Reading source info at runtime
Open DevTools and inspect any element to see its data-source attribute, or:
// Paste in browser console
document.addEventListener("click", (e) => {
const src =
e.target.getAttribute("data-source") ||
e.target.closest("[data-source]")?.getAttribute("data-source");
if (src) console.log(e.target.tagName, "→", src);
}, true);.gitignore
The plugin copies a WASM file to your project root for Turbopack compatibility. Add this to .gitignore:
swc_plugin_source_tracker.wasmLicense
MIT
