DynatracePS.psm1
### --- PUBLIC FUNCTIONS --- ### #Region - Connect-DynatraceAccountManagement.ps1 function Connect-DynatraceAccountManagement { <# .SYNOPSIS Connect to the Dynatrace Account Management API for SaaS. internal use .DESCRIPTION Connect to the Dynatrace Account Management API for SaaS. internal use .PARAMETER OauthClientSecret Client secret generated from the Manage account API OAuth Clients page .PARAMETER AccountUuid Account UUID from Dynatrace .PARAMETER GetNewToken Force getting a fresh token .EXAMPLE Connect-DynatraceAccountManagement .NOTES https://account.dynatrace.com/my/enterprise-api? #> [CmdletBinding()] param( [String]$OauthClientSecret, [String]$AccountUuid, [Switch]$GetNewtoken ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $config = Get-DynatracePSConfig $AccountUuid = $config.AccountUuid $OauthClientSecret = $config.OauthClientSecret if (-not $AccountUuid) { Write-Warning "[$($MyInvocation.MyCommand.Name)] AccountUuid is required. Please use Set-DynatracePSConfig first. Exiting..." break } if (-not $OauthClientSecret) { Write-Warning "[$($MyInvocation.MyCommand.Name)] OauthClientSecret is required. Please use Set-DynatracePSConfig first. Exiting..." break } $GetTokenURL = 'https://sso.dynatrace.com/sso/oauth2/token' $client_id = (($OauthClientSecret -split '\.') | Select-Object -First 2) -join '.' $scope = 'account-idm-read account-idm-write' $resource = "urn:dtaccount:$AccountUuid" $Body = @{ grant_type = 'client_credentials' client_id = $client_id client_secret = $OauthClientSecret scope = $scope resource = $resource } $ContentType = 'application/x-www-form-urlencoded' $TokenData = $MyInvocation.MyCommand.Module.PrivateData.TokenData } process { Write-Debug "[$($MyInvocation.MyCommand.Name)] TokenData: $($TokenData | Out-String)" $Now = Get-Date if (($Now -lt $TokenData.token_expires) -and (-not $GetNewtoken)) { Write-Debug "[$($MyInvocation.MyCommand.Name)] Existing token should still be good, using it" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Existing token should still be good, using it" } else { Write-Debug "[$($MyInvocation.MyCommand.Name)] Getting new token" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Getting new token" try { $splatParameter = @{ Uri = $GetTokenURL Method = 'POST' Body = $body ContentType = $ContentType } $GetTokenReturn = (Invoke-WebRequest @splatParameter).Content | ConvertFrom-Json Write-Debug "[$($MyInvocation.MyCommand.Name)] Adding results to module PrivateData" $TokenData = @{ 'scope' = $GetTokenReturn.scope 'token_type' = $GetTokenReturn.token_type 'expires_in' = $GetTokenReturn.expires_in 'access_token' = $GetTokenReturn.access_token 'resource' = $GetTokenReturn.resource 'token_expires' = (Get-Date).AddSeconds($GetTokenReturn.expires_in) } $MyInvocation.MyCommand.Module.PrivateData.TokenData = $TokenData } catch { Write-Warning "[$($MyInvocation.MyCommand.Name)] Problem getting $GetTokenURL" $_ break } } # return everything to the pipeline $TokenData } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Connect-DynatraceAccountManagement #EndRegion - Connect-DynatraceAccountManagement.ps1 #Region - Get-DynatraceContainer.ps1 function Get-DynatraceContainer { <# .SYNOPSIS Gets containers in Dynatrace environment .DESCRIPTION Gets containers in Dynatrace environment .EXAMPLE Get-DynatraceContainer .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/entities" $GetParameter = @{ entitySelector = 'type("CONTAINER_GROUP_INSTANCE")' pageSize = 500 } Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri GetParameter = $GetParameter RestResponseProperty = 'entities' } Invoke-DynatraceAPIMethod @splatParameters } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceContainer #EndRegion - Get-DynatraceContainer.ps1 #Region - Get-DynatraceEffectivePermission.ps1 function Get-DynatraceEffectivePermission { <# .SYNOPSIS Gets effective permissions for a user or group .DESCRIPTION Gets effective permissions for a user or group .PARAMETER levelType The type of the policy level. Valid values: account or environment .PARAMETER levelId The ID of the policy level. for account, use the UUID of the account. For environment, use the ID of the environment. .PARAMETER entityType The entity type. Valid values: user or group .PARAMETER entityId The entity id .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceEffectivePermission -levelType account -levelID <accountUuid> .EXAMPLE Get-DynatraceEffectivePermission -levelType environment -levelID <environment id> .NOTES https://api.dynatrace.com/spec/#/Policy%20management/PolicyController_getEffectivePermissions #> [CmdletBinding()] param( [Parameter(Mandatory)] [ValidateSet('account','environment')] [String]$levelType, [Parameter(Mandatory)] [String]$levelID, [String]$entityType, [String]$entityId, [switch]$explain, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $RestPath = "/iam/v1/resolution/$levelType/$levelID/effectivepermissions" $UrlParameters = "?entityType=$entityType&entityID=$entityID&explain=$explain" Write-Verbose "[$($MyInvocation.MyCommand.Name)] RestPath: $RestPath" Write-Verbose "[$($MyInvocation.MyCommand.Name)] URLParameters: $URLParameters" $path = "$RestPath$URLParameters" } process { try { $splatParameters = @{ RestPath =$path OutputAsJson = $OutputAsJson } Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceEffectivePermission #EndRegion - Get-DynatraceEffectivePermission.ps1 #Region - Get-DynatraceEntity.ps1 function Get-DynatraceEntity { <# .SYNOPSIS Get entities in Dynatrace environment .DESCRIPTION Get entities in Dynatrace environment .PARAMETER Type The type of entity to get .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceEntity -Type HOST_GROUP .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param( [Parameter(Mandatory)] [String]$Type, [Switch]$outputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/entities" $GetParameter = @{ entitySelector = "type(`"$Type`")" pageSize = 200 } Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri GetParameter = $GetParameter RestResponseProperty = 'entities' } $output = Invoke-DynatraceAPIMethod @splatParameters if ($OutputAsJson) { $output | ConvertTo-Json -Depth 6 } else { $output } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceEntity #EndRegion - Get-DynatraceEntity.ps1 #Region - Get-DynatraceEntityProperty.ps1 function Get-DynatraceEntityProperty { <# .SYNOPSIS Get properties for a specified entity in Dynatrace environment .DESCRIPTION Get properties for a specified entity in Dynatrace environment .PARAMETER entityID The entity ID .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceEntityProperty -entityID HOST-9FADEDA85A24F460 .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param( [Parameter(Mandatory)] [String]$entityID, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/entities/$entityID" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri } $output = Invoke-DynatraceAPIMethod @splatParameters if ($OutputAsJson) { $output | ConvertTo-Json -Depth 6 } else { $output } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceEntityProperty #EndRegion - Get-DynatraceEntityProperty.ps1 #Region - Get-DynatraceEntityType.ps1 function Get-DynatraceEntityType { <# .SYNOPSIS Get list of entity types in Dynatrace environment .DESCRIPTION Get list of entity types in Dynatrace environment .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceEntityType .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/entityTypes" $GetParameter = @{ pageSize = 200 } Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri GetParameter = $GetParameter RestResponseProperty = 'types' } $output = Invoke-DynatraceAPIMethod @splatParameters if ($OutputAsJson) { $output | ConvertTo-Json -Depth 6 } else { $output } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceEntityType #EndRegion - Get-DynatraceEntityType.ps1 #Region - Get-DynatraceEnvironment.ps1 function Get-DynatraceEnvironment { <# .SYNOPSIS Lists all environments and management zones of a Dynatrace account .DESCRIPTION Lists all environments and management zones of a Dynatrace account .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceEnvironment .NOTES https://api.dynatrace.com/spec/#/Environment%20management/EnvironmentResourcesController_getEnvironmentResources #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/env/v1/accounts/$($AccountUuid)/environments" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceEnvironment #EndRegion - Get-DynatraceEnvironment.ps1 #Region - Get-DynatraceGroup.ps1 function Get-DynatraceGroup { <# .SYNOPSIS List the groups on a Dynatrace account .DESCRIPTION List the groups on a Dynatrace account .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceGroup .NOTES https://api.dynatrace.com/spec/#/Group%20management/GroupsController_getGroups #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/iam/v1/accounts/$($AccountUuid)/groups" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } $return = Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } Write-Verbose "[$($MyInvocation.MyCommand.Name)] Count of results: $($return.count)" if ($OutputAsJson) { $return } else { $return.items } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceGroup #EndRegion - Get-DynatraceGroup.ps1 #Region - Get-DynatraceGroupPermission.ps1 function Get-DynatraceGroupPermission { <# .SYNOPSIS List all permissions for a single user group .DESCRIPTION List all permissions for a single user group .PARAMETER GroupUuid The UUID of a user group .PARAMETER GroupName The name of a group .PARAMETER OutputNotNested Set to make it so output is not nested, helpful for exporting to excel .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceGroupPermission -groupUuid e5e9b12d-daf8-40d0-a6b5-7094667dd142 -OutputNotNested .EXAMPLE Get-DynatraceGroupPermission -GroupName 'Monitoring Viewer' .EXAMPLE Get-DynatraceGroup | %{Get-DynatraceGroupPermission -groupUuid $_.uuid} .NOTES https://api.dynatrace.com/spec/#/Group%20management/GroupsController_getUsersForGroup #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'Uuid')] [String]$groupUuid, [Parameter(Mandatory,ParameterSetName = 'Name')] [String]$GroupName, [switch]$OutputNotNested, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid if ($GroupName) { $groupUuid = (Get-DynatraceGroup | Where-Object{$_.Name -eq $GroupName}).Uuid } $RestPath = "/iam/v1/accounts/$AccountUuid/groups/$groupUuid/permissions" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" $output = @() } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } $result = Invoke-DynatraceAccountManagementAPIMethod @splatParameters if ($OutputNotNested) { # caching management zones for lookup # $mz = Get-DynatraceManagementZone foreach ($permission in $result.permissions) { if ($permission.scope -match ':') { # if there is colon in permissions scope, it will be a string # with environment name:management zone id # $splitPermissionScope = $permission.scope -split ':' $mzName = ($mz | Where-Object{$_.ID -eq $splitPermissionScope[1]}).Name $scope = "{0}:{1}" -f $splitPermissionScope[0],$mzName } else { $scope = $permission.scope; } $output += [pscustomobject]@{ uuid = $result.uuid; name = $result.name; owner = $result.owner; description = $result.description; hidden = $result.hidden; createdAt = $result.createdAt; updatedAt = $result.updatedAt; permissionName = $permission.permissionName; Scope = $scope; ScopeType = $permission.scopeType; permissionCreatedAt = $permission.createdAt; permissionUpdatedAt = $permission.updatedAt; } } } else { $output = $result } } catch { $_ break } } end { $output Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceGroupPermission #EndRegion - Get-DynatraceGroupPermission.ps1 #Region - Get-DynatraceGroupUser.ps1 function Get-DynatraceGroupUser { <# .SYNOPSIS List all members of a group on a Dynatrace account .DESCRIPTION List all members of a group on a Dynatrace account .PARAMETER GroupUuid The UUID of the user group .PARAMETER GroupName The Name of the group .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceGroupUser -groupUuid e5e9b12d-daf8-40d0-a6b5-7094667dd142 .EXAMPLE Get-DynatraceGroupUser -GroupName 'Monitoring Viewer' .NOTES https://api.dynatrace.com/spec/#/Group%20management/GroupsController_getUsersForGroup #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'Uuid')] [String]$groupUuid, [Parameter(Mandatory,ParameterSetName = 'Name')] [String]$GroupName, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid if ($GroupName) { $groupUuid = (Get-DynatraceGroup | Where-Object{$_.Name -eq $GroupName}).Uuid } $RestPath = "/iam/v1/accounts/$AccountUuid/groups/$groupUuid/users" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } $return = Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } Write-Verbose "[$($MyInvocation.MyCommand.Name)] Count of results: $($return.count)" if ($OutputAsJson) { $return } else { $return.items } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceGroupUser #EndRegion - Get-DynatraceGroupUser.ps1 #Region - Get-DynatraceHost.ps1 function Get-DynatraceHost { <# .SYNOPSIS Gets hosts in Dynatrace environment .DESCRIPTION Gets hosts in Dynatrace environment .EXAMPLE Get-DynatraceHost .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2 #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceEntity -Type 'HOST' } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHost #EndRegion - Get-DynatraceHost.ps1 #Region - Get-DynatraceHostGroup.ps1 function Get-DynatraceHostGroup { <# .SYNOPSIS Get host groups in Dynatrace environment .DESCRIPTION Get host groups in Dynatrace environment .EXAMPLE Get-DynatraceHostGroup .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2 #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceEntity -Type 'HOST_GROUP' } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHostGroup #EndRegion - Get-DynatraceHostGroup.ps1 #Region - Get-DynatraceHostGroupProperty.ps1 function Get-DynatraceHostGroupProperty { <# .SYNOPSIS Get properties for a host group .DESCRIPTION Get properties for a host group .PARAMETER Id Unique id of the host group .PARAMETER Name Name of the host group .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceHostGroupProperty -id hostgroupid .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2/get-entity #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $Id = (Get-DynatraceHostGroup | Where-Object {$_.displayName -eq $Name}).entityID } } process { $splatParm = @{ entityID = $Id OutputAsJson = $OutputAsJson } Get-DynatraceEntityProperty @splatParm } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHostGroupProperty #EndRegion - Get-DynatraceHostGroupProperty.ps1 #Region - Get-DynatraceHostProperty.ps1 function Get-DynatraceHostProperty { <# .SYNOPSIS Get properties for a host .DESCRIPTION Get properties for a host .PARAMETER Id Unique id of the host .PARAMETER Name Name of the host .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceHostProperty -id hostid .EXAMPLE Get-DynatraceHostProperty -Name hostname -OutputAsJson .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2/get-entity #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $Id = (Get-DynatraceHost | Where-Object {$_.displayName -eq $Name}).entityId Write-Verbose "[$($MyInvocation.MyCommand.Name)] Got $Name entityID value of $Id" } } process { $splatParm = @{ entityID = $Id OutputAsJson = $OutputAsJson } Get-DynatraceEntityProperty @splatParm } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHostProperty #EndRegion - Get-DynatraceHostProperty.ps1 #Region - Get-DynatraceHostsInHostGroup.ps1 function Get-DynatraceHostsInHostGroup { <# .SYNOPSIS Get hosts in host group .DESCRIPTION Get hosts in host group .PARAMETER Id Unique id of the host group .PARAMETER Name Name of the host group .EXAMPLE Get-DynatraceHostsInHostGroup -Name HOST_GROUP_NAME .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2/get-entity #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $Id = (Get-DynatraceHostGroup | Where-Object {$_.displayName -eq $Name}).entityID } $Output = @() $AllHosts = Get-DynatraceHost } process { $splatParm = @{ entityID = $Id } $Properties = Get-DynatraceEntityProperty @splatParm foreach ($Host_ in $Properties.toRelationships.isInstanceOf) { $Output += [PSCustomObject]@{ HostGroup = $Properties.displayName HostName = ($AllHosts | Where-Object{$_.entityID -eq $Host_.ID}).displayName } } $Output } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHostsInHostGroup #EndRegion - Get-DynatraceHostsInHostGroup.ps1 #Region - Get-DynatraceHTTPCheck.ps1 function Get-DynatraceHTTPCheck { <# .SYNOPSIS Get HTTP checks .DESCRIPTION Get HTTP Checks .EXAMPLE Get-DynatraceHTTPCheck .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2 #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceEntity -Type 'HTTP_CHECK' } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHTTPCheck #EndRegion - Get-DynatraceHTTPCheck.ps1 #Region - Get-DynatraceHTTPCheckProperty.ps1 function Get-DynatraceHTTPCheckProperty { <# .SYNOPSIS Get properties for an http check .DESCRIPTION Get properties for an http check .PARAMETER Id Entity id of the http check .PARAMETER Name Name of the http check .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceHTTPCheckProperty -id entityid .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2/get-entity #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $Id = (Get-DynatraceHTTPCheck | Where-Object {$_.displayName -eq $Name}).entityID } } process { $splatParm = @{ entityID = $Id OutputAsJson = $OutputAsJson } Get-DynatraceEntityProperty @splatParm } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHTTPCheckProperty #EndRegion - Get-DynatraceHTTPCheckProperty.ps1 #Region - Get-DynatraceHTTPCheckStatus.ps1 function Get-DynatraceHTTPCheckStatus { <# .SYNOPSIS Get results of all HTTP check monitor executions .DESCRIPTION Get results of all HTTP check monitor executions .PARAMETER All Get all records, not just the latest ones .EXAMPLE Get-DynatraceHTTPCheckStatus Return the most recent failed execution for all http check synthetic monitors .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/synthetic-v2/synthetic-monitor-execution/get-http-monitor #> [CmdletBinding()] param( [Switch]$All ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $HTTPChecks = Get-DynatraceHTTPCheck $SyntheticLocations = Get-DynatraceSyntheticLocation $Output = @() } process { foreach ($HTTPCheck in $HTTPChecks) { $SuccessResults = Get-DynatraceHTTPCheckMonitorExecution -monitorID $HTTPCheck.entityID -resultType SUCCESS $FailedResults = Get-DynatraceHTTPCheckMonitorExecution -monitorID $HTTPCheck.entityID -resultType FAILED foreach ($location in $SuccessResults.locationsExecutionResults) { $Output += [PSCustomObject]@{ MonitorName = $HTTPCheck.displayName Location = ($SyntheticLocations | Where-Object {$_.ID -eq $location.locationId}).Name ResponseStatusCode = $location.requestResults.ResponseStatusCode ResponseMessage = $location.requestResults.ResponseMessage HealthStatus = $location.requestResults.healthStatus StartTime = (ConvertTo-Datetime $location.requestResults.startTimestamp) WaitingTime = $location.requestResults.waitingTime } } foreach ($location in $FailedResults.locationsExecutionResults) { $Output += [PSCustomObject]@{ MonitorName = $HTTPCheck.displayName Location = ($SyntheticLocations | Where-Object {$_.ID -eq $location.locationId}).Name ResponseStatusCode = $location.requestResults.ResponseStatusCode ResponseMessage = $location.requestResults.ResponseMessage HealthStatus = $location.requestResults.healthStatus StartTime = (ConvertTo-Datetime $location.requestResults.startTimestamp) WaitingTime = $location.requestResults.waitingTime } } } if ($All) { $Output } else { $Output | Group-Object MonitorName | Foreach-Object {$_.Group | Sort-Object StartTime | Select-Object -Last 1} } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceHTTPCheckStatus #EndRegion - Get-DynatraceHTTPCheckStatus.ps1 #Region - Get-DynatraceManagementZone.ps1 function Get-DynatraceManagementZone { <# .SYNOPSIS Get list of management zones in Dynatrace environment .DESCRIPTION Get list of management zones in Dynatrace environment .EXAMPLE Get-DynatraceManagementZone .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri RestResponseProperty = 'values' } Invoke-DynatraceAPIMethod @splatParameters } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceManagementZone #EndRegion - Get-DynatraceManagementZone.ps1 #Region - Get-DynatraceManagementZoneProperty.ps1 function Get-DynatraceManagementZoneProperty { <# .SYNOPSIS Get properties of a management zone in Dynatrace environment .DESCRIPTION Get properties of a management zone in Dynatrace environment .PARAMETER Id The unique id of the management zone. Required if not using name .PARAMETER Name The name of the management zone. Required if not using id .PARAMETER OutputAsJson Output the management zone properties as Json .EXAMPLE Get-DynatraceManagementZoneProperty -id 1234554321 Get management zone properties associated with management zone with id of 1234554321. .EXAMPLE Get-DynatraceManagementZoneProperty -Name PROD_WINDOWS -OutputAsJson Get management zone properties for the management zone named PROD_WINDOWS and output them as json .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/get-mz #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $id = (Get-DynatraceManagementZone | Where-Object {$_.Name -eq $Name}).id } $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones/$id" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri } $output = Invoke-DynatraceAPIMethod @splatParameters if ($OutputAsJson) { $output | ConvertTo-Json -Depth 6 } else { $output } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceManagementZoneProperty #EndRegion - Get-DynatraceManagementZoneProperty.ps1 #Region - Get-DynatraceManagementZoneRule.ps1 function Get-DynatraceManagementZoneRule { <# .SYNOPSIS Get rules associated with a management zone in Dynatrace environment .DESCRIPTION Get rules associated with a management zone in Dynatrace environment .PARAMETER Id The unique id of the management zone. Required if not using name .PARAMETER Name The name of the management zone. Required if not using id .EXAMPLE Get-DynatraceManagementZoneRule -id 1234554321 Get management zone rules associated with management zone with id of 1234554321. .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/get-mz #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $id = (Get-DynatraceManagementZone | Where-Object {$_.Name -eq $Name}).id } $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones/$id" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" $output = @() } process { $return = Get-DynatraceManagementZoneProperty -id $id foreach ($rule in $return.Rules) { # using a for loop because the key is in one property # and the comparisons are in a different property # for ($i = 0; $i -lt ($rule.conditions).Count; $i++) { $condition = $rule.conditions[$i] $comparisonType = $condition.comparisonInfo.Type if ($condition.key.dynamicKey) { $key = $condition.key.dynamicKey } elseif ($condition.key.attribute) { $key = $condition.key.attribute } else { $key = '' } if ($comparisonType -eq 'TAG') { $comparisonType = "TAG:$($condition.comparisonInfo.value.key)" $value = "$($condition.comparisonInfo.value.value)" } elseif ($comparisonType -eq 'SIMPLE_TECH') { $comparisonType = "TECH:$($condition.comparisonInfo.value.type)" } else { $comparisonType = '' $value = $condition.comparisonInfo.value } $output += [PSCustomObject]@{ ManagementZoneName = $return.name RuleType = $rule.Type Enabled = $rule.enabled Key = $key ComparisonType = $comparisonType Operator = $condition.comparisonInfo.operator ComparisonValue = $value Negate = $condition.comparisonInfo.negate } } } $output } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceManagementZoneRule #EndRegion - Get-DynatraceManagementZoneRule.ps1 #Region - Get-DynatracePermission.ps1 function Get-DynatracePermission { <# .SYNOPSIS Lists all available permissions .DESCRIPTION Lists all available permissions .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatracePermission .NOTES https://api.dynatrace.com/spec/#/Reference%20data/ReferenceDataController_getPermissions #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $RestPath = "/ref/v1/account/permissions" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatracePermission #EndRegion - Get-DynatracePermission.ps1 #Region - Get-DynatraceProblem.ps1 function Get-DynatraceProblem { <# .SYNOPSIS Gets problem(s) in Dynatrace environment .DESCRIPTION Gets problem(s) in Dynatrace environment .PARAMETER From Start of the requested time frame. Defaults to now-2h There are several recognized formats available, see: https://www.dynatrace.com/support/help/shortlink/api-problems-v2-get-list#parameters .PARAMETER To End of the requested time frame. Defaults to current timestamp There are several recognized formats available, see: https://www.dynatrace.com/support/help/shortlink/api-problems-v2-get-list#parameters .PARAMETER Status Specific status of problem to get. may be open or closed. defaults to both .PARAMETER Raw Output the raw json result, no formatting of results .EXAMPLE Get-DynatraceProblem .EXAMPLE Get-DynatraceProblem -From now-12h Get all problems in last 12 hours .EXAMPLE Get-DynatraceProblem -From now-12h -To now-11h Get all problems between 12 and 11 hours ago .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/problems-v2/ #> [CmdletBinding()] param( #[Parameter(Mandatory,ParameterSetName = 'id')] #[string]$Id, #[Parameter(Mandatory,ParameterSetName = 'name')] #[string]$Name [string]$From, [string]$To, [ValidateSet('open','closed')] [string]$Status, [switch]$Raw ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/problems" $problemSelector = @() if ($Status) { $problemSelector += "status(`"$($Status)`")" } $GetParameter = @{} if ($from) { $GetParameter += @{from = $from} } if ($to) { $GetParameter += @{to = $to} } # If we had problems selectors, join them together and add to get # if ($problemSelector) { $problemSelectorJoined = $problemSelector -join ',' $GetParameter += @{ problemSelector = $problemSelectorJoined } } Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri GetParameter = $GetParameter RestResponseProperty = 'problems' } $problems = Invoke-DynatraceAPIMethod @splatParameters if ($Raw) { $output = $problems } else { $output = @() foreach ($problem in $problems) { $StartTime = ConvertTo-DateTime -TimeStamp $problem.StartTime if ($problem.EntTime -ne '-1') { $EndTime = ConvertTo-DateTime -TimeStamp $problem.EndTime } else { $EndTime = '' } $ManagementZones = $problem.managementZones.name -join ',' $AffectedEntities = $problem.AffectedEntities.name -join ',' $Tags = $problem.entityTags.stringRepresentation -join ',' $item = [PSCustomObject]@{ ProblemID = $problem.displayID Title = $problem.Title Impact = $problem.impactLevel Severity = $problem.severityLevel Status = $problem.status ManagementZones = $ManagementZones AffectedEntities = $AffectedEntities Tags = $tags StartTime = $StartTime EndTime = $EndTime } $output += $item } } $output } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceProblem #EndRegion - Get-DynatraceProblem.ps1 #Region - Get-DynatraceProcess.ps1 function Get-DynatraceProcess { <# .SYNOPSIS Get list of monitored processes from Dynatrace environment .DESCRIPTION Get list of monitored processes from Dynatrace environment .EXAMPLE Get-DynatraceProcess .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2 #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceEntity -Type 'PROCESS_GROUP_INSTANCE' } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceProcess #EndRegion - Get-DynatraceProcess.ps1 #Region - Get-DynatraceProcessGroup.ps1 function Get-DynatraceProcessGroup { <# .SYNOPSIS Get process groups in Dynatrace environment .DESCRIPTION Get process groups in Dynatrace environment .EXAMPLE Get-DynatraceProcessGroup .NOTES https://www.dynatrace.com/support/help/how-to-use-dynatrace/process-groups #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceEntity -Type 'PROCESS_GROUP' } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceProcessGroup #EndRegion - Get-DynatraceProcessGroup.ps1 #Region - Get-DynatraceProcessGroupProperty.ps1 function Get-DynatraceProcessGroupProperty { <# .SYNOPSIS Get process group properties from Dynatrace environment .DESCRIPTION Get process group properties from Dynatrace environment .PARAMETER Id Unique id of the process group .PARAMETER Name Name of the process group .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceProcessGroupProperty -Id <process-group-id> .EXAMPLE Get-DynatraceProcessGroupProperty -Name <process-group-name> -OutputAsJson .NOTES https://www.dynatrace.com/support/help/how-to-use-dynatrace/process-groups #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $entityIds = (Get-DynatraceProcessGroup | Where-Object {$_.displayName -eq $Name}).entityID } else { $entityIds = $Id } } process { foreach ($entityId in $entityIDs) { $splatParm = @{ entityID = $entityId OutputAsJson = $OutputAsJson } Get-DynatraceEntityProperty @splatParm } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceProcessGroupProperty #EndRegion - Get-DynatraceProcessGroupProperty.ps1 #Region - Get-DynatraceProcessProperty.ps1 function Get-DynatraceProcessProperty { <# .SYNOPSIS Get a process's properties from Dynatrace environment .DESCRIPTION Get a process's properties from Dynatrace environment .PARAMETER Id Unique id of the process .PARAMETER Name Name of the process .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceProcessProperty -Id <process-id> .EXAMPLE Get-DynatraceProcessProperty -Name <process-name> -OutputAsJson .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/entity-v2/get-entity #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$Id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $entityIds = (Get-DynatraceProcess | Where-Object {$_.displayName -eq $Name}).entityID } else { $entityIds = $Id } } process { foreach ($entityId in $entityIDs) { $splatParm = @{ entityID = $entityId OutputAsJson = $OutputAsJson } Get-DynatraceEntityProperty @splatParm } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceProcessProperty #EndRegion - Get-DynatraceProcessProperty.ps1 #Region - Get-DynatracePSConfig.ps1 function Get-DynatracePSConfig { <# .SYNOPSIS Get default configurations for DynatracePS from config.json file .DESCRIPTION Get default configurations for DynatracePS from config.json file .EXAMPLE Get-DynatracePSConfig #> [CmdletBinding()] [OutputType([PSCustomObject])] Param () begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $config = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\config.json" $OauthXmlFile = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\OauthSecret.xml" $AccessXmlFile = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\AccessToken.xml" } process { $Output = [PSCustomObject]@() if (Test-Path $config) { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Getting config from [$config]" if (Test-Path $OauthXmlFile) { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Getting Oauth Secret from [$OauthXmlFile]" $OauthCredential = [PSCredential](Import-Clixml $OauthXmlFile) $OauthClientSecret = $OauthCredential.GetNetworkCredential().Password } else { $OauthClientSecret = '' } if (Test-Path $AccessXmlFile) { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Getting Access Token from [$AccessXmlFile]" $AccessCredential = [PSCredential](Import-Clixml $AccessXmlFile) $AccessToken = $AccessCredential.GetNetworkCredential().Password } else { $AccessToken = '' } $Output = (Get-Content -Path "$config" -ErrorAction Stop | ConvertFrom-Json) $Output | Add-Member -MemberType NoteProperty -Name OauthClientSecret -Value $OauthClientSecret $Output | Add-Member -MemberType NoteProperty -Name AccessToken -Value $AccessToken } else { Write-Warning "[$($MyInvocation.MyCommand.Name)] No config found at [$config]" Write-Warning "[$($MyInvocation.MyCommand.Name)] Use Set-DynatracePSConfig first!" break } $Output } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function complete" } } # end function Export-ModuleMember -Function Get-DynatracePSConfig #EndRegion - Get-DynatracePSConfig.ps1 #Region - Get-DynatraceQuota.ps1 function Get-DynatraceQuota { <# .SYNOPSIS Gets the host units quota of a Dynatrace account .DESCRIPTION Gets the host units quota of a Dynatrace account .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceQuote .NOTES https://api.dynatrace.com/spec/#/Quota%20management/QuotaController_getQuota #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/env/v1/accounts/$($AccountUuid)/quotas/host-monitoring" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceQuota #EndRegion - Get-DynatraceQuota.ps1 #Region - Get-DynatraceSettingsSchema.ps1 function Get-DynatraceSettingsSchema { <# .SYNOPSIS Get list of settings schemas in Dynatrace environment .DESCRIPTION Get list of settings schemas in Dynatrace environment .EXAMPLE Get-DynatraceSettingsSchema .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/settings/schemas" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri RestResponseProperty = 'items' } Invoke-DynatraceAPIMethod @splatParameters } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceSettingsSchema #EndRegion - Get-DynatraceSettingsSchema.ps1 #Region - Get-DynatraceSubscription.ps1 function Get-DynatraceSubscription { <# .SYNOPSIS Lists all Dynatrace platform subscriptions of an account .DESCRIPTION Lists all Dynatrace platform subscriptions of an account .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceSubscription .NOTES https://api.dynatrace.com/spec/#/Dynatrace%20platform%20subscription/LimaClaController_getClaSubscriptions #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/sub/v1/accounts/$($AccountUuid)/subscriptions" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } $return = Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } Write-Verbose "[$($MyInvocation.MyCommand.Name)] Count of results: $($return.totalCount)" if ($OutputAsJson) { $return | ConvertTo-Json -Depth 6 } else { $return.records } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceSubscription #EndRegion - Get-DynatraceSubscription.ps1 #Region - Get-DynatraceSyntheticLocation.ps1 function Get-DynatraceSyntheticLocation { <# .SYNOPSIS Lists all locations, public and private, and their parameters available for your environment .DESCRIPTION Lists all locations, public and private, and their parameters available for your environment Access token must have Read synthetic locations (syntheticLocations.read) scope. .PARAMETER Type Get only locations of the specified type. May be PUBLIC or PRIVATE. Optional. .EXAMPLE Get-DynatraceSyntheticLocation .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/synthetic-v2/synthetic-locations-v2/get-all-locations #> [CmdletBinding()] param( [string]$Type ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $locationsUri = "https://$EnvironmentID.live.dynatrace.com/api/v2/synthetic/locations" if ($Type) { $GetParameter = @{ type = $Type.ToUpper() } } $output = @() } process { $splatParameters = @{ Uri = $locationsUri RestResponseProperty = 'locations' GetParameter = $GetParameter } $results = Invoke-DynatraceAPIMethod @splatParameters foreach ($result in $results) { # Get the decimal value from the hex in the entityID # $id = [uint64]($result.entityID -replace 'SYNTHETIC_LOCATION-','0x') # Add it to the result # $result | Add-Member -MemberType NoteProperty -Name 'ID' -Value $id $result } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceSyntheticLocation #EndRegion - Get-DynatraceSyntheticLocation.ps1 #Region - Get-DynatraceTag.ps1 function Get-DynatraceTag { <# .SYNOPSIS Get tags in Dynatrace environment .DESCRIPTION Get tags in Dynatrace environment .PARAMETER entitySelector The entity selector string to get the tags for. Example: 'type("HOST")' .EXAMPLE Get-DynatraceTag -entitySelector 'type("HOST")' Get all the tags for HOST entities .EXAMPLE Get-DynatraceTag -entitySelector 'type("HOST_GROUP")' Get all the tags for HOST_GROUP entities .EXAMPLE Get-DynatraceTag -entitySelector 'entityId("123456789")' Get the tags associated with entity with ID of 123456789 .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/custom-tags/get-tags #> [CmdletBinding()] param( [Parameter(Mandatory)] [string]$entitySelector ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/v2/tags" $GetParameter = @{ entitySelector = $entitySelector } Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { $splatParameters = @{ Uri = $uri GetParameter = $GetParameter #RestResponseProperty = 'tags' } Invoke-DynatraceAPIMethod @splatParameters } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceTag #EndRegion - Get-DynatraceTag.ps1 #Region - Get-DynatraceUser.ps1 function Get-DynatraceUser { <# .SYNOPSIS List the users of a Dynatrace account .DESCRIPTION List the users of a Dynatrace account .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceUser .NOTES https://api.dynatrace.com/spec/#/User%20management/UsersController_getUsers #> [CmdletBinding()] param( [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/iam/v1/accounts/$($AccountUuid)/users" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } $return = Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } Write-Verbose "[$($MyInvocation.MyCommand.Name)] Count of results: $($return.count)" if ($OutputAsJson) { $return } else { $return.items } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceUser #EndRegion - Get-DynatraceUser.ps1 #Region - Get-DynatraceUserGroup.ps1 function Get-DynatraceUserGroup { <# .SYNOPSIS List the groups for a user .DESCRIPTION List the groups for a user .PARAMETER OutputAsJson Output the properties as a JSON string .EXAMPLE Get-DynatraceUserGroup -Email name@domain.com .NOTES https://api.dynatrace.com/spec/#/User%20management/UsersController_getUserGroups #> [CmdletBinding()] param( [Parameter(Mandatory)] [String]$Email, [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $AccountUuid = (Get-DynatracePSConfig).AccountUuid $RestPath = "/iam/v1/accounts/$($AccountUuid)/users/$Email" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $RestPath" } process { try { $splatParameters = @{ RestPath =$RestPath OutputAsJson = $OutputAsJson } Invoke-DynatraceAccountManagementAPIMethod @splatParameters } catch { $_ break } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceUserGroup #EndRegion - Get-DynatraceUserGroup.ps1 #Region - Get-DynatraceUserLastLogin.ps1 function Get-DynatraceUserLastLogin { <# .SYNOPSIS List the users with last login time .DESCRIPTION List the users with last login time .EXAMPLE Get-DynatraceUserLastLogin .NOTES https://api.dynatrace.com/spec/#/User%20management/UsersController_getUsers #> [CmdletBinding()] param() begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" } process { Get-DynatraceUser | Select-Object email, @{ n='lastSuccessfulLoginUTC'; e={ ($_.userLoginMetadata).lastSuccessfulLogin } }, @{ n='lastSuccessfulLoginLocal'; e={ $ParsedDateTime = Get-Date ($_.userLoginMetadata).lastSuccessfulLogin; $ParsedDateTime.ToLocalTime() } }, @{ n='successfulLoginCounter'; e={ ($_.userLoginMetaData).successfulLoginCounter } } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Get-DynatraceUserLastLogin #EndRegion - Get-DynatraceUserLastLogin.ps1 #Region - New-DynatraceManagementZone.ps1 function New-DynatraceManagementZone { <# .SYNOPSIS Create new Dynatrace Management Zone .DESCRIPTION Create new Dynatrace Management Zone .PARAMETER Name Name of the management zone .PARAMETER Description Description for the management zone .PARAMETER Rules One or more management zone rule objects See https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/post-mz#definition--MzRule .EXAMPLE $Rule = New-DynatraceMzRuleHostGroup -HostGroupName 'TEST_HG' New-DynatraceManagementZone -Name 'Test MZ' -Rules $Rule Create a new management zone named `Test MZ`, with a rule that maps TEST_HG host group to the new management zone .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/post-mz #> [CmdletBinding(SupportsShouldProcess)] param( [string]$Name, [string]$Description, [PSCustomObject]$Rules ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones" $uriValidator = "$uri/validator" $Headers = @{ 'Content-Type' = 'application/json' } $Body = [ordered]@{ name = $Name rules = @($Rules) } $JsonBody = $Body | ConvertTo-Json -Depth 10 Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { # First call is to validator URL -- this confirms the payload is valid $splatParameters = @{ Uri = $uriValidator Method = 'POST' Body = $JsonBody Headers = $Headers } Invoke-DynatraceAPIMethod @splatParameters # Second call is to actually create $splatParameters.Uri = $uri if ($PSCmdlet.ShouldContinue('Would you like to continue?',"Creating new management zone $Name")) { Invoke-DynatraceAPIMethod @splatParameters } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function New-DynatraceManagementZone #EndRegion - New-DynatraceManagementZone.ps1 #Region - New-DynatraceMzRuleHostGroup.ps1 Function New-DynatraceMzRuleHostGroup { <# .SYNOPSIS Output a management zone rule object for a host group .DESCRIPTION Output a management zone rule object for mapping host group to a management zone .PARAMETER HostGroupID Entity ID of the host group for the rule .PARAMETER HostGroupName Host group name, will be used to look up the entity ID of the hose group .NOTES This page contains the format of what the rule object should look like: https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/post-mz#example #> [CmdletBinding()] [OutputType([PSCustomObject])] Param ( [string]$HostGroupID, [string]$HostGroupName ) begin { $output = @{} if ($HostGroupName) { $HostGroupID = (Get-DynatraceHostGroup | Where-Object {$_.DisplayName -eq $HostGroupName}).entityID } $conditions = @() } process { $conditions += ( [ordered]@{ key = [ordered]@{ attribute = 'HOST_GROUP_ID' type = 'STATIC' } comparisonInfo = [ordered]@{ type = 'ENTITY_ID' operator = 'EQUALS' value = $HostGroupID negate = $false } } ) $output = [ordered]@{ type = 'HOST' enabled = $true propagationTypes = @() conditions = $conditions } } # end process end { $output } } Export-ModuleMember -Function New-DynatraceMzRuleHostGroup #EndRegion - New-DynatraceMzRuleHostGroup.ps1 #Region - Remove-DynatraceManagementZone.ps1 function Remove-DynatraceManagementZone { <# .SYNOPSIS Remove the specified Management Zone .DESCRIPTION Remove the specified Management Zone .PARAMETER ID Entity ID of the management zone to remove. Required if not using Name .PARAMETER Name Name of the management zone to remove. Required if not using ID .EXAMPLE Remove-DynatraceManagementZone -Name 'Test MZ' .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/del-mz #> [CmdletBinding(SupportsShouldProcess)] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" if ($Name) { $id = (Get-DynatraceManagementZone | Where-Object {$_.Name -eq $Name}).id } else { $Name = (Get-DynatraceManagementZone | Where-Object {$_.id -eq $id}).Name } $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones/$id" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" Write-Debug "[$($MyInvocation.MyCommand.Name)] $Uri" } process { # First call is to validator URL -- this confirms the payload is valid $splatParameters = @{ Uri = $uri Method = 'DELETE' } Write-Debug "[$($MyInvocation.MyCommand.Name)] splatParameters: $($splatParameters | Out-String)" if ($PSCmdlet.ShouldContinue('Would you like to continue?',"Remove management zone $Name")) { Invoke-DynatraceAPIMethod @splatParameters } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Remove-DynatraceManagementZone #EndRegion - Remove-DynatraceManagementZone.ps1 #Region - Rename-DynatraceManagementZone.ps1 function Rename-DynatraceManagementZone { <# .SYNOPSIS Rename a Management zone .DESCRIPTION Rename a Management zone .PARAMETER Id The unique id of the management zone to rename. Required if not using name .PARAMETER Name The name of the management zone to rename. Required if not using id .PARAMETER NewName The new name of the management zone. .EXAMPLE Rename-DynatraceManagementZone -id 1234554321 -NewName 'MANAGEMENT_ZONE_1' .EXAMPLE Rename-DynatraceManagementZone -Name 'MANAGEMENT_ZONE' -NewName 'MANAGEMENT_ZONE_1' .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/get-mz #> [CmdletBinding()] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [Parameter(Mandatory)] [string]$NewName ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $baseUri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones" Write-Verbose "[$($MyInvocation.MyCommand.Name)] baseUri: $baseUri" } process { # If name was used, we need the mz id # if ($Name) { $id = (Get-DynatraceManagementZone | Where-Object {$_.Name -eq $Name}).id } $ExistingMZ = Get-DynatraceManagementZoneProperty -id $id $ExistingMZ.Name = $NewName $body = $ExistingMZ | ConvertTo-Json -Depth 5 $uri = "$baseUri/$id" $validatorUri = "$uri/validator" # Validate the payload $splatParameters = @{ Uri = $validatorUri Body = $body Method = 'Post' ContentType = 'application/json' } Invoke-DynatraceAPIMethod @splatParameters # it passed, do the actual post $splatParameters = @{ Uri = $Uri Body = $body Method = 'Put' ContentType = 'application/json' } Invoke-DynatraceAPIMethod @splatParameters } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Rename-DynatraceManagementZone #EndRegion - Rename-DynatraceManagementZone.ps1 #Region - Set-DynatracePSConfig.ps1 function Set-DynatracePSConfig { <# .SYNOPSIS Set the Dynatrace SaaS Environment ID to use when connecting .DESCRIPTION Set the Dynatrace SaaS Environment ID to use when connecting Saves the information to DynatracePS/config.json file in user profile .PARAMETER EnvironmentID Dynatrace SaaS Environment ID. This is the left most part of the hostname name: envid.live.dynatrace.com .PARAMETER AccountUuid Dynatrace Account ID. You can find the UUID on the Account > Account management API page, during creation of an OAuth client .PARAMETER OAuthClientSecret The client_secret value that is created in the Account management API page. Used for connecting to Dynatrace Account Management API .PARAMETER AccessToken The access token or personal access token for Dynatrace API .EXAMPLE Set-DynatracePSConfig -EnvironmentID 'envid' -AccountUuid 'dynatrace-account-id' .NOTES https://www.dynatrace.com/support/help/dynatrace-api/basics/dynatrace-api-authentication#tabgroup--generate-token--personal-access-token https://www.dynatrace.com/support/help/get-started/access-tokens #> [CmdletBinding()] [Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseShouldProcessForStateChangingFunctions', '', Justification='This function is trivial enough that we do not need ShouldProcess')] [Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSAvoidUsingConvertToSecureStringWithPlainText', '', Justification='There is no other easy way to do this. at least i can not come up with it at 1am')] Param ( [String]$EnvironmentID, [String]$AccountUuid, [String]$OAuthClientSecret, [String]$AccessToken ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" $cliXmlFile = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\OauthSecret.xml" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Oauth secret will be stored in $($OauthXmlFile)" $AccessXmlFile = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\AccessToken.xml" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Access token will be stored in $($AccessXmlFile)" $configPath = "$([Environment]::GetFolderPath('ApplicationData'))\DynatracePS\config.json" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Configuration will be stored in $($configPath)" if (-not (Test-Path $configPath)) { # If the config file doesn't exist, create it $null = New-Item -Path $configPath -ItemType File -Force } } process { $ExistingConfig = Get-DynatracePSConfig # If no environment ID passed in, and there is existing value, use existing if ((-not $EnvironmentID) -and ($ExistingConfig.EnvironmentID)) { $EnvironmentID = $ExistingConfig.EnvironmentID } if ((-not $AccountUuid) -and ($ExistingConfig.AccountUuid)) { $AccountUuid = $ExistingConfig.AccountUuid } $config = [ordered]@{ EnvironmentID = $EnvironmentID AccountUuid = $AccountUuid } $config | ConvertTo-Json | Set-Content -Path "$configPath" if ($OAuthClientSecret) { $username = 'DynatraceAccountManagement' $pass = ConvertTo-SecureString $OAuthClientSecret -AsPlainText -Force [PSCredential]$credential = New-Object System.Management.Automation.PSCredential( $UserName, $pass ) $credential | Export-Clixml $cliXmlFile } if ($AccessToken) { $username = 'DynatraceAccess' $pass = ConvertTo-SecureString $AccessToken -AsPlainText -Force [PSCredential]$credential = New-Object System.Management.Automation.PSCredential( $UserName, $pass ) $credential | Export-Clixml $AccessXmlFile } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" } } # end function Export-ModuleMember -Function Set-DynatracePSConfig #EndRegion - Set-DynatracePSConfig.ps1 #Region - Update-DynatraceManagementZone.ps1 function Update-DynatraceManagementZone { <# .SYNOPSIS Update the specified Management Zone .DESCRIPTION Update the specified Management Zone .PARAMETER ID Entity ID of the management zone to update. Required if not using Name .PARAMETER Name Name of the management zone to update. Required if not using ID .PARAMETER Description Updated description for the management zone .PARAMETER Rules One or more management zone rule objects See https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/post-mz#definition--MzRule .EXAMPLE $Rule = New-DynatraceMzRuleHostGroup -HostGroupName 'TEST_HG' New-DynatraceManagementZone -Name 'Test MZ' -Rules $Rule Create a new management zone named `Test MZ`, with a rule that maps TEST_HG host group to the new management zone .NOTES https://www.dynatrace.com/support/help/dynatrace-api/configuration-api/management-zones-api/put-mz #> [CmdletBinding(SupportsShouldProcess)] param( [Parameter(Mandatory,ParameterSetName = 'id')] [string]$id, [Parameter(Mandatory,ParameterSetName = 'name')] [string]$Name, [string]$Description, [PSCustomObject]$Rules ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $uri = "https://$EnvironmentID.live.dynatrace.com/api/config/v1/managementZones" $uriValidator = "$uri/validator" $Headers = @{ 'Content-Type' = 'application/json' } if ($Name) { $id = (Get-DynatraceManagementZone | Where-Object {$_.Name -eq $Name}).id } else { $Name = (Get-DynatraceManagementZone | Where-Object {$_.id -eq $id}).Name } $Body = [ordered]@{ id = $id name = $Name rules = @($Rules) } $JsonBody = $Body | ConvertTo-Json -Depth 10 Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { # First call is to validator URL -- this confirms the payload is valid $splatParameters = @{ Uri = $uriValidator Method = 'POST' Body = $JsonBody Headers = $Headers } Invoke-DynatraceAPIMethod @splatParameters # Second call is to actually update $splatParameters.Uri = $uri $splatParameters.Method = 'PUT' if ($PSCmdlet.ShouldContinue('Would you like to continue?',"Update management zone $Name")) { Invoke-DynatraceAPIMethod @splatParameters } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } Export-ModuleMember -Function Update-DynatraceManagementZone #EndRegion - Update-DynatraceManagementZone.ps1 ### --- PRIVATE FUNCTIONS --- ### #Region - ConvertTo-Datetime.ps1 Function ConvertTo-Datetime { <# .SYNOPSIS Convert a timestamp value from dynatrace (which uses millisecond timestamps) to a datetime .DESCRIPTION Convert a timestamp value from dynatrace (which uses millisecond timestamps) to a datetime .PARAMETER TimeStamp Timestamp value .NOTES https://community.dynatrace.com/t5/REST-API/Dynatrace-API-Timestamp/td-p/81309 #> param( [long]$TimeStamp ) begin { [DateTime]$Epoch = Get-Date 1970-01-01 } process { (($Epoch) + ([System.TimeSpan]::FromMilliseconds($TimeStamp))).ToLocalTime() } } #EndRegion - ConvertTo-Datetime.ps1 #Region - ConvertTo-GetParameter.ps1 function ConvertTo-GetParameter { <# .SYNOPSIS Generate the GET parameter string for an URL from a hashtable #> [CmdletBinding()] param ( [Parameter( Position = 0, Mandatory = $true, ValueFromPipeline = $true )] [hashtable]$InputObject ) process { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Making HTTP get parameter string out of a hashtable" Write-Verbose ($InputObject | Out-String) [string]$parameters = "?" # If the key is name nextPageKey is in the input object, it is *the only* # key that should be included in the parameters # if ('nextPageKey' -in $InputObject.Keys) { $value = $InputObject['nextPageKey'] $parameters += "nextPageKey=$($value)&" } else { foreach ($key in $InputObject.Keys) { $value = $InputObject[$key] $parameters += "$key=$($value)&" } } $parameters -replace ".$" } } #EndRegion - ConvertTo-GetParameter.ps1 #Region - ConvertTo-ParameterHash.ps1 function ConvertTo-ParameterHash { <# .SYNOPSIS Given a URI or uri query, return the query portion as a hash table. For internal use .DESCRIPTION Extract query portion from a URI and return it as a hash table. For internal use .PARAMETER Uri Uri to extract query from and convert to hash .PARAMETER Query Query to convert to hash #> [CmdletBinding( DefaultParameterSetName = 'ByString' )] param ( # URI from which to use the query [Parameter( Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName, ParameterSetName = 'ByUri' )] [Uri]$Uri, # Query string [Parameter( Position = 0, Mandatory, ParameterSetName = 'ByString' )] [String]$Query ) process { $GetParameter = @{} if ($Uri) { $Query = $Uri.Query } if ($Query -match "^\?.+") { $Query.TrimStart("?").Split("&") | ForEach-Object { $key, $value = $_.Split("=") $GetParameter.Add($key, $value) } } Write-Output $GetParameter } } #EndRegion - ConvertTo-ParameterHash.ps1 #Region - Get-DynatraceHTTPCheckMonitorExecution.ps1 function Get-DynatraceHTTPCheckMonitorExecution { <# .SYNOPSIS Get results of HTTP check monitor executions .DESCRIPTION Get results of HTTP check monitor executions .PARAMETER monitorID monitorID (entityID) identifier for which last execution result is returned .PARAMETER resultType SUCCESS or FAILED .EXAMPLE Get-DynatraceHTTPCheckMonitorExecution -monitorID HTTP_CHECK-0123456789ABCDEF -resultType SUCCESS Return the most recent SUCCESS execution for HTTP_CHECK-0123456789ABCDEF .NOTES https://www.dynatrace.com/support/help/dynatrace-api/environment-api/synthetic-v2/synthetic-monitor-execution/get-http-monitor #> [CmdletBinding()] param( [Parameter(Mandatory)] [string]$monitorID, [Parameter(Mandatory)][ValidateSet('SUCCESS','FAILED')] [string]$resultType ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $EnvironmentID = (Get-DynatracePSConfig).EnvironmentID $baseUri = "https://$EnvironmentID.live.dynatrace.com/api/v2/synthetic/execution/$monitorID/" } process { $uri = "$($baseUri)$resultType" Invoke-DynatraceAPIMethod -Uri $uri } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } #EndRegion - Get-DynatraceHTTPCheckMonitorExecution.ps1 #Region - Invoke-DynatraceAccountManagementAPIMethod.ps1 function Invoke-DynatraceAccountManagementAPIMethod { <# .SYNOPSIS Invoke a method on in the Dynatrace Account Management API .DESCRIPTION Invoke a method on in the Dynatrace Account Management API .PARAMETER RestPath The rest path to append to base url .EXAMPLE Invoke-DynatraceAccountManagementAPIMethod -RestPath '/ref/v1/account/permissions' .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param( [Parameter(Mandatory)] [String]$RestPath, [Microsoft.PowerShell.Commands.WebRequestMethod]$Method = 'GET', [switch]$OutputAsJson ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name)] Function started" $Connection = Connect-DynatraceAccountManagement $access_token = $Connection.access_token $headers = @{ Authorization = "Bearer $access_token" } $Uri = "https://api.dynatrace.com$RestPath" Write-Verbose "[$($MyInvocation.MyCommand.Name)] $Uri" } process { try { $splatParameters = @{ Uri = $Uri Method = $Method Headers = $headers } $Return = Invoke-WebRequest @splatParameters $output = $Return.Content | ConvertFrom-JSON } catch { Write-Warning "[$($MyInvocation.MyCommand.Name)] Problem with Invoke-WebRequest $uri" $_ break } if ($OutputAsJson) { $output | ConvertTo-Json -Depth 6 } else { $output } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } #EndRegion - Invoke-DynatraceAccountManagementAPIMethod.ps1 #Region - Invoke-DynatraceAPIMethod.ps1 function Invoke-DynatraceAPIMethod { <# .SYNOPSIS Invoke a method in the Dynatrace API. This is a service function to be called by other functions. .DESCRIPTION Invoke a method in the Dynatrace API. This is a service function to be called by other functions. .PARAMETER Uri Uri to use for Invoke-RestMethod .PARAMETER Method Defaults to GET .PARAMETER Headers Headers to use. Will be joined with authorization header. .PARAMETER GetParameter Get parameters to include .PARAMETER RestResponseProperty Property of the rest response to return as results. .PARAMETER LevelOfRecursion Internal parameter used to help determine how far into the matrix we are .EXAMPLE Invoke-DynatraceAPIMethod -Uri https://environmentid.live.dynatrace.com/api/v2/entityTypes -RestResponseProperty types .NOTES https://api.dynatrace.com/spec/#/ #> [CmdletBinding()] param( [Parameter(Mandatory)] [Uri]$Uri, [Microsoft.PowerShell.Commands.WebRequestMethod]$Method = 'GET', [Hashtable]$Headers, [Hashtable]$GetParameter = @{}, [string]$RestResponseProperty, [System.Object]$Body, [string]$ContentType, [int]$LevelOfRecursion = 1 ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] Function started" Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] Function started. PSBoundParameters: $($PSBoundParameters | Out-String)" #region Headers $config = Get-DynatracePSConfig $access_token = $config.accesstoken if (-not $access_token) { Write-Warning "[$($MyInvocation.MyCommand.Name) $Level] Must first configure an access token with Set-DynatracePSConfig -AccessToken <token>. Exiting..." break } $_headers = @{ Authorization = "Api-Token $access_token" } if ($Headers) { $_headers += $Headers } #endregion Headers # Create a hash table from the query in the URI, makes it easier to # manage in powershell # $uriQuery = ConvertTo-ParameterHash -Uri $Uri # Generate the Get parameter hashtable that we will use # $internalGetParameter = Join-Hashtable $uriQuery, $GetParameter [Uri]$LeftPartOfURI = $Uri.GetLeftPart('Path') # Concat the url and query together to form the URI address we are going to use # [Uri]$FinalURI = "{0}{1}" -f $LeftPartOfURI,(ConvertTo-GetParameter $internalGetParameter) Write-Verbose "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] FinalURI: [$FinalUri]" try { $splatParameters = @{ Uri = $FinalURI Method = $Method Headers = $_headers } # If -body parm is used, we add it to the splat parameters # if ($body) { Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] body: $($body | Out-String)" $splatParameters += @{ Body = $body } } # if contenttype is defined, add it to the parameters # if ($ContentType) { $splatParameters += @{ ContentType = $ContentType } } Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] splatParameters: $($splatParameters | Out-String)" # Invoke-WebRequest (IWR) to Dynatrace. We use IWR instead of Invoke-RestMethod (IRM) because of reasons: # 1) IWR is standard from PS version 3 and up. IRM is not # 2) IRM doesn't do good job of returning headers and status codes consistently. IWR does. # # https://www.truesec.com/hub/blog/invoke-webrequest-or-invoke-restmethod # $Response = Invoke-WebRequest @splatParameters $RestResponse = $Response.Content | ConvertFrom-JSON $ResponseHeaders = $Response.Headers $StatusCode = $Response.StatusCode Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] RestResponse: $($RestResponse | Out-String)" Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] ResponseHeaders: $($ResponseHeaders | Out-String)" Write-Debug "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] StatusCode: $($StatusCode | Out-String)" } catch { Write-Warning "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] Problem with Invoke-RestMethod $uri" $_ break } Write-Verbose "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] Executed RestMethod" # If there are bad status codes, this will break and cause function to exit # Test-ServerResponse -InputObject $RestResponse -StatusCode $StatusCode } process { if ($RestResponse) { Write-Verbose "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] nextPageKey: $($RestResponse.nextPageKey)" # Set next page key to get # $NextPageKey = $RestResponse.nextPageKey if ($RestResponseProperty) { $result = ($RestResponse).$RestResponseProperty } else { $result = $RestResponse } if (-not $PSBoundParameters["GetParameter"]) { $PSBoundParameters["GetParameter"] = $internalGetParameter } do { if (-not $NextPageKey) { # if there is no page key, then quit, as there are no more pages # break } else { # Output results from this loop, and continue on the recursion # $result } $PSBoundParameters["GetParameter"]['nextPageKey'] = $NextPageKey $PSBoundParameters["LevelOfRecursion"] = $LevelOfRecursion + 1 Write-Verbose "[$($MyInvocation.MyCommand.Name) $LevelOfRecursion] Calling Invoke-DynatraceApiMethod" # Call this same function again (recursion) # $result = Invoke-DynatraceApiMethod @PSBoundParameters } while (-not $NextPageKey) $result } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Complete" Write-Debug "[$($MyInvocation.MyCommand.Name)] Complete" } } #EndRegion - Invoke-DynatraceAPIMethod.ps1 #Region - Join-Hashtable.ps1 function Join-Hashtable { <# .SYNOPSIS Combines multiple hashtables into a single table. .DESCRIPTION Combines multiple hashtables into a single table. On multiple identic keys, the last wins. .PARAMETER Hashtable Hash tables to merge together .EXAMPLE PS C:\> Join-Hashtable -Hashtable $Hash1, $Hash2 Merges the hashtables contained in $Hash1 and $Hash2 into a single hashtable. #> [CmdletBinding()] [OutputType([System.Collections.Hashtable])] Param ( # The tables to merge. [Parameter( Mandatory, ValueFromPipeline )] [AllowNull()] [System.Collections.IDictionary[]] $Hashtable ) begin { $table = @{ } } process { foreach ($item in $Hashtable) { foreach ($key in $item.Keys) { $table[$key] = $item[$key] } } } end { $table } } #EndRegion - Join-Hashtable.ps1 #Region - Test-ServerResponse.ps1 function Test-ServerResponse { [CmdletBinding()] <# .SYNOPSIS Evaluate the response of the API call .NOTES Thanks to Lipkau: https://github.com/AtlassianPS/JiraPS/blob/master/JiraPS/Private/Test-ServerResponse.ps1 #> param ( [Parameter( ValueFromPipeline )] [PSObject]$InputObject, [string]$StatusCode ) begin { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Checking response for error" Write-Debug "[$($MyInvocation.MyCommand.Name)] Checking response for error" } process { if ($StatusCode -in (201,204)) { Write-Debug "[$($MyInvocation.MyCommand.Name)] Response code $StatusCode : Success" Write-Verbose "[$($MyInvocation.MyCommand.Name)] Response code $StatusCode : Success" } elseif ($StatusCode -gt 204) { Write-Debug "[$($MyInvocation.MyCommand.Name)] Error code found, throwing error" throw ("Code {0}: {1}" -f $StatusCode,($InputObject.message -join ',')) } else { Write-Debug "[$($MyInvocation.MyCommand.Name)] Code: $StatusCode" } } end { Write-Verbose "[$($MyInvocation.MyCommand.Name)] Done checking response for error" Write-Debug "[$($MyInvocation.MyCommand.Name)] Done checking response for error" } } #EndRegion - Test-ServerResponse.ps1 # SIG # Begin signature block # MIIFjQYJKoZIhvcNAQcCoIIFfjCCBXoCAQExCzAJBgUrDgMCGgUAMGkGCisGAQQB # gjcCAQSgWzBZMDQGCisGAQQBgjcCAR4wJgIDAQAABBAfzDtgWUsITrck0sYpfvNR # AgEAAgEAAgEAAgEAAgEAMCEwCQYFKw4DAhoFAAQULSxDBbFXJyAjDlLaaDdm3O/J # ivugggMnMIIDIzCCAgugAwIBAgIQfxlXoOWZRbhMi6xrw92ZDzANBgkqhkiG9w0B # AQsFADAbMRkwFwYDVQQDDBBzZWxmLnNpZ25lZC5jZXJ0MB4XDTIyMDQzMDAyNDYw # MFoXDTIzMDQzMDAzMDYwMFowGzEZMBcGA1UEAwwQc2VsZi5zaWduZWQuY2VydDCC # ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALUk2x84obgu2AqpvrBQ47LK # T01imCRSOYU3wIVEyd0H0WE/gZkc/Aji68mojxlKcdLKGRNiEFDsXbWX2fWM6KC2 # PVS/txe1fgCpz5eeq9CyHqTuUz8m3XDRMtAX91R8xyiLQSFWgrfDPJWRBWHv3sNv # ZD4c00hle+YHLhuw76oc2z22ikMhCND8GfVlSWxoIiI2hcNN5oCkqiNjxYs3fWD5 # sUcYTDWj62AL00Zml+FI6CvRO2XSdKVRMvAqN2vskwwO6ayMASYrEcJ4WTcQj1dp # WjCZdgqMrBGVxvc6wg6YWVDzlHRCg4AxVZjt12LGkqYwkjROHN2wzE/4/0svU00C # AwEAAaNjMGEwDgYDVR0PAQH/BAQDAgeAMBMGA1UdJQQMMAoGCCsGAQUFBwMDMBsG # A1UdEQQUMBKCEHNlbGYuc2lnbmVkLmNlcnQwHQYDVR0OBBYEFMYfeufU5fggCTcR # +V0v1lQC6bOkMA0GCSqGSIb3DQEBCwUAA4IBAQAsI+0UFKIeVPZ36nodt9JqhyQK # yC1SsuvIwGew0QsdeDaM2mLwbZfmKumAPq27tOIhozaydme4vnbKyDv4MShR6MLk # UwquAJ70k+mMrivol7SL+I208iO0itt5Kxxd+cNKl2G1tRIfGvE9qoZ02WIjvNQH # BazJHjldlW/QXkoy0Ip/02mR3KvnGGRiipU8DjLi/lUbAUJAVO3zZ99iiXg2w5Be # 2gOt7n7Csx10Fe2KJfKrbXVYShcim6wMbrHtvYBrtagFaAT2RXzZyQfCoGYtP2Vw # w8fHDmJ8yFy3fRCHL53A7FsJ499gJDbj0afH0AE7uDShNoc2F8WoHaLLe7UfMYIB # 0DCCAcwCAQEwLzAbMRkwFwYDVQQDDBBzZWxmLnNpZ25lZC5jZXJ0AhB/GVeg5ZlF # uEyLrGvD3ZkPMAkGBSsOAwIaBQCgeDAYBgorBgEEAYI3AgEMMQowCKACgAChAoAA # MBkGCSqGSIb3DQEJAzEMBgorBgEEAYI3AgEEMBwGCisGAQQBgjcCAQsxDjAMBgor # BgEEAYI3AgEVMCMGCSqGSIb3DQEJBDEWBBSWr26UaCBmYUsHIbWARlOQht0/BzAN # BgkqhkiG9w0BAQEFAASCAQCQlOAweizt4jfM0dvo8xehqRrnkMXVYONNFzmgvaap # PRjPOUgQDbTpSruxZQ46uo/3ls4oL/pv4gkkSrAScREhSAJD4WIS5GrwrWsufyQk # b6cKYAj/hQZOChIdkVXGuleWMe2Hx+aCiPUYzgXtXo2r3xrqGvSpr5jYe/rwzK8S # G41C4PTzFQ+EEareAo+GFxE7MT35kDNJ5COLd59K2BKHmVKLy1qhdMM85ZaELAML # RvU5dlPjps4fHqYQaBRC/Id01QjbFNaM05G0jIyw74nrkvMbDpNMDoqZD2bwgAa+ # EucFp3QzAAb6KS37pTotjc0kvjPJkFPE9IXvEt3KLs6W # SIG # End signature block |