I had a bit of a rant yesterday about the fact I have had to compromise naming member properties when I've inadvertently created them with the wrong data type. As I mentioned, I found a Dimension attribute collection method in the Planning client assemblies that hinted that it might allow me to delete a member property so I decided to give it a go.
Below is some really rough and ready C# code that actually does delete a dimension member property. I will improve the code and probably add it in to my PPSCMD GUI interface as a 'feature pack' bonus at some stage, however, if you are in desperate need for the code to delete a member property, and you can't wait for PPSCMD GUI v0.2 or PerformancePoint Version 2 (I'm not sure which will come first !) the code is below (Use at your own risk !!)
Note: Replace "MyApp", "MyDimension", "MyAttribute", oh, and the server address, accordingly..
// Setup the PPS Application Metadata Manager
ServerHandler serverHandler = new ServerHandler("http://localhost:46787");
MetadataManager manager = new MetadataManager();
manager.ServerHandler = serverHandler;
// Get the system metadata
BizSystem system = manager.GetSystem(true);
// Get hold of the PPS Application
BizApplication ppsApp = system.Applications["MyApp"];
// Obtain the root model site from the application
BizModelSite site = ppsApp.RootModelSite;
// Obtain the dimension that contains the member property
BizDimension dimension = site.Dimensions["MyDimension"];
// Obtain the member property
BizDimensionAttribute attribute = dimension.Attributes["MyAttribute"];
// Check out the dimension
// Perform the delete
// Submit the change
manager.SubmitModelSite(ppsApp.Id, dimension.ParentModelSite, Microsoft.PerformancePoint.Planning.Bmo.Interfaces.SubmissionType.Update);
// Check in the dimension
Update: I've since discovered that you can obtain an unsupported utility from Microsoft Support that reportedly does the same thing, doh !
Oh well, always nice to have the code ..J
I'm building a generic helper class to flatten an ADOMD data set to a data table for easier consumption by default and third party .NET controls. I can't rely on the Load method of the data table, nor the CellSet object as in some cases not all the information is persisted; datatypes and top level hierarchies to name two.
To persist all of the information I need to traverse the actual xml dataset returned by the ExecuteXMLReader method of the ADOMDCommand object.
I don't use xml enough these days to remember all the nuances with namespaces and it took me a little while to work out what to set the namespaces to in order for the 'SelectNodes' method to work.
Below is the code snippet I used to ensure the output from the ExecuteXmlReader method is fully traversable.
// Execute the command returning the XML data set
XmlReader reader = command.ExecuteXmlReader();
// Load the object into an XML document
XmlDocument xml = new XmlDocument();
// Create an XML namespace manager
System.Xml.XmlNamespaceManager nsManager=new XmlNamespaceManager(xml.NameTable);
// Add the namepsaces to the manager
// Return a list of nodes that represent the row information
XmlNodeList rows = xml.SelectNodes("defaultNS:root/defaultNS:Axes/defaultNS:Axis[@name ='Axis1']", nsManager);
This kb article helped me out a bit:
There are some more goodies included in my helper class that I will blog about in the future, once it's stable !