chrome-devtools-frontend 1.0.1636056 → 1.0.1640418

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.
Files changed (171) hide show
  1. package/front_end/core/common/Color.ts +0 -4
  2. package/front_end/core/host/AidaClientTypes.ts +8 -6
  3. package/front_end/core/root/Runtime.ts +2 -2
  4. package/front_end/core/sdk/DOMStorageModel.ts +1 -1
  5. package/front_end/core/sdk/SourceMap.ts +8 -3
  6. package/front_end/core/sdk/TargetManager.ts +14 -1
  7. package/front_end/entrypoints/heap_snapshot_worker/HeapSnapshot.ts +147 -0
  8. package/front_end/generated/ARIAProperties.js +17 -4
  9. package/front_end/generated/InspectorBackendCommands.ts +13 -7
  10. package/front_end/generated/SupportedCSSProperties.js +1 -0
  11. package/front_end/generated/protocol-mapping.d.ts +7 -0
  12. package/front_end/generated/protocol-proxy-api.d.ts +14 -0
  13. package/front_end/generated/protocol.ts +120 -2
  14. package/front_end/global_typings/global_defs.d.ts +13 -0
  15. package/front_end/models/ai_assistance/AiAgent2.ts +116 -0
  16. package/front_end/models/ai_assistance/AiConversation.ts +22 -36
  17. package/front_end/models/ai_assistance/AiHistoryStorage.ts +0 -1
  18. package/front_end/models/ai_assistance/AiOrigins.ts +46 -0
  19. package/front_end/models/ai_assistance/AiUtils.ts +9 -0
  20. package/front_end/models/ai_assistance/README.md +16 -0
  21. package/front_end/models/ai_assistance/StorageItem.ts +30 -26
  22. package/front_end/models/ai_assistance/agents/AccessibilityAgent.ts +12 -5
  23. package/front_end/models/ai_assistance/agents/AiAgent.ts +86 -32
  24. package/front_end/models/ai_assistance/agents/ContextSelectionAgent.snapshot.txt +2 -2
  25. package/front_end/models/ai_assistance/agents/ContextSelectionAgent.ts +31 -10
  26. package/front_end/models/ai_assistance/agents/ConversationSummaryAgent.ts +1 -1
  27. package/front_end/models/ai_assistance/agents/FileAgent.ts +2 -2
  28. package/front_end/models/ai_assistance/agents/GreenDevAgent.ts +1 -3
  29. package/front_end/models/ai_assistance/agents/NetworkAgent.snapshot.txt +19 -0
  30. package/front_end/models/ai_assistance/agents/NetworkAgent.ts +9 -4
  31. package/front_end/models/ai_assistance/agents/PerformanceAgent.snapshot.txt +2 -2
  32. package/front_end/models/ai_assistance/agents/PerformanceAgent.ts +41 -12
  33. package/front_end/models/ai_assistance/agents/StorageAgent.ts +442 -122
  34. package/front_end/models/ai_assistance/agents/StylingAgent.ts +2 -2
  35. package/front_end/models/ai_assistance/ai_assistance.ts +4 -2
  36. package/front_end/models/ai_assistance/data_formatters/PerformanceTraceFormatter.snapshot.txt +2 -2
  37. package/front_end/models/ai_assistance/performance/AIContext.ts +7 -8
  38. package/front_end/models/ai_assistance/skills/README.md +40 -0
  39. package/front_end/models/ai_assistance/skills/Skill.ts +13 -0
  40. package/front_end/models/ai_assistance/skills/SkillRegistry.ts +10 -0
  41. package/front_end/models/ai_assistance/skills/styling.md +6 -0
  42. package/front_end/models/bindings/CompilerScriptMapping.ts +12 -4
  43. package/front_end/models/breakpoints/BreakpointManager.ts +54 -2
  44. package/front_end/models/greendev/Prototypes.ts +0 -7
  45. package/front_end/models/heap_snapshot/HeapSnapshotModel.ts +20 -0
  46. package/front_end/models/heap_snapshot/HeapSnapshotProxy.ts +5 -0
  47. package/front_end/models/issues_manager/EmailVerificationRequestIssue.ts +293 -0
  48. package/front_end/models/issues_manager/IssuesManager.ts +5 -0
  49. package/front_end/models/issues_manager/descriptions/emailVerificationRequestDnsFetchFailed.md +1 -0
  50. package/front_end/models/issues_manager/descriptions/emailVerificationRequestDnsInvalidRecord.md +1 -0
  51. package/front_end/models/issues_manager/descriptions/emailVerificationRequestInvalidEmail.md +1 -0
  52. package/front_end/models/issues_manager/descriptions/emailVerificationRequestKeyBindingSigningFailed.md +1 -0
  53. package/front_end/models/issues_manager/descriptions/emailVerificationRequestRpOriginIsOpaque.md +1 -0
  54. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenHttpNotFound.md +1 -0
  55. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenInvalidContentType.md +1 -0
  56. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenInvalidResponse.md +1 -0
  57. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenInvalidSdJwt.md +1 -0
  58. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenMalformedSdJwt.md +1 -0
  59. package/front_end/models/issues_manager/descriptions/emailVerificationRequestTokenNoResponse.md +1 -0
  60. package/front_end/models/issues_manager/descriptions/emailVerificationRequestUserLoggedOut.md +1 -0
  61. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownAccountsEndpointCrossOrigin.md +1 -0
  62. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownHttpNotFound.md +1 -0
  63. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownInvalidContentType.md +1 -0
  64. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownInvalidResponse.md +1 -0
  65. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownIssuanceEndpointCrossOrigin.md +1 -0
  66. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownListEmpty.md +1 -0
  67. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownMissingAccountsEndpoint.md +1 -0
  68. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownMissingIssuanceEndpoint.md +1 -0
  69. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownNoResponse.md +1 -0
  70. package/front_end/models/issues_manager/descriptions/emailVerificationRequestWellKnownUnsupportedSigningAlgorithm.md +1 -0
  71. package/front_end/models/issues_manager/issues_manager.ts +2 -0
  72. package/front_end/models/javascript_metadata/NativeFunctions.js +1748 -1739
  73. package/front_end/models/live-metrics/web-vitals-injected/web-vitals-injected.ts +1 -1
  74. package/front_end/models/stack_trace/DetailedErrorStackParser.ts +9 -1
  75. package/front_end/models/stack_trace/StackTraceImpl.ts +29 -9
  76. package/front_end/models/stack_trace/StackTraceModel.ts +23 -11
  77. package/front_end/models/stack_trace/Trie.ts +11 -1
  78. package/front_end/models/trace/extras/TraceTree.ts +20 -1
  79. package/front_end/models/trace/insights/Common.ts +9 -0
  80. package/front_end/models/trace/lantern/core/NetworkAnalyzer.ts +21 -25
  81. package/front_end/panels/ai_assistance/AiAssistancePanel.ts +19 -75
  82. package/front_end/panels/ai_assistance/components/AccessibilityAgentMarkdownRenderer.ts +10 -3
  83. package/front_end/panels/ai_assistance/components/ChatMessage.ts +148 -2
  84. package/front_end/panels/ai_assistance/components/PerformanceAgentMarkdownRenderer.ts +2 -3
  85. package/front_end/panels/ai_assistance/components/chatMessage.css +27 -0
  86. package/front_end/panels/application/CookieItemsView.ts +24 -0
  87. package/front_end/panels/application/DOMStorageItemsView.ts +9 -4
  88. package/front_end/panels/application/preloading/components/PreloadingString.ts +6 -0
  89. package/front_end/panels/application/preloading/components/UsedPreloadingView.ts +4 -4
  90. package/front_end/panels/console/ConsoleViewMessage.ts +13 -102
  91. package/front_end/panels/elements/StandaloneStylesContainer.ts +10 -0
  92. package/front_end/panels/elements/StylePropertiesSection.ts +6 -2
  93. package/front_end/panels/elements/StylePropertyTreeElement.ts +30 -1
  94. package/front_end/panels/elements/StylesContainer.ts +3 -0
  95. package/front_end/panels/elements/StylesSidebarPane.ts +54 -4
  96. package/front_end/panels/elements/elements-meta.ts +14 -0
  97. package/front_end/panels/layer_viewer/layerDetailsView.css +1 -1
  98. package/front_end/panels/lighthouse/LighthouseController.ts +1 -1
  99. package/front_end/panels/lighthouse/LighthouseProtocolService.ts +4 -4
  100. package/front_end/panels/network/NetworkDataGridNode.ts +14 -0
  101. package/front_end/panels/network/NetworkLogViewColumns.ts +2 -2
  102. package/front_end/panels/network/RequestHeadersView.ts +55 -19
  103. package/front_end/panels/network/networkTimingTable.css +2 -4
  104. package/front_end/panels/recorder/components/ReplaySection.ts +28 -16
  105. package/front_end/panels/recorder/converters/LighthouseConverter.snapshot.txt +47 -0
  106. package/front_end/panels/recorder/converters/PuppeteerConverter.snapshot.txt +49 -0
  107. package/front_end/panels/recorder/converters/PuppeteerReplayConverter.snapshot.txt +33 -0
  108. package/front_end/panels/settings/SettingsScreen.ts +1 -2
  109. package/front_end/panels/sources/BreakpointsView.ts +23 -42
  110. package/front_end/panels/sources/DebuggerPlugin.ts +12 -5
  111. package/front_end/panels/sources/ScopeChainSidebarPane.ts +169 -106
  112. package/front_end/panels/timeline/components/IgnoreListSetting.ts +1 -0
  113. package/front_end/third_party/chromium/README.chromium +1 -1
  114. package/front_end/third_party/lighthouse/lighthouse-dt-bundle.js +2 -2
  115. package/front_end/third_party/marked/README.chromium +3 -6
  116. package/front_end/third_party/marked/package/README.md +5 -5
  117. package/front_end/third_party/marked/package/bin/main.js +27 -22
  118. package/front_end/third_party/marked/package/bin/marked.js +2 -1
  119. package/front_end/third_party/marked/package/lib/marked.esm.d.ts +346 -256
  120. package/front_end/third_party/marked/package/lib/marked.esm.js +67 -2698
  121. package/front_end/third_party/marked/package/lib/marked.esm.js.map +7 -1
  122. package/front_end/third_party/marked/package/lib/marked.umd.js +69 -2722
  123. package/front_end/third_party/marked/package/lib/marked.umd.js.map +7 -1
  124. package/front_end/third_party/marked/package/man/marked.1 +4 -2
  125. package/front_end/third_party/marked/package/man/marked.1.md +2 -1
  126. package/front_end/third_party/marked/package/package.json +49 -57
  127. package/front_end/third_party/puppeteer-replay/README.chromium +2 -2
  128. package/front_end/third_party/puppeteer-replay/package/lib/cli.js +84 -80
  129. package/front_end/third_party/puppeteer-replay/package/lib/cli.js.map +1 -1
  130. package/front_end/third_party/puppeteer-replay/package/lib/extension-test.js +79 -83
  131. package/front_end/third_party/puppeteer-replay/package/lib/extension-test.js.map +1 -1
  132. package/front_end/third_party/puppeteer-replay/package/lib/main.d.ts +43 -171
  133. package/front_end/third_party/puppeteer-replay/package/lib/main.js +51 -206
  134. package/front_end/third_party/puppeteer-replay/package/lib/main.js.map +1 -1
  135. package/front_end/third_party/puppeteer-replay/package/package.json +37 -67
  136. package/front_end/tsconfig.json +1 -1
  137. package/front_end/ui/components/markdown_view/CodeBlock.ts +17 -6
  138. package/front_end/ui/components/markdown_view/MarkdownView.ts +39 -3
  139. package/front_end/ui/components/markdown_view/codeBlock.css +11 -0
  140. package/front_end/ui/components/markdown_view/markdownView.css +17 -0
  141. package/front_end/ui/legacy/components/object_ui/ObjectPropertiesSection.ts +0 -79
  142. package/front_end/ui/legacy/components/object_ui/RemoteObjectPreviewFormatter.ts +16 -4
  143. package/front_end/ui/visual_logging/KnownContextValues.ts +4 -0
  144. package/inspector_overlay/testing/InspectorOverlayHelpers.ts +2 -0
  145. package/mcp/mcp.ts +1 -6
  146. package/package.json +14 -16
  147. package/front_end/models/ai_assistance/agents/BreakpointDebuggerAgent.ts +0 -1015
  148. package/front_end/models/ai_assistance/agents/BreakpointDebuggerAgentOverlay.ts +0 -87
  149. package/front_end/third_party/marked/package/bin/marked +0 -215
  150. package/front_end/third_party/marked/package/lib/marked.cjs +0 -2726
  151. package/front_end/third_party/marked/package/lib/marked.cjs.map +0 -1
  152. package/front_end/third_party/marked/package/lib/marked.d.cts +0 -670
  153. package/front_end/third_party/marked/package/lib/marked.js +0 -2780
  154. package/front_end/third_party/marked/package/man/marked.1.txt +0 -86
  155. package/front_end/third_party/marked/package/marked.min.js +0 -6
  156. package/front_end/third_party/marked/package/src/Lexer.js +0 -492
  157. package/front_end/third_party/marked/package/src/Parser.js +0 -286
  158. package/front_end/third_party/marked/package/src/Renderer.js +0 -166
  159. package/front_end/third_party/marked/package/src/Slugger.js +0 -49
  160. package/front_end/third_party/marked/package/src/TextRenderer.js +0 -42
  161. package/front_end/third_party/marked/package/src/Tokenizer.js +0 -755
  162. package/front_end/third_party/marked/package/src/defaults.js +0 -29
  163. package/front_end/third_party/marked/package/src/helpers.js +0 -249
  164. package/front_end/third_party/marked/package/src/marked.js +0 -350
  165. package/front_end/third_party/marked/package/src/rules.js +0 -285
  166. package/front_end/third_party/puppeteer-replay/package/lib/cjs/main.cjs +0 -2099
  167. package/front_end/third_party/puppeteer-replay/package/lib/cjs/main.cjs.map +0 -1
  168. package/front_end/third_party/puppeteer-replay/package/lib/cjs/main.d.cts +0 -686
  169. package/front_end/third_party/puppeteer-replay/package/lib/cjs/main.d.ts +0 -35
  170. package/mcp/HostBindings.ts +0 -319
  171. /package/front_end/third_party/marked/package/{LICENSE.md → LICENSE} +0 -0
@@ -160,13 +160,13 @@ export class NodeContext extends ConversationContext<SDK.DOMModel.DOMNode> {
160
160
  this.#node = node;
161
161
  }
162
162
 
163
- getOrigin(): string {
163
+ override getURL(): string {
164
164
  const ownerDocument = this.#node.ownerDocument;
165
165
  if (!ownerDocument) {
166
166
  // The node is detached from a document.
167
167
  return 'detached';
168
168
  }
169
- return new URL(ownerDocument.documentURL).origin;
169
+ return ownerDocument.documentURL;
170
170
  }
171
171
 
172
172
  getItem(): SDK.DOMModel.DOMNode {
@@ -5,7 +5,6 @@
5
5
  import * as AgentProject from './AgentProject.js';
6
6
  import * as AccessibilityAgent from './agents/AccessibilityAgent.js';
7
7
  import * as AiAgent from './agents/AiAgent.js';
8
- import * as BreakpointDebuggerAgent from './agents/BreakpointDebuggerAgent.js';
9
8
  import * as ContextSelectionAgent from './agents/ContextSelectionAgent.js';
10
9
  import * as ConversationSummaryAgent from './agents/ConversationSummaryAgent.js';
11
10
  import * as FileAgent from './agents/FileAgent.js';
@@ -18,8 +17,10 @@ import * as PerformanceAgent from './agents/PerformanceAgent.js';
18
17
  import * as PerformanceAnnotationsAgent from './agents/PerformanceAnnotationsAgent.js';
19
18
  import * as StorageAgent from './agents/StorageAgent.js';
20
19
  import * as StylingAgent from './agents/StylingAgent.js';
20
+ import * as AiAgent2 from './AiAgent2.js';
21
21
  import * as AiConversation from './AiConversation.js';
22
22
  import * as AiHistoryStorage from './AiHistoryStorage.js';
23
+ import * as AiOrigins from './AiOrigins.js';
23
24
  import * as AiUtils from './AiUtils.js';
24
25
  import * as BuiltInAi from './BuiltInAi.js';
25
26
  import * as ChangeManager from './ChangeManager.js';
@@ -42,13 +43,14 @@ export {
42
43
  AccessibilityAgent,
43
44
  AgentProject,
44
45
  AiAgent,
46
+ AiAgent2,
45
47
  AICallTree,
46
48
  AIContext,
47
49
  AiConversation,
48
50
  AiHistoryStorage,
51
+ AiOrigins,
49
52
  AIQueries,
50
53
  AiUtils,
51
- BreakpointDebuggerAgent,
52
54
  BuiltInAi,
53
55
  ChangeManager,
54
56
  ContextSelectionAgent,
@@ -376,7 +376,7 @@ This is the bottom-up summary for the entire trace. Only the top 20 activities (
376
376
 
377
377
  # Third parties
378
378
 
379
- - name: Yahoo!, main thread time: 214 ms, network transfer size: 2.4 MB
379
+ - name: Yahoo!, main thread time: 214 ms, network transfer size: 1.6 MB
380
380
  - name: Taboola, main thread time: 41 ms, network transfer size: 391.7 kB
381
381
  - name: Google/Doubleclick Ads, main thread time: 41 ms, network transfer size: 225.7 kB
382
382
  - name: Google Tag Manager, main thread time: 19 ms, network transfer size: 123.8 kB
@@ -932,7 +932,7 @@ Title: PerformanceTraceFormatter formatThirdPartySummary yahoo-news.json.gz
932
932
  Content:
933
933
  # 3rd party summary
934
934
 
935
- - name: Yahoo!, main thread time: 270 ms, network transfer size: 2.4 MB
935
+ - name: Yahoo!, main thread time: 270 ms, network transfer size: 1.6 MB
936
936
  - name: Google/Doubleclick Ads, main thread time: 53 ms, network transfer size: 258.6 kB
937
937
  - name: Taboola, main thread time: 43 ms, network transfer size: 393.6 kB
938
938
  - name: Google Tag Manager, main thread time: 19 ms, network transfer size: 123.8 kB
@@ -124,15 +124,14 @@ export class AgentFocus {
124
124
  return focus;
125
125
  }
126
126
 
127
- lookupEvent(key: Trace.Types.File.SerializableKey): Trace.Types.Events.Event|null {
127
+ lookupEvent(key: string): Trace.Types.Events.Event|null {
128
128
  try {
129
- return this.eventsSerializer.eventForKey(key, this.#data.parsedTrace);
130
- } catch (err) {
131
- if (err.toString().includes('Unknown trace event') || err.toString().includes('Unknown profile call')) {
132
- return null;
133
- }
134
-
135
- throw err;
129
+ return this.eventsSerializer.eventForKey(key as Trace.Types.File.SerializableKey, this.#data.parsedTrace) ?? null;
130
+ } catch {
131
+ // We must silence all lookup and serialization errors here. Otherwise,
132
+ // any malformed link or invalid event key in the LLM response will throw
133
+ // an unhandled exception, breaking the panel's markdown rendering entirely.
134
+ return null;
136
135
  }
137
136
  }
138
137
 
@@ -0,0 +1,40 @@
1
+ # AI Assistant Skills
2
+
3
+ This directory contains the definitions for skills used by `AiAgent2`.
4
+
5
+ ## Authoring Skills
6
+
7
+ Skills are authored as Markdown files with YAML frontmatter.
8
+
9
+ Example:
10
+ ```markdown
11
+ ---
12
+ name: styling
13
+ allowed-tools: [search_web]
14
+ ---
15
+ You are a CSS expert...
16
+ ```
17
+
18
+ * **Frontmatter**: Contains metadata like `name` and `allowed-tools`.
19
+ * **Body**: The instructions for the skill (prompt).
20
+
21
+ ### Why Markdown?
22
+
23
+ Skills are stored as Markdown to make it easier to share them with other codebases or systems that might not be using TypeScript or the DevTools build system. This is an intentional trade-off that requires a build step for DevTools.
24
+
25
+ ## Build System
26
+
27
+ Markdown files are converted to JavaScript files (`.skill.js`) during the build process.
28
+
29
+ * **Script**: `scripts/build/build_ai_skills.mjs` processes each file individually.
30
+ * **GN Target**: `action_foreach("generate_skills")` in `front_end/models/ai_assistance/skills/BUILD.gn`.
31
+ * **Output**: Files are placed in the generation directory, e.g., `out/Default/gen/front_end/models/ai_assistance/skills/styling.skill.js`.
32
+
33
+ ## Consumption
34
+
35
+ To use a skill in TypeScript:
36
+
37
+ 1. Import it: `import {skill} from './styling.skill.js';`
38
+ 2. Register it in `SkillRegistry.ts`.
39
+
40
+ Types are provided globally in `front_end/global_typings/global_defs.d.ts` via a wildcard module declaration (`*.skill.js`). This avoids the need to generate `tsconfig.json` files for the generated skills.
@@ -0,0 +1,13 @@
1
+ // Copyright 2026 The Chromium Authors
2
+ // Use of this source code is governed by a BSD-style license that can be
3
+ // found in the LICENSE file.
4
+
5
+ // This will become a union type as we add more skills (e.g. 'styling' | 'network').
6
+ export type SkillName = 'styling';
7
+
8
+ export interface Skill {
9
+ name: SkillName;
10
+ description: string;
11
+ allowedTools: string[];
12
+ instructions: string;
13
+ }
@@ -0,0 +1,10 @@
1
+ // Copyright 2026 The Chromium Authors
2
+ // Use of this source code is governed by a BSD-style license that can be
3
+ // found in the LICENSE file.
4
+
5
+ import type {Skill, SkillName} from './Skill.js';
6
+ import {skill as stylingSkill} from './styling.skill.js';
7
+
8
+ export const SKILLS: Record<SkillName, Skill> = {
9
+ styling: stylingSkill,
10
+ };
@@ -0,0 +1,6 @@
1
+ ---
2
+ name: styling
3
+ description: Helping with CSS and styling
4
+ allowed-tools: []
5
+ ---
6
+ You are a CSS expert helping the user style elements.
@@ -231,16 +231,24 @@ export class CompilerScriptMapping implements DebuggerSourceMapping {
231
231
  SDK.DebuggerModel.Location[] {
232
232
  const locations = [];
233
233
  for (const sourceMap of this.#uiSourceCodeToSourceMaps.get(uiSourceCode)) {
234
- const entry = sourceMap.sourceLineMapping(uiSourceCode.url(), lineNumber, columnNumber);
235
- if (!entry) {
234
+ const firstEntry = sourceMap.sourceLineMapping(uiSourceCode.url(), lineNumber, columnNumber);
235
+ if (!firstEntry) {
236
+ continue;
237
+ }
238
+ const entries = sourceMap.findReverseEntries(
239
+ uiSourceCode.url(), firstEntry.sourceLineNumber, firstEntry.sourceColumnNumber, true);
240
+ if (entries.length === 0) {
236
241
  continue;
237
242
  }
238
243
  const script = this.#sourceMapManager.clientForSourceMap(sourceMap);
239
244
  if (!script) {
240
245
  continue;
241
246
  }
242
- const location = script.relativeLocationToRawLocation(entry);
243
- locations.push(script.debuggerModel.createRawLocation(script, location.lineNumber, location.columnNumber));
247
+
248
+ for (const entry of entries) {
249
+ const location = script.relativeLocationToRawLocation(entry);
250
+ locations.push(script.debuggerModel.createRawLocation(script, location.lineNumber, location.columnNumber));
251
+ }
244
252
  }
245
253
  return locations;
246
254
  }
@@ -696,9 +696,19 @@ export class Breakpoint implements SDK.TargetManager.SDKModelObserver<SDK.Debugg
696
696
 
697
697
  // Do we need to do this? Not sure if bound locations will leak...
698
698
  if (this.bound()) {
699
+ const removedUILocations = new Map<string, Workspace.UISourceCode.UILocation>();
699
700
  for (const uiLocation of this.#uiLocations) {
700
701
  if (uiLocation.uiSourceCode === uiSourceCode) {
701
702
  this.#uiLocations.delete(uiLocation);
703
+ removedUILocations.set(uiLocation.id(), uiLocation);
704
+ }
705
+ }
706
+
707
+ for (const uiLocation of removedUILocations.values()) {
708
+ // Multiple physically distinct UILocations can map to the same logical location
709
+ // (same ID). We only notify the manager if all instances of this logical location are gone.
710
+ const isGoneLogically = !Array.from(this.#uiLocations).some(loc => loc.id() === uiLocation.id());
711
+ if (isGoneLogically) {
702
712
  this.breakpointManager.uiLocationRemoved(uiLocation);
703
713
  }
704
714
  }
@@ -730,14 +740,26 @@ export class Breakpoint implements SDK.TargetManager.SDKModelObserver<SDK.Debugg
730
740
  // This is our first bound location; remove all unbound locations
731
741
  this.removeAllUnboundLocations();
732
742
  }
743
+ // A single logical breakpoint can resolve to multiple raw locations (e.g. due to
744
+ // inlining or SSR/client template duplication) that map back to the same logical
745
+ // UILocation. We only notify the manager once per logical UILocation to avoid
746
+ // duplicate items/decorations in the UI.
747
+ const isNewLogicalLocation = !Array.from(this.#uiLocations).some(loc => loc.id() === uiLocation.id());
733
748
  this.#uiLocations.add(uiLocation);
734
- this.breakpointManager.uiLocationAdded(this, uiLocation);
749
+ if (isNewLogicalLocation) {
750
+ this.breakpointManager.uiLocationAdded(this, uiLocation);
751
+ }
735
752
  }
736
753
 
737
754
  uiLocationRemoved(uiLocation: Workspace.UISourceCode.UILocation): void {
738
755
  if (this.#uiLocations.has(uiLocation)) {
739
756
  this.#uiLocations.delete(uiLocation);
740
- this.breakpointManager.uiLocationRemoved(uiLocation);
757
+ // We only notify the manager if there are no other resolved locations left
758
+ // that map to this same logical UILocation (same ID).
759
+ const isGoneLogically = !Array.from(this.#uiLocations).some(loc => loc.id() === uiLocation.id());
760
+ if (isGoneLogically) {
761
+ this.breakpointManager.uiLocationRemoved(uiLocation);
762
+ }
741
763
  if (!this.bound() && !this.isRemoved) {
742
764
  this.addAllUnboundLocations();
743
765
  }
@@ -752,6 +774,36 @@ export class Breakpoint implements SDK.TargetManager.SDKModelObserver<SDK.Debugg
752
774
  return this.#uiLocations.size !== 0;
753
775
  }
754
776
 
777
+ getClosestResolvedLocation(): Workspace.UISourceCode.UILocation|null {
778
+ if (this.#uiLocations.size === 0) {
779
+ return null;
780
+ }
781
+ let closestLocation: Workspace.UISourceCode.UILocation|null = null;
782
+ let minLineDiff = Infinity;
783
+ let minColDiff = Infinity;
784
+
785
+ const breakpointLine = this.lineNumber();
786
+ const breakpointColumn = this.columnNumber() ?? 0;
787
+
788
+ for (const uiLocation of this.#uiLocations) {
789
+ const lineDiff = Math.abs(uiLocation.lineNumber - breakpointLine);
790
+ const colDiff = Math.abs((uiLocation.columnNumber ?? 0) - breakpointColumn);
791
+
792
+ if (lineDiff < minLineDiff) {
793
+ minLineDiff = lineDiff;
794
+ minColDiff = colDiff;
795
+ closestLocation = uiLocation;
796
+ } else if (lineDiff === minLineDiff) {
797
+ if (colDiff < minColDiff) {
798
+ minColDiff = colDiff;
799
+ closestLocation = uiLocation;
800
+ }
801
+ }
802
+ }
803
+
804
+ return closestLocation;
805
+ }
806
+
755
807
  setEnabled(enabled: boolean): void {
756
808
  this.updateState({...this.#storageState, enabled});
757
809
  }
@@ -11,7 +11,6 @@ export interface GreenDevSettings {
11
11
  aiAnnotations: Common.Settings.Setting<boolean>;
12
12
  beyondStylingGemini: Common.Settings.Setting<boolean>;
13
13
  beyondStylingAntigravity: Common.Settings.Setting<boolean>;
14
- breakpointDebuggerAgent: Common.Settings.Setting<boolean>;
15
14
  emulationCapabilities: Common.Settings.Setting<boolean>;
16
15
  }
17
16
 
@@ -53,11 +52,6 @@ export class Prototypes {
53
52
  false,
54
53
  Common.Settings.SettingStorageType.GLOBAL,
55
54
  );
56
- const breakpointDebuggerAgent = settings.createSetting(
57
- 'greendev-breakpoint-debugger-agent-enabled',
58
- false,
59
- Common.Settings.SettingStorageType.LOCAL,
60
- );
61
55
  const emulationCapabilities = settings.createSetting(
62
56
  'greendev-emulation-capabilities-enabled',
63
57
  false,
@@ -68,7 +62,6 @@ export class Prototypes {
68
62
  aiAnnotations,
69
63
  beyondStylingGemini,
70
64
  beyondStylingAntigravity,
71
- breakpointDebuggerAgent,
72
65
  emulationCapabilities
73
66
  };
74
67
  }
@@ -267,3 +267,23 @@ export class Location {
267
267
  this.columnNumber = columnNumber;
268
268
  }
269
269
  }
270
+
271
+ export interface RetainingEdge {
272
+ edgeIndex: number;
273
+ edgeName: string;
274
+ edgeType: string;
275
+ nodeId: number;
276
+ nodeIndex: number;
277
+ nodeName: string;
278
+ distance: number;
279
+ children: RetainingEdge[];
280
+ }
281
+
282
+ export interface RetainingPaths {
283
+ paths: RetainingEdge[];
284
+ limitsReached: {
285
+ depth?: boolean,
286
+ nodes?: boolean,
287
+ siblings?: boolean,
288
+ };
289
+ }
@@ -363,6 +363,11 @@ export class HeapSnapshotProxy extends HeapSnapshotProxyObject {
363
363
  return this.callMethodPromise('ignoreNodeInRetainersView', nodeIndex);
364
364
  }
365
365
 
366
+ getRetainingPaths(nodeIndex: number, maxDepth?: number, maxNodes?: number, maxSiblings?: number):
367
+ Promise<HeapSnapshotModel.RetainingPaths> {
368
+ return this.callMethodPromise('getRetainingPaths', nodeIndex, maxDepth, maxNodes, maxSiblings);
369
+ }
370
+
366
371
  unignoreNodeInRetainersView(nodeIndex: number): Promise<void> {
367
372
  return this.callMethodPromise('unignoreNodeInRetainersView', nodeIndex);
368
373
  }
@@ -0,0 +1,293 @@
1
+ // Copyright 2026 The Chromium Authors
2
+ // Use of this source code is governed by a BSD-style license that can be
3
+ // found in the LICENSE file.
4
+
5
+ import * as i18n from '../../core/i18n/i18n.js';
6
+ import type * as SDK from '../../core/sdk/sdk.js';
7
+ import * as Protocol from '../../generated/protocol.js';
8
+
9
+ import {Issue, IssueCategory, IssueKind} from './Issue.js';
10
+ import {
11
+ type LazyMarkdownIssueDescription,
12
+ type MarkdownIssueDescription,
13
+ resolveLazyDescription,
14
+ } from './MarkdownIssueDescription.js';
15
+
16
+ const UIStrings = {
17
+ /**
18
+ * @description Title for Email Verification Protocol specification url link
19
+ */
20
+ emailVerification: 'Email Verification Protocol',
21
+ } as const;
22
+ const str_ = i18n.i18n.registerUIStrings('models/issues_manager/EmailVerificationRequestIssue.ts', UIStrings);
23
+ const i18nLazyString = i18n.i18n.getLazilyComputedLocalizedString.bind(undefined, str_);
24
+
25
+ export class EmailVerificationRequestIssue extends Issue<Protocol.Audits.EmailVerificationRequestIssueDetails> {
26
+ constructor(
27
+ issueDetails: Protocol.Audits.EmailVerificationRequestIssueDetails,
28
+ issuesModel: SDK.IssuesModel.IssuesModel|null) {
29
+ super(
30
+ {
31
+ code: Protocol.Audits.InspectorIssueCode.EmailVerificationRequestIssue,
32
+ umaCode: [
33
+ Protocol.Audits.InspectorIssueCode.EmailVerificationRequestIssue,
34
+ issueDetails.emailVerificationRequestIssueReason,
35
+ ].join('::'),
36
+ },
37
+ issueDetails, issuesModel);
38
+ }
39
+
40
+ getCategory(): IssueCategory {
41
+ return IssueCategory.OTHER;
42
+ }
43
+
44
+ getDescription(): MarkdownIssueDescription|null {
45
+ const description = issueDescriptions.get(this.details().emailVerificationRequestIssueReason);
46
+ if (!description) {
47
+ return null;
48
+ }
49
+ return resolveLazyDescription(description);
50
+ }
51
+
52
+ primaryKey(): string {
53
+ return JSON.stringify(this.details());
54
+ }
55
+
56
+ getKind(): IssueKind {
57
+ return IssueKind.PAGE_ERROR;
58
+ }
59
+
60
+ static fromInspectorIssue(
61
+ issuesModel: SDK.IssuesModel.IssuesModel|null,
62
+ inspectorIssue: Protocol.Audits.InspectorIssue): EmailVerificationRequestIssue[] {
63
+ const details = inspectorIssue.details.emailVerificationRequestIssueDetails;
64
+ if (!details) {
65
+ console.warn('Email verification request issue without details received.');
66
+ return [];
67
+ }
68
+ return [new EmailVerificationRequestIssue(details, issuesModel)];
69
+ }
70
+ }
71
+
72
+ const issueDescriptions = new Map<Protocol.Audits.EmailVerificationRequestIssueReason, LazyMarkdownIssueDescription>([
73
+ [
74
+ Protocol.Audits.EmailVerificationRequestIssueReason.InvalidEmail,
75
+ {
76
+ file: 'emailVerificationRequestInvalidEmail.md',
77
+ links: [{
78
+ link: 'https://github.com/WICG/email-verification-protocol',
79
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
80
+ }],
81
+ },
82
+ ],
83
+ [
84
+ Protocol.Audits.EmailVerificationRequestIssueReason.DnsFetchFailed,
85
+ {
86
+ file: 'emailVerificationRequestDnsFetchFailed.md',
87
+ links: [{
88
+ link: 'https://github.com/WICG/email-verification-protocol',
89
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
90
+ }],
91
+ },
92
+ ],
93
+ [
94
+ Protocol.Audits.EmailVerificationRequestIssueReason.DnsInvalidRecord,
95
+ {
96
+ file: 'emailVerificationRequestDnsInvalidRecord.md',
97
+ links: [{
98
+ link: 'https://github.com/WICG/email-verification-protocol',
99
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
100
+ }],
101
+ },
102
+ ],
103
+ [
104
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownHttpNotFound,
105
+ {
106
+ file: 'emailVerificationRequestWellKnownHttpNotFound.md',
107
+ links: [{
108
+ link: 'https://github.com/WICG/email-verification-protocol',
109
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
110
+ }],
111
+ },
112
+ ],
113
+ [
114
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownNoResponse,
115
+ {
116
+ file: 'emailVerificationRequestWellKnownNoResponse.md',
117
+ links: [{
118
+ link: 'https://github.com/WICG/email-verification-protocol',
119
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
120
+ }],
121
+ },
122
+ ],
123
+ [
124
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownInvalidResponse,
125
+ {
126
+ file: 'emailVerificationRequestWellKnownInvalidResponse.md',
127
+ links: [{
128
+ link: 'https://github.com/WICG/email-verification-protocol',
129
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
130
+ }],
131
+ },
132
+ ],
133
+ [
134
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownListEmpty,
135
+ {
136
+ file: 'emailVerificationRequestWellKnownListEmpty.md',
137
+ links: [{
138
+ link: 'https://github.com/WICG/email-verification-protocol',
139
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
140
+ }],
141
+ },
142
+ ],
143
+ [
144
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownInvalidContentType,
145
+ {
146
+ file: 'emailVerificationRequestWellKnownInvalidContentType.md',
147
+ links: [{
148
+ link: 'https://github.com/WICG/email-verification-protocol',
149
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
150
+ }],
151
+ },
152
+ ],
153
+ [
154
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownMissingIssuanceEndpoint,
155
+ {
156
+ file: 'emailVerificationRequestWellKnownMissingIssuanceEndpoint.md',
157
+ links: [{
158
+ link: 'https://github.com/WICG/email-verification-protocol',
159
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
160
+ }],
161
+ },
162
+ ],
163
+ [
164
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownIssuanceEndpointCrossOrigin,
165
+ {
166
+ file: 'emailVerificationRequestWellKnownIssuanceEndpointCrossOrigin.md',
167
+ links: [{
168
+ link: 'https://github.com/WICG/email-verification-protocol',
169
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
170
+ }],
171
+ },
172
+ ],
173
+ [
174
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownUnsupportedSigningAlgorithm,
175
+ {
176
+ file: 'emailVerificationRequestWellKnownUnsupportedSigningAlgorithm.md',
177
+ links: [{
178
+ link: 'https://github.com/WICG/email-verification-protocol',
179
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
180
+ }],
181
+ },
182
+ ],
183
+ [
184
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenHttpNotFound,
185
+ {
186
+ file: 'emailVerificationRequestTokenHttpNotFound.md',
187
+ links: [{
188
+ link: 'https://github.com/WICG/email-verification-protocol',
189
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
190
+ }],
191
+ },
192
+ ],
193
+ [
194
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenNoResponse,
195
+ {
196
+ file: 'emailVerificationRequestTokenNoResponse.md',
197
+ links: [{
198
+ link: 'https://github.com/WICG/email-verification-protocol',
199
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
200
+ }],
201
+ },
202
+ ],
203
+ [
204
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenInvalidResponse,
205
+ {
206
+ file: 'emailVerificationRequestTokenInvalidResponse.md',
207
+ links: [{
208
+ link: 'https://github.com/WICG/email-verification-protocol',
209
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
210
+ }],
211
+ },
212
+ ],
213
+ [
214
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenInvalidContentType,
215
+ {
216
+ file: 'emailVerificationRequestTokenInvalidContentType.md',
217
+ links: [{
218
+ link: 'https://github.com/WICG/email-verification-protocol',
219
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
220
+ }],
221
+ },
222
+ ],
223
+ [
224
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenMalformedSdJwt,
225
+ {
226
+ file: 'emailVerificationRequestTokenMalformedSdJwt.md',
227
+ links: [{
228
+ link: 'https://github.com/WICG/email-verification-protocol',
229
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
230
+ }],
231
+ },
232
+ ],
233
+ [
234
+ Protocol.Audits.EmailVerificationRequestIssueReason.TokenInvalidSdJwt,
235
+ {
236
+ file: 'emailVerificationRequestTokenInvalidSdJwt.md',
237
+ links: [{
238
+ link: 'https://github.com/WICG/email-verification-protocol',
239
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
240
+ }],
241
+ },
242
+ ],
243
+ [
244
+ Protocol.Audits.EmailVerificationRequestIssueReason.KeyBindingSigningFailed,
245
+ {
246
+ file: 'emailVerificationRequestKeyBindingSigningFailed.md',
247
+ links: [{
248
+ link: 'https://github.com/WICG/email-verification-protocol',
249
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
250
+ }],
251
+ },
252
+ ],
253
+ [
254
+ Protocol.Audits.EmailVerificationRequestIssueReason.RpOriginIsOpaque,
255
+ {
256
+ file: 'emailVerificationRequestRpOriginIsOpaque.md',
257
+ links: [{
258
+ link: 'https://github.com/WICG/email-verification-protocol',
259
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
260
+ }],
261
+ },
262
+ ],
263
+ [
264
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownMissingAccountsEndpoint,
265
+ {
266
+ file: 'emailVerificationRequestWellKnownMissingAccountsEndpoint.md',
267
+ links: [{
268
+ link: 'https://github.com/WICG/email-verification-protocol',
269
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
270
+ }],
271
+ },
272
+ ],
273
+ [
274
+ Protocol.Audits.EmailVerificationRequestIssueReason.UserLoggedOut,
275
+ {
276
+ file: 'emailVerificationRequestUserLoggedOut.md',
277
+ links: [{
278
+ link: 'https://github.com/WICG/email-verification-protocol',
279
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
280
+ }],
281
+ },
282
+ ],
283
+ [
284
+ Protocol.Audits.EmailVerificationRequestIssueReason.WellKnownAccountsEndpointCrossOrigin,
285
+ {
286
+ file: 'emailVerificationRequestWellKnownAccountsEndpointCrossOrigin.md',
287
+ links: [{
288
+ link: 'https://github.com/WICG/email-verification-protocol',
289
+ linkTitle: i18nLazyString(UIStrings.emailVerification),
290
+ }],
291
+ },
292
+ ],
293
+ ]);
@@ -17,6 +17,7 @@ import {CorsIssue} from './CorsIssue.js';
17
17
  import {CrossOriginEmbedderPolicyIssue, isCrossOriginEmbedderPolicyIssue} from './CrossOriginEmbedderPolicyIssue.js';
18
18
  import {DeprecationIssue} from './DeprecationIssue.js';
19
19
  import {ElementAccessibilityIssue} from './ElementAccessibilityIssue.js';
20
+ import {EmailVerificationRequestIssue} from './EmailVerificationRequestIssue.js';
20
21
  import {FederatedAuthRequestIssue} from './FederatedAuthRequestIssue.js';
21
22
  import {GenericIssue} from './GenericIssue.js';
22
23
  import {HeavyAdIssue} from './HeavyAdIssue.js';
@@ -105,6 +106,10 @@ const issueCodeHandlers = new Map<
105
106
  Protocol.Audits.InspectorIssueCode.ClientHintIssue,
106
107
  ClientHintIssue.fromInspectorIssue,
107
108
  ],
109
+ [
110
+ Protocol.Audits.InspectorIssueCode.EmailVerificationRequestIssue,
111
+ EmailVerificationRequestIssue.fromInspectorIssue,
112
+ ],
108
113
  [
109
114
  Protocol.Audits.InspectorIssueCode.FederatedAuthRequestIssue,
110
115
  FederatedAuthRequestIssue.fromInspectorIssue,
@@ -0,0 +1 @@
1
+ # Email verification request failed because the DNS fetch failed.
@@ -0,0 +1 @@
1
+ # Email verification request failed because the DNS record is invalid.
@@ -0,0 +1 @@
1
+ # Email verification request failed because the email address is invalid.
@@ -0,0 +1 @@
1
+ # Email verification request failed because key binding signing failed.