functions/export-axmodelv2.ps1

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184

<#
    .SYNOPSIS
        Export AX 2012 model
         
    .DESCRIPTION
        Export AX 2012 model from the AX 2012 model store
         
    .PARAMETER DatabaseServer
        Server name of the database server
         
        Default value is: "localhost"
         
    .PARAMETER ModelstoreDatabase
        Name of the modelstore database
         
        Default value is: "MicrosoftDynamicsAx_model"
         
        Note: From AX 2012 R2 and upwards you need to provide the full name for the modelstore database. E.g. "AX2012R3_PROD_model"
         
    .PARAMETER Path
        Path to the location where you want the file to be exported
         
        Default value is: "c:\temp\ax2012.tools"
         
    .PARAMETER Name
        Name of the AX 2012 model that you are looking for
         
        Accepts wildcards for searching. E.g. -Name "ISV*MODULE*"
         
        Default value is "*" which will search for all models
         
    .PARAMETER Id
        Id of the AX 2012 model that you are looking for
         
        Accepts wildcards for searching. E.g. -Id "2*"
         
        Default value is "*" which will search for all models
         
    .PARAMETER Layer
        Layer where the AX 2012 model that you are looking for should reside
         
        Accepts wildcards for searching. E.g. -Layer "IS*"
         
        Default value is "*" which will search for models in all layers
         
    .PARAMETER ShowOriginalProgress
        Instruct the cmdlet to show the standard output in the console
         
        Default is $false which will silence the standard output
         
    .PARAMETER OutputCommandOnly
        Instruct the cmdlet to output the script to execute the command in hand
         
    .EXAMPLE
        PS C:\> Get-AxAosInstance | Export-AxModelV2
         
        This will fetch all the AX 2012 AOS instances that are configured on the machine.
        Foreach of the instances it will export all AX 2012 Models into a sub folder to "c:\temp\ax2012.tools".
         
    .EXAMPLE
        PS C:\> Export-AxModelV2 -DatabaseServer localhost -ModelstoreDatabase MicrosoftDynamicsAx_model -Name *CUS*
         
        This will fetch all the AX 2012 AOS instances that are configured on the machine.
        Foreach of the instances it will export all AX 2012 Models into a sub folder to "c:\temp\ax2012.tools".
         
    .NOTES
        Author: Mötz Jensen (@Splaxi)
         
#>

Function Export-AxModelV2 {
    [CmdletBinding()]
    [OutputType([System.String], ParameterSetName="Generate")]
    Param(
        [Parameter(ValueFromPipelineByPropertyName = $true)]
        [string] $DatabaseServer = $Script:ActiveAosDatabaseserver,

        [Parameter(ValueFromPipelineByPropertyName = $true)]
        [string] $ModelstoreDatabase = $Script:ActiveAosModelstoredatabase,
        
        [string] $Path = $Script:DefaultTempPath,

        [string] $Name = "*",

        [string] $Id = "*",

        [string] $Layer = "*",

        [switch] $ShowOriginalProgress,

        [Parameter(ParameterSetName = "Generate")]
        [switch] $OutputCommandOnly
    )

    BEGIN {
        if (-not ($OutputCommandOnly)) {
            if (-not (Test-PathExists -Path $Path -Type Container -Create)) { return }
            $backupFilePath = New-FolderWithDateTime -Path $Path
        }
        else {
            $backupFilePath = New-FolderWithDateTime -Path $Path -NoCreate
        }

        $null = Import-Module $Script:AxPowerShellModule
    }

    PROCESS {
        Invoke-TimeSignal -Start

        $xml = (Get-AXModel -Server $DatabaseServer -Database $ModelstoreDatabase | ConvertTo-Xml )
        $nodes = $xml.SelectNodes("Objects/Object")

        foreach ($obj in $nodes) {
            $filenameAxModel = ""
            $modelId = ""
            $modelLayer = ""
            $modelName = ""

            # Loop all properties
            foreach ($property in $obj.SelectNodes("Property")) {
                if ($property.GetAttribute("Name").Equals( "Name" )) {
                    $modelName = $property.InnerText
                }
        
                if ($property.GetAttribute("Name").Equals( "Layer" )) {
                    $modelLayer = $property.InnerText
                }
        
                if ($property.GetAttribute("Name").Equals( "ModelId" )) {
                    $modelId = $property.InnerText
                }
            }
    
            $filenameAxModel = $modelId + "_" + $modelName + ".axmodel"

            Write-PSFMessage -Level Verbose -Message "Testing that ModelName, ModelId and Layer matches the search criteria"
            if ($modelName -NotLike $Name) { continue }
            if ($modelId -NotLike $Id) { continue }
            if ($modelLayer -NotLike $Layer) { continue }

            if ($Script:LayerDictionary.ContainsKey($modelLayer.ToUpper()) -and $filenameAxModel -ne "") {
                $localLayer = $Script:LayerDictionary.Get_Item($modelLayer.ToUpper()) + $modelLayer.ToUpper()
                $tempPath = Join-Path $backupFilePath $localLayer
        
                $filenameAxModel = Join-Path $tempPath $filenameAxModel

                $params = @{Model = $modelName; File = $filenameAxModel;
                    Server = $DatabaseServer; Database = $ModelstoreDatabase
                }

                if ($OutputCommandOnly) {
                    $arguments = Convert-HashToArgString -InputObject $params

                    "Export-AXModel $($arguments -join ' ')"
                }
                else {
                    if (-not (Test-PathExists -Path $tempPath -Type Container -Create)) { return }

                    Write-PSFMessage -Level Verbose -Message "Starting the export of the ax model file"
                    $outputRes = Export-AXModel @params

                    if ($ShowOriginalProgress) {
                        $outputRes
                    }
                }
            }
            else {
                Write-PSFMessage -Level Verbose -Message "Skipping $filenameAxModel in layer $modelLayer"
            }
        }

        Invoke-TimeSignal -End
    }

    END {
        if (-not ($OutputCommandOnly)) {
            [PSCustomObject]@{
                Path = $backupFilePath
            }
        }

        Clear-Ax2012StandardPowershellModule
    }
}