Parsing nested properties in show plan nodes. (#1351)

* Parsing nested properties in show plan nodes.

* Creating a base class for ExecutionGraphProp
Adding a simple test to see if the nested props are parsed correctly.

* Fixing doc comment

* simplifying class name
This commit is contained in:
Aasim Khan
2022-01-19 14:31:19 -08:00
committed by GitHub
parent 1cdb2b94ac
commit 0f54d60921
3 changed files with 74 additions and 20 deletions

View File

@@ -47,7 +47,7 @@ namespace Microsoft.SqlTools.ServiceLayer.ShowPlan
/// <summary>
/// Node properties to be shown in the tooltip
/// </summary>
public List<ExecutionPlanGraphElementProperties> Properties { get; set; }
public List<ExecutionPlanGraphPropertyBase> Properties { get; set; }
/// <summary>
/// Display name for the node
/// </summary>
@@ -64,17 +64,13 @@ namespace Microsoft.SqlTools.ServiceLayer.ShowPlan
public List<ExecutionPlanEdges> Edges { get; set; }
}
public class ExecutionPlanGraphElementProperties
public class ExecutionPlanGraphPropertyBase
{
/// <summary>
/// Name of the property
/// </summary>
public string Name { get; set; }
/// <summary>
/// Formatted value for the property
/// </summary>
public string FormattedValue { get; set; }
/// <summary>
/// Flag to show/hide props in tooltip
/// </summary>
public bool ShowInTooltip { get; set; }
@@ -88,6 +84,22 @@ namespace Microsoft.SqlTools.ServiceLayer.ShowPlan
public bool IsLongString { get; set; }
}
public class NestedExecutionPlanGraphProperty: ExecutionPlanGraphPropertyBase
{
/// <summary>
/// In case of nested properties, the value field is a list of properties.
/// </summary>
public List<ExecutionPlanGraphPropertyBase> Value { get; set; }
}
public class ExecutionPlanGraphProperty : ExecutionPlanGraphPropertyBase
{
/// <summary>
/// Formatted value for the property
/// </summary>
public string Value { get; set; }
}
public class ExecutionPlanEdges
{
/// <summary>
@@ -103,6 +115,6 @@ namespace Microsoft.SqlTools.ServiceLayer.ShowPlan
/// Edge properties to be shown in the tooltip.
/// </summary>
/// <value></value>
public List<ExecutionPlanGraphElementProperties> Properties { get; set; }
public List<ExecutionPlanGraphPropertyBase> Properties { get; set; }
}
}

View File

@@ -50,19 +50,37 @@ namespace Microsoft.SqlTools.ServiceLayer.ShowPlan
};
}
private static List<ExecutionPlanGraphElementProperties> GetProperties(PropertyDescriptorCollection props)
private static List<ExecutionPlanGraphPropertyBase> GetProperties(PropertyDescriptorCollection props)
{
List<ExecutionPlanGraphElementProperties> propsList = new List<ExecutionPlanGraphElementProperties>();
List<ExecutionPlanGraphPropertyBase> propsList = new List<ExecutionPlanGraphPropertyBase>();
foreach (PropertyValue prop in props)
{
propsList.Add(new ExecutionPlanGraphElementProperties()
var complexProperty = prop.Value as ExpandableObjectWrapper;
if (complexProperty == null)
{
Name = prop.DisplayName,
FormattedValue = prop.DisplayValue,
ShowInTooltip = prop.IsBrowsable,
DisplayOrder = prop.DisplayOrder,
IsLongString = prop.IsLongString
});
var propertyValue = prop.DisplayValue;
propsList.Add(new ExecutionPlanGraphProperty()
{
Name = prop.DisplayName,
Value = propertyValue,
ShowInTooltip = prop.IsBrowsable,
DisplayOrder = prop.DisplayOrder,
IsLongString = prop.IsLongString,
});
}
else
{
var propertyValue = GetProperties(complexProperty.Properties);
propsList.Add(new NestedExecutionPlanGraphProperty()
{
Name = prop.DisplayName,
Value = propertyValue,
ShowInTooltip = prop.IsBrowsable,
DisplayOrder = prop.DisplayOrder,
IsLongString = prop.IsLongString,
});
}
}
return propsList;
}

View File

@@ -1,3 +1,4 @@
using System;
//
// Copyright (c) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
@@ -13,17 +14,40 @@ namespace Microsoft.SqlTools.ServiceLayer.UnitTests.ShowPlan
{
public class ShowPlanXMLTests
{
[Test]
public void ParseXMLFileReturnsValidShowPlanGraph()
private string queryPlanFileText;
[SetUp]
public void LoadQueryPlanBeforeEachTest()
{
Assembly assembly = Assembly.GetAssembly(typeof(ShowPlanXMLTests));
Stream scriptStream = assembly.GetManifestResourceStream(assembly.GetName().Name + ".ShowPlan.TestExecutionPlan.xml");
StreamReader reader = new StreamReader(scriptStream);
string text = reader.ReadToEnd();
var showPlanGraphs = ShowPlanGraphUtils.CreateShowPlanGraph(text);
queryPlanFileText = reader.ReadToEnd();
}
[Test]
public void ParseXMLFileReturnsValidShowPlanGraph()
{
var showPlanGraphs = ShowPlanGraphUtils.CreateShowPlanGraph(queryPlanFileText);
Assert.AreEqual(1, showPlanGraphs.Count, "exactly one show plan graph should be returned");
Assert.NotNull(showPlanGraphs[0], "graph should not be null");
Assert.NotNull(showPlanGraphs[0].Root, "graph should have a root");
}
[Test]
public void ParsingNestedProperties()
{
string[] commonNestedPropertiesNames = { "MemoryGrantInfo", "OptimizerHardwareDependentProperties" };
var showPlanGraphs = ShowPlanGraphUtils.CreateShowPlanGraph(queryPlanFileText);
ExecutionPlanNode rootNode = showPlanGraphs[0].Root;
rootNode.Properties.ForEach(p =>
{
if (Array.FindIndex(commonNestedPropertiesNames, i => i.Equals(p.Name)) != -1 && (NestedExecutionPlanGraphProperty)p != null)
{
Assert.NotZero(((NestedExecutionPlanGraphProperty)p).Value.Count);
}
});
}
}
}