@@ -466,6 +466,7 @@ document.addEventListener('DOMContentLoaded', function() {
466466 document . getElementById ( 'save' ) ?. addEventListener ( 'click' , saveUrl ) ;
467467 document . getElementById ( 'refresh' ) ?. addEventListener ( 'click' , refreshIcal ) ;
468468 document . getElementById ( 'refresh-debug' ) ?. addEventListener ( 'click' , requestDebugInfo ) ;
469+ document . getElementById ( 'export-diagnostics' ) ?. addEventListener ( 'click' , requestDiagnostics ) ;
469470
470471 // Auto-save on settings changes
471472 const settingsInputs = [ 'timeWindow' , 'excludeAllDay' , 'titleDisplayDuration' , 'flashOnMeetingStart' , 'orangeThreshold' , 'redThreshold' ] ;
@@ -489,6 +490,45 @@ document.addEventListener('DOMContentLoaded', function() {
489490 requestDebugInfo ( ) ;
490491} ) ;
491492
493+ /**
494+ * Request diagnostic report from plugin and copy to clipboard
495+ */
496+ function requestDiagnostics ( ) {
497+ const opener = getOpener ( ) ;
498+ console . log ( '[SETUP] requestDiagnostics called' ) ;
499+
500+ const btn = document . getElementById ( 'export-diagnostics' ) ;
501+ if ( btn ) {
502+ btn . textContent = '⏳ Generating...' ;
503+ btn . disabled = true ;
504+ }
505+
506+ if ( opener && opener . websocket ) {
507+ const json = {
508+ event : 'sendToPlugin' ,
509+ action : opener . actionInfo ?. action || 'com.pedrofuentes.ical.combined' ,
510+ context : opener . uuid ,
511+ payload : { action : 'getDiagnostics' }
512+ } ;
513+ opener . websocket . send ( JSON . stringify ( json ) ) ;
514+
515+ // Timeout fallback in case the plugin doesn't respond
516+ setTimeout ( ( ) => {
517+ if ( btn && btn . disabled ) {
518+ btn . textContent = '📋 Export Diagnostics' ;
519+ btn . disabled = false ;
520+ showAlert ( 'No response from plugin. Is the plugin running?' ) ;
521+ }
522+ } , 5000 ) ;
523+ } else {
524+ if ( btn ) {
525+ btn . textContent = '📋 Export Diagnostics' ;
526+ btn . disabled = false ;
527+ }
528+ showAlert ( 'Error: Cannot communicate with plugin.' ) ;
529+ }
530+ }
531+
492532/**
493533 * Request debug info from plugin
494534 */
@@ -578,6 +618,41 @@ function handlePluginMessage(message) {
578618 }
579619 }
580620 }
621+
622+ if ( message && message . action === 'diagnosticReport' ) {
623+ const btn = document . getElementById ( 'export-diagnostics' ) ;
624+ const text = message . data && message . data . text ;
625+ if ( text ) {
626+ // Copy to clipboard
627+ navigator . clipboard . writeText ( text ) . then ( ( ) => {
628+ if ( btn ) {
629+ btn . textContent = '✅ Copied!' ;
630+ btn . disabled = false ;
631+ setTimeout ( ( ) => { btn . textContent = '📋 Export Diagnostics' ; } , 3000 ) ;
632+ }
633+ showAlert ( 'Diagnostics copied to clipboard! Paste into a GitHub issue.' , 'notice' , 5 ) ;
634+ } ) . catch ( ( ) => {
635+ // Fallback: open in a new window
636+ const w = window . open ( '' , '_blank' , 'width=700,height=500' ) ;
637+ if ( w ) {
638+ w . document . write ( '<pre style="white-space:pre-wrap;font-size:12px;">' +
639+ text . replace ( / & / g, '&' ) . replace ( / < / g, '<' ) + '</pre>' ) ;
640+ w . document . title = 'Diagnostic Report' ;
641+ }
642+ if ( btn ) {
643+ btn . textContent = '📋 Export Diagnostics' ;
644+ btn . disabled = false ;
645+ }
646+ showAlert ( 'Clipboard not available. Report opened in a new window.' , 'notice' , 5 ) ;
647+ } ) ;
648+ } else {
649+ if ( btn ) {
650+ btn . textContent = '📋 Export Diagnostics' ;
651+ btn . disabled = false ;
652+ }
653+ showAlert ( 'No diagnostic data received.' ) ;
654+ }
655+ }
581656}
582657
583658// Listen for messages from opener window
0 commit comments