react-grep 0.1.2 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +19 -0
- package/dist/index.global.js +2 -2
- package/dist/index.js +4 -3
- package/package.json +3 -10
- package/dist/index.cjs +0 -607
- package/dist/index.d.cts +0 -4
package/README.md
CHANGED
|
@@ -41,6 +41,25 @@ destroy(); // stop and clean up
|
|
|
41
41
|
|
|
42
42
|
The inspector starts automatically when the script loads.
|
|
43
43
|
|
|
44
|
+
## Compatibility
|
|
45
|
+
|
|
46
|
+
react-grep works with any React app that uses `react-dom` in development mode. It reads React's internal fiber tree, so no framework-specific plugin is needed.
|
|
47
|
+
|
|
48
|
+
| Framework / Bundler | Status |
|
|
49
|
+
| --------------------------------- | ---------------------- |
|
|
50
|
+
| Vite + React | Tested |
|
|
51
|
+
| Next.js 15 (Turbopack) | Tested |
|
|
52
|
+
| Next.js (Webpack) | Untested — should work |
|
|
53
|
+
| Create React App | Untested — should work |
|
|
54
|
+
| Remix | Untested — should work |
|
|
55
|
+
| Gatsby | Untested — should work |
|
|
56
|
+
| Custom Webpack / Rollup / esbuild | Untested — should work |
|
|
57
|
+
| React Native | Not supported (no DOM) |
|
|
58
|
+
|
|
59
|
+
Next.js has dedicated support for server component names and Turbopack indexed source maps.
|
|
60
|
+
|
|
61
|
+
Source map resolution is automatic — if your dev server serves source maps (inline or external), react-grep will resolve bundled locations back to original files.
|
|
62
|
+
|
|
44
63
|
## How it works
|
|
45
64
|
|
|
46
65
|
react-grep reads React's internal fiber tree to find component names and source locations (`_debugSource` / `_debugStack`). This data is only available in **development builds** of React — production builds strip it out.
|
package/dist/index.global.js
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
var ReactGrep=(function(exports){'use strict';var k=new Map,T="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",P=[];for(let e=0;e<T.length;e++)P[T.charCodeAt(e)]=e;var m=(e,t)=>{let n=0,i=0;for(;t.i<e.length;){let o=P[e.charCodeAt(t.i++)];if(i+=(o&31)<<n,!(o&32))return i&1?-(i>>1):i>>1;n+=5;}return 0},F=e=>{let t=[],n=0,i=0,o=0;for(let r of e.split(";")){let s=[],a=0;if(r){let l={i:0};for(;l.i<r.length;){if(r.charCodeAt(l.i)===44){l.i++;continue}a+=m(r,l),!(l.i>=r.length||r.charCodeAt(l.i)===44)&&(n+=m(r,l),i+=m(r,l),o+=m(r,l),l.i<r.length&&r.charCodeAt(l.i)!==44&&m(r,l),s.push([a,n,i,o]));}}t.push(s);}return t},U=/^data:application\/json[^,]*;base64,([A-Za-z0-9+/=]+)$/,j=(e,t)=>{try{return new URL(e).origin===new URL(t).origin}catch{return false}},I=async(e,t)=>{if(e.startsWith("data:")){let o=U.exec(e);return o?atob(o[1]):null}let n=new URL(e,t).href;if(!j(t,n))return null;let i=await fetch(n);return i.ok?i.text():null},K=e=>{let t=[],n=[];for(let i of e){let o=F(i.map.mappings),r=i.offset.line,s=i.offset.column,a=t.length;for(;n.length<r+o.length;)n.push([]);for(let l=0;l<o.length;l++){let d=n[r+l];for(let h of o[l])d.push([l===0?h[0]+s:h[0],h[1]+a,h[2],h[3]]);}t.push(...i.map.sources);}for(let i of n)i.length>1&&i.sort((o,r)=>o[0]-r[0]);return {sources:t,mappings:n}},
|
|
2
|
-
`)){let i=q.exec(n.trim());if(!i)continue;let[,o,r,s,a]=i;if(!(o&&Q.has(o))&&!r.includes("/node_modules/"))return {url:r,line:Number(s),column:Number(a)}}return null},x=async e=>{let t=await D(e.url,e.line,e.column);if(t)return t;let n=e.url;try{let i=new URL(e.url);n=decodeURIComponent(i.pathname);let o=n.indexOf("?");o!==-1&&(n=n.substring(0,o));}catch{}return n=n.replace(/\.\.\//g,""),n.startsWith("/")&&(n=n.substring(1)),{fileName:n,lineNumber:e.line,columnNumber:e.column}}
|
|
1
|
+
var ReactGrep=(function(exports){'use strict';var k=new Map,T="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",P=[];for(let e=0;e<T.length;e++)P[T.charCodeAt(e)]=e;var m=(e,t)=>{let n=0,i=0;for(;t.i<e.length;){let o=P[e.charCodeAt(t.i++)];if(i+=(o&31)<<n,!(o&32))return i&1?-(i>>1):i>>1;n+=5;}return 0},F=e=>{let t=[],n=0,i=0,o=0;for(let r of e.split(";")){let s=[],a=0;if(r){let l={i:0};for(;l.i<r.length;){if(r.charCodeAt(l.i)===44){l.i++;continue}a+=m(r,l),!(l.i>=r.length||r.charCodeAt(l.i)===44)&&(n+=m(r,l),i+=m(r,l),o+=m(r,l),l.i<r.length&&r.charCodeAt(l.i)!==44&&m(r,l),s.push([a,n,i,o]));}}t.push(s);}return t},U=/^data:application\/json[^,]*;base64,([A-Za-z0-9+/=]+)$/,j=(e,t)=>{try{return new URL(e).origin===new URL(t).origin}catch{return false}},I=async(e,t)=>{if(e.startsWith("data:")){let o=U.exec(e);return o?atob(o[1]):null}let n=new URL(e,t).href;if(!j(t,n))return null;let i=await fetch(n);return i.ok?i.text():null},K=e=>{let t=[],n=[];for(let i of e){let o=F(i.map.mappings),r=i.offset.line,s=i.offset.column,a=t.length;for(;n.length<r+o.length;)n.push([]);for(let l=0;l<o.length;l++){let d=n[r+l];for(let h of o[l])d.push([l===0?h[0]+s:h[0],h[1]+a,h[2],h[3]]);}t.push(...i.map.sources);}for(let i of n)i.length>1&&i.sort((o,r)=>o[0]-r[0]);return {sources:t,mappings:n}},f=e=>{try{let t=JSON.parse(e);return Array.isArray(t.sections)?K(t.sections):!t.sources||!t.mappings?null:{sources:t.sources,mappings:F(t.mappings)}}catch{return null}},W=async e=>{try{let t=await fetch(e),i=(await t.text()).match(/\/\/[#@]\s*sourceMappingURL=([^\s]+)$/m);if(i){let s=await I(i[1].trim(),e);if(s){let a=f(s);if(a)return a}}let o=t.headers.get("SourceMap")??t.headers.get("X-SourceMap");if(o){let s=await I(o.trim(),e);if(s){let a=f(s);if(a)return a}}let r=await fetch(`${e}.map`);if(r.ok){let s=await r.text();return f(s)}return null}catch{return null}},R=/^about:\/\/React\/Server\/file:\/\/\//,G=/[/\\](\.next[/\\].+?)(?:\?.*)?$/,X=async e=>{try{let t=decodeURIComponent(e.replace(R,"")),n=G.exec(t);if(!n)return null;let o=`${typeof location<"u"?location.origin:""}/__nextjs_source-map?filename=${encodeURIComponent(n[1])}`,r=await fetch(o);if(!r.ok)return null;let s=await r.text();return s?f(s):null}catch{return null}},z=e=>{let t=k.get(e);return t||(t=R.test(e)?X(e):W(e),k.set(e,t)),t},V=(e,t,n)=>{if(t<0||t>=e.mappings.length)return null;let i=e.mappings[t];if(!i.length)return null;let o=0,r=i.length-1;for(;o<r;){let s=o+r+1>>1;i[s][0]<=n?o=s:r=s-1;}return i[o]},D=async(e,t,n)=>{let i=await z(e);if(!i)return null;let o=V(i,t-1,n-1);if(!o)return null;let r=i.sources[o[1]];return r.startsWith("file:///")&&(r=decodeURIComponent(new URL(r).pathname)),{fileName:r,lineNumber:o[2]+1,columnNumber:o[3]+1}};var g=e=>"env"in e&&typeof e.name=="string",w=new Set([0,1,11,14,15]),Y=e=>{try{let t=Object.keys(e).find(n=>n.startsWith("__reactFiber$"));return t?e[t]:null}catch{return null}},B=e=>{let t=e;for(;t;){if(w.has(t.tag))return t;t=t.return;}return null},J=e=>{if(typeof e=="function")return e;if(e&&typeof e=="object"){if("render"in e&&typeof e.render=="function")return e.render;if("type"in e&&typeof e.type=="function")return e.type}return null},v=e=>{let{type:t}=e;if(typeof t=="function")return t.displayName||t.name||"Anonymous";if(t&&typeof t=="object"){if("displayName"in t&&t.displayName)return t.displayName;let n=J(t);if(n)return n.displayName||n.name||"Anonymous"}return "Anonymous"},Q=new Set(["jsxDEV","jsxs","jsx","react-stack-top-frame","react_stack_bottom_frame","fakeJSXCallSite"]),q=/at (?:(\S+) )?\(?(.+):(\d+):(\d+)\)?$/,C=e=>{let t=e._debugStack?.stack;if(!t)return null;for(let n of t.split(`
|
|
2
|
+
`)){let i=q.exec(n.trim());if(!i)continue;let[,o,r,s,a]=i;if(!(o&&Q.has(o))&&!r.includes("/node_modules/"))return {url:r,line:Number(s),column:Number(a)}}return null},x=async e=>{let t=await D(e.url,e.line,e.column);if(t)return t;let n=e.url;try{let i=new URL(e.url);n=decodeURIComponent(i.pathname);let o=n.indexOf("?");o!==-1&&(n=n.substring(0,o));}catch{}return n=n.replace(/\.\.\//g,""),n.startsWith("/")&&(n=n.substring(1)),{fileName:n,lineNumber:e.line,columnNumber:e.column}},$=async e=>{if(e._debugSource)return e._debugSource;let t=e._debugOwner;if(t&&!g(t)&&t._debugSource)return t._debugSource;let n=C(e);if(n)return x(n);if(t&&!g(t)){let i=C(t);if(i)return x(i)}return null},N=async e=>{if(e._debugSource)return e._debugSource;let t=C(e);return t?x(t):null},M=async e=>{let t=Y(e);if(!t)return null;let n=B(t);if(!n)return null;if(t.return!=null&&w.has(t.return.tag))return {kind:"component",name:v(n),elementTag:null,source:await $(n),callSite:null};let o=t._debugOwner,r=typeof t.type=="string"?t.type:null;return o&&!g(o)&&o===n?{kind:"element",name:v(o),elementTag:r,source:await N(t),callSite:await $(n)}:{kind:"children",name:o&&g(o)?o.name:v(o&&!g(o)&&w.has(o.tag)?o:n),elementTag:r,source:await N(t),callSite:null}};var Z=typeof navigator<"u"&&/Mac|iPhone|iPad/.test(navigator.platform),c={name:"#93c5fd",tag:"#a78bfa",path:"#71717a",pathActive:"#a1a1aa",pathDim:"#3f3f46",hint:"#52525b"},tt={position:"fixed",pointerEvents:"none",zIndex:"2147483646",backgroundColor:"rgba(66, 135, 245, 0.15)",border:"1.5px solid rgba(66, 135, 245, 0.6)",borderRadius:"3px",display:"none",transition:"top 60ms ease-out, left 60ms ease-out, width 60ms ease-out, height 60ms ease-out"},et={position:"fixed",pointerEvents:"none",zIndex:"2147483647",display:"none",fontFamily:"ui-monospace, SFMono-Regular, 'SF Mono', Menlo, monospace",fontSize:"12px",lineHeight:"1.4",color:"#e4e4e7",backgroundColor:"#18181b",border:"1px solid #3f3f46",borderRadius:"6px",padding:"4px 8px",whiteSpace:"nowrap",maxWidth:"500px",overflow:"hidden",textOverflow:"ellipsis",boxShadow:"0 4px 12px rgba(0, 0, 0, 0.4)"},_=(e,t)=>{Object.assign(e.style,t);},y=e=>{let t=e.split("/");return t.length<=2?e:`.../${t.slice(-2).join("/")}`},u=(e,t)=>{let n=document.createElement("span");return n.textContent=e,Object.assign(n.style,t),n},b=class{highlight=null;tooltip=null;init(){this.highlight||(this.highlight=document.createElement("div"),this.highlight.dataset.reactGrep="highlight",_(this.highlight,tt),document.body.appendChild(this.highlight),this.tooltip=document.createElement("div"),this.tooltip.dataset.reactGrep="tooltip",_(this.tooltip,et),document.body.appendChild(this.tooltip));}show(t,n,i="source"){if(!this.highlight||!this.tooltip)return;let o=t.getBoundingClientRect();this.highlight.style.top=`${o.top}px`,this.highlight.style.left=`${o.left}px`,this.highlight.style.width=`${o.width}px`,this.highlight.style.height=`${o.height}px`,this.highlight.style.display="block",this.tooltip.textContent="",this.tooltip.appendChild(u(n.name,{color:c.name,fontWeight:"600"})),n.elementTag!=null&&(this.tooltip.appendChild(u(" > ",{color:c.path})),this.tooltip.appendChild(u(n.elementTag,{color:c.tag,fontWeight:"600"})));let r=n.source?`${n.source.fileName}:${n.source.lineNumber}`:null,s=n.callSite?`${n.callSite.fileName}:${n.callSite.lineNumber}`:null;if(r&&s){let h=i==="source"?c.pathActive:c.pathDim,A=i==="callSite"?c.pathActive:c.pathDim,L=Z?"\u21E7":"Shift",O=y(r),H=y(s);this.tooltip.appendChild(u(` ${i==="callSite"?"(":""}${O}${i==="callSite"?")":""}`,{color:h})),this.tooltip.appendChild(u(` ${L} `,{color:c.hint})),this.tooltip.appendChild(u(`${i==="source"?"(":""}${H}${i==="source"?")":""}`,{color:A}));}else r&&this.tooltip.appendChild(u(` ${y(r)}`,{color:c.path}));let a=this.tooltip.getBoundingClientRect(),l=o.top-a.height-6,d=o.left;l<4&&(l=o.bottom+6),d+a.width>window.innerWidth-4&&(d=window.innerWidth-a.width-4),this.tooltip.style.top=`${l}px`,this.tooltip.style.left=`${Math.max(4,d)}px`,this.tooltip.style.display="block";}showCopied(t){this.tooltip&&(this.tooltip.textContent="",this.tooltip.appendChild(u("Copied!",{color:"#4ade80",fontWeight:"600"})),this.tooltip.appendChild(u(` ${y(t)}`,{color:"#a1a1aa"})),this.tooltip.style.display="block",setTimeout(()=>this.hide(),1500));}hide(){this.highlight&&(this.highlight.style.display="none"),this.tooltip&&(this.tooltip.style.display="none");}destroy(){this.highlight?.remove(),this.tooltip?.remove(),this.highlight=null,this.tooltip=null;}};var E=typeof navigator<"u"&&/Mac|iPhone|iPad/.test(navigator.platform),S=class{overlay=new b;moveGeneration=0;lastTarget=null;lastInfo=null;sourceToggled=false;shiftPressedClean=false;boundHandlers;constructor(){this.boundHandlers={mousemove:this.handleMouseMove.bind(this),click:this.handleClick.bind(this),keydown:this.handleKeyDown.bind(this),keyup:this.handleKeyUp.bind(this)};}start(){window.addEventListener("mousemove",this.boundHandlers.mousemove),window.addEventListener("click",this.boundHandlers.click,true),window.addEventListener("keydown",this.boundHandlers.keydown),window.addEventListener("keyup",this.boundHandlers.keyup);}stop(){window.removeEventListener("mousemove",this.boundHandlers.mousemove),window.removeEventListener("click",this.boundHandlers.click,true),window.removeEventListener("keydown",this.boundHandlers.keydown),window.removeEventListener("keyup",this.boundHandlers.keyup),this.overlay.destroy(),document.body.style.cursor="",this.lastTarget=null,this.lastInfo=null,this.sourceToggled=false,this.shiftPressedClean=false;}isModifierHeld(t){return E?t.metaKey:t.ctrlKey}async handleMouseMove(t){if(!this.isModifierHeld(t)){this.overlay.hide(),document.body.style.cursor="",this.lastTarget=null,this.lastInfo=null;return}this.overlay.init(),document.body.style.cursor="crosshair";let n=document.elementFromPoint(t.clientX,t.clientY);if(!n||n.closest("[data-react-grep]"))return;n!==this.lastTarget&&(this.sourceToggled=false);let i=++this.moveGeneration,o=await M(n);if(i===this.moveGeneration){if(!o){this.overlay.hide(),this.lastTarget=null,this.lastInfo=null;return}this.lastTarget=n,this.lastInfo=o,this.overlay.show(n,o,this.getActiveSource());}}async handleClick(t){if(!this.isModifierHeld(t)||!t.shiftKey)return;let n=document.elementFromPoint(t.clientX,t.clientY);if(!n||n.closest("[data-react-grep]"))return;t.preventDefault(),t.stopPropagation(),t.stopImmediatePropagation(),this.shiftPressedClean=false;let i=await M(n);if(!i)return;let o=this.getActiveCopySource(i);if(!o)return;let{fileName:r,lineNumber:s,columnNumber:a}=o,l=a!=null?`${r}:${s}:${a}`:`${r}:${s}`;await this.copyToClipboard(l),this.overlay.showCopied(l);}handleKeyDown(t){t.key==="Shift"&&this.isModifierHeld(t)&&(this.shiftPressedClean=true);}handleKeyUp(t){if(E&&t.key==="Meta"||!E&&t.key==="Control"){this.overlay.hide(),document.body.style.cursor="",this.lastTarget=null,this.lastInfo=null;return}t.key==="Shift"&&this.shiftPressedClean&&this.lastTarget&&this.lastInfo&&this.lastInfo.callSite&&(this.sourceToggled=!this.sourceToggled,this.overlay.show(this.lastTarget,this.lastInfo,this.getActiveSource())),this.shiftPressedClean=false;}getActiveSource(){return this.sourceToggled?"callSite":"source"}getActiveCopySource(t){return this.sourceToggled&&t.callSite?t.callSite:t.source}async copyToClipboard(t){try{await navigator.clipboard.writeText(t);}catch{}}};var p=null,nt=()=>{p||(p=new S,p.start());},ht=()=>{p&&(p.stop(),p=null);};if(typeof window<"u"){let e=()=>nt();document.readyState==="loading"?document.addEventListener("DOMContentLoaded",e):e();}
|
|
3
3
|
exports.destroy=ht;exports.init=nt;return exports;})({});
|
package/dist/index.js
CHANGED
|
@@ -270,11 +270,12 @@ var resolveFrame = async (frame) => {
|
|
|
270
270
|
};
|
|
271
271
|
var getCompositeDebugSource = async (fiber) => {
|
|
272
272
|
if (fiber._debugSource) return fiber._debugSource;
|
|
273
|
-
|
|
273
|
+
const owner = fiber._debugOwner;
|
|
274
|
+
if (owner && !isServerComponent(owner) && owner._debugSource) return owner._debugSource;
|
|
274
275
|
const frame = parseFirstUserFrame(fiber);
|
|
275
276
|
if (frame) return resolveFrame(frame);
|
|
276
|
-
if (
|
|
277
|
-
const ownerFrame = parseFirstUserFrame(
|
|
277
|
+
if (owner && !isServerComponent(owner)) {
|
|
278
|
+
const ownerFrame = parseFirstUserFrame(owner);
|
|
278
279
|
if (ownerFrame) return resolveFrame(ownerFrame);
|
|
279
280
|
}
|
|
280
281
|
return null;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-grep",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.2.0",
|
|
4
4
|
"description": "Hold CMD to see React component names + file:line overlaid on any element",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"component",
|
|
@@ -30,21 +30,14 @@
|
|
|
30
30
|
],
|
|
31
31
|
"type": "module",
|
|
32
32
|
"sideEffects": true,
|
|
33
|
-
"main": "dist/index.cjs",
|
|
34
33
|
"module": "dist/index.js",
|
|
35
34
|
"browser": "dist/index.global.js",
|
|
36
35
|
"types": "dist/index.d.ts",
|
|
37
36
|
"exports": {
|
|
38
37
|
"./package.json": "./package.json",
|
|
39
38
|
".": {
|
|
40
|
-
"
|
|
41
|
-
|
|
42
|
-
"default": "./dist/index.js"
|
|
43
|
-
},
|
|
44
|
-
"require": {
|
|
45
|
-
"types": "./dist/index.d.cts",
|
|
46
|
-
"default": "./dist/index.cjs"
|
|
47
|
-
}
|
|
39
|
+
"types": "./dist/index.d.ts",
|
|
40
|
+
"default": "./dist/index.js"
|
|
48
41
|
}
|
|
49
42
|
},
|
|
50
43
|
"publishConfig": {
|
package/dist/index.cjs
DELETED
|
@@ -1,607 +0,0 @@
|
|
|
1
|
-
'use strict';
|
|
2
|
-
|
|
3
|
-
// src/source-map.ts
|
|
4
|
-
var cache = /* @__PURE__ */ new Map();
|
|
5
|
-
var VLQ_CHARS = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
|
6
|
-
var charToInt = [];
|
|
7
|
-
for (let i = 0; i < VLQ_CHARS.length; i++) charToInt[VLQ_CHARS.charCodeAt(i)] = i;
|
|
8
|
-
var decodeVLQ = (str, pos) => {
|
|
9
|
-
let shift = 0;
|
|
10
|
-
let value = 0;
|
|
11
|
-
while (pos.i < str.length) {
|
|
12
|
-
const digit = charToInt[str.charCodeAt(pos.i++)];
|
|
13
|
-
value += (digit & 31) << shift;
|
|
14
|
-
if (!(digit & 32)) return value & 1 ? -(value >> 1) : value >> 1;
|
|
15
|
-
shift += 5;
|
|
16
|
-
}
|
|
17
|
-
return 0;
|
|
18
|
-
};
|
|
19
|
-
var decodeMappings = (raw) => {
|
|
20
|
-
const result = [];
|
|
21
|
-
let srcIdx = 0;
|
|
22
|
-
let origLine = 0;
|
|
23
|
-
let origCol = 0;
|
|
24
|
-
for (const line of raw.split(";")) {
|
|
25
|
-
const segments = [];
|
|
26
|
-
let genCol = 0;
|
|
27
|
-
if (line) {
|
|
28
|
-
const pos = { i: 0 };
|
|
29
|
-
while (pos.i < line.length) {
|
|
30
|
-
if (line.charCodeAt(pos.i) === 44) {
|
|
31
|
-
pos.i++;
|
|
32
|
-
continue;
|
|
33
|
-
}
|
|
34
|
-
genCol += decodeVLQ(line, pos);
|
|
35
|
-
if (pos.i >= line.length || line.charCodeAt(pos.i) === 44) continue;
|
|
36
|
-
srcIdx += decodeVLQ(line, pos);
|
|
37
|
-
origLine += decodeVLQ(line, pos);
|
|
38
|
-
origCol += decodeVLQ(line, pos);
|
|
39
|
-
if (pos.i < line.length && line.charCodeAt(pos.i) !== 44) decodeVLQ(line, pos);
|
|
40
|
-
segments.push([genCol, srcIdx, origLine, origCol]);
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
result.push(segments);
|
|
44
|
-
}
|
|
45
|
-
return result;
|
|
46
|
-
};
|
|
47
|
-
var DATA_URI_RE = /^data:application\/json[^,]*;base64,([A-Za-z0-9+/=]+)$/;
|
|
48
|
-
var isSameOrigin = (a, b) => {
|
|
49
|
-
try {
|
|
50
|
-
return new URL(a).origin === new URL(b).origin;
|
|
51
|
-
} catch {
|
|
52
|
-
return false;
|
|
53
|
-
}
|
|
54
|
-
};
|
|
55
|
-
var fetchSourceMapJson = async (ref, baseUrl) => {
|
|
56
|
-
if (ref.startsWith("data:")) {
|
|
57
|
-
const dataMatch = DATA_URI_RE.exec(ref);
|
|
58
|
-
return dataMatch ? atob(dataMatch[1]) : null;
|
|
59
|
-
}
|
|
60
|
-
const mapUrl = new URL(ref, baseUrl).href;
|
|
61
|
-
if (!isSameOrigin(baseUrl, mapUrl)) return null;
|
|
62
|
-
const mapRes = await fetch(mapUrl);
|
|
63
|
-
if (!mapRes.ok) return null;
|
|
64
|
-
return mapRes.text();
|
|
65
|
-
};
|
|
66
|
-
var flattenIndexedMap = (sections) => {
|
|
67
|
-
const allSources = [];
|
|
68
|
-
const allMappings = [];
|
|
69
|
-
for (const section of sections) {
|
|
70
|
-
const decoded = decodeMappings(section.map.mappings);
|
|
71
|
-
const lineOff = section.offset.line;
|
|
72
|
-
const colOff = section.offset.column;
|
|
73
|
-
const srcOff = allSources.length;
|
|
74
|
-
while (allMappings.length < lineOff + decoded.length) allMappings.push([]);
|
|
75
|
-
for (let i = 0; i < decoded.length; i++) {
|
|
76
|
-
const target = allMappings[lineOff + i];
|
|
77
|
-
for (const seg of decoded[i]) {
|
|
78
|
-
target.push([i === 0 ? seg[0] + colOff : seg[0], seg[1] + srcOff, seg[2], seg[3]]);
|
|
79
|
-
}
|
|
80
|
-
}
|
|
81
|
-
allSources.push(...section.map.sources);
|
|
82
|
-
}
|
|
83
|
-
for (const line of allMappings) {
|
|
84
|
-
if (line.length > 1) line.sort((a, b) => a[0] - b[0]);
|
|
85
|
-
}
|
|
86
|
-
return { sources: allSources, mappings: allMappings };
|
|
87
|
-
};
|
|
88
|
-
var parseSourceMap = (json) => {
|
|
89
|
-
try {
|
|
90
|
-
const raw = JSON.parse(json);
|
|
91
|
-
if (Array.isArray(raw.sections)) return flattenIndexedMap(raw.sections);
|
|
92
|
-
if (!raw.sources || !raw.mappings) return null;
|
|
93
|
-
return { sources: raw.sources, mappings: decodeMappings(raw.mappings) };
|
|
94
|
-
} catch {
|
|
95
|
-
return null;
|
|
96
|
-
}
|
|
97
|
-
};
|
|
98
|
-
var fetchAndParse = async (url) => {
|
|
99
|
-
try {
|
|
100
|
-
const res = await fetch(url);
|
|
101
|
-
const text = await res.text();
|
|
102
|
-
const match = text.match(/\/\/[#@]\s*sourceMappingURL=([^\s]+)$/m);
|
|
103
|
-
if (match) {
|
|
104
|
-
const json = await fetchSourceMapJson(match[1].trim(), url);
|
|
105
|
-
if (json) {
|
|
106
|
-
const map = parseSourceMap(json);
|
|
107
|
-
if (map) return map;
|
|
108
|
-
}
|
|
109
|
-
}
|
|
110
|
-
const headerRef = res.headers.get("SourceMap") ?? res.headers.get("X-SourceMap");
|
|
111
|
-
if (headerRef) {
|
|
112
|
-
const json = await fetchSourceMapJson(headerRef.trim(), url);
|
|
113
|
-
if (json) {
|
|
114
|
-
const map = parseSourceMap(json);
|
|
115
|
-
if (map) return map;
|
|
116
|
-
}
|
|
117
|
-
}
|
|
118
|
-
const conventionRes = await fetch(`${url}.map`);
|
|
119
|
-
if (conventionRes.ok) {
|
|
120
|
-
const json = await conventionRes.text();
|
|
121
|
-
return parseSourceMap(json);
|
|
122
|
-
}
|
|
123
|
-
return null;
|
|
124
|
-
} catch {
|
|
125
|
-
return null;
|
|
126
|
-
}
|
|
127
|
-
};
|
|
128
|
-
var ABOUT_SERVER_RE = /^about:\/\/React\/Server\/file:\/\/\//;
|
|
129
|
-
var NEXT_DOTDIR_RE = /[/\\](\.next[/\\].+?)(?:\?.*)?$/;
|
|
130
|
-
var fetchAndParseServerFile = async (url) => {
|
|
131
|
-
try {
|
|
132
|
-
const filePath = decodeURIComponent(url.replace(ABOUT_SERVER_RE, ""));
|
|
133
|
-
const dotNextMatch = NEXT_DOTDIR_RE.exec(filePath);
|
|
134
|
-
if (!dotNextMatch) return null;
|
|
135
|
-
const origin = typeof location !== "undefined" ? location.origin : "";
|
|
136
|
-
const mapUrl = `${origin}/__nextjs_source-map?filename=${encodeURIComponent(dotNextMatch[1])}`;
|
|
137
|
-
const res = await fetch(mapUrl);
|
|
138
|
-
if (!res.ok) return null;
|
|
139
|
-
const json = await res.text();
|
|
140
|
-
if (!json) return null;
|
|
141
|
-
return parseSourceMap(json);
|
|
142
|
-
} catch {
|
|
143
|
-
return null;
|
|
144
|
-
}
|
|
145
|
-
};
|
|
146
|
-
var getSourceMap = (url) => {
|
|
147
|
-
let promise = cache.get(url);
|
|
148
|
-
if (!promise) {
|
|
149
|
-
promise = ABOUT_SERVER_RE.test(url) ? fetchAndParseServerFile(url) : fetchAndParse(url);
|
|
150
|
-
cache.set(url, promise);
|
|
151
|
-
}
|
|
152
|
-
return promise;
|
|
153
|
-
};
|
|
154
|
-
var lookup = (map, genLine, genCol) => {
|
|
155
|
-
if (genLine < 0 || genLine >= map.mappings.length) return null;
|
|
156
|
-
const segments = map.mappings[genLine];
|
|
157
|
-
if (!segments.length) return null;
|
|
158
|
-
let lo = 0;
|
|
159
|
-
let hi = segments.length - 1;
|
|
160
|
-
while (lo < hi) {
|
|
161
|
-
const mid = lo + hi + 1 >> 1;
|
|
162
|
-
if (segments[mid][0] <= genCol) lo = mid;
|
|
163
|
-
else hi = mid - 1;
|
|
164
|
-
}
|
|
165
|
-
return segments[lo];
|
|
166
|
-
};
|
|
167
|
-
var resolveOriginalPosition = async (url, line, column) => {
|
|
168
|
-
const map = await getSourceMap(url);
|
|
169
|
-
if (!map) return null;
|
|
170
|
-
const seg = lookup(map, line - 1, column - 1);
|
|
171
|
-
if (!seg) return null;
|
|
172
|
-
let fileName = map.sources[seg[1]];
|
|
173
|
-
if (fileName.startsWith("file:///")) {
|
|
174
|
-
fileName = decodeURIComponent(new URL(fileName).pathname);
|
|
175
|
-
}
|
|
176
|
-
return {
|
|
177
|
-
fileName,
|
|
178
|
-
lineNumber: seg[2] + 1,
|
|
179
|
-
columnNumber: seg[3] + 1
|
|
180
|
-
};
|
|
181
|
-
};
|
|
182
|
-
|
|
183
|
-
// src/fiber.ts
|
|
184
|
-
var isServerComponent = (owner) => "env" in owner && typeof owner.name === "string";
|
|
185
|
-
var COMPOSITE_TAGS = /* @__PURE__ */ new Set([
|
|
186
|
-
0,
|
|
187
|
-
// FunctionComponent
|
|
188
|
-
1,
|
|
189
|
-
// ClassComponent
|
|
190
|
-
11,
|
|
191
|
-
// ForwardRef
|
|
192
|
-
14,
|
|
193
|
-
// MemoComponent
|
|
194
|
-
15
|
|
195
|
-
// SimpleMemoComponent
|
|
196
|
-
]);
|
|
197
|
-
var getFiberFromElement = (el) => {
|
|
198
|
-
try {
|
|
199
|
-
const key = Object.keys(el).find((k) => k.startsWith("__reactFiber$"));
|
|
200
|
-
if (!key) return null;
|
|
201
|
-
return el[key];
|
|
202
|
-
} catch {
|
|
203
|
-
return null;
|
|
204
|
-
}
|
|
205
|
-
};
|
|
206
|
-
var getCompositeComponentFiber = (fiber) => {
|
|
207
|
-
let current = fiber;
|
|
208
|
-
while (current) {
|
|
209
|
-
if (COMPOSITE_TAGS.has(current.tag)) return current;
|
|
210
|
-
current = current.return;
|
|
211
|
-
}
|
|
212
|
-
return null;
|
|
213
|
-
};
|
|
214
|
-
var getInnerFunction = (type) => {
|
|
215
|
-
if (typeof type === "function") return type;
|
|
216
|
-
if (type && typeof type === "object") {
|
|
217
|
-
if ("render" in type && typeof type.render === "function")
|
|
218
|
-
return type.render;
|
|
219
|
-
if ("type" in type && typeof type.type === "function")
|
|
220
|
-
return type.type;
|
|
221
|
-
}
|
|
222
|
-
return null;
|
|
223
|
-
};
|
|
224
|
-
var getComponentName = (fiber) => {
|
|
225
|
-
const { type } = fiber;
|
|
226
|
-
if (typeof type === "function") {
|
|
227
|
-
return type.displayName || type.name || "Anonymous";
|
|
228
|
-
}
|
|
229
|
-
if (type && typeof type === "object") {
|
|
230
|
-
if ("displayName" in type && type.displayName) return type.displayName;
|
|
231
|
-
const inner = getInnerFunction(type);
|
|
232
|
-
if (inner) return inner.displayName || inner.name || "Anonymous";
|
|
233
|
-
}
|
|
234
|
-
return "Anonymous";
|
|
235
|
-
};
|
|
236
|
-
var SKIP_FRAMES = /* @__PURE__ */ new Set([
|
|
237
|
-
"jsxDEV",
|
|
238
|
-
"jsxs",
|
|
239
|
-
"jsx",
|
|
240
|
-
"react-stack-top-frame",
|
|
241
|
-
"react_stack_bottom_frame",
|
|
242
|
-
"fakeJSXCallSite"
|
|
243
|
-
]);
|
|
244
|
-
var FRAME_RE = /at (?:(\S+) )?\(?(.+):(\d+):(\d+)\)?$/;
|
|
245
|
-
var parseFirstUserFrame = (fiber) => {
|
|
246
|
-
const stack = fiber._debugStack?.stack;
|
|
247
|
-
if (!stack) return null;
|
|
248
|
-
for (const line of stack.split("\n")) {
|
|
249
|
-
const match = FRAME_RE.exec(line.trim());
|
|
250
|
-
if (!match) continue;
|
|
251
|
-
const [, fnName, url, lineStr, colStr] = match;
|
|
252
|
-
if (fnName && SKIP_FRAMES.has(fnName)) continue;
|
|
253
|
-
if (url.includes("/node_modules/")) continue;
|
|
254
|
-
return { url, line: Number(lineStr), column: Number(colStr) };
|
|
255
|
-
}
|
|
256
|
-
return null;
|
|
257
|
-
};
|
|
258
|
-
var resolveFrame = async (frame) => {
|
|
259
|
-
const resolved = await resolveOriginalPosition(frame.url, frame.line, frame.column);
|
|
260
|
-
if (resolved) return resolved;
|
|
261
|
-
let fileName = frame.url;
|
|
262
|
-
try {
|
|
263
|
-
const parsed = new URL(frame.url);
|
|
264
|
-
fileName = decodeURIComponent(parsed.pathname);
|
|
265
|
-
const qIdx = fileName.indexOf("?");
|
|
266
|
-
if (qIdx !== -1) fileName = fileName.substring(0, qIdx);
|
|
267
|
-
} catch {
|
|
268
|
-
}
|
|
269
|
-
fileName = fileName.replace(/\.\.\//g, "");
|
|
270
|
-
if (fileName.startsWith("/")) fileName = fileName.substring(1);
|
|
271
|
-
return { fileName, lineNumber: frame.line, columnNumber: frame.column };
|
|
272
|
-
};
|
|
273
|
-
var getCompositeDebugSource = async (fiber) => {
|
|
274
|
-
if (fiber._debugSource) return fiber._debugSource;
|
|
275
|
-
if (fiber._debugOwner?._debugSource) return fiber._debugOwner._debugSource;
|
|
276
|
-
const frame = parseFirstUserFrame(fiber);
|
|
277
|
-
if (frame) return resolveFrame(frame);
|
|
278
|
-
if (fiber._debugOwner) {
|
|
279
|
-
const ownerFrame = parseFirstUserFrame(fiber._debugOwner);
|
|
280
|
-
if (ownerFrame) return resolveFrame(ownerFrame);
|
|
281
|
-
}
|
|
282
|
-
return null;
|
|
283
|
-
};
|
|
284
|
-
var getDomDebugSource = async (fiber) => {
|
|
285
|
-
if (fiber._debugSource) return fiber._debugSource;
|
|
286
|
-
const frame = parseFirstUserFrame(fiber);
|
|
287
|
-
if (frame) return resolveFrame(frame);
|
|
288
|
-
return null;
|
|
289
|
-
};
|
|
290
|
-
var getComponentInfo = async (el) => {
|
|
291
|
-
const domFiber = getFiberFromElement(el);
|
|
292
|
-
if (!domFiber) return null;
|
|
293
|
-
const composite = getCompositeComponentFiber(domFiber);
|
|
294
|
-
if (!composite) return null;
|
|
295
|
-
const isComponentRoot = domFiber.return != null && COMPOSITE_TAGS.has(domFiber.return.tag);
|
|
296
|
-
if (isComponentRoot) {
|
|
297
|
-
return {
|
|
298
|
-
kind: "component",
|
|
299
|
-
name: getComponentName(composite),
|
|
300
|
-
elementTag: null,
|
|
301
|
-
source: await getCompositeDebugSource(composite),
|
|
302
|
-
callSite: null
|
|
303
|
-
};
|
|
304
|
-
}
|
|
305
|
-
const owner = domFiber._debugOwner;
|
|
306
|
-
const elementTag = typeof domFiber.type === "string" ? domFiber.type : null;
|
|
307
|
-
if (owner && !isServerComponent(owner) && owner === composite) {
|
|
308
|
-
return {
|
|
309
|
-
kind: "element",
|
|
310
|
-
name: getComponentName(owner),
|
|
311
|
-
elementTag,
|
|
312
|
-
source: await getDomDebugSource(domFiber),
|
|
313
|
-
callSite: await getCompositeDebugSource(composite)
|
|
314
|
-
};
|
|
315
|
-
}
|
|
316
|
-
const name = owner && isServerComponent(owner) ? owner.name : getComponentName(
|
|
317
|
-
owner && !isServerComponent(owner) && COMPOSITE_TAGS.has(owner.tag) ? owner : composite
|
|
318
|
-
);
|
|
319
|
-
return {
|
|
320
|
-
kind: "children",
|
|
321
|
-
name,
|
|
322
|
-
elementTag,
|
|
323
|
-
source: await getDomDebugSource(domFiber),
|
|
324
|
-
callSite: null
|
|
325
|
-
};
|
|
326
|
-
};
|
|
327
|
-
|
|
328
|
-
// src/overlay.ts
|
|
329
|
-
var isMac = typeof navigator !== "undefined" && /Mac|iPhone|iPad/.test(navigator.platform);
|
|
330
|
-
var COLORS = {
|
|
331
|
-
name: "#93c5fd",
|
|
332
|
-
tag: "#a78bfa",
|
|
333
|
-
path: "#71717a",
|
|
334
|
-
pathActive: "#a1a1aa",
|
|
335
|
-
pathDim: "#3f3f46",
|
|
336
|
-
hint: "#52525b"
|
|
337
|
-
};
|
|
338
|
-
var HIGHLIGHT_STYLES = {
|
|
339
|
-
position: "fixed",
|
|
340
|
-
pointerEvents: "none",
|
|
341
|
-
zIndex: "2147483646",
|
|
342
|
-
backgroundColor: "rgba(66, 135, 245, 0.15)",
|
|
343
|
-
border: "1.5px solid rgba(66, 135, 245, 0.6)",
|
|
344
|
-
borderRadius: "3px",
|
|
345
|
-
display: "none",
|
|
346
|
-
transition: "top 60ms ease-out, left 60ms ease-out, width 60ms ease-out, height 60ms ease-out"
|
|
347
|
-
};
|
|
348
|
-
var TOOLTIP_STYLES = {
|
|
349
|
-
position: "fixed",
|
|
350
|
-
pointerEvents: "none",
|
|
351
|
-
zIndex: "2147483647",
|
|
352
|
-
display: "none",
|
|
353
|
-
fontFamily: "ui-monospace, SFMono-Regular, 'SF Mono', Menlo, monospace",
|
|
354
|
-
fontSize: "12px",
|
|
355
|
-
lineHeight: "1.4",
|
|
356
|
-
color: "#e4e4e7",
|
|
357
|
-
backgroundColor: "#18181b",
|
|
358
|
-
border: "1px solid #3f3f46",
|
|
359
|
-
borderRadius: "6px",
|
|
360
|
-
padding: "4px 8px",
|
|
361
|
-
whiteSpace: "nowrap",
|
|
362
|
-
maxWidth: "500px",
|
|
363
|
-
overflow: "hidden",
|
|
364
|
-
textOverflow: "ellipsis",
|
|
365
|
-
boxShadow: "0 4px 12px rgba(0, 0, 0, 0.4)"
|
|
366
|
-
};
|
|
367
|
-
var applyStyles = (el, styles) => {
|
|
368
|
-
Object.assign(el.style, styles);
|
|
369
|
-
};
|
|
370
|
-
var truncatePath = (filePath) => {
|
|
371
|
-
const parts = filePath.split("/");
|
|
372
|
-
if (parts.length <= 2) return filePath;
|
|
373
|
-
return `.../${parts.slice(-2).join("/")}`;
|
|
374
|
-
};
|
|
375
|
-
var createSpan = (text, styles) => {
|
|
376
|
-
const span = document.createElement("span");
|
|
377
|
-
span.textContent = text;
|
|
378
|
-
Object.assign(span.style, styles);
|
|
379
|
-
return span;
|
|
380
|
-
};
|
|
381
|
-
var OverlayManager = class {
|
|
382
|
-
highlight = null;
|
|
383
|
-
tooltip = null;
|
|
384
|
-
init() {
|
|
385
|
-
if (this.highlight) return;
|
|
386
|
-
this.highlight = document.createElement("div");
|
|
387
|
-
this.highlight.dataset.reactGrep = "highlight";
|
|
388
|
-
applyStyles(this.highlight, HIGHLIGHT_STYLES);
|
|
389
|
-
document.body.appendChild(this.highlight);
|
|
390
|
-
this.tooltip = document.createElement("div");
|
|
391
|
-
this.tooltip.dataset.reactGrep = "tooltip";
|
|
392
|
-
applyStyles(this.tooltip, TOOLTIP_STYLES);
|
|
393
|
-
document.body.appendChild(this.tooltip);
|
|
394
|
-
}
|
|
395
|
-
show(el, info, activeSource = "source") {
|
|
396
|
-
if (!this.highlight || !this.tooltip) return;
|
|
397
|
-
const rect = el.getBoundingClientRect();
|
|
398
|
-
this.highlight.style.top = `${rect.top}px`;
|
|
399
|
-
this.highlight.style.left = `${rect.left}px`;
|
|
400
|
-
this.highlight.style.width = `${rect.width}px`;
|
|
401
|
-
this.highlight.style.height = `${rect.height}px`;
|
|
402
|
-
this.highlight.style.display = "block";
|
|
403
|
-
this.tooltip.textContent = "";
|
|
404
|
-
this.tooltip.appendChild(createSpan(info.name, { color: COLORS.name, fontWeight: "600" }));
|
|
405
|
-
if (info.elementTag != null) {
|
|
406
|
-
this.tooltip.appendChild(createSpan(" > ", { color: COLORS.path }));
|
|
407
|
-
this.tooltip.appendChild(
|
|
408
|
-
createSpan(info.elementTag, { color: COLORS.tag, fontWeight: "600" })
|
|
409
|
-
);
|
|
410
|
-
}
|
|
411
|
-
const filePath = info.source ? `${info.source.fileName}:${info.source.lineNumber}` : null;
|
|
412
|
-
const callSitePath = info.callSite ? `${info.callSite.fileName}:${info.callSite.lineNumber}` : null;
|
|
413
|
-
if (filePath && callSitePath) {
|
|
414
|
-
const sourceColor = activeSource === "source" ? COLORS.pathActive : COLORS.pathDim;
|
|
415
|
-
const callSiteColor = activeSource === "callSite" ? COLORS.pathActive : COLORS.pathDim;
|
|
416
|
-
const shiftHint = isMac ? "\u21E7" : "Shift";
|
|
417
|
-
const sourceText = truncatePath(filePath);
|
|
418
|
-
const callSiteText = truncatePath(callSitePath);
|
|
419
|
-
this.tooltip.appendChild(
|
|
420
|
-
createSpan(
|
|
421
|
-
` ${activeSource === "callSite" ? "(" : ""}${sourceText}${activeSource === "callSite" ? ")" : ""}`,
|
|
422
|
-
{ color: sourceColor }
|
|
423
|
-
)
|
|
424
|
-
);
|
|
425
|
-
this.tooltip.appendChild(createSpan(` ${shiftHint} `, { color: COLORS.hint }));
|
|
426
|
-
this.tooltip.appendChild(
|
|
427
|
-
createSpan(
|
|
428
|
-
`${activeSource === "source" ? "(" : ""}${callSiteText}${activeSource === "source" ? ")" : ""}`,
|
|
429
|
-
{ color: callSiteColor }
|
|
430
|
-
)
|
|
431
|
-
);
|
|
432
|
-
} else if (filePath) {
|
|
433
|
-
this.tooltip.appendChild(createSpan(` ${truncatePath(filePath)}`, { color: COLORS.path }));
|
|
434
|
-
}
|
|
435
|
-
const tooltipRect = this.tooltip.getBoundingClientRect();
|
|
436
|
-
let top = rect.top - tooltipRect.height - 6;
|
|
437
|
-
let left = rect.left;
|
|
438
|
-
if (top < 4) {
|
|
439
|
-
top = rect.bottom + 6;
|
|
440
|
-
}
|
|
441
|
-
if (left + tooltipRect.width > window.innerWidth - 4) {
|
|
442
|
-
left = window.innerWidth - tooltipRect.width - 4;
|
|
443
|
-
}
|
|
444
|
-
this.tooltip.style.top = `${top}px`;
|
|
445
|
-
this.tooltip.style.left = `${Math.max(4, left)}px`;
|
|
446
|
-
this.tooltip.style.display = "block";
|
|
447
|
-
}
|
|
448
|
-
showCopied(location2) {
|
|
449
|
-
if (!this.tooltip) return;
|
|
450
|
-
this.tooltip.textContent = "";
|
|
451
|
-
this.tooltip.appendChild(createSpan("Copied!", { color: "#4ade80", fontWeight: "600" }));
|
|
452
|
-
this.tooltip.appendChild(createSpan(` ${truncatePath(location2)}`, { color: "#a1a1aa" }));
|
|
453
|
-
this.tooltip.style.display = "block";
|
|
454
|
-
setTimeout(() => this.hide(), 1500);
|
|
455
|
-
}
|
|
456
|
-
hide() {
|
|
457
|
-
if (this.highlight) this.highlight.style.display = "none";
|
|
458
|
-
if (this.tooltip) this.tooltip.style.display = "none";
|
|
459
|
-
}
|
|
460
|
-
destroy() {
|
|
461
|
-
this.highlight?.remove();
|
|
462
|
-
this.tooltip?.remove();
|
|
463
|
-
this.highlight = null;
|
|
464
|
-
this.tooltip = null;
|
|
465
|
-
}
|
|
466
|
-
};
|
|
467
|
-
|
|
468
|
-
// src/inspector.ts
|
|
469
|
-
var isMac2 = typeof navigator !== "undefined" && /Mac|iPhone|iPad/.test(navigator.platform);
|
|
470
|
-
var Inspector = class {
|
|
471
|
-
overlay = new OverlayManager();
|
|
472
|
-
moveGeneration = 0;
|
|
473
|
-
lastTarget = null;
|
|
474
|
-
lastInfo = null;
|
|
475
|
-
sourceToggled = false;
|
|
476
|
-
shiftPressedClean = false;
|
|
477
|
-
boundHandlers;
|
|
478
|
-
constructor() {
|
|
479
|
-
this.boundHandlers = {
|
|
480
|
-
mousemove: this.handleMouseMove.bind(this),
|
|
481
|
-
click: this.handleClick.bind(this),
|
|
482
|
-
keydown: this.handleKeyDown.bind(this),
|
|
483
|
-
keyup: this.handleKeyUp.bind(this)
|
|
484
|
-
};
|
|
485
|
-
}
|
|
486
|
-
start() {
|
|
487
|
-
window.addEventListener("mousemove", this.boundHandlers.mousemove);
|
|
488
|
-
window.addEventListener("click", this.boundHandlers.click, true);
|
|
489
|
-
window.addEventListener("keydown", this.boundHandlers.keydown);
|
|
490
|
-
window.addEventListener("keyup", this.boundHandlers.keyup);
|
|
491
|
-
}
|
|
492
|
-
stop() {
|
|
493
|
-
window.removeEventListener("mousemove", this.boundHandlers.mousemove);
|
|
494
|
-
window.removeEventListener("click", this.boundHandlers.click, true);
|
|
495
|
-
window.removeEventListener("keydown", this.boundHandlers.keydown);
|
|
496
|
-
window.removeEventListener("keyup", this.boundHandlers.keyup);
|
|
497
|
-
this.overlay.destroy();
|
|
498
|
-
document.body.style.cursor = "";
|
|
499
|
-
this.lastTarget = null;
|
|
500
|
-
this.lastInfo = null;
|
|
501
|
-
this.sourceToggled = false;
|
|
502
|
-
this.shiftPressedClean = false;
|
|
503
|
-
}
|
|
504
|
-
isModifierHeld(e) {
|
|
505
|
-
return isMac2 ? e.metaKey : e.ctrlKey;
|
|
506
|
-
}
|
|
507
|
-
async handleMouseMove(e) {
|
|
508
|
-
if (!this.isModifierHeld(e)) {
|
|
509
|
-
this.overlay.hide();
|
|
510
|
-
document.body.style.cursor = "";
|
|
511
|
-
this.lastTarget = null;
|
|
512
|
-
this.lastInfo = null;
|
|
513
|
-
return;
|
|
514
|
-
}
|
|
515
|
-
this.overlay.init();
|
|
516
|
-
document.body.style.cursor = "crosshair";
|
|
517
|
-
const target = document.elementFromPoint(e.clientX, e.clientY);
|
|
518
|
-
if (!target || target.closest("[data-react-grep]")) return;
|
|
519
|
-
if (target !== this.lastTarget) {
|
|
520
|
-
this.sourceToggled = false;
|
|
521
|
-
}
|
|
522
|
-
const gen = ++this.moveGeneration;
|
|
523
|
-
const info = await getComponentInfo(target);
|
|
524
|
-
if (gen !== this.moveGeneration) return;
|
|
525
|
-
if (!info) {
|
|
526
|
-
this.overlay.hide();
|
|
527
|
-
this.lastTarget = null;
|
|
528
|
-
this.lastInfo = null;
|
|
529
|
-
return;
|
|
530
|
-
}
|
|
531
|
-
this.lastTarget = target;
|
|
532
|
-
this.lastInfo = info;
|
|
533
|
-
this.overlay.show(target, info, this.getActiveSource());
|
|
534
|
-
}
|
|
535
|
-
async handleClick(e) {
|
|
536
|
-
if (!this.isModifierHeld(e) || !e.shiftKey) return;
|
|
537
|
-
const target = document.elementFromPoint(e.clientX, e.clientY);
|
|
538
|
-
if (!target || target.closest("[data-react-grep]")) return;
|
|
539
|
-
e.preventDefault();
|
|
540
|
-
e.stopPropagation();
|
|
541
|
-
e.stopImmediatePropagation();
|
|
542
|
-
this.shiftPressedClean = false;
|
|
543
|
-
const info = await getComponentInfo(target);
|
|
544
|
-
if (!info) return;
|
|
545
|
-
const source = this.getActiveCopySource(info);
|
|
546
|
-
if (!source) return;
|
|
547
|
-
const { fileName, lineNumber, columnNumber } = source;
|
|
548
|
-
const location2 = columnNumber != null ? `${fileName}:${lineNumber}:${columnNumber}` : `${fileName}:${lineNumber}`;
|
|
549
|
-
await this.copyToClipboard(location2);
|
|
550
|
-
this.overlay.showCopied(location2);
|
|
551
|
-
}
|
|
552
|
-
handleKeyDown(e) {
|
|
553
|
-
if (e.key === "Shift" && this.isModifierHeld(e)) {
|
|
554
|
-
this.shiftPressedClean = true;
|
|
555
|
-
}
|
|
556
|
-
}
|
|
557
|
-
handleKeyUp(e) {
|
|
558
|
-
if (isMac2 && e.key === "Meta" || !isMac2 && e.key === "Control") {
|
|
559
|
-
this.overlay.hide();
|
|
560
|
-
document.body.style.cursor = "";
|
|
561
|
-
this.lastTarget = null;
|
|
562
|
-
this.lastInfo = null;
|
|
563
|
-
return;
|
|
564
|
-
}
|
|
565
|
-
if (e.key === "Shift" && this.shiftPressedClean && this.lastTarget && this.lastInfo && this.lastInfo.callSite) {
|
|
566
|
-
this.sourceToggled = !this.sourceToggled;
|
|
567
|
-
this.overlay.show(this.lastTarget, this.lastInfo, this.getActiveSource());
|
|
568
|
-
}
|
|
569
|
-
this.shiftPressedClean = false;
|
|
570
|
-
}
|
|
571
|
-
getActiveSource() {
|
|
572
|
-
return this.sourceToggled ? "callSite" : "source";
|
|
573
|
-
}
|
|
574
|
-
getActiveCopySource(info) {
|
|
575
|
-
return this.sourceToggled && info.callSite ? info.callSite : info.source;
|
|
576
|
-
}
|
|
577
|
-
async copyToClipboard(text) {
|
|
578
|
-
try {
|
|
579
|
-
await navigator.clipboard.writeText(text);
|
|
580
|
-
} catch {
|
|
581
|
-
}
|
|
582
|
-
}
|
|
583
|
-
};
|
|
584
|
-
|
|
585
|
-
// src/index.ts
|
|
586
|
-
var inspector = null;
|
|
587
|
-
var init = () => {
|
|
588
|
-
if (inspector) return;
|
|
589
|
-
inspector = new Inspector();
|
|
590
|
-
inspector.start();
|
|
591
|
-
};
|
|
592
|
-
var destroy = () => {
|
|
593
|
-
if (!inspector) return;
|
|
594
|
-
inspector.stop();
|
|
595
|
-
inspector = null;
|
|
596
|
-
};
|
|
597
|
-
if (typeof window !== "undefined") {
|
|
598
|
-
const bootstrap = () => init();
|
|
599
|
-
if (document.readyState === "loading") {
|
|
600
|
-
document.addEventListener("DOMContentLoaded", bootstrap);
|
|
601
|
-
} else {
|
|
602
|
-
bootstrap();
|
|
603
|
-
}
|
|
604
|
-
}
|
|
605
|
-
|
|
606
|
-
exports.destroy = destroy;
|
|
607
|
-
exports.init = init;
|
package/dist/index.d.cts
DELETED