Component
SQL collection scripts
Performance Monitor Version
3.2.0
SQL Server Version
SQL Server 2022 CU (docker image mcr.microsoft.com/mssql/server:2022-latest)
Windows Version
N/A - reproduced via Docker. The bug is independent of the client/host OS
Describe the Bug
report.daily_summary_v2 pivots mixed-type metrics into a single metric_value sql_variant column so callers can SELECT sort_order, metric_name, metric_value FROM report.daily_summary_v2 ORDER BY sort_order. The worst_query_hash row boxes the raw binary(8) query_hash (collect.query_stats.query_hash is declared binary(8), not varbinary) directly:
metric_name = N'worst_query_hash',
metric_value = CONVERT(sql_variant, wq.query_hash)
Any caller that follows the view's documented usage and converts metric_value straight to a string type gets unreadable output instead of a hash, because SQL Server's binary-to-char conversion reinterprets the raw bytes as UTF-16 code units.
Every other row in the view is a scalar (date/int/nvarchar) and converts to a sane string. Only the worst_query_hash row is affected, since it's the one row carrying a binary payload.
Steps to Reproduce
docker pull mcr.microsoft.com/mssql/server:2022-latest
docker run -e ACCEPT_EULA=Y -e MSSQL_SA_PASSWORD='NotStrong!Passw0rd' \
--name sqltest -p 1433:1433 -d mcr.microsoft.com/mssql/server:2022-latest
# short pause so database service can start up
sleep 15
Reproduce the view's own pattern with a literal hash:
docker exec -it sqltest /opt/mssql-tools18/bin/sqlcmd -S localhost -U sa \
-P 'NotStrong!Passw0rd' -C -Q "
DECLARE @query_hash binary(8) = 0x1F7A7FB76757088B;
DECLARE @metric_value sql_variant = CONVERT(sql_variant, @query_hash);
SELECT metric_value = CONVERT(nvarchar(500), @metric_value);"
Confirm the base type SQL Server sees:
docker exec -it sqltest /opt/mssql-tools18/bin/sqlcmd -S localhost -U sa \
-P 'NotStrong!Passw0rd' -C -Q "
DECLARE @query_hash binary(8) = 0x1F7A7FB76757088B;
DECLARE @metric_value sql_variant = CONVERT(sql_variant, @query_hash);
SELECT base_type = SQL_VARIANT_PROPERTY(@metric_value, 'BaseType');"
Expected: binary. Note for anyone patching a caller-side workaround instead of the view itself: SQL_VARIANT_PROPERTY(..., 'BaseType') reports binary here, not varbinary - matching query_hash's actual declared column type - so a workaround CASE needs to check for binary (and varbinary, for safety against a future column-type change) rather than assuming varbinary.
Compare against the fixed expression (convert to hex before boxing):
docker exec -it sqltest /opt/mssql-tools18/bin/sqlcmd -S localhost -U sa \
-P 'NotStrong!Passw0rd' -C -Q "
DECLARE @query_hash binary(8) = 0x1F7A7FB76757088B;
DECLARE @metric_value sql_variant = CONVERT(sql_variant, CONVERT(nvarchar(20), @query_hash, 1));
SELECT metric_value = CONVERT(nvarchar(500), @metric_value);"
Cleanup:
Expected Behavior
metric_value
-------------------
0x1F7A7FB76757088B
A readable hex hash, matching every other scalar row in the view.
Actual Behavior
metric_value
------------
稟띿坧謈
The raw bytes get reinterpreted as UTF-16 code units instead of rendering as hex.
Error Messages / Log Output
NA - no error is raised; the conversion silently produces garbled text.
Screenshots
NA
Additional Context
Checked Dashboard/Services/DatabaseService.Overview.cs's GetDailySummaryAsync - it queries report.daily_summary (v1), which has no query_hash/worst_query_* columns at all, so the WPF app itself never hits this. daily_summary_v2 appears to only be consumed by callers that follow the view's own documented ad hoc usage (as my Grafana Daily Summary panel does downstream).
Fix: convert wq.query_hash to a hex nvarchar before boxing it into sql_variant, matching the style already used elsewhere in the codebase for query_hash display:
metric_value = CONVERT(sql_variant, CONVERT(nvarchar(20), wq.query_hash, 1))
Applied as a one-line change to the worst_query_hash projection in install/47_create_reporting_views.sql (report.daily_summary_v2 view definition), idempotent via CREATE OR ALTER VIEW.
Component
SQL collection scripts
Performance Monitor Version
3.2.0
SQL Server Version
SQL Server 2022 CU (docker image
mcr.microsoft.com/mssql/server:2022-latest)Windows Version
N/A - reproduced via Docker. The bug is independent of the client/host OS
Describe the Bug
report.daily_summary_v2pivots mixed-type metrics into a singlemetric_value sql_variantcolumn so callers canSELECT sort_order, metric_name, metric_value FROM report.daily_summary_v2 ORDER BY sort_order. Theworst_query_hashrow boxes the rawbinary(8)query_hash(collect.query_stats.query_hashis declaredbinary(8), notvarbinary) directly:Any caller that follows the view's documented usage and converts
metric_valuestraight to a string type gets unreadable output instead of a hash, because SQL Server's binary-to-char conversion reinterprets the raw bytes as UTF-16 code units.Every other row in the view is a scalar (date/int/nvarchar) and converts to a sane string. Only the
worst_query_hashrow is affected, since it's the one row carrying a binary payload.Steps to Reproduce
Reproduce the view's own pattern with a literal hash:
Confirm the base type SQL Server sees:
Expected:
binary. Note for anyone patching a caller-side workaround instead of the view itself:SQL_VARIANT_PROPERTY(..., 'BaseType')reportsbinaryhere, notvarbinary- matchingquery_hash's actual declared column type - so a workaround CASE needs to check forbinary(andvarbinary, for safety against a future column-type change) rather than assumingvarbinary.Compare against the fixed expression (convert to hex before boxing):
Cleanup:
Expected Behavior
A readable hex hash, matching every other scalar row in the view.
Actual Behavior
The raw bytes get reinterpreted as UTF-16 code units instead of rendering as hex.
Error Messages / Log Output
Screenshots
NA
Additional Context
Checked
Dashboard/Services/DatabaseService.Overview.cs'sGetDailySummaryAsync- it queriesreport.daily_summary(v1), which has noquery_hash/worst_query_*columns at all, so the WPF app itself never hits this.daily_summary_v2appears to only be consumed by callers that follow the view's own documented ad hoc usage (as my Grafana Daily Summary panel does downstream).Fix: convert
wq.query_hashto a hexnvarcharbefore boxing it intosql_variant, matching the style already used elsewhere in the codebase forquery_hashdisplay:Applied as a one-line change to the
worst_query_hashprojection ininstall/47_create_reporting_views.sql(report.daily_summary_v2view definition), idempotent viaCREATE OR ALTER VIEW.