Public/Invoke-SDPRestMethod.ps1
|
function Invoke-SDPRestMethod { <# .SYNOPSIS Sends an authenticated HTTP request to the ServiceDesk Plus REST API. .DESCRIPTION Wraps Invoke-RestMethod with SDP-specific authentication headers, input_data encoding, and error translation. Sub-modules use this as their HTTP transport; callers can also use it directly for endpoints not yet covered by a dedicated cmdlet. .PARAMETER Endpoint The API endpoint path relative to the v3 base URI, e.g. 'requests' or 'requests/123/notes'. .PARAMETER Method HTTP method. Defaults to GET. .PARAMETER Body Request body hashtable, serialized as JSON and sent as form-encoded input_data. Used for POST/PUT/PATCH requests. .PARAMETER InputData Query-string hashtable, serialized as JSON and appended as the input_data parameter. Used for GET requests that require list_info or search criteria. .EXAMPLE Invoke-SDPRestMethod -Endpoint 'requests' -InputData @{ list_info = @{ row_count = 10 } } .EXAMPLE Invoke-SDPRestMethod -Endpoint 'requests/123' -Method PUT -Body @{ request = @{ status = @{ name = 'Closed' } } } #> [CmdletBinding()] param( [Parameter(Mandatory)] [string]$Endpoint, [Parameter()] [Microsoft.PowerShell.Commands.WebRequestMethod]$Method = 'GET', [Parameter()] [hashtable]$Body, [Parameter()] [hashtable]$InputData ) $session = Get-SDPSession $uri = "$($session.ApiBaseUri)/$Endpoint" if ($InputData) { $encoded = [System.Uri]::EscapeDataString(($InputData | ConvertTo-Json -Depth 10 -Compress)) $uri = "${uri}?input_data=$encoded" } $headers = @{ 'TECHNICIAN_KEY' = $session.GetPlainKey() 'PORTALID' = $session.PortalId 'Accept' = 'application/vnd.manageengine.sdp.v3+json' } $params = @{ Uri = $uri Method = $Method Headers = $headers SkipHttpErrorCheck = $true StatusCodeVariable = 'httpStatus' SkipCertificateCheck = $session.SkipCertificateCheck } if ($Body -and $Method -in 'POST', 'PUT', 'PATCH') { $params['ContentType'] = 'application/x-www-form-urlencoded' $params['Body'] = @{ input_data = ($Body | ConvertTo-Json -Depth 10 -Compress) } } try { $response = Invoke-RestMethod @params } catch { $PSCmdlet.ThrowTerminatingError($_) } if ($null -ne $response -and $response.PSObject.Properties['response_status']) { $status = $response.response_status # response_status may be an array (approvals endpoint) or a single object $statusObj = if ($status -is [array]) { $status[0] } else { $status } if ($null -ne $statusObj -and $statusObj.status_code -ne 2000) { $messages = @($statusObj.messages).Where({ $_ }) | ForEach-Object { $parts = @() if ($_.message) { $parts += $_.message } if ($_.field) { $parts += "field=$($_.field)" } if ($_.status_code) { $parts += "code=$($_.status_code)" } $parts -join ', ' } $msg = if ($messages) { $messages -join '; ' } else { "SDP API error (code $($statusObj.status_code))" } $PSCmdlet.ThrowTerminatingError( [System.Management.Automation.ErrorRecord]::new( [System.Exception]::new($msg), 'SDPApiError', [System.Management.Automation.ErrorCategory]::InvalidResult, $response ) ) } } elseif ($httpStatus -ge 400) { $PSCmdlet.ThrowTerminatingError( [System.Management.Automation.ErrorRecord]::new( [System.Exception]::new("HTTP $httpStatus received from SDP API."), 'SDPHttpError', [System.Management.Automation.ErrorCategory]::ConnectionError, $null ) ) } $response } |