diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1f999e77..f10f250d 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -5,6 +5,67 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+## [2.0.0] - 2026-02-25
+
+### Important
+
+- **Schema upgrade**: The `collect.memory_grant_stats` table gains new delta columns and drops unused warning columns. The `collect.session_wait_stats` table, its collector procedure, reporting view, and schedule entry are removed (zero UI coverage). Upgrade scripts run automatically via the CLI/GUI installer and use idempotent checks.
+
+### Added
+
+- **Graphical query plan viewer** — native ShowPlan rendering in both Dashboard and Lite with SSMS-parity operator icons, properties panel, tooltips, warning/parallelism badges, and tabbed plan display ([#220])
+- **Actual execution plan support** — execute queries with SET STATISTICS XML ON to capture actual plans, with loading indicator and confirmation dialog ([#233])
+- **PlanAnalyzer** — automated plan analysis with rules for missing indexes, eager spools, key lookups, implicit conversions, memory grants, and more
+- **Current Active Queries live snapshot** — real-time view of running queries with estimated/live plan download ([#149])
+- **Memory clerks tab** in Lite with picker-driven chart ([#145])
+- **Current Waits charts** in Blocking tab for both Dashboard and Lite ([#280])
+- **File I/O throughput charts** — read/write throughput trends, file-level latency breakdown, queued I/O overlay ([#281])
+- **Memory grant stats charts** — standardized collection with delta framework integration and trend visualization ([#281])
+- **CPU scheduler pressure status** — real-time scheduler, worker, runnable task counts with color-coded pressure level below CPU chart
+- **Collection log drill-down** and daily summary in Lite ([#138])
+- **Collector duration trends chart** in Dashboard Collection Health ([#138])
+- **Themed perfmon counter packs** — 14 new counters with organized themed groups ([#255])
+- **User-configurable connection timeout** setting ([#236])
+- **Per-collector retention** — uses per-collector retention from `config.collection_schedule` in data retention ([#237])
+- **Query identifiers** in drill-down windows — query hash, plan hash, SQL handle visible for identification ([#268])
+- **Trace pattern drill-down** with missing columns and query text tooltips ([#273])
+- **Query Store Regressions drill-down** with TVF rewrite for performance ([#274])
+- **CLI `--help` flag** for installer ([#111])
+- Sort arrows, right-aligned numerics, and initial sort indicators across all grids ([#110])
+- Copyable plan viewer properties ([#269])
+- Standardized chart save/export filenames between Dashboard and Lite ([#284])
+- Full Dashboard column parity for query_stats, procedure_stats, and query_store_stats
+- Min/max extremes surfaced in both apps — physical reads, rows, grant KB, spills, CLR time, log bytes ([#281])
+
+### Changed
+
+- Query Store detection uses `sys.database_query_store_options` instead of `sys.databases.is_query_store_on` for Azure SQL DB compatibility ([#287])
+- Config tab consolidation, DB drop on server remove, DuckDB-first plan lookups, procedure stats parity
+- Collector health status now detects consecutive recent failures — 5+ consecutive errors = FAILING, 3+ = WARNING
+- Plan buttons now show a MessageBox when no plan is available instead of silently doing nothing
+- CSV export uses locale-appropriate separators for non-US locales ([#240])
+- Query Store Regressions and Query Trace Patterns migrated to popup grid filtering ([#260])
+- NuGet packages updated; xUnit v3 migration
+
+### Fixed
+
+- **DuckDB file corruption** during maintenance — ReaderWriterLockSlim coordination, archive-all-and-reset at 512MB replaces compaction ([#218])
+- Archive view column mismatch, wait_stats thread-safety, and percent_complete type cast ([#234])
+- Collector health status bar text color ([#234])
+- View Plan for Query Store and Query Store Regressions tabs ([#261])
+- Query Store drill-down time filter alignment with main view ([#263])
+- Execution count mismatches between main views and drill-downs
+- Drill-down chart UX — sparse data markers, hover tooltips, window sizing ([#271])
+- Truncated status text in Add Server dialog ([#257])
+- Scrollbar visibility, self-filtering artifacts, missing columns, and context menus ([#245], [#246], [#247], [#248])
+- query_stats and procedure_stats collectors ignoring recent queries
+- Blank tooltips on warning and parallel badge icons
+- Missing chart context menu on File I/O Throughput charts in Lite
+
+### Removed
+
+- `collect.session_wait_stats` table, `collect.session_wait_stats_collector` procedure, `report.session_wait_analysis` view, and schedule entry — zero UI coverage, never surfaced in Dashboard or Lite ([#281])
+
## [1.3.0] - 2026-02-20
### Important
@@ -119,6 +180,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Delta normalization for per-second rate calculations
- Dark theme UI
+[2.0.0]: https://github.com/erikdarlingdata/PerformanceMonitor/compare/v1.3.0...v2.0.0
[1.3.0]: https://github.com/erikdarlingdata/PerformanceMonitor/compare/v1.2.0...v1.3.0
[1.2.0]: https://github.com/erikdarlingdata/PerformanceMonitor/compare/v1.1.0...v1.2.0
[1.1.0]: https://github.com/erikdarlingdata/PerformanceMonitor/compare/v1.0.0...v1.1.0
@@ -187,3 +249,28 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
[#206]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/206
[#210]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/210
[#214]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/214
+[#218]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/218
+[#220]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/220
+[#233]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/233
+[#234]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/234
+[#236]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/236
+[#237]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/237
+[#240]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/240
+[#245]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/245
+[#246]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/246
+[#247]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/247
+[#248]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/248
+[#255]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/255
+[#257]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/257
+[#260]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/260
+[#261]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/261
+[#263]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/263
+[#268]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/268
+[#269]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/269
+[#271]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/271
+[#273]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/273
+[#274]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/274
+[#280]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/280
+[#281]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/281
+[#284]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/284
+[#287]: https://github.com/erikdarlingdata/PerformanceMonitor/issues/287
diff --git a/Dashboard/Controls/QueryPerformanceContent.xaml.cs b/Dashboard/Controls/QueryPerformanceContent.xaml.cs
index a5071322..5e610547 100644
--- a/Dashboard/Controls/QueryPerformanceContent.xaml.cs
+++ b/Dashboard/Controls/QueryPerformanceContent.xaml.cs
@@ -699,45 +699,60 @@ private void ApplyCurrentActiveFilters()
private void DownloadCurrentActiveEstPlan_Click(object sender, RoutedEventArgs e)
{
- if (sender is Button button && button.DataContext is LiveQueryItem item && !string.IsNullOrEmpty(item.QueryPlan))
+ if (sender is not Button button || button.DataContext is not LiveQueryItem item) return;
+
+ if (string.IsNullOrEmpty(item.QueryPlan))
{
- var timestamp = DateTime.Now.ToString("yyyyMMdd_HHmmss", CultureInfo.InvariantCulture);
- var defaultFileName = $"estimated_plan_{item.SessionId}_{timestamp}.sqlplan";
+ MessageBox.Show("No estimated plan is available for this query.", "No Plan Available",
+ MessageBoxButton.OK, MessageBoxImage.Information);
+ return;
+ }
- var saveFileDialog = new SaveFileDialog
- {
- FileName = defaultFileName,
- DefaultExt = ".sqlplan",
- Filter = "SQL Plan (*.sqlplan)|*.sqlplan|XML Files (*.xml)|*.xml|All Files (*.*)|*.*",
- Title = "Save Query Plan"
- };
+ var timestamp = DateTime.Now.ToString("yyyyMMdd_HHmmss", CultureInfo.InvariantCulture);
+ var defaultFileName = $"estimated_plan_{item.SessionId}_{timestamp}.sqlplan";
- if (saveFileDialog.ShowDialog() == true)
- {
- File.WriteAllText(saveFileDialog.FileName, item.QueryPlan);
- }
+ var saveFileDialog = new SaveFileDialog
+ {
+ FileName = defaultFileName,
+ DefaultExt = ".sqlplan",
+ Filter = "SQL Plan (*.sqlplan)|*.sqlplan|XML Files (*.xml)|*.xml|All Files (*.*)|*.*",
+ Title = "Save Query Plan"
+ };
+
+ if (saveFileDialog.ShowDialog() == true)
+ {
+ File.WriteAllText(saveFileDialog.FileName, item.QueryPlan);
}
}
private void DownloadCurrentActiveLivePlan_Click(object sender, RoutedEventArgs e)
{
- if (sender is Button button && button.DataContext is LiveQueryItem item && !string.IsNullOrEmpty(item.LiveQueryPlan))
+ if (sender is not Button button || button.DataContext is not LiveQueryItem item) return;
+
+ if (string.IsNullOrEmpty(item.LiveQueryPlan))
{
- var timestamp = DateTime.Now.ToString("yyyyMMdd_HHmmss", CultureInfo.InvariantCulture);
- var defaultFileName = $"live_plan_{item.SessionId}_{timestamp}.sqlplan";
+ MessageBox.Show(
+ "No live query plan is available for this session. The query may have completed before the plan could be captured.",
+ "No Plan Available",
+ MessageBoxButton.OK,
+ MessageBoxImage.Information);
+ return;
+ }
- var saveFileDialog = new SaveFileDialog
- {
- FileName = defaultFileName,
- DefaultExt = ".sqlplan",
- Filter = "SQL Plan (*.sqlplan)|*.sqlplan|XML Files (*.xml)|*.xml|All Files (*.*)|*.*",
- Title = "Save Live Query Plan"
- };
+ var timestamp = DateTime.Now.ToString("yyyyMMdd_HHmmss", CultureInfo.InvariantCulture);
+ var defaultFileName = $"live_plan_{item.SessionId}_{timestamp}.sqlplan";
- if (saveFileDialog.ShowDialog() == true)
- {
- File.WriteAllText(saveFileDialog.FileName, item.LiveQueryPlan);
- }
+ var saveFileDialog = new SaveFileDialog
+ {
+ FileName = defaultFileName,
+ DefaultExt = ".sqlplan",
+ Filter = "SQL Plan (*.sqlplan)|*.sqlplan|XML Files (*.xml)|*.xml|All Files (*.*)|*.*",
+ Title = "Save Live Query Plan"
+ };
+
+ if (saveFileDialog.ShowDialog() == true)
+ {
+ File.WriteAllText(saveFileDialog.FileName, item.LiveQueryPlan);
}
}
@@ -798,7 +813,17 @@ private async void ViewEstimatedPlan_Click(object sender, RoutedEventArgs e)
}
if (planXml != null)
+ {
ViewPlanRequested?.Invoke(planXml, label, queryText);
+ }
+ else
+ {
+ MessageBox.Show(
+ "No query plan is available for this row. The plan may have been evicted from the plan cache since it was last collected.",
+ "No Plan Available",
+ MessageBoxButton.OK,
+ MessageBoxImage.Information);
+ }
}
private async void GetActualPlan_Click(object sender, RoutedEventArgs e)
diff --git a/Dashboard/Controls/ResourceMetricsContent.xaml b/Dashboard/Controls/ResourceMetricsContent.xaml
index 63ad4e7e..2801a3e5 100644
--- a/Dashboard/Controls/ResourceMetricsContent.xaml
+++ b/Dashboard/Controls/ResourceMetricsContent.xaml
@@ -44,9 +44,14 @@
+
+
diff --git a/Dashboard/Controls/ResourceMetricsContent.xaml.cs b/Dashboard/Controls/ResourceMetricsContent.xaml.cs
index 88bb7d28..9c8c8896 100644
--- a/Dashboard/Controls/ResourceMetricsContent.xaml.cs
+++ b/Dashboard/Controls/ResourceMetricsContent.xaml.cs
@@ -16,6 +16,7 @@
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
+using System.Windows.Documents;
using System.Windows.Media;
using Microsoft.Win32;
using PerformanceMonitorDashboard.Models;
@@ -982,6 +983,16 @@ private async Task RefreshServerTrendsAsync()
LoadServerTrendsTempdbChart(await tempdbTask, _serverTrendsHoursBack, _serverTrendsFromDate, _serverTrendsToDate);
LoadServerTrendsMemoryChart(await memoryTask, _serverTrendsHoursBack, _serverTrendsFromDate, _serverTrendsToDate);
LoadServerTrendsPerfmonChart(await perfmonTask, _serverTrendsHoursBack, _serverTrendsFromDate, _serverTrendsToDate);
+
+ try
+ {
+ var pressure = await _databaseService.GetCpuPressureAsync();
+ UpdateCpuSchedulerStatus(pressure);
+ }
+ catch (Exception pressureEx)
+ {
+ Logger.Error($"Error loading CPU scheduler pressure: {pressureEx.Message}", pressureEx);
+ }
}
catch (Exception ex)
{
@@ -989,6 +1000,41 @@ private async Task RefreshServerTrendsAsync()
}
}
+ private void UpdateCpuSchedulerStatus(CpuPressureItem? pressure)
+ {
+ if (pressure == null)
+ {
+ CpuSchedulerStatusText.Text = "";
+ return;
+ }
+
+ CpuSchedulerStatusText.Inlines.Clear();
+
+ var summary = $"Schedulers: {pressure.TotalSchedulers} | " +
+ $"Workers: {pressure.TotalWorkers:N0}/{pressure.MaxWorkers:N0} ({pressure.WorkerUtilizationPercent:F1}%) | " +
+ $"Runnable: {pressure.TotalRunnableTasks} ({pressure.AvgRunnableTasksPerScheduler:F2}/sched) | " +
+ $"Active: {pressure.TotalActiveRequests} | " +
+ $"Queued: {pressure.TotalQueuedRequests} | ";
+
+ CpuSchedulerStatusText.Inlines.Add(new Run(summary));
+
+ var levelText = pressure.PressureLevel;
+ var levelRun = new Run(levelText);
+
+ if (levelText.Contains("CRITICAL") || levelText.Contains("HIGH"))
+ {
+ levelRun.Foreground = new SolidColorBrush(Color.FromRgb(0xFF, 0x44, 0x44));
+ levelRun.FontWeight = FontWeights.Bold;
+ }
+ else if (levelText.Contains("MEDIUM"))
+ {
+ levelRun.Foreground = new SolidColorBrush(Color.FromRgb(0xFF, 0xA5, 0x00));
+ levelRun.FontWeight = FontWeights.Bold;
+ }
+
+ CpuSchedulerStatusText.Inlines.Add(levelRun);
+ }
+
private void LoadServerTrendsCpuChart(IEnumerable cpuData, int hoursBack, DateTime? fromDate, DateTime? toDate)
{
DateTime rangeEnd = toDate ?? Helpers.ServerTimeHelper.ServerNow;
diff --git a/Dashboard/Dashboard.csproj b/Dashboard/Dashboard.csproj
index d9b1c628..cbacd1ef 100644
--- a/Dashboard/Dashboard.csproj
+++ b/Dashboard/Dashboard.csproj
@@ -6,7 +6,7 @@
true
PerformanceMonitorDashboard
SQL Server Performance Monitor Dashboard
- 1.3.0
+ 2.0.0
Darling Data, LLC
Copyright © 2026 Darling Data, LLC
EDD.ico
diff --git a/Dashboard/MainWindow.xaml.cs b/Dashboard/MainWindow.xaml.cs
index 494b5c38..3b30f358 100644
--- a/Dashboard/MainWindow.xaml.cs
+++ b/Dashboard/MainWindow.xaml.cs
@@ -445,6 +445,17 @@ private void OpenServerTab(ServerConnection server)
/* Set server UTC offset for chart axis bounds */
var connStatus = _serverManager.GetConnectionStatus(server.Id);
+ if (!connStatus.UtcOffsetMinutes.HasValue)
+ {
+ /* Background check hasn't run yet — fetch offset synchronously so
+ the first tab open doesn't default to local timezone. */
+ try
+ {
+ _serverManager.CheckConnectionAsync(server.Id).GetAwaiter().GetResult();
+ connStatus = _serverManager.GetConnectionStatus(server.Id);
+ }
+ catch { /* Fall through to local offset default */ }
+ }
var utcOffset = connStatus.UtcOffsetMinutes ?? (int)TimeZoneInfo.Local.GetUtcOffset(DateTime.UtcNow).TotalMinutes;
Helpers.ServerTimeHelper.UtcOffsetMinutes = utcOffset;
diff --git a/Installer/PerformanceMonitorInstaller.csproj b/Installer/PerformanceMonitorInstaller.csproj
index a5091055..f245a1b5 100644
--- a/Installer/PerformanceMonitorInstaller.csproj
+++ b/Installer/PerformanceMonitorInstaller.csproj
@@ -20,10 +20,10 @@
PerformanceMonitorInstaller
SQL Server Performance Monitor Installer
- 1.3.0
- 1.3.0.0
- 1.3.0.0
- 1.3.0
+ 2.0.0
+ 2.0.0.0
+ 2.0.0.0
+ 2.0.0
Darling Data, LLC
Copyright © 2026 Darling Data, LLC
Installation utility for SQL Server Performance Monitor - Supports SQL Server 2016-2025
diff --git a/InstallerGui/InstallerGui.csproj b/InstallerGui/InstallerGui.csproj
index c9d3797a..3312f93a 100644
--- a/InstallerGui/InstallerGui.csproj
+++ b/InstallerGui/InstallerGui.csproj
@@ -8,7 +8,7 @@
PerformanceMonitorInstallerGui
PerformanceMonitorInstallerGui
SQL Server Performance Monitor Installer
- 1.3.0
+ 2.0.0
Darling Data, LLC
Copyright © 2026 Darling Data, LLC
EDD.ico
diff --git a/Lite/Controls/ServerTab.xaml.cs b/Lite/Controls/ServerTab.xaml.cs
index 95cad55b..ea704080 100644
--- a/Lite/Controls/ServerTab.xaml.cs
+++ b/Lite/Controls/ServerTab.xaml.cs
@@ -2649,13 +2649,35 @@ private async void DownloadProcedurePlan_Click(object sender, RoutedEventArgs e)
private void DownloadSnapshotPlan_Click(object sender, RoutedEventArgs e)
{
- if (sender is not Button btn || btn.DataContext is not QuerySnapshotRow row || row.QueryPlan == null) return;
+ if (sender is not Button btn || btn.DataContext is not QuerySnapshotRow row) return;
+
+ if (row.QueryPlan == null)
+ {
+ MessageBox.Show(
+ "No estimated plan is available for this snapshot. The plan may have been evicted from the plan cache.",
+ "No Plan Available",
+ MessageBoxButton.OK,
+ MessageBoxImage.Information);
+ return;
+ }
+
SavePlanFile(row.QueryPlan, $"EstimatedPlan_Session{row.SessionId}");
}
private void DownloadSnapshotLivePlan_Click(object sender, RoutedEventArgs e)
{
- if (sender is not Button btn || btn.DataContext is not QuerySnapshotRow row || row.LiveQueryPlan == null) return;
+ if (sender is not Button btn || btn.DataContext is not QuerySnapshotRow row) return;
+
+ if (row.LiveQueryPlan == null)
+ {
+ MessageBox.Show(
+ "No live query plan is available for this snapshot. The query may have completed before the plan could be captured.",
+ "No Plan Available",
+ MessageBoxButton.OK,
+ MessageBoxImage.Information);
+ return;
+ }
+
SavePlanFile(row.LiveQueryPlan, $"ActualPlan_Session{row.SessionId}");
}
@@ -2786,6 +2808,14 @@ private async void ViewEstimatedPlan_Click(object sender, RoutedEventArgs e)
OpenPlanTab(planXml, label, queryText);
PlanViewerTabItem.IsSelected = true;
}
+ else
+ {
+ MessageBox.Show(
+ "No query plan is available for this row. The plan may have been evicted from the plan cache since it was last collected.",
+ "No Plan Available",
+ MessageBoxButton.OK,
+ MessageBoxImage.Information);
+ }
}
private async void GetActualPlan_Click(object sender, RoutedEventArgs e)
diff --git a/Lite/PerformanceMonitorLite.csproj b/Lite/PerformanceMonitorLite.csproj
index 30d1fe97..c87dd8a5 100644
--- a/Lite/PerformanceMonitorLite.csproj
+++ b/Lite/PerformanceMonitorLite.csproj
@@ -7,7 +7,7 @@
PerformanceMonitorLite
PerformanceMonitorLite
SQL Server Performance Monitor Lite
- 1.3.0
+ 2.0.0
Darling Data, LLC
Copyright © 2026 Darling Data, LLC
Lightweight SQL Server performance monitoring - no installation required on target servers
diff --git a/upgrades/1.3.0-to-2.0.0/02_session_wait_stats_cleanup.sql b/upgrades/1.3.0-to-2.0.0/02_session_wait_stats_cleanup.sql
new file mode 100644
index 00000000..9c8932d5
--- /dev/null
+++ b/upgrades/1.3.0-to-2.0.0/02_session_wait_stats_cleanup.sql
@@ -0,0 +1,63 @@
+/*
+Copyright 2026 Darling Data, LLC
+https://www.erikdarling.com/
+
+Upgrade from 1.3.0 to 2.0.0
+Removes session_wait_stats collector (zero UI, never surfaced in Dashboard or Lite).
+*/
+
+SET ANSI_NULLS ON;
+SET ANSI_PADDING ON;
+SET ANSI_WARNINGS ON;
+SET ARITHABORT ON;
+SET CONCAT_NULL_YIELDS_NULL ON;
+SET QUOTED_IDENTIFIER ON;
+SET NUMERIC_ROUNDABORT OFF;
+SET IMPLICIT_TRANSACTIONS OFF;
+SET STATISTICS TIME, IO OFF;
+GO
+
+USE PerformanceMonitor;
+GO
+
+/* Remove reporting view */
+IF OBJECT_ID(N'report.session_wait_analysis', N'V') IS NOT NULL
+BEGIN
+ DROP VIEW
+ report.session_wait_analysis;
+
+ PRINT 'Dropped report.session_wait_analysis';
+END;
+GO
+
+/* Remove collector procedure */
+IF OBJECT_ID(N'collect.session_wait_stats_collector', N'P') IS NOT NULL
+BEGIN
+ DROP PROCEDURE
+ collect.session_wait_stats_collector;
+
+ PRINT 'Dropped collect.session_wait_stats_collector';
+END;
+GO
+
+/* Remove collection table */
+IF OBJECT_ID(N'collect.session_wait_stats', N'U') IS NOT NULL
+BEGIN
+ DROP TABLE
+ collect.session_wait_stats;
+
+ PRINT 'Dropped collect.session_wait_stats';
+END;
+GO
+
+/* Remove schedule entry */
+IF OBJECT_ID(N'config.collection_schedule', N'U') IS NOT NULL
+BEGIN
+ DELETE FROM
+ config.collection_schedule
+ WHERE
+ collector_name = N'session_wait_stats_collector';
+
+ PRINT 'Removed session_wait_stats_collector from config.collection_schedule';
+END;
+GO
diff --git a/upgrades/1.3.0-to-2.0.0/upgrade.txt b/upgrades/1.3.0-to-2.0.0/upgrade.txt
index d4d53f95..4b7bdf58 100644
--- a/upgrades/1.3.0-to-2.0.0/upgrade.txt
+++ b/upgrades/1.3.0-to-2.0.0/upgrade.txt
@@ -1 +1,2 @@
01_memory_grant_stats_schema.sql
+02_session_wait_stats_cleanup.sql