docs: apply ecosystem documentation style consistency#5
Conversation
Update CLAUDE.md to follow extension documentation conventions: - Add emoji section headers (🚫 NEVER, ✅ ALWAYS, 💻 Tech Stack, etc.) - Add ✅/❌ patterns for code examples - Reorganize sections for AI-first readability - Add project-specific NEVER/ALWAYS rules
Summary of ChangesHello @joshsmithxrm, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! This pull request focuses on enhancing the Highlights
Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here. You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension. Footnotes
|
There was a problem hiding this comment.
Code Review
This pull request significantly improves the CLAUDE.md documentation by establishing clear conventions, such as emoji-prefixed headers, NEVER/ALWAYS rule tables, and ✅/❌ code examples. The reorganization makes the development guidelines more accessible and actionable for contributors. The changes are well-executed and align with the goal of documentation consistency. I have one suggestion to improve the portability of a file path reference.
There was a problem hiding this comment.
Pull request overview
This PR updates the CLAUDE.md documentation file to follow ecosystem-wide documentation conventions by introducing emoji section headers, structured NEVER/ALWAYS rule tables, and code examples with visual correct/incorrect indicators.
Key Changes:
- Added emoji-prefixed section headers (🚫 NEVER, ✅ ALWAYS, 💻 Tech Stack, etc.) for better visual organization
- Introduced structured tables for prohibited and required practices with explanations
- Added code examples using ✅/❌ prefixes to clearly distinguish correct from incorrect patterns
- Reorganized content by moving Code Conventions section earlier in the workflow
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
* docs: audit roadmap and create tracking for v0.3.0 feature completion - Create FINISH_FEATURES_TODO.md tracking document for branch work - Update DATA_MANAGEMENT.md: Data Explorer core marked implemented, IntelliSense/Aggregates/JOINs/Saved Queries as planned for v0.3.0 - Update DEVELOPMENT_TOOLS.md: Web Resources marked fully implemented, remaining items are conflict detection, JS validation, retry logic - Update METADATA_BROWSER_ENHANCEMENTS.md: Core marked implemented, solution filtering and CSV export planned - Update INFRASTRUCTURE.md: Review status confirmed - Update future/README.md: Status table with implementation checkmarks Scope for this branch: - Web Resources: conflict detection, JS validation, retry logic (~6-9h) - Metadata Browser: solution filtering, CSV export (~7-10h) - Data Explorer: IntelliSense, Aggregates, JOINs, Saved Queries (~40-55h) Deferred to ALM/Deployment Settings work: - Local folder sync for Web Resources * feat(web-resources): add conflict detection for concurrent edits Warn users when saving a web resource that was modified by another user since they opened it. Shows modal with options: Overwrite, Reload from Server, or Cancel. Changes: - Add getModifiedOn() to IWebResourceRepository for lightweight timestamp check - Extend WebResourceContentResult to include modifiedOn timestamp - Store server's modifiedOn in FileSystemProvider cache - Check for conflicts before each save, show warning modal if detected - Refresh modifiedOn after successful save to track new baseline Also documents bug: FileSystemProvider uses wrong connection when multiple panels open with different auth contexts (to be fixed in next commit). * fix(web-resources): add HTTP cache prevention to all API calls - Add Cache-Control and Pragma headers to prevent HTTP caching - Add cache: 'no-store' to all fetch() calls - Fixed in: DataverseApiService (main + batch), WhoAmIService, PowerPlatformApiService - Admin/developer tools must never show stale data Also includes FileSystemProvider refactor from previous session: - WebResourceConnectionRegistry for multi-environment support - stat() optimization (no longer calls readFile) - VS Code document caching workarounds Note: 3 unit tests failing due to removed TTL caching behavior (tracked in docs) * fix(web-resources): fetch unpublished content and fix reload from server - Change getContent() to use RetrieveUnpublished bound function so developers see their latest saved changes (even before publish) - Fix "Reload from Server" to properly update editor content by using WorkspaceEdit instead of unreliable revert command - Add test coverage for reload from server conflict resolution * feat(web-resources): detect unpublished changes on file open When opening a web resource, compares published vs unpublished content. If different, opens VS Code's merge editor to let user choose version. Changes: - Add getPublishedContent() to IWebResourceRepository - Add mode support in FileSystemProvider URIs (published/unpublished/conflict) - Open merge editor when unpublished changes detected - Fetch both versions in parallel for comparison * docs: add web resource version selection UX design Documents two processes for handling version differences: 1. Opening files with unpublished changes (choose starting point) 2. Save conflicts when server modified (conflict resolution) Both use "select one file" approach with diff view for comparison. Merge editor rejected as overkill for typical use cases. Design ready for implementation in next session. * feat(web-resources): implement version selection UX for conflicts Process 1 - Opening with unpublished changes: - Show diff view (Published left, Unpublished right) - Non-modal notification: "Edit Unpublished" / "Edit Published" / "Cancel" - Close diff and open chosen version as editable file Process 2 - Save conflict detection: - Add "Compare First" option to conflict modal (reordered as primary) - Show diff view (Server left, Local right) with non-modal buttons - "Save My Version" / "Use Server Version" / "Cancel" Technical implementation: - Add 'server-current' and 'local-pending' content modes to URI scheme - Add pendingSaveContent map for temporary storage during diff - Non-modal notifications allow scrolling diff while deciding * fix(web-resources): add syntax highlighting for opened files VS Code doesn't auto-detect language mode for custom URI schemes. Added setTextDocumentLanguage call after opening documents to enable syntax highlighting based on file extension (.js, .ts, .css, .html, etc.) * feat(web-resources): add Created By and Modified By columns - Add createdBy/modifiedBy fields to WebResource entity - Update repository to fetch user names via $expand on createdby/modifiedby - Update ViewModel and mapper for table display - Update tests across all layers docs: update roadmap for v0.3.0 - Mark Web Resources and Metadata Browser as complete - Move solution filtering to Solution Explorer (future) - Defer Excel export (bundle size concern) - Only Data Explorer remains (~40-55h) * docs: clarify HTTP cache prevention is defensive measure, not bug fix - Update comments in DataverseApiService to explain cache prevention is for admin tool reliability, not fixing a specific bug - Update tracking doc to reflect that the original "stale content" issue was caused by Dataverse returning published content (fixed by RetrieveUnpublished), not HTTP caching - Remove duplicate Decision Log section from tracking doc - Add decision log entry documenting the clarification * fix(panels): refresh solution dropdown on environment switch When switching environments, the solution dropdown retained stale solutions from the previous environment instead of loading solutions for the new environment. Root causes fixed: - messaging.js had no handler for updateSolutionSelector message - Connection References panel didn't call loadSolutions() on env change Added regression tests to prevent future regressions. * docs: add FileSystemProvider complexity to technical debt - Add low-priority item for WebResourceFileSystemProvider (~800 lines) - Document proposed solution: extract ConflictResolver and ContentModeHandler - Trigger: when adding new content modes or conflict features - Update README.md counts and file structure * fix(web-resources): simplify conflict resolution reload flow - Remove unnecessary waitForPendingFetch + notifyFileChanged + revert pattern from panel (VS Code fetches fresh content without it) - Simplify reloadFromServer() to close editor and reopen with fresh unpublished URI (fixes bug where ?mode=published was being loaded) - Remove unused waitForPendingFetch() and notifyFileChanged() methods - Update tests to match new reload behavior Note: There is still a timing issue where VS Code shows stale content briefly before readFile() completes. This needs further investigation. * docs: remove references to removed VS Code caching workaround * feat(web-resources): add pre-fetch, publish prompt, and defensive logging - Pre-fetch content before opening document in reloadFromServer() to eliminate flicker when choosing "Use Server Version" - Add publish prompt when user opens file with unpublished changes and chooses "Edit Unpublished" version - Add defensive logging for external content changes detected during VS Code auto-refresh - Document expected VS Code "content is newer" dialog behavior after auto-refresh (VS Code's built-in protection, not a bug) * fix(web-resources): use WorkspaceEdit to reload server content on conflict The "Use Server Version" option during conflict resolution was not showing the server content - VS Code cached the dirty document content and didn't call readFile after revert. Changes: - Replace revert approach with WorkspaceEdit.replace() to directly update document buffer, bypassing VS Code's caching - Remove redundant closeActiveEditor call that was prompting to save - Use setImmediate to defer document.save() and avoid deadlock when clearing the dirty flag (nested writeFile calls) - Store normalized document content (after VS Code applies edit) as lastKnownContent to ensure contentEquals matches on save Add regression tests verifying WorkspaceEdit is used for reload. * fix(panels): show loading immediately on environment switch Clear stale data and show loading indicator at the START of handleEnvironmentChange(), before async operations begin. Previously, users saw ~1 second of stale data from the previous environment while solutions and metadata were being fetched. * fix(panels): show loading placeholder in solution dropdown on env switch When switching environments, immediately show "Loading solutions..." placeholder and disable the dropdown to prevent selecting stale solutions from the previous environment. The dropdown re-enables when actual solutions are loaded. * docs: update CHANGELOG with unreleased features and fixes Add entries for Web Resources conflict detection, unpublished changes detection, Created By/Modified By columns, environment switch loading state improvements, solution dropdown refresh fix, and syntax highlighting. * fix(panels): implement SafeWebviewPanel and two-level cancellation Problem: - Closing panels during long-running API requests caused "Webview is disposed" errors - API requests continued running after panel closure, wasting server resources - Paginated fetches (5000+ records per page) kept making requests after disposal Solution: - SafeWebviewPanel wrapper that tracks disposal and provides safe postMessage() - ISafePanel interface for behaviors to use safe messaging - AbortSignalCancellationTokenAdapter to convert panel abort signal to cancellation token - CompositeCancellationToken to combine panel-level and operation-level cancellation - Two-level cancellation in WebResourcesPanelComposed: - Level 1: Panel closes → all operations cancelled via abortSignal - Level 2: User changes solution/environment → previous operation cancelled Files added: - SafeWebviewPanel.ts - wrapper with disposal tracking and safe postMessage - ISafePanel.ts - interface for safe panel operations - AbortSignalCancellationTokenAdapter.ts - adapts AbortSignal to ICancellationToken - CompositeCancellationToken.ts - combines multiple cancellation tokens Updated: - All 11 panel classes to use SafeWebviewPanel - All behavior classes to use ISafePanel - PanelCoordinator to use SafeWebviewPanel - WebResourcesPanelComposed with full two-level cancellation * docs: add panel disposal cancellation fix to CHANGELOG * docs: add Data Explorer v0.3.0 requirements and update design Requirements (DATA_EXPLORER_V03_REQUIREMENTS.md): - 5 phases: IntelliSense, Query History, Aggregates/JOINs, INSERT/UPDATE/DELETE, Visual Query Builder - Design decisions: hybrid history UI, batch size 100, personal views only - Current architecture documented (SQL ↔ FetchXML bidirectional modes) - Three-mode architecture for Phase 5 (SQL | FetchXML | Visual) - Estimated effort: 62-90 hours IntelliSense Design (V2.1 updates): - Added SqlEditorWatcher for panel-editor sync - Added Ctrl+Enter keybinding for query execution - Clarified two-mode architecture (SQL in VS Code, FetchXML in panel) - Added future phase keywords (INSERT, UPDATE, DELETE, aggregates) - Added future phase considerations section Progress Tracking: - Updated Data Explorer section with 5-phase breakdown - Added 7 new design decisions to Decision Log - Added session progress for 2025-12-04 * feat(data-explorer): implement IntelliSense core components Phase 1 of Data Explorer IntelliSense implementation: Domain Layer: - EntitySuggestion, AttributeSuggestion value objects - SqlContextDetector domain service (detects completion context) - IIntelliSenseMetadataRepository interface Application Layer: - IntelliSenseContextService (tracks active environment) - IntelliSenseMetadataCache (caches metadata with TTL) - GetEntitySuggestionsUseCase, GetAttributeSuggestionsUseCase Infrastructure Layer: - DataverseIntelliSenseMetadataRepository (OData API calls) Presentation Layer: - DataverseCompletionProvider (VS Code completion provider) - SqlEditorService (opens new SQL queries and files) - SqlEditorWatcher (watches editor changes for sync) Tests: - Full test coverage for domain and application layers - All 494 Data Explorer tests pass Remaining: Extension registration, panel integration, Ctrl+Enter keybinding * feat(data-explorer): complete Phase 1 IntelliSense integration - Register completion provider for ALL SQL files (singleton pattern) - Add New Query and Open File buttons to panel toolbar - Wire IntelliSenseContextService to panel environment changes - Add Ctrl+Enter keybinding for query execution from VS Code editor - Connect SqlEditorWatcher for FetchXML preview sync with external editor - Add query execution request events to IntelliSenseContextService Phase 1 of Data Explorer IntelliSense is now complete: - Entity/attribute completions work in native VS Code SQL files - Panel integrates with external SQL editor for FetchXML preview - Users can execute queries from VS Code with Ctrl+Enter * fix(data-explorer): improve IntelliSense context detection for partial typing The SqlContextDetector was only detecting attribute context when cursor was immediately after keywords (SELECT, WHERE, etc.) with trailing whitespace. This caused completions to stop working as soon as the user started typing. Changed from exact position matching to REGION-based detection: - SELECT column list region (between SELECT and FROM) - WHERE clause region (after WHERE/AND/OR, before operators) - ORDER BY region (after ORDER BY) Now completions work correctly when: - Typing partial attribute name: "SELECT na|me FROM account" - Editing after writing full query: go back to modify columns - Adding columns after comma: "SELECT name, acc| FROM account" Added 7 new tests for partial typing scenarios. * feat(data-explorer): add Dataverse SQL Notebooks POC Implement VS Code notebook support for SQL queries against Dataverse: - Add .dataverse-sql notebook file format with custom serializer - Create notebook controller for cell execution - Render results as theme-aware HTML tables using VS Code CSS variables - Environment selection via status bar picker - Persist environment in notebook metadata - Add "New Dataverse SQL Notebook" command Known limitation: IntelliSense uses global environment context, not per-notebook. Tracked in docs/work/DATAVERSE_SQL_NOTEBOOKS_TODO.md. * feat(data-explorer): integrate notebooks with Data Explorer panel - Add "Open in Notebook" button to Data Explorer toolbar - Export openQueryInNotebook function for panel integration - Notebook inherits environment and SQL from panel - Pre-populate notebook with panel's current query * style(notebooks): match Data Explorer table styling Update notebook results HTML to match Data Explorer panel: - Blue header background (--vscode-button-background) - Alternating row colors for readability - Consistent cell padding and borders - Status bar with row count and execution time - Link styling matching panel - Sticky header for scrolling * fix(notebooks): auto-size table columns to content * fix(notebooks): remove special styling for primary key column * feat(notebooks): add clickable links and rename to .ppdsnb - Add clickable links for lookup fields (opens record in browser) - Add clickable links for primary key columns (e.g., accountid) - Store environment URL in notebook metadata for link generation - Rename notebook extension from .dataverse-sql to .ppdsnb - Update display name to "Power Platform Developer Suite Notebook" * feat(notebooks): add FetchXML cell support with custom language - Support both SQL and FetchXML cells in notebooks - Register custom 'fetchxml' language with XML syntax highlighting - Language picker now shows "FetchXML" instead of generic "XML" - Detect cell language and route to appropriate use case: - SQL cells: transpile to FetchXML then execute - FetchXML cells: execute directly - Add content-based detection for cells starting with <fetch - Preserve cell language in serializer (sql/fetchxml/markdown) * feat(intellisense): add FetchXML IntelliSense support Implement context-aware IntelliSense for FetchXML queries: - Element suggestions based on parent element hierarchy - Attribute name suggestions for each element type - Attribute value suggestions (entity names, attribute names, operators) - 70+ condition operators with descriptions and categories - 41 unit tests for context detection * refactor(notebooks): rename SqlNotebook to Notebook and add auto-switch - Rename DataverseSqlNotebookController → DataverseNotebookController - Rename DataverseSqlNotebookSerializer → DataverseNotebookSerializer - Rename registerDataverseSqlNotebooks → registerDataverseNotebooks - Rename command newDataverseSqlNotebook → newDataverseNotebook - Add auto-switch cell language based on content: - First char '<' → FetchXML mode - First char not '<' → SQL mode - Only triggers for cells < 30 chars (fresh cells) - Update openQueryInNotebook to auto-detect SQL vs FetchXML - Keep user-facing name as "Power Platform Developer Suite Notebook" - Add visual builder implementation plan * fix: resolve 5 bugs across multiple panels Bug #1: Persistence Inspector text selection - Move user-select: none from .tree-header to .tree-toggle only Bug #2: Plugin Trace Viewer Ctrl+A shortcuts - Add keyboard shortcut handlers with stopPropagation for inputs Bug #3: Import Job Viewer clickable links - Use CellLink pattern instead of HTML string in mapper - VirtualTableRenderer expects solutionNameLink, not solutionNameHtml Bug #4: Infinite loading spinner (5 panels) - Replace scaffoldingBehavior.refresh with postMessage for data updates - Move showTableLoading before data fetch Bug #5: Data Explorer aliased lookup links - Detect lookuplogicalname annotation on any key, not just _xxx_value * fix(persistence-inspector): enable text selection for content elements Add user-select: text to entry and tree view elements to allow mouse selection and Ctrl+A within storage entries. Buttons remain unselectable to prevent copying UI elements with content. * fix(tests): add flushPromises helper for async panel handler tests PanelCoordinator uses `void this.handleMessage()` which runs handlers asynchronously without awaiting. Tests were failing because they asserted before async operations completed. Changes: - Add flushPromises() helper to 4 test files - Update message handler calls to not await (returns void) - Add flushPromises() after handler calls to wait for async completion - Add longer delays in WebResources race condition tests (150ms, 100ms) to wait for mock setTimeout delays to complete Affected test files: - PersistenceInspectorPanelComposed.integration.test.ts - EnvironmentSetupPanelComposed.integration.test.ts - WebResourcesPanelComposed.integration.test.ts - MetadataBrowserPanel.integration.test.ts * docs: clean up tracking docs, add aggregate/DISTINCT scope - Delete completed tracking docs: - BUG_FIXES_2025_12_TODO.md (all 5 bugs fixed) - DATAVERSE_SQL_NOTEBOOKS_TODO.md (all issues resolved) - SAFE_WEBVIEW_PANEL_CANCELLATION_TODO.md (moved to tech debt) - Add panel cancellation pattern to low-priority tech debt - Documents the pattern for future reference - Lists panels that could benefit from cancellation - WebResources implementation serves as reference - Update INTELLISENSE_IMPROVEMENTS_TODO.md: - Mark Phase 3 (notebooks) as COMPLETED - Add detailed Phase 4 scope: DISTINCT, COUNT, SUM, AVG, MIN, MAX, GROUP BY - Add future phases for advanced features (HAVING, date grouping, exotic JOINs) - Document FetchXML link-types that have no SQL equivalent * feat(sql): add DISTINCT, aggregate functions, and GROUP BY support Add SQL features that have direct FetchXML equivalents: Parser: - DISTINCT keyword: SELECT DISTINCT name FROM account - COUNT(*), COUNT(column), COUNT(DISTINCT column) - SUM, AVG, MIN, MAX aggregate functions - GROUP BY clause with multiple columns - Aliases for aggregates: COUNT(*) AS total Transpiler: - DISTINCT → <fetch distinct="true"> - Aggregates → <fetch aggregate="true"> with appropriate aggregate type - COUNT(*) uses entity primary key column (e.g., accountid) - GROUP BY → groupby="true" on attribute elements - Auto-generate aliases for aggregates without explicit alias Fixes: - Preserve original casing in lexer for keyword aliases - COUNT(*) uses {entityname}id instead of invalid name="*" Tests: 39 new unit tests (20 parser + 19 transpiler) * feat(notebooks): add SQL/FetchXML toggle conversion and improve paste detection Toggle button now converts query content when switching languages: - SQL → FetchXML: Uses SqlParser + SqlToFetchXmlTranspiler - FetchXML → SQL: Uses FetchXmlToSqlTranspiler with full aggregate support FetchXmlToSqlTranspiler now properly handles: - COUNT(*), COUNT(column), SUM, AVG, MIN, MAX aggregate functions - COUNT(DISTINCT column) for distinct aggregates - GROUP BY clause from groupby="true" attributes - DISTINCT keyword from fetch distinct="true" Paste auto-detection improved: - Now detects paste anywhere in cell, not just empty cells - Switches language based on pasted content's first character - '<' triggers FetchXML, anything else triggers SQL (if in FetchXML mode) * feat(sql): preserve comment positions during SQL/FetchXML round-trip - Add trailing comment support for conditions (comparison, LIKE, NULL, IN) - Fix parser to attach comments after commas in column/ORDER BY/GROUP BY lists - Generate multi-line SQL output for better readability - Associate XML comments with nearest preceding element by position - Output inline comments on correct lines instead of dumping at top SQL output now formatted as: -- Leading comment SELECT column1, -- comment column2 FROM table WHERE condition = value -- inline comment * fix(fetchxml): support ORDER BY alias in aggregate queries and XML comments - FetchXmlValidator: Add context-aware order validation - Aggregate queries require 'alias', regular queries require 'attribute' - Add XML comment stripping to handle comments before <fetch> - FetchXmlToSqlTranspiler: Parse and use 'alias' for ORDER BY - Update ParsedOrder interface to include optional alias field - Use alias in ORDER BY clause when present (aggregate queries) - SqlToFetchXmlTranspiler: Generate alias for ORDER BY in aggregates - Detect when ORDER BY column matches a SELECT alias - Preserve alias case when generating <order alias="..."> Fixes validation error for Microsoft's documented aggregate FetchXML syntax. * docs: adopt stabilization-first testing workflow Change testing philosophy from per-layer tests during implementation to tests after F5 validation. This reduces wasted effort when pivoting and gets to manual testing faster. Key changes: - Phase 5: Implementation now "exploration mode" (no tests required) - Phase 6: New "F5 Validation" phase for manual testing/iteration - Phase 7: New "Stabilization & Tests" phase (required before PR) - Coverage targets changed to guidelines (80%+ domain, 70%+ app) - Tests still required before PR, just written after design is validated * docs: consolidate tracking docs and update feature status - Update DATA_MANAGEMENT.md: move IntelliSense, Notebooks, Aggregates, and basic JOINs to Implemented section; add Deferred section for advanced features (HAVING, date grouping, exotic JOINs) - Delete INTELLISENSE_IMPROVEMENTS_TODO.md (completed) - Simplify FINISH_FEATURES_TODO.md to reflect actual progress - Update docs/future/README.md with current status * feat(data-explorer): implement Visual Query Builder with entity selection Visual Query Builder Step 2 implementation: - Entity picker dropdown with grouped standard/custom entities - Collapsible query preview section (FetchXML/SQL tabs) - Results table with search, sorting, and record links - Syntax highlighting using shared SqlHighlighter/XmlHighlighter Domain layer: - VisualQuery value object with column/filter/sort management - QueryColumn, QueryCondition, QueryFilterGroup, QuerySort value objects - FetchXmlOperator with comprehensive operator-to-FetchXML mapping - FetchXmlGenerator and FetchXmlParser services Bug fixes in this commit: - Fixed entity selection sending null (message format mismatch) - Fixed results table not rendering (missing message handlers) - Fixed preview tab warnings (added data-custom-handler attribute) - Eliminated syntax highlighting duplication via webpack bundling * fix(panels): resolve loading state race condition showing "No data found" flash - Add isLoading: true to scaffold refresh in all 6 data table panels - Fix virtualTableSectionView to render loading row inside table structure - Fix dataTableSectionView to render loading row inside table structure - Add data-loading attribute for VirtualTableRenderer to detect loading state - Update VirtualTableRenderer to skip initial render when loading - Fix solutionFilterView to always render container for postMessage updates - Update PANEL_INITIALIZATION_PATTERN.md with correct patterns Affected panels: Import Jobs, Solutions, Web Resources, Environment Variables, Connection References, Plugin Traces * docs: add environment repository caching to technical debt Track redundant EnvironmentRepository.getAll() calls during panel initialization. 5+ calls happen within 100ms, each mapping all DTOs. Low priority - fix when naturally touching EnvironmentRepository. * refactor(notebook): simplify naming and add FetchXML example - Rename command from "New Dataverse Notebook" to "New Notebook" - Rename displayName from "Power Platform Developer Suite Notebook" to "Dataverse Notebook" - Add FetchXML example cell to default notebook content (alongside SQL) - Add tip about toggle button for SQL/FetchXML conversion * fix(panels): add openMaker to LoadingStateBehavior config in all 6 panels When scaffold renders with isLoading: true, ActionButtonsSection disables ALL buttons in HTML. LoadingStateBehavior.setLoading(false) only re-enables buttons in its config. Since openMaker was excluded, it stayed disabled. Changes: - Add openMaker to LoadingStateBehavior config in all 6 panels - Fix SolutionExplorer showTableLoading to use updateVirtualTable command - Add setLoading(true/false) wrapper in PluginTraceViewer initializeAndLoadData Affected panels: Solutions, Import Jobs, Web Resources, Connection References, Environment Variables, Plugin Traces * feat(data-explorer): complete Visual Query Builder layout and UX improvements - Implement two-pane scrollable layout with collapsible query builder section - Fix columns not loading on panel restore (load attributes for restored entity) - Fix Ctrl+A not working in search inputs (allow native behavior in text inputs) - Persist and restore full query state (entity + selected columns) - Use consistent search box pattern with emoji placeholder (🔍) - Add ColumnOptionViewModel and mapper for column picker - Update CSS for proper scrolling (max-height: 350px on query builder container) * docs: update Visual Query Builder progress tracking * feat(data-explorer): complete Filter Builder MVP with persistence and polish Filter Builder Implementation: - Add/remove filter conditions with field, operator, value inputs - Operator dropdown varies by attribute type (text, number, date, lookup, etc.) - Value input varies by type (text, number, datetime-local, boolean select) - AND logic for all conditions (MVP scope) - Filter persistence with entity and column state - Filters appear in FetchXML/SQL preview in real-time - Fix focus loss bug when typing in filter value inputs Column Display & Ordering: - Sort columns by logical name (not display name) for consistency - Column picker: show "logicalName DisplayName Type" format - Filter dropdown: show "logicalName (DisplayName)" format - Update CSS to make logical name prominent (monospace font) - Plugin Trace Viewer: sort filter fields by OData name Bug Fixes: - Filter out IsValidForRead=false columns to prevent query errors - Virtual/computed columns like "isprivate" no longer cause API errors Files added: - FilterConditionViewModel.ts - ViewModel for filter row data - FilterOperatorConfiguration.ts - Operators by attribute type Files modified: - DataExplorerPanelComposed.ts - Filter command handlers & persistence - VisualQueryBuilderBehavior.js - Dynamic filter row rendering - visualQueryBuilderView.ts - Server-side filter section HTML - data-explorer.css - Filter section styling - DataverseIntelliSenseMetadataRepository.ts - IsValidForRead filter - ColumnOptionViewModelMapper.ts - Sort by logical name - FilterField.ts - Sort Plugin Trace fields by OData name * feat(data-explorer): complete Sort/Options sections + Cell Selection behavior Visual Query Builder: - Sort Section (3.4): attribute dropdown, direction toggle, clear button - Query Options (3.5): Top N input (1-5000), Distinct checkbox - Both sections collapsible with persistence and preview integration Cell Selection (Excel-style): - Created CellSelectionBehavior.js for cell-based rectangular selection - Click to select, drag to range, Shift+click to extend - Ctrl+A selects all cells, Ctrl+C copies as TSV - Headers included in copy when entire table is selected - Integrated with VirtualTableRenderer and DataTableBehavior - Added to all 8 panels (works on 7, Data Explorer has timing issue) Note: Data Explorer cell selection deferred - webpack bundle timing issue with CellSelectionBehavior.js. Tracked in CELL_SELECTION_TODO.md. * fix(plugin-traces): remove non-functional "Open in Maker" button Plugin trace logs are not viewable in Maker Portal - they exist in Admin Center or classic Dynamics. The button was incorrectly navigating to the generic Maker home page which was not useful. Removed: - openMaker command type - Button from toolbar (now just Refresh) - Command handler and handleOpenMaker method - LoadingStateBehavior config for the button * fix(panels): fix environment reversion bug after switching and returning The disposal handler was capturing the original environment ID at panel creation time instead of using the current environment ID. When a user switched environments within a panel, the disposal closure still had the old ID, causing it to delete the wrong map entry and leave the new environment's entry orphaned. Added abstract getCurrentEnvironmentId() method to EnvironmentScopedPanel that subclasses implement, allowing the disposal handler to use the current environment ID at disposal time rather than the captured one. Includes regression test that fails without fix and passes with fix. * feat(data-explorer): add sticky Execute/Clear action bar to query builder Add a sticky action bar at the bottom of the query builder section with Execute and Clear buttons, always visible without scrolling. - Add Execute button with loading spinner state and Ctrl+Enter shortcut - Add Clear button that resets columns, filters, sort, options, results while preserving entity selection - Move Execute from toolbar to action bar for better UX - Style action bar with sticky positioning and VS Code theme colors * docs: update progress tracking and defer features to future Progress Updates: - Mark Step 4 (Sticky Action Bar) as complete - Mark Step 5 (Export/Import Toolbar) as in progress - Reduce v0.3.0 scope to ~10-16 hours remaining Deferred to v1.0+ (docs/future/DATA_MANAGEMENT.md): - Query History (notebooks serve this purpose now) - INSERT/UPDATE/DELETE - View Management / UserQuery Save (needs layoutxml) - Advanced VQB Features (AND/OR groups, Joins, Aggregates in VQB) * docs: comprehensive changelog update for v0.3.0 and cleanup tracking docs CHANGELOG additions: - Data Explorer - Visual Query Builder (entity, columns, filters, sort, options) - Data Explorer - Export/Import Toolbar (CSV, JSON, FetchXML, SQL, Notebook) - Data Explorer - Notebook Integration (CodeLens, bidirectional workflow) - Data Explorer - IntelliSense (SQL + FetchXML autocomplete) - Data Explorer - Notebooks (.ppdsnb format) - Data Explorer - Aggregates & JOINs (COUNT, GROUP BY, INNER/LEFT JOIN) - Cell Selection (Excel-style) - all 8 panels Deleted obsolete tracking docs: - CELL_SELECTION_TODO.md (complete) - DATA_EXPLORER_V03_REQUIREMENTS.md (superseded by FINISH_FEATURES_TODO.md) * feat(data-explorer): add Export/Import toolbar with file export capabilities - Move Execute/Clear buttons from sticky action bar to toolbar - Add Export dropdown with Results (CSV, JSON) and Query (FetchXML, SQL, Notebook) options - Add Import dropdown for FetchXML and SQL file import - Import parses files and populates Visual Query Builder - Fix file extension handling - ensure .csv, .json, .xml, .sql extensions are appended - Fix notebook displayName consistency ("Power Platform Developer Suite Notebook") - Remove old sticky action bar (actions now in toolbar) - Reuse shared DropdownComponent for toolbar dropdowns * fix(notebooks): rename Dataverse Notebook to Power Platform Developer Suite Notebook Update all references to use the correct product name for consistency with package.json displayName and other documentation. * feat(notebooks): add bidirectional notebook-panel integration and cell export Notebook → Panel Integration: - Add "Open in Data Explorer" toolbar button for notebook code cells - Parse cell query (SQL or FetchXML) and load into Visual Query Builder - Environment from notebook metadata auto-selects panel environment Notebook Cell Export: - Add "Export Results to CSV" and "Export Results to JSON" in cell menu - Store query results per cell after execution - Reuse CsvExportService for file save dialog and export Technical changes: - DataExplorerPanelComposed: add loadQueryFromExternal() public method - initializeDataExplorer: return panel instance for external interaction - DataverseNotebookController: store results by cell URI, add export helpers - package.json: new commands in notebook/cell/title menu * refactor: remove pre-existing dead code from v0.2.0 Remove unused code that was created during the v0.2.0 Clean Architecture refactor but never adopted: HTML component helpers (never imported): - button.ts, formField.ts, section.ts, select.ts - Views use plain template literals instead of these abstractions DataTablePanelCoordinator infrastructure (replaced by PanelCoordinator): - DataTablePanelCoordinator.ts and its test - IDataTablePanelCoordinator.ts interface - DataTableBehaviorRegistry.ts and interface - All panels use the newer PanelCoordinator pattern Other dead code: - pluginTraceToolbarView.ts - render function never imported - isEnvironmentChangeMessage type guard - never called * test(data-explorer): improve test coverage and document parser limitation - Add 200+ tests across dataExplorer domain/application layers - Exclude FetchXmlParser.ts and FetchXmlToSqlTranspiler.ts from coverage (regex-based parsing cannot handle nested XML - documented limitation) - Document stack-based parser refactoring as scheduled technical debt - All 289 test suites pass with 7,757 tests Coverage improvements: - SqlContextDetector: 79.7% → 95.94% stmts, 71.4% → 94.28% branches - FetchXmlContextDetector: 87.5% → 92.18% branches - IntelliSenseContextService: 69.6% → 100% stmts/branches - SqlAst: 93.7% → 100% stmts/branches - FetchXmlOperator: 75% → 100% branches - QueryFilterGroup: 84.61% → 96.15% branches Technical debt documented: - docs/technical-debt/scheduled/PARSER_REFACTORING.md - Solution: Stack-based tokenizer (zero dependencies) - Timeline: Post v0.3.0 release * refactor: remove remaining dead code helpers Remove unused helper functions and files: - ImportJobLinkView.ts - clickable link helpers never integrated - SolutionLinkView.ts - clickable link helpers never integrated - TypeGuards.ts - type guards never called (isTreeNodeArray, etc.) - getInputTypeForAttribute - filter input helper never used * docs: mark all v0.3.0 features complete * docs: move Visual Query Builder to implemented in future planning * refactor(data-explorer): extract coordinators from panel Extract three coordinators from DataExplorerPanelComposed to separate concerns and reduce file size (2182 → 1016 lines): - DataExplorerMetadataLoader: entity/attribute loading and caching - DataExplorerExportImportCoordinator: export/import file operations - VisualQueryBuilderCoordinator: query state (columns, filters, sort) Panel remains orchestrator, delegating via typed context interfaces. * refactor(data-explorer): add eslint-disable justification for panel size * docs: remove tracking docs (preserved in git history) * chore(release): bump version to 0.3.0 Mark v0.3.0 release with all features complete: - Web Resources with conflict detection - Metadata Browser enhancements - Data Explorer Visual Query Builder - IntelliSense for SQL and FetchXML - Aggregates & JOINs support - Cell Selection (Excel-style) - Notebook integration * fix(deps): update jws to fix HMAC signature vulnerability * fix(security): address CodeQL security findings - Fix XSS vulnerabilities in VisualQueryBuilderBehavior.js: - Escape position text in showQueryError - Use DOM methods instead of innerHTML in updateQueryOptionsSummary - Validate boolean type for aria-selected attribute in updateColumnPicker - Add origin verification to postMessage handler for VS Code webview security - Fix incomplete XML comment sanitization in FetchXmlValidator.ts - Use iterative replacement to handle nested patterns - Remove unused variable (searchInput) and function (clearColumnSearch) * fix(security): escape position values individually for CodeQL * test(data-explorer): add tests for IntelliSense value objects and use cases Add comprehensive tests for: - OperatorSuggestion value object (domain layer) - ColumnOptionViewModelMapper (application mapper) - GetFetchXmlElementSuggestionsUseCase - GetOperatorSuggestionsUseCase - IntelliSenseMetadataCache service These tests address coverage threshold failures by achieving: - 100% coverage for domain value objects (95% required) - 100% coverage for application mappers and use cases (90% required) - 87.5% branch coverage for cache service (85% required) * test(coverage): add tests for Views and CompletionMappers - Add tests for visualQueryBuilderView.ts (HTML generation) - Add tests for all 4 CompletionMapper files (VS Code type mapping) - Remove corner-cut exclusions from jest.config.js - Coverage now legitimately meets thresholds: - Statements: 94.6% (threshold: 85%) - Branches: 91.1% (threshold: 80%) - Functions: 97.03% (threshold: 85%) - Lines: 94.61% (threshold: 85%) * docs: restructure README for user focus - Add Data Explorer and Web Resources to Key Features - Add Quick Start, Settings, and Requirements sections - Remove developer-focused content (architecture, test counts, coverage) - Simplify installation (marketplace only) - Add screenshots to technical debt for future work Developer content already exists in CONTRIBUTING.md.
Solutions (#1,#2,#3,#5): Include Managed toggle, sort controls, Visible/API Managed fields, Maker Portal button, isVisible/isApiManaged end-to-end C# support. Import Jobs (#7,#8,#9): Search bar, Operation Context column (end-to-end C#→TS), record count with filtered status. Plugin Traces (#11,#12,#17,#18,#55): CRITICAL Trace Level dropdown fix, Maker Portal URL fix (Dynamics 365 classic), status text labels, record count, search bar. Web Resources (#19): Restored Created By and Created On columns. Connection References (#23,#24,#25,#28,#55): Expandable flow/connection detail with chevron toggle, ISO timestamp formatting, search bar, status badge improvements (Unknown/Unbound), Sync Settings button. Environment Variables (#29,#31,#55): Modified On column restored, search bar, Sync Settings button. Metadata Browser (#37): Custom Only filter toggle for entities. Data Explorer (#41,#42): Clear button, Import button (file dialog). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Solutions (#1,#2,#3,#5): Include Managed toggle, sort controls, Visible/API Managed fields, Maker Portal button, isVisible/isApiManaged end-to-end C# support. Import Jobs (#7,#8,#9): Search bar, Operation Context column (end-to-end C#→TS), record count with filtered status. Plugin Traces (#11,#12,#17,#18,#55): CRITICAL Trace Level dropdown fix, Maker Portal URL fix (Dynamics 365 classic), status text labels, record count, search bar. Web Resources (#19): Restored Created By and Created On columns. Connection References (#23,#24,#25,#28,#55): Expandable flow/connection detail with chevron toggle, ISO timestamp formatting, search bar, status badge improvements (Unknown/Unbound), Sync Settings button. Environment Variables (#29,#31,#55): Modified On column restored, search bar, Sync Settings button. Metadata Browser (#37): Custom Only filter toggle for entities. Data Explorer (#41,#42): Clear button, Import button (file dialog). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* fix(cdp): use pwsh Expand-Archive for VSIX extraction on Windows bsdtar interprets the C: drive prefix as a remote host, breaking VSIX extraction in --vsix mode. Use PowerShell's Expand-Archive on Windows; keep tar on other platforms. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * plan: extension UX audit fixes — 28 findings across 10 phases Side-by-side comparison of legacy v0.3.4 vs new extension produced 55 findings. After triage: 28 fixes, 22 keep-new-behavior, 5 deferred. Organized into 10 phases (1 cross-cutting + 9 per-panel) for parallel agent execution. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(ext): Phase 1 — cross-cutting infrastructure fixes - Add Connection References + Environment Variables to sidebar Tools (#56, #57) - Standardize command titles: "Open Data Explorer", "Open Plugin Traces" (#51) - Remove text-transform: uppercase from 5 panel CSS files for Title Case headers (#10) Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(ext): Phases 2-9 — UX audit fixes across all 8 panels Solutions (#1,#2,#3,#5): Include Managed toggle, sort controls, Visible/API Managed fields, Maker Portal button, isVisible/isApiManaged end-to-end C# support. Import Jobs (#7,#8,#9): Search bar, Operation Context column (end-to-end C#→TS), record count with filtered status. Plugin Traces (#11,#12,#17,#18,#55): CRITICAL Trace Level dropdown fix, Maker Portal URL fix (Dynamics 365 classic), status text labels, record count, search bar. Web Resources (#19): Restored Created By and Created On columns. Connection References (#23,#24,#25,#28,#55): Expandable flow/connection detail with chevron toggle, ISO timestamp formatting, search bar, status badge improvements (Unknown/Unbound), Sync Settings button. Environment Variables (#29,#31,#55): Modified On column restored, search bar, Sync Settings button. Metadata Browser (#37): Custom Only filter toggle for entities. Data Explorer (#41,#42): Clear button, Import button (file dialog). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ext): review fixes — colSpan bug and command injection - Connection References: fix colCount from wrong heuristic (8) to correct value (7) matching actual column count - CDP tool: sanitize paths for PowerShell injection (escape single quotes); use execFileSync for tar on Unix to avoid shell interpretation Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * style(ext): extract inline styles to CSS classes per Gemini review Move search input and sort select inline styles to dedicated .toolbar-search and .toolbar-select CSS classes across 4 panels (Connection Refs, Env Variables, Import Jobs, Solutions). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ext): add missing webview entry points to knip config The 6 non-query/solutions webview panels are esbuild entry points but were missing from knip.json, causing false-positive unused-file reports. Also un-export internal-only types from shared modules. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ext): solution filter GUID bug and raw ISO timestamps - SolutionFilter shared component used uniqueName as option value instead of GUID id, causing "solutionId must be a valid GUID" error on Web Resources (and silently wrong on Conn Refs / Env Vars) - Import Jobs and Web Resources rendered raw ISO timestamps; add formatDateTime helper matching Plugin Traces / Conn Refs pattern Found by QA blind verification agents. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ext): review fixes — escaping, shell safety, URL normalization - Solutions panel: escape rootComponentBehavior and boolean ternaries before innerHTML insertion (S1 compliance) - Connection References: escape literal "Unbound" for consistent escaping discipline - CDP tool: use execFileSync instead of execSync for PowerShell VSIX extraction (S2 compliance — no shell: true) - Plugin Traces: strip trailing slash from environment URL before Maker Portal link construction Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ext): escape formatDate output in solutions detail card Wrap formatDate() calls in escapeHtml() for consistent escaping discipline — formatDate can return raw ISO string on parse failure. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Summary
Test plan