{"id":1123,"date":"2008-03-15T07:30:02","date_gmt":"2008-03-15T07:30:02","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/heaths\/2008\/03\/15\/group-by-different-properties-for-format-table\/"},"modified":"2019-02-17T15:30:04","modified_gmt":"2019-02-17T22:30:04","slug":"group-by-different-properties-for-format-table","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/setup\/group-by-different-properties-for-format-table\/","title":{"rendered":"Group by Different Properties for Format-Table"},"content":{"rendered":"<p>For my <a href=\"http:\/\/www.codeplex.com\/psmsi\">Windows Installer PowerShell Extensions<\/a>, I&#8217;ve been simplifying some of the use cases and adding additional formats. One thing I wanted to do was display source list information in a table and group either by the attached ProductCode or PatchCode properties. The format-table cmdlet doesn&#8217;t support multiple properties and doesn&#8217;t appear to allow you to condition the label. It also seemed that <em>Display.xml<\/em>, or <em>*.formats.ps1xml<\/em> files, didn&#8217;t natively support grouping by multiple property names.<\/p>\n<p>The help topic <em>about_Display.xml<\/em> hinted at a CustomControl tag, but examples of this and related tags in the default <em>*.formats.ps1xml<\/em> files offered little insight about their true power. With some help from a simple <a href=\"http:\/\/www.thomas-krause.de\/weblogs\/elcaroop\/2007\/09\/powershell-format-xml-schema.html\">user-generated XML schema<\/a> and some trial and error, I was able to display a label with an appropriate value conditionally, such that the following expressions displayed the partial table shown below.<\/p>\n<pre>PS&gt; $packages = get-msiproductinfo | ?{ $_.Name -match \"Visual Studio\" }\nPS&gt; $packages += get-msipatchinfo\nPS&gt; $packages | get-msisource | format-table -view package\n    <span class=\"highlight\" style=\"background: yellow\">ProductCode<\/span>: {388E4B09-3E71-4649-8921-F44A3A2954A7}\nIndex Type    Path\n----- ----    ----\n    0 Network m:\\c0367ae0d89851da1a\\\n    1 Network C:\\Program Files\\Common Files\\Microsoft Shared\\VSTO\\8.0\\Micros...\n    2 Network m:\\3d218a0f32f61beaf41a01459217\\\n    <span class=\"highlight\" style=\"background: yellow\">PatchCode<\/span>: {6E52C409-0D0D-4B84-AB63-463438D4D33B}\nIndex Type    Path\n----- ----    ----\n    0 Network m:\\ec91ccc92c8f730e8d87188036\\\n<\/pre>\n<p>I accomplished this by using a scriptblock to group, but referencing a CustomControl with multiple ExpressionBinding elements as shown in the partial example below.<\/p>\n<pre class=\"code\"><span>&lt;<\/span><span>Configuration<\/span><span>&gt;\n  &lt;<\/span><span>Controls<\/span><span>&gt;\n    &lt;<\/span><span>Control<\/span><span>&gt;\n      &lt;<\/span><span>Name<\/span><span>&gt;<\/span>PatchOrProductGrouping<span>&lt;\/<\/span><span>Name<\/span><span>&gt;\n      &lt;<\/span><span>CustomControl<\/span><span>&gt;\n        &lt;<\/span><span>CustomEntries<\/span><span>&gt;\n          &lt;<\/span><span>CustomEntry<\/span><span>&gt;\n            &lt;<\/span><span>CustomItem<\/span><span>&gt;\n              &lt;<\/span><span>Frame<\/span><span>&gt;\n                &lt;<\/span><span>LeftIndent<\/span><span>&gt;<\/span>4<span>&lt;\/<\/span><span>LeftIndent<\/span><span>&gt;\n                &lt;<\/span><span>CustomItem<\/span><span>&gt;\n                  &lt;<\/span><span>ExpressionBinding<\/span><span>&gt;\n                    &lt;<\/span><span>ItemSelectionCondition<\/span><span>&gt;\n                      &lt;<\/span><span>ScriptBlock<\/span><span>&gt;&lt;![CDATA[<\/span><span>$_.ProductCode -ne $null<\/span><span>]]&gt;&lt;\/<\/span><span>ScriptBlock<\/span><span>&gt;\n                    &lt;\/<\/span><span>ItemSelectionCondition<\/span><span>&gt;\n                    &lt;<\/span><span>ScriptBlock<\/span><span>&gt;&lt;![CDATA[<\/span><span>\"ProductCode: \" + $_.ProductCode<\/span><span>]]&gt;&lt;\/<\/span><span>ScriptBlock<\/span><span>&gt;\n                  &lt;\/<\/span><span>ExpressionBinding<\/span><span>&gt;\n                  &lt;<\/span><span>ExpressionBinding<\/span><span>&gt;\n                    &lt;<\/span><span>ItemSelectionCondition<\/span><span>&gt;\n                      &lt;<\/span><span>ScriptBlock<\/span><span>&gt;&lt;![CDATA[<\/span><span>$_.PatchCode -ne $null<\/span><span>]]&gt;&lt;\/<\/span><span>ScriptBlock<\/span><span>&gt;\n                    &lt;\/<\/span><span>ItemSelectionCondition<\/span><span>&gt;\n                    &lt;<\/span><span>ScriptBlock<\/span><span>&gt;&lt;![CDATA[<\/span><span>\"PatchCode: \" + $_.PatchCode<\/span><span>]]&gt;&lt;\/<\/span><span>ScriptBlock<\/span><span>&gt;\n                  &lt;\/<\/span><span>ExpressionBinding<\/span><span>&gt;\n                  &lt;<\/span><span>NewLine<\/span><span>\/&gt;\n                &lt;\/<\/span><span>CustomItem<\/span><span>&gt;\n              &lt;\/<\/span><span>Frame<\/span><span>&gt;\n            &lt;\/<\/span><span>CustomItem<\/span><span>&gt;\n          &lt;\/<\/span><span>CustomEntry<\/span><span>&gt;\n        &lt;\/<\/span><span>CustomEntries<\/span><span>&gt;\n      &lt;\/<\/span><span>CustomControl<\/span><span>&gt;\n    &lt;\/<\/span><span>Control<\/span><span>&gt;<\/span>\n<span>  &lt;\/<\/span><span>Controls<\/span><span>&gt;\n  &lt;<\/span><span>ViewDefinitions<\/span><span>&gt;\n    &lt;<\/span><span>View<\/span><span>&gt;<\/span>\n<span>      &lt;<\/span><span>Name<\/span><span>&gt;<\/span>Package<span>&lt;\/<\/span><span>Name<\/span><span>&gt;\n      &lt;<\/span><span>ViewSelectedBy<\/span><span>&gt;\n        &lt;<\/span><span>TypeName<\/span><span>&gt;<\/span>Microsoft.Windows.Installer.PackageSource<span>&lt;\/<\/span><span>TypeName<\/span><span>&gt;\n      &lt;\/<\/span><span>ViewSelectedBy<\/span><span>&gt;\n      &lt;<\/span><span>GroupBy<\/span><span>&gt;\n        &lt;<\/span><span>ScriptBlock<\/span><span>&gt;&lt;![CDATA[\n<\/span><span>          if ($_.ProductCode -ne $null)\n          {\n            $_.ProductCode\n          }\n          elseif ($_.PatchCode -ne $null)\n          {\n            $_.PatchCode\n          }\n        <\/span><span>]]&gt;&lt;\/<\/span><span>ScriptBlock<\/span><span>&gt;\n        &lt;<\/span><span>CustomControlName<\/span><span>&gt;<\/span>PatchOrProductGrouping<span>&lt;\/<\/span><span>CustomControlName<\/span><span>&gt;\n      &lt;\/<\/span><span>GroupBy<\/span><span>&gt;\n      &lt;<\/span><span>TableControl<\/span><span>&gt;<\/span>\n<span>        &lt;!--<\/span><span> Omitted for brevity <\/span><span>--&gt;\n      &lt;\/<\/span><span>TableControl<\/span><span>&gt;\n    &lt;\/<\/span><span>View<\/span><span>&gt;\n  &lt;\/<\/span><span>ViewDefinitions<\/span><span>&gt;\n&lt;\/<\/span><span>Configuration<\/span><span>&gt;<\/span><\/pre>\n<p>Hopefully this serves as a good example of more powerful features of formatting in PowerShell.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>For my Windows Installer PowerShell Extensions, I&#8217;ve been simplifying some of the use cases and adding additional formats. One thing I wanted to do was display source list information in a table and group either by the attached ProductCode or PatchCode properties. The format-table cmdlet doesn&#8217;t support multiple properties and doesn&#8217;t appear to allow you [&hellip;]<\/p>\n","protected":false},"author":389,"featured_media":3843,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[30,39],"class_list":["post-1123","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-uncategorized","tag-powershell","tag-tip"],"acf":[],"blog_post_summary":"<p>For my Windows Installer PowerShell Extensions, I&#8217;ve been simplifying some of the use cases and adding additional formats. One thing I wanted to do was display source list information in a table and group either by the attached ProductCode or PatchCode properties. The format-table cmdlet doesn&#8217;t support multiple properties and doesn&#8217;t appear to allow you [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/posts\/1123","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/users\/389"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/comments?post=1123"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/posts\/1123\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/media\/3843"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/media?parent=1123"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/categories?post=1123"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/setup\/wp-json\/wp\/v2\/tags?post=1123"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}