diff --git a/verkadaModule/Private/Invoke-VerkadaFormCall.ps1 b/verkadaModule/Private/Invoke-VerkadaFormCall.ps1 index 5d8d9b7..6a240d0 100644 --- a/verkadaModule/Private/Invoke-VerkadaFormCall.ps1 +++ b/verkadaModule/Private/Invoke-VerkadaFormCall.ps1 @@ -7,7 +7,7 @@ function Invoke-VerkadaFormCall Private function to build Invoke-RestMethod calls for Verkada's private API enpoints that require a form #> - [CmdletBinding(PositionalBinding = $true)] + [CmdletBinding(PositionalBinding = $true, DefaultParameterSetName = 'Default')] Param( #The url for the enpoint to be used [Parameter(Mandatory = $true, Position = 0)] @@ -20,24 +20,47 @@ function Invoke-VerkadaFormCall #Object to pass form parameters to forms [Parameter(Mandatory = $true,Position = 2)] [Object]$form_params, + #Object containing the query parameters need that will be put into the query string of the uri + [Parameter()] + [Object]$query_params, #HTTP method required [Parameter()] [String]$method = 'POST', #The Verkada(CSRF) token of the user running the command - [Parameter(Mandatory = $true)] + [Parameter(Mandatory = $true, ParameterSetName = 'UnPwd')] [ValidateNotNullOrEmpty()] [ValidatePattern('^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$')] [string]$x_verkada_token, #The Verkada Auth(session auth) token of the user running the command - [Parameter(Mandatory = $true)] + [Parameter(Mandatory = $true, ParameterSetName = 'UnPwd')] [ValidateNotNullOrEmpty()] - [string]$x_verkada_auth + [string]$x_verkada_auth, + #The public API token obatined via the Login endpoint to be used for calls that hit the public API gateway + [Parameter(ParameterSetName = 'Default')] + [String]$x_verkada_auth_api ) Process { - $headers=@{ - 'x-verkada-token' = $x_verkada_token - 'X-Verkada-Auth' = $x_verkada_auth + if ($PSCmdlet.ParameterSetName -eq 'UnPwd'){ + $headers=@{ + 'x-verkada-token' = $x_verkada_token + 'X-Verkada-Auth' = $x_verkada_auth + } + } else { + $headers=@{ + 'x-verkada-auth' = $x_verkada_auth_api + } + } + + if($query_params){ + $query = [System.Web.HttpUtility]::ParseQueryString([String]::Empty) + foreach ($qp in $query_params.GetEnumerator()) { + $query.add("$($qp.name)", "$($qp.value)") + } + $uri = [System.UriBuilder]"$url" + $uri.Query = $query.ToString() + $uri = $uri.Uri.OriginalString + $url = $uri } $uri = $url diff --git a/verkadaModule/Public/Set-VerkadaAccessUserProfilePicture.ps1 b/verkadaModule/Public/Set-VerkadaAccessUserProfilePicture.ps1 index 0acdc43..74b0914 100644 --- a/verkadaModule/Public/Set-VerkadaAccessUserProfilePicture.ps1 +++ b/verkadaModule/Public/Set-VerkadaAccessUserProfilePicture.ps1 @@ -1,11 +1,11 @@ function Set-VerkadaAccessUserProfilePicture{ <# .SYNOPSIS - Adds/replaces an Access user's profile picture in an organization. + Adds/replaces an Access user's profile picture in an organization using https://apidocs.verkada.com/reference/putprofilephotoviewv1 .DESCRIPTION - This will set the Access user's, specified by the userId, profile picture. This must be a png or jpeg/jpg format image. - The org_id and reqired tokens can be directly submitted as parameters, but is much easier to use Connect-Verkada to cache this information ahead of time and for subsequent commands. + This will set the Access user's, specified by the user_Id or external_ID, profile picture. This must be a png or jpeg/jpg format image. + The org_id and reqired token can be directly submitted as parameters, but is much easier to use Connect-Verkada to cache this information ahead of time and for subsequent commands. .LINK https://github.com/bepsoccer/verkadaModule/blob/master/docs/function-documentation/Set-VerkadaAccessUserProfilePicture.md @@ -15,8 +15,8 @@ function Set-VerkadaAccessUserProfilePicture{ This sets the Access user with userId 801c9551-b04c-4293-84ad-b0a6aa0588b3 to use the picture specified at path ./myPicture.jpg. The org_id and tokens will be populated from the cached created by Connect-Verkada. .EXAMPLE - Set-VerkadaAccessUserProfilePicture -userId '801c9551-b04c-4293-84ad-b0a6aa0588b3' -imagePath './myPicture.png' -org_id '7cd47706-f51b-4419-8675-3b9f0ce7c12d' -x_verkada_token 'a366ef47-2c20-4d35-a90a-10fd2aee113a' -x_verkada_auth 'auth-token-uuid-dscsdc' -usr 'a099bfe6-34ff-4976-9d53-ac68342d2b60' - This sets the Access user with userId 801c9551-b04c-4293-84ad-b0a6aa0588b3 to use the picture specified at path ./myPicture.png. The org_id and tokens are submitted as parameters in the call. + Set-VerkadaAccessUserProfilePicture -externalId 'newUserUPN@contoso.com' -imagePath './myPicture.png' -org_id '7cd47706-f51b-4419-8675-3b9f0ce7c12d' -x_verkada_auth_api 'sd78ds-uuid-of-verkada-token' + This sets the Access user with externalId newUserUPN@contoso.com to use the picture specified at path ./myPicture.png. The org_id and tokens are submitted as parameters in the call. #> [CmdletBinding(PositionalBinding = $true)] [Alias("Set-VrkdaAcUsrPrflPic","s-VrkdaAcUsrPrflPic")] @@ -27,72 +27,93 @@ function Set-VerkadaAccessUserProfilePicture{ [ValidatePattern('^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$')] [Alias('user_id')] [String]$userId, + #unique identifier managed externally provided by the consumer + [Parameter(ValueFromPipelineByPropertyName = $true)] + [Alias('external_id')] + [String]$externalId, #This is the path the image will be uploaded from [Parameter(ValueFromPipelineByPropertyName = $true)] [ValidateNotNullOrEmpty()] [ValidatePattern('^.*\.(jpg|jpeg|png)$')] [string]$imagePath, + #The flag that states whether to overwrite the existing profile photo + [Parameter(ValueFromPipelineByPropertyName = $true)] + [bool]$overwrite=$false, #The UUID of the organization the user belongs to [Parameter(ValueFromPipelineByPropertyName = $true)] [ValidateNotNullOrEmpty()] [ValidatePattern('^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$')] [String]$org_id = $Global:verkadaConnection.org_id, - #The Verkada(CSRF) token of the user running the command + #The public API token obatined via the Login endpoint to be used for calls that hit the public API gateway [Parameter()] [ValidateNotNullOrEmpty()] - [ValidatePattern('^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$')] - [string]$x_verkada_token = $Global:verkadaConnection.csrfToken, - #The Verkada Auth(session auth) token of the user running the command + [String]$x_verkada_auth_api = $Global:verkadaConnection.x_verkada_auth_api, + #The region of the public API to be used [Parameter()] - [ValidateNotNullOrEmpty()] - [string]$x_verkada_auth = $Global:verkadaConnection.userToken, - #The UUID of the user account making the request + [ValidateSet('api','api.eu','api.au')] + [String]$region='api', + #Switch to write errors to file [Parameter()] - [ValidateNotNullOrEmpty()] - [ValidatePattern('^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$')] - [string]$usr = $Global:verkadaConnection.usr + [switch]$errorsToFile ) begin { + $url = "https://$($region).verkada.com/access/v1/access_users/user/profile_photo" #parameter validation if ([string]::IsNullOrEmpty($org_id)) {throw "org_id is missing but is required!"} - if ([string]::IsNullOrEmpty($x_verkada_token)) {throw "x_verkada_token is missing but is required!"} - if ([string]::IsNullOrEmpty($x_verkada_auth)) {throw "x_verkada_auth is missing but is required!"} - if ([string]::IsNullOrEmpty($usr)) {throw "usr is missing but is required!"} - - $url = 'https://vcerberus.command.verkada.com/user/photos/upload' + if ([string]::IsNullOrEmpty($x_verkada_auth_api)) {throw "x_verkada_auth_api is missing but is required!"} + $myErrors = @() } #end begin process { - if (!(Test-Path -Path $imagePath -PathType Leaf)){ - Write-Error "$imagePath is not a valid file path" - return - } - if ([string]::IsNullOrEmpty($userId)){ - Write-Error "userId required" + if ([string]::IsNullOrEmpty($externalId) -and [string]::IsNullOrEmpty($userId)){ + Write-Error "Either externalId or userId required" return } $form = @{ - organizationId = $org_id - userId = $userId - file = Get-Item -Path $imagePath + file = Get-Item -Path $imagePath + } + + $query_params = @{ + 'overwrite' = $overwrite } + if (!([string]::IsNullOrEmpty($userId))){ + $query_params.user_id = $userId + } elseif (!([string]::IsNullOrEmpty($externalId))){ + $query_params.external_id = $externalId + } + try { - Invoke-VerkadaFormCall $url $org_id $form -x_verkada_token $x_verkada_token -x_verkada_auth $x_verkada_auth -Method 'POST' + Invoke-VerkadaFormCall $url $org_id $form -query_params $query_params -x_verkada_auth_api $x_verkada_auth_api -Method 'PUT' + return "Successfully uploaded $imagePath to $($query_params | ConvertTo-Json -Compress)" } catch [Microsoft.PowerShell.Commands.HttpResponseException] { $err = $_.ErrorDetails | ConvertFrom-Json $errorMes = $_ | Convertto-Json -WarningAction SilentlyContinue $err | Add-Member -NotePropertyName StatusCode -NotePropertyValue (($errorMes | ConvertFrom-Json -Depth 100 -WarningAction SilentlyContinue).Exception.Response.StatusCode) -Force - - Write-Host "$($err.StatusCode) - $($err.message)" -ForegroundColor Red - Return + $msg = "$($err.StatusCode) - $($err.message)" + $msg += ": $(($query_params + $form) | ConvertTo-Json -Compress)" + Write-Error $msg + $myErrors += $msg + $msg = $null + } + catch [VerkadaRestMethodException] { + $msg = $_.ToString() + $msg += ": $(($query_params + $body_params) | ConvertTo-Json -Compress)" + Write-Error $msg + $myErrors += $msg + $msg = $null } } #end process end { - + if ($errorsToFile.IsPresent){ + if (![string]::IsNullOrEmpty($myErrors)){ + Get-Date | Out-File ./errors.txt -Append + $myErrors | Out-File ./errors.txt -Append + } + } } #end end } #end function \ No newline at end of file