HOWTO: csharp - Exchange powershell - call get-StorageGroupCopyStatus with managed code.

This sample is good for both calling and for using with calling other commandlets and seeing what is returend - ie it breaks-down the return results  in general. See, most examples I've found so far show only how to get exact properties and not just dump out specific ones.  You should be aware of what type of item your getting in the results - string, string array, etc - assuming that everything comes back as a string will get you into trouble.  You may want to use this sample to play with several commandlets to see what can and is returned...

//HOWTO: csharp - powershell - call  get-StorageGroupCopyStatus with managed code.

//  An example sample which calls get-StorageGroupCopyStatus and returns a list of properties.
// TODO:
//#1 - Create a C# winform application and add a button called cmdGetStorageGroupCopyStatus. Paste-in the code below.
//#2 - Add namespace reference statements (using statements):
//      //Need for handing things like SecureString types...
//      using System.Security;
//      // For calling commandlets:
//      using System.Management.Automation;
//      using System.Management.Automation.Host;
//      using System.Management.Automation.Runspaces;
//      //General collection handling:
//      using System.Collections.Generic;
//      using System.Collections.ObjectModel;
// #3 - Set a eference to the "System.Management.Automation.dll"
//      This is installed by the Windows Powershell SDK.
//      OK, some articles say the files are here in some articles:
//          32bit:  C:\WINDOWS\SysWOW64\windowspowershell\v1.0
//          64bit:  C:\WINDOWS\system32\windowspowershell\v1.0
//      However, you will find it here after installing: 
//          C:\Program Files\Reference Assemblies\Microsoft\WindowsPowerShell\v1.0
//
// Here are some places to get whats neeed for powershell development.
//    How to Download Windows PowerShell 1.0
//    <https://www.microsoft.com/windowsserver2003/technologies/management/powershell/download.mspx>
//    Note: Exchange will install Powershell itself, so you will not need to do this on an Exchange server.
//
//    How to Install Windows PowerShell and Download the Windows PowerShell SDK
//    <https://msdn2.microsoft.com/en-us/library/Bb204630.aspx>
//
//    Microsoft® Windows® Software Development Kit for Windows Vista™ and .NET Framework 3.0 Runtime Components
//    <https://www.microsoft.com/downloads/details.aspx?FamilyId=C2B1E300-F358-4523-B479-F53D234CDCCF&displaylang=en>
//    Note: This is for an internet install.
//
// Here are some good articles to look over:
//    Windows PowerShell SDK
//    <https://msdn2.microsoft.com/en-us/library/ms714469.aspx>
//    Using Exchange Management Shell Commands With Managed Code
//    <https://msdn2.microsoft.com/en-us/library/bb332449.aspx>

//C# winform test stub for powershell calls
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Diagnostics;   // need for doing trace, etc

// Need for handing things like SecureString types...
using System.Security;

// For calling commandlets:
using System.Management.Automation;
using System.Management.Automation.Host;
using System.Management.Automation.Runspaces;

// General collection handling:
//using System.Collections.Generic;
using System.Collections.ObjectModel;

 

        private void cmdGetStorageGroupCopyStatus_Click(object sender, EventArgs e)
        {
           //GetStorageGroupCopyStatus("", "", "", "");   // Test All
           //GetStorageGroupCopyStatus("", "", "myexchangeserver\\First Storage Group", "");             
        }

        // ===========================================================================
        // GetStorageGroupCopyStatus
        //    string sServer -
        //    string sDomainController -
        //    string sIdentity  -
        //    string sStorageGroupIdParameter -
        // ===========================================================================    
        public static void GetStorageGroupCopyStatus(
            string sServer,
            string sDomainController,
            string sIdentity,
            string sStorageGroupIdParameter)
        {

            ICollection<PSObject> results;

            // Create a runspace. We can't use the RunspaceInvoke class this time
            // because we need to get at the underlying runspace to explicitly
            // add the commands.
            RunspaceConfiguration rc = RunspaceConfiguration.Create();
            PSSnapInException snapEx = null;
            PSSnapInInfo info = rc.AddPSSnapIn(
                "Microsoft.Exchange.Management.PowerShell.Admin",
                out snapEx);
            Runspace myRunSpace = RunspaceFactory.CreateRunspace(rc);
            myRunSpace.Open();

            // Create a pipeline...
            Pipeline pipeLine = myRunSpace.CreatePipeline();

            using (pipeLine)
            {
                // Create a command object so we can set some parameters
                // for this command.
                Command oCommand = new Command("get-StorageGroupCopyStatus");

                if (sServer.Length != 0)
                {
                    oCommand.Parameters.Add("Server", sServer);
                }
                if (sDomainController.Length != 0)
                {
                    oCommand.Parameters.Add("DomainController", sDomainController);
                }
                if (sIdentity.Length != 0)
                {
                    oCommand.Parameters.Add("Identity", sIdentity);
                }
                if (sStorageGroupIdParameter.Length != 0)
                {
                    oCommand.Parameters.Add("StorageGroupIdParameter", sStorageGroupIdParameter);
                }

                // Add the command we've constructed
                pipeLine.Commands.Add(oCommand);

                // Execute the pipeline and save the objects returned.
                results = pipeLine.Invoke();

                // Print out any errors in the pipeline execution
                // NOTE: These error are NOT thrown as exceptions!
                // Be sure to check this to ensure that no errors
                // happened while executing the command.
                if (pipeLine.Error != null && pipeLine.Error.Count > 0)   // NOTE: Always check for errors!!!
                {
                    Trace.WriteLine("ERROR: There were pipeline errors...");
                    foreach (object item in pipeLine.Error.ReadToEnd())
                    {
                        Trace.WriteLine("Error: " + item.ToString() + "");
                    }
                    Trace.Flush();
                }

                //PSObject//
                // Print out the results of the pipeline execution
                PSObject oPS = null;
                PSMemberInfo oMember = null;
                if (results != null && results.Count > 0)    // NOTE: Be sure there are results!!!
                {
                    // Use this foreach for getting specific properties:
                    Trace.WriteLine("\n");
                    Trace.WriteLine("------=======********************************=======------");
                    Trace.WriteLine("------=======*****  SPECIFIC PROPERTIES  ****=======------");
                    Trace.WriteLine("------=======********************************=======------");
                    Trace.WriteLine("\n");
                    foreach (PSObject ps in results)
                    {
                        oPS = ps;
                        TraceProperty(ref oPS, "Identity");
                        TraceProperty(ref oPS, "StorageGroupName");
                        TraceProperty(ref oPS, "SummaryCopyStatus");
                        TraceProperty(ref oPS, "FailedMessage");
                        TraceProperty(ref oPS, "Suspend");
                        TraceProperty(ref oPS, "Seeding");
                        TraceProperty(ref oPS, "Failed");
                        TraceProperty(ref oPS, "LastReplayedLogTime");
                        TraceProperty(ref oPS, "LastLogReplayed");
                        TraceProperty(ref oPS, "LastLogCopied");
                        TraceProperty(ref oPS, "LastLogGenerated");
                        oPS = null;
                    }

                    // Use this foreach for getting all properties:
                    Trace.WriteLine("\n");
                    Trace.WriteLine("------=======***************************=======------");
                    Trace.WriteLine("------=======*****  ALL PROPERTIES  ****=======------");
                    Trace.WriteLine("------=======***************************=======------");
                    Trace.WriteLine("\n");
                    foreach (PSObject ps in results)
                    {
                        foreach (PSMemberInfo  psMember in ps.Members)
                        {
                            oMember = psMember;
                            TraceDumpMemberProperties(ref oMember);
                            oPS = null;
                        }
                    }
                }
            }

            pipeLine = null;
            myRunSpace.Close();
            myRunSpace = null;
        }

        public static void TraceDumpMemberProperties(ref PSMemberInfo psMember)
        {
            string[] aString;
            int iCount = 0;

            if (psMember.MemberType.ToString() == "Property")   // Only look at Properties
            {
                Trace.WriteLine("----[Begin:" + psMember.Name + "]----------------------------------------------------------\n");

                 Trace.WriteLine("--Response Member Info:");

                Trace.WriteLine("      TypeNameOfValue:  " + psMember.TypeNameOfValue + "");
                Trace.WriteLine("      MemberType:       " + psMember.MemberType.ToString() + "");
                Trace.WriteLine("      Name:             " + psMember.Name + "");
                Trace.WriteLine("--");

                if (psMember.Value != null)
                {                  

                    if (psMember.TypeNameOfValue == "System.String[]")
                    {
                        Trace.WriteLine("Values: ");
                        aString = (string[])psMember.Value;
                        for (iCount = 0; aString.Length != iCount; iCount++)
                        {
                            Trace.WriteLine("    (" + iCount.ToString() + ") " + aString[iCount]);
                        }
                    }
                    else
                    {
                        Trace.WriteLine("Value: " + psMember.Value + "");
                    }
                }
                else
                {
                    Trace.WriteLine("Value of member is null."  );
                }
                Trace.WriteLine("\n----[End:" + psMember.Name + "]-------------------------------------------------------\n");
        
            }

            Trace.Flush();
        }

        public static void TraceProperty(ref PSObject ps, string sMemberName)
        {
            string[] aString;
            int iCount = 0;
            Trace.WriteLine("----[Begin: " + sMemberName + "]----------------------------------------------------------\n");
            if (ps.Members[sMemberName].Value != null)
            {
                Trace.WriteLine("--Response Member Info:");

                Trace.WriteLine("      TypeNameOfValue:  " + ps.Members[sMemberName].TypeNameOfValue + "");
                Trace.WriteLine("      MemberType:       " + ps.Members[sMemberName].MemberType.ToString() + "");
                Trace.WriteLine("      Name:             " + ps.Members[sMemberName].Name + "");
                Trace.WriteLine("--");

                if (ps.Members[sMemberName].TypeNameOfValue == "System.String[]")
                {
                    Trace.WriteLine("Values: ");
                    aString = (string[])ps.Members[sMemberName].Value;
                    for (iCount = 0; aString.Length != iCount; iCount++)
                    {
                        Trace.WriteLine("    (" + iCount.ToString() + ") " + aString[iCount]);
                    }

                }
                else
                {
                    Trace.WriteLine("Value: " + ps.Members[sMemberName].Value + "");
                }
            }
            else
            {
                Trace.WriteLine("Member '" +sMemberName + "' is null."  );
            }

            Trace.WriteLine("\n----[End: " + sMemberName + "]-------------------------------------------------------\n");

            Trace.Flush();
        }

 

For further information on PowerShell, please visit the link below:

Links on Common PowerShell Automation Questions

https://blogs.msdn.com/webdav_101/archive/2008/09/26/links-on-common-powershell-automation-questions.aspx