Forum Discussion

NitishKrishB's avatar
NitishKrishB
New Contributor
4 days ago
Solved

Is it possible to extract(as xml) a Maintenance Unit and it's components using extensibility rule?

Hello OneStream experts, 

We are trying to extract a maintenance unit and all it's components underneath it using a BR/Extensibility rule with the latest OS version - 9.0.1. 

But, however after the run we could able to see a empty xml in the fileshare folder. 

Below is the snippet of code which we are using. 

Any suggestions or help would be greatly appreciated. Thanks!

Public Function Main(ByVal si As SessionInfo, ByVal globals As BRGlobals, ByVal api As Object, ByVal args As ExtenderArgs) As Object
			Try
				Select Case args.FunctionType
					Case Is = ExtenderFunctionType.ExecuteDataMgmtBusinessRuleStep, ExtenderFunctionType.Unknown
						'Get Configuration Settings
							Dim configSettings As AppServerConfigSettings = AppServerConfig.GetSettings(si)
							'Data Management extract location
							Dim folderPath As String = FileShareFolderHelper.GetDataManagementExportUsernameFolderForApp(si, True, configSettings.FileShareRootFolder,
							 si.AppToken.AppName
							 ) & "\" & DateTime.UtcNow.ToString("yyyyMMdd") & "\Extracts"  'If the directory does not exist create
						If Not Directory.Exists(folderPath) Then Directory.CreateDirectory(folderPath)
							'Full path and file name for extract
							Dim filePath As String = folderPath & "\MaintainanceUnitBkp " & DateTime.UtcNow.ToString("yyyyMMdd") & ".xml"
						'If file already exist
						If File.Exists(filePath) Then File.Delete(filePath)
						'Extract Options
'						Dim xmlOptions As New XmlExtractOptions
'						xmlOptions.ExtractAllItems = False
						
						Dim xmlOptions As New XmlExtractOptions
						Dim dashboardOptions As New DashboardMaintUnit
						
						xmlOptions.ExtractAllItems = False


'Extract Maintainance Unit
Dim extractDict As New Dictionary(Of XmlExtractItemPk, Boolean)

Dim strMaintUnit As String = "DataExtract_Main" 'Maintenance Unit
extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnit, strMaintUnit), True)

'Execute the Metadata Extract
						Using dbConnFW As DbConnInfo = BRApi.Database.CreateFrameworkDbConnInfo(si)
							Using dbConnApp As DbConnInfo = BRApi.Database.CreateApplicationDbConnInfo(si)
								'Extract XML metadata to target location
								File.WriteAllText(filePath, MetadataExtract.ExtractXml(dbConnFW, dbConnApp, xmlOptions, extractDict))
								File.WriteAllText(filePath,XmlExtractController.ExtractXML(dbConnFW,dbConnApp,Nothing,xmlOptions,extractDict,XmlLoadExtractType.ApplicationWorkspaces))
							End Using
						End Using
  • The way to do this is to "build up" your xml file with the things you add to the extractDict. If you want a maintenance unit, you need to first add types DashboardWorkspaces, DashboardWorkspace, and DashboardMaintUnits.  If you look at the XML for an ApplicationWOrkspace export, it has these types on the outside enclosing the maintenance units.  

    Look at how the xml file is composed when you export Application Workspaces through the Load/Extract screen.  The use that as your pattern to build up your extract dict.  Here I'm extracting a maintenance unit with a Workspace Assembly.  Use this pattern...

    This code will extract the maintenance unit, its assembly, components, adapters, and groups within that maintenance unit:
    modify it using this pattern to get what you want out of your maintenance unit.

    Dim xmlOptions As New XmlExtractOptions() With {
        .ExtractAllItems = False
    }
    
    ' Define the maintenance unit to extract
    Dim extractDict As New Dictionary(Of XmlExtractItemPk, Boolean)()
    Dim maintUnitId As New Guid("A76AC44C-88E0-4115-BE03-B6B29F890998")
    Dim workspaceId As New Guid("BA09DD97-F470-4865-A4C8-F5B55EC7E03B")
    Dim assemblyId As New Guid("0ACA5739-73A1-44B5-BE57-A8235B7C9F82")
    
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardWorkspaces, SharedConstants.Unknown), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardWorkspace, workspaceId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnits, workspaceId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnit, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.WorkspaceAssemblies, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.WorkspaceAssembly, assemblyId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardAdapters, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardComponents, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.Groups, maintUnitId), True)
    
    ' Execute the metadata extract
    Using dbConnFW As DbConnInfo = BRApi.Database.CreateFrameworkDbConnInfo(si)
        Using dbConnApp As DbConnInfo = BRApi.Database.CreateApplicationDbConnInfo(si)
            Dim xmlContent As String = XmlExtractController.ExtractXml(
                dbConnFW,
                dbConnApp,
                Nothing,
                xmlOptions,
                extractDict,
                XmlLoadExtractType.ApplicationWorkspaces
            )
    
            BRApi.ErrorLog.LogMessage(si, xmlContent)
    
            ' Write output to file
            File.WriteAllText(filePath, xmlContent)
        End Using
    End Using

     

4 Replies

  • RobbSalzmann's avatar
    RobbSalzmann
    Valued Contributor II

    The way to do this is to "build up" your xml file with the things you add to the extractDict. If you want a maintenance unit, you need to first add types DashboardWorkspaces, DashboardWorkspace, and DashboardMaintUnits.  If you look at the XML for an ApplicationWOrkspace export, it has these types on the outside enclosing the maintenance units.  

    Look at how the xml file is composed when you export Application Workspaces through the Load/Extract screen.  The use that as your pattern to build up your extract dict.  Here I'm extracting a maintenance unit with a Workspace Assembly.  Use this pattern...

    This code will extract the maintenance unit, its assembly, components, adapters, and groups within that maintenance unit:
    modify it using this pattern to get what you want out of your maintenance unit.

    Dim xmlOptions As New XmlExtractOptions() With {
        .ExtractAllItems = False
    }
    
    ' Define the maintenance unit to extract
    Dim extractDict As New Dictionary(Of XmlExtractItemPk, Boolean)()
    Dim maintUnitId As New Guid("A76AC44C-88E0-4115-BE03-B6B29F890998")
    Dim workspaceId As New Guid("BA09DD97-F470-4865-A4C8-F5B55EC7E03B")
    Dim assemblyId As New Guid("0ACA5739-73A1-44B5-BE57-A8235B7C9F82")
    
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardWorkspaces, SharedConstants.Unknown), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardWorkspace, workspaceId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnits, workspaceId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnit, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.WorkspaceAssemblies, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.WorkspaceAssembly, assemblyId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardAdapters, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.DashboardComponents, maintUnitId), True)
    extractDict.Add(New XmlExtractItemPk(XmlExtractItemType.Groups, maintUnitId), True)
    
    ' Execute the metadata extract
    Using dbConnFW As DbConnInfo = BRApi.Database.CreateFrameworkDbConnInfo(si)
        Using dbConnApp As DbConnInfo = BRApi.Database.CreateApplicationDbConnInfo(si)
            Dim xmlContent As String = XmlExtractController.ExtractXml(
                dbConnFW,
                dbConnApp,
                Nothing,
                xmlOptions,
                extractDict,
                XmlLoadExtractType.ApplicationWorkspaces
            )
    
            BRApi.ErrorLog.LogMessage(si, xmlContent)
    
            ' Write output to file
            File.WriteAllText(filePath, xmlContent)
        End Using
    End Using

     

  • You will have to go one by one and get everything under that maintenance unit. All items will get you all the maintenance units. You can then probably edit the XML and get what you want. But if it is just a backup, I would go with all options and back up all the maintenance units.

  • db_pdx's avatar
    db_pdx
    Valued Contributor

    Does it have to be a BR? This is exactly what XFProject files solve: the export and import of full maintenance units with as little as 5 lines of xml.

  • NitishKrishB's avatar
    NitishKrishB
    New Contributor

    RobbSalzmann​ , ckattookaran​ , db_pdx​ - Thank you all for your valuable responses.

    Robb - I wrote the below code to extract entire maintenance unit without specifying each objects and it is working as expected. Here, I made "isExtractAllItems = True". The code isolates the desired maintenance unit from the extracted XML, reconstructs a minimal XML structure containing just this unit (and its workspace context), and saves the result as a new XML file for backup or migration purposes. And both the methods were tested and both works as expected. 

    Thanks everyone for the inputs!
    Cheers!

    Case Is = ExtenderFunctionType.Unknown, ExtenderFunctionType.ExecuteDataMgmtBusinessRuleStep
    					
    						
    						'Get Configuration Settings
    							Dim configSettings As AppServerConfigSettings = AppServerConfig.GetSettings(si)
    							'Data Management extract location
    							Dim folderPath As String = FileShareFolderHelper.GetDataManagementExportUsernameFolderForApp(si, True, configSettings.FileShareRootFolder,
    							 si.AppToken.AppName
    							 ) & "\" & DateTime.UtcNow.ToString("yyyyMMdd") & "\Extracts"  'If the directory does not exist create
    						If Not Directory.Exists(folderPath) Then Directory.CreateDirectory(folderPath)
    							'Full path and file name for extract
    							Dim filePath As String = folderPath & "\Dashboards " & DateTime.UtcNow.ToString("yyyyMMdd") & ".xml"
    						'If file already exist
    						If File.Exists(filePath) Then File.Delete(filePath)
    						
    							Dim isExtractAllItemsTrue = True
    							Dim isExtractUniqueIdsTrue = True 
    							Dim xmlOptions As New XmlExtractOptions(isExtractAllItemsTrue, isExtractUniqueIdsTrue) 
    							Dim xmlString As String = String.Empty
    							Dim maintUnitToExtract As String = "YourMaintenanceUnit"							
    							
    							
    							' extract specified items doesn't seem to work, but we need it
    							Dim extractDict As New Dictionary(Of XmlExtractItemPk, Boolean) From {
    								{New XmlExtractItemPk(XmlExtractItemType.DashboardMaintUnit, maintUnitToExtract), True}
    																								}	
    							
    							'Execute the Metadata Extract
    							Using dbConnFW As DBConnInfo = BRAPi.Database.CreateFrameworkDbConnInfo(si)
    								Using dbConnApp As DBConnInfo = BRAPi.Database.CreateApplicationDbConnInfo(si)
    									xmlString = XmlExtractController.ExtractXML(dbConnFW, dbConnApp, Nothing, xmlOptions, extractDict, XmlLoadExtractType.ApplicationWorkspaces)
    								End Using
    							End Using	
    							
    							Dim xmlDoc As XDocument = XDocument.Parse(xmlString)
    							Dim extractedMaintUnitElement As XElement = xmlDoc.Descendants("maintenanceUnit").Where(Function(mu) mu.Attribute("name").Value = maintUnitToExtract).FirstOrDefault()
    							
    							If extractedMaintUnitElement IsNot Nothing Then
    							    Dim workspaceElement = extractedMaintUnitElement.Ancestors("workspace").FirstOrDefault()
    							    Dim newWorkspaceElement As New XElement("workspace", workspaceElement.Attributes())
    							    newWorkspaceElement.Add(New XElement("maintenanceUnits", extractedMaintUnitElement))
    						
    							    Dim newXmlDoc As New XDocument(
    							        New XElement("OneStreamXF", xmlDoc.Root.Attributes(),
    							            New XElement("applicationWorkspacesRoot",
    							            	New XElement("workspaces", newWorkspaceElement)
    							            )
    							        )
    							    )
    							    newXmlDoc.Save(filePath)
    							
    							End If		
    				End Select