@@ -138,12 +138,29 @@ async function postJSON(url, body) {
138138 return res . json ( ) ;
139139}
140140
141- async function sendToChat ( prompt , refresh ) {
141+ function recordAction ( action , resourceKind ) {
142+ const body = resourceKind ? { action, resourceKind } : { action } ;
143+ void fetch ( "/api/telemetry/action" , {
144+ method : "POST" ,
145+ headers : { "Content-Type" : "application/json" } ,
146+ body : JSON . stringify ( body ) ,
147+ keepalive : true ,
148+ } ) . catch ( ( ) => {
149+ /* telemetry must not affect the Canvas interaction */
150+ } ) ;
151+ }
152+
153+ async function sendToChat ( prompt , refresh , resourceKind ) {
142154 try {
155+ const body = {
156+ prompt,
157+ ...( refresh ? { refresh } : { } ) ,
158+ ...( resourceKind ? { resourceKind } : { } ) ,
159+ } ;
143160 const res = await fetch ( "/api/send" , {
144161 method : "POST" ,
145162 headers : { "Content-Type" : "application/json" } ,
146- body : JSON . stringify ( refresh ? { prompt , refresh } : { prompt } ) ,
163+ body : JSON . stringify ( body ) ,
147164 } ) ;
148165 if ( ! res . ok ) throw new Error ( "HTTP " + res . status ) ;
149166 toast ( "Sent to chat \u2713" ) ;
@@ -235,17 +252,39 @@ function renderBuild() {
235252 operatingSystem : detectOperatingSystem ( ) ,
236253 pluginVersion : state . pluginVersion ,
237254 } ) ;
255+ issueLink . addEventListener ( "click" , ( ) => recordAction ( "report_issue" ) ) ;
238256 }
239257
240258 // Set portal links for "Deploy new model" / "Add or update toolbox" / "Create new skill" / "Create new guardrail".
241259 const modelLink = node . querySelector ( "#deployNewModelLink" ) ;
242260 const toolLink = node . querySelector ( "#addToolboxLink" ) ;
243261 const skillLink = node . querySelector ( "#createSkillLink" ) ;
244262 const guardrailLink = node . querySelector ( "#createGuardrailLink" ) ;
245- if ( modelLink ) modelLink . addEventListener ( "click" , ( ) => { closeModelMenu ( ) ; openPortalPage ( "build/models/deployments" ) ; } ) ;
246- if ( toolLink ) toolLink . addEventListener ( "click" , ( ) => { closeToolMenu ( ) ; openPortalPage ( "build/tools?tab=toolboxes" ) ; } ) ;
247- if ( skillLink ) skillLink . addEventListener ( "click" , ( ) => { closeSkillMenu ( ) ; openPortalPage ( "build/tools?tab=skills" ) ; } ) ;
248- if ( guardrailLink ) guardrailLink . addEventListener ( "click" , ( ) => { closeGuardrailMenu ( ) ; openPortalPage ( "build/guardrails/list" ) ; } ) ;
263+ if ( modelLink ) modelLink . addEventListener ( "click" , ( ) => {
264+ recordAction ( "open_foundry_creation_link" , "model" ) ;
265+ closeModelMenu ( ) ;
266+ openPortalPage ( "build/models/deployments" ) ;
267+ } ) ;
268+ if ( toolLink ) toolLink . addEventListener ( "click" , ( ) => {
269+ recordAction ( "open_foundry_creation_link" , "toolbox" ) ;
270+ closeToolMenu ( ) ;
271+ openPortalPage ( "build/tools?tab=toolboxes" ) ;
272+ } ) ;
273+ if ( skillLink ) skillLink . addEventListener ( "click" , ( ) => {
274+ recordAction ( "open_foundry_creation_link" , "project_skill" ) ;
275+ closeSkillMenu ( ) ;
276+ openPortalPage ( "build/tools?tab=skills" ) ;
277+ } ) ;
278+ if ( guardrailLink ) guardrailLink . addEventListener ( "click" , ( ) => {
279+ recordAction ( "open_foundry_creation_link" , "guardrail" ) ;
280+ closeGuardrailMenu ( ) ;
281+ openPortalPage ( "build/guardrails/list" ) ;
282+ } ) ;
283+ const playgroundLink = node . querySelector ( "#testPlaygroundLink" ) ;
284+ if ( playgroundLink ) {
285+ playgroundLink . addEventListener ( "click" , ( ) =>
286+ recordAction ( "test_in_foundry_portal" , "agent" ) ) ;
287+ }
249288
250289 root . replaceChildren ( node ) ;
251290
@@ -506,6 +545,7 @@ function renderHostedAgentPicker() {
506545
507546 item . addEventListener ( "click" , ( ) => {
508547 closeHostedAgentMenu ( ) ;
548+ recordAction ( "switch_agent" , "agent" ) ;
509549 selectHostedAgent ( agent . agentName ) ;
510550 } ) ;
511551 list . appendChild ( item ) ;
@@ -558,7 +598,7 @@ async function refreshHostedAgentsAfterSession() {
558598 const added = workspaceHostedAgentOptions ( ) . filter (
559599 ( agent ) => ! previousNames . has ( agent . agentName . toLowerCase ( ) ) ,
560600 ) ;
561- if ( added . length === 1 ) await selectHostedAgent ( added [ 0 ] . agentName ) ;
601+ if ( added . length === 1 ) await selectHostedAgent ( added [ 0 ] . agentName , { created : true } ) ;
562602}
563603
564604function showNewAgent ( prompt = "" ) {
@@ -575,6 +615,7 @@ function showNewAgent(prompt = "") {
575615}
576616
577617async function selectHostedAgent ( agentName ) {
618+ const created = arguments [ 1 ] ?. created === true ;
578619 const previous = state . hostedAgents . selected ;
579620 const wasCreatingNew = state . hostedAgents . creatingNew === true ;
580621 if ( ! agentName || ( agentName === previous && ! wasCreatingNew ) ) return ;
@@ -600,7 +641,7 @@ async function selectHostedAgent(agentName) {
600641 return ;
601642 }
602643 try {
603- await postJSON ( "/api/select-hosted-agent" , { agentName } ) ;
644+ await postJSON ( "/api/select-hosted-agent" , { agentName, created } ) ;
604645 } catch {
605646 state . hostedAgents . selected = previous ;
606647 state . hostedAgents . creatingNew = wasCreatingNew ;
@@ -965,7 +1006,8 @@ function renderDeployList() {
9651006
9661007 item . addEventListener ( "click" , ( ) => {
9671008 closeModelMenu ( ) ;
968- sendToChat ( withActionContext ( m . prompt ) ) ;
1009+ recordAction ( "switch_model" , "model" ) ;
1010+ sendToChat ( withActionContext ( m . prompt ) , "" , "model" ) ;
9691011 } ) ;
9701012 host . appendChild ( item ) ;
9711013 }
@@ -1028,7 +1070,8 @@ function renderToolboxList() {
10281070 use . addEventListener ( "click" , ( e ) => {
10291071 e . stopPropagation ( ) ;
10301072 closeToolMenu ( ) ;
1031- sendToChat ( withActionContext ( t . prompt ) ) ;
1073+ recordAction ( "connect_toolbox" , "toolbox" ) ;
1074+ sendToChat ( withActionContext ( t . prompt ) , "" , "toolbox" ) ;
10321075 } ) ;
10331076 item . append ( toggle , use ) ;
10341077
@@ -1105,7 +1148,8 @@ function renderGuardrailList() {
11051148
11061149 item . addEventListener ( "click" , ( ) => {
11071150 closeGuardrailMenu ( ) ;
1108- sendToChat ( withActionContext ( g . prompt ) ) ;
1151+ recordAction ( "apply_guardrail" , "guardrail" ) ;
1152+ sendToChat ( withActionContext ( g . prompt ) , "" , "guardrail" ) ;
11091153 } ) ;
11101154 host . appendChild ( item ) ;
11111155 }
@@ -1143,7 +1187,8 @@ function renderSkillList() {
11431187
11441188 item . addEventListener ( "click" , ( ) => {
11451189 closeSkillMenu ( ) ;
1146- sendToChat ( withActionContext ( s . prompt ) ) ;
1190+ recordAction ( "add_project_skill" , "project_skill" ) ;
1191+ sendToChat ( withActionContext ( s . prompt ) , "" , "project_skill" ) ;
11471192 } ) ;
11481193 host . appendChild ( item ) ;
11491194 }
@@ -1678,6 +1723,7 @@ function renderSubList() {
16781723}
16791724
16801725async function selectSubscription ( s ) {
1726+ recordAction ( "select_subscription" , "subscription" ) ;
16811727 const previousProject = state . selection . project ?. endpoint || "" ;
16821728 const next = transitionSubscription ( state . selection , s ) ;
16831729 try {
@@ -1754,6 +1800,7 @@ function renderProjList() {
17541800}
17551801
17561802async function selectProject ( p ) {
1803+ recordAction ( "select_project" , "project" ) ;
17571804 const subscription = state . selection . subscription ;
17581805 const next = transitionProject ( state . selection , {
17591806 subscriptionId : p . subscriptionId || subscription . id ,
@@ -1888,7 +1935,8 @@ root.addEventListener("click", async (e) => {
18881935 state . hostedAgents . creatingNew = true ;
18891936 renderHostedAgentPicker ( ) ;
18901937 renderHostedAgentDeployment ( ) ;
1891- sendToChat ( withActionContext ( text ) ) ;
1938+ recordAction ( "start_agent_creation" , "agent" ) ;
1939+ sendToChat ( withActionContext ( text ) , "" , "agent" ) ;
18921940 showBuildSections ( ) ;
18931941 }
18941942 return ;
@@ -1916,6 +1964,7 @@ root.addEventListener("click", async (e) => {
19161964 return ;
19171965 }
19181966 if ( e . target . closest ( "#deployRefresh" ) ) {
1967+ recordAction ( "refresh_resources" , "model" ) ;
19191968 loadDeployments ( true ) ;
19201969 return ;
19211970 }
@@ -1925,6 +1974,7 @@ root.addEventListener("click", async (e) => {
19251974 return ;
19261975 }
19271976 if ( e . target . closest ( "#toolboxRefresh" ) ) {
1977+ recordAction ( "refresh_resources" , "toolbox" ) ;
19281978 loadToolboxes ( true ) ;
19291979 return ;
19301980 }
@@ -1934,6 +1984,7 @@ root.addEventListener("click", async (e) => {
19341984 return ;
19351985 }
19361986 if ( e . target . closest ( "#guardrailRefresh" ) ) {
1987+ recordAction ( "refresh_resources" , "guardrail" ) ;
19371988 loadGuardrails ( true ) ;
19381989 return ;
19391990 }
@@ -1943,10 +1994,12 @@ root.addEventListener("click", async (e) => {
19431994 return ;
19441995 }
19451996 if ( e . target . closest ( "#skillRefresh" ) ) {
1997+ recordAction ( "refresh_resources" , "project_skill" ) ;
19461998 loadSkills ( true ) ;
19471999 return ;
19482000 }
19492001 if ( e . target . closest ( "#newHostedAgentBtn" ) ) {
2002+ recordAction ( "create_agent" , "agent" ) ;
19502003 showNewAgent ( ) ;
19512004 return ;
19522005 }
@@ -1959,11 +2012,17 @@ root.addEventListener("click", async (e) => {
19592012 return ;
19602013 }
19612014 if ( e . target . closest ( "#pmAuthBtn" ) ) {
1962- if ( state . identity . signedIn ) doSignOut ( ) ;
1963- else startSignIn ( ) ;
2015+ if ( state . identity . signedIn ) {
2016+ recordAction ( "sign_out" ) ;
2017+ doSignOut ( ) ;
2018+ } else {
2019+ recordAction ( "sign_in" ) ;
2020+ startSignIn ( ) ;
2021+ }
19642022 return ;
19652023 }
19662024 if ( e . target . closest ( "#createProjectLink" ) ) {
2025+ recordAction ( "open_foundry_creation_link" , "project" ) ;
19672026 closeProjectMenu ( ) ;
19682027 openFoundryHome ( ) ;
19692028 return ;
@@ -2001,13 +2060,15 @@ root.addEventListener("click", async (e) => {
20012060 return ;
20022061 }
20032062 resetHostedAgentDeployment ( ) ;
2004- sendToChat ( withActionContext ( state . deployPrompt ) , "deployment" ) ;
2063+ recordAction ( "deploy_to_foundry" , "agent" ) ;
2064+ sendToChat ( withActionContext ( state . deployPrompt ) , "deployment" , "agent" ) ;
20052065 return ;
20062066 }
20072067 if ( e . target . closest ( "#inspectBtn" ) ) {
20082068 if ( state . hostedAgents . creatingNew ) {
20092069 toast ( "Select an existing agent to inspect locally." ) ;
20102070 } else {
2071+ recordAction ( "inspect_locally" , "agent" ) ;
20112072 launchInspector ( e . target . closest ( "#inspectBtn" ) ) ;
20122073 }
20132074 return ;
0 commit comments