GW2.PS.LiteDB-InputOutput.psm1
Function New-GW2DBCollection { param( [parameter(Mandatory)] [string]$CollectionName, [string[]]$DefaultIndex = @('Id') ) If ($CollectionName -eq 'items') { $DefaultIndex += @('default_skin','name') } $Collection = Get-GW2DBCollection -CollectionName $CollectionName ForEach ($Index in $DefaultIndex) { $Collection.EnsureIndex($Index) } Write-Output $Collection } Function Get-GW2DBCollection { param( [parameter(Mandatory)] [string]$CollectionName ) $DB = Get-GW2LiteDB $DB.GetCollection($CollectionName) } Function Test-GW2DBCollection { param( [parameter(Mandatory)] [string]$CollectionName ) $DB = Get-GW2LiteDB Write-Output ([bool]($DB.CollectionExists($CollectionName))) } Function Get-GW2DBMapper { [LiteDB.BSONMapper]::New() } Function ConvertTo-GW2DBDocument { [OutputType('LiteDB.BsonDocument')] [cmdletbinding()] param( [parameter(ValueFromPipeline)] $InputObject ) Begin { $BSONMapper = [LiteDB.BSONMapper]::New() } Process { If ($InputObject) { [LiteDB.BsonDocument]$result = ($BSONMapper.ToDocument($InputObject)) return $result } } } Function Format-GW2DBDocumentValue { param($Value) $ConversionAttempts = 0 While (($value -match "^(([""\{])|(\[[^&]))") -and ($ConversionAttempts -lt 5) ) { try { $ConversionAttempts++ Write-Debug "attempting [$ConversionAttempts] to convert [ $value ]" $Value = $Value | ConvertFrom-Json -ErrorAction Stop } catch { Write-Debug "Failed to convert [ $value ] after [ $ConversionAttempts ] attempts" $ConversionAttempts++ } } $Value } Function ConvertFrom-GW2DBDocumentStatic { <# .SYNOPSIS Removes JSON obfuscation of BSON Document properties and builds array into standard PSCustomObject #> param($Document) $result = @{} ForEach ($Property in $Document) { $result.($Property.key) = Format-GW2DBDocumentValue -Value ($Property.Value) } [PSCustomObject]$result } Function ConvertFrom-GW2DBDocument { <# .SYNOPSIS Removes JSON obfuscation of BSON Document properties and builds array into standard PSCustomObject #> param( [parameter(ValueFromPipeline,Mandatory)] $Document) Process { $result = [PSCustomObject]@{ "Document" = $Document } ForEach ($Property in $Document) { Invoke-Expression @" `$result | Add-Member ScriptProperty '$($Property.Key)' { `$Property = `$this.Document | Where-Object { `$_.Key -eq '$($Property.Key)' } If (`$Property){ Format-GW2DBDocumentValue -Value `$Property.Value } } -Force "@ #Invoke-Expression @" #`$result | Add-Member NoteProperty '$($Property.Key)' ($($Property.Value)) -Force #"@ } [PSCustomObject]$result } } Function Add-GW2DBEntry { [cmdletbinding()] param( [parameter(ValueFromPipeline)] [PSCustomObject]$InputObject, [parameter(Mandatory)] [string]$CollectionName, [switch]$CheckExist, [switch]$PassThru ) Begin { #Ensure that if they past an endpoint name, we ensure its a proper collection name before we get the collection $CollectionName = Get-GW2DBCollectionName -EndPointName $CollectionName If (-not (Test-GW2DBCollection -CollectionName $CollectionName)) { $CollectionCreation = New-GW2DBCollection -CollectionName $CollectionName } $Collection = Get-GW2DBCollection -CollectionName $CollectionName $BSONMapper = Get-GW2DBMapper $Documents = [System.Collections.ArrayList]@() } Process { #$doc = [LiteDB.BsonDocument]::New() $doc = $BSONMapper.ToDocument(@{'id' = $InputObject.Id }) ForEach ($prop in ($InputObject | Get-Member -MemberType NoteProperty )) { #| select -first $count)) { If (-not ([string]::IsNullOrEmpty( $InputObject.($prop.Name)))) { #.length -gt 0) { Write-Debug "$($Collection.name): $($prop.name) => '$($InputObject.($prop.Name))' [$($InputObject.($prop.Name).length)]" $doc[$prop.name] = $InputObject.($prop.Name) | ConvertTo-Json -Depth 10 # $BSONMapper.ToDocument( } } Write-Debug "$($Collection.name): $($doc['id']) => $($doc['name'])" If ($CheckExist) { $Found = $Collection.FindOne("`$.Id = '$($doc['id'])'") If ($Found) { $doc['_id']=$Found['_id'] $UpsertResult = $Collection.Update($doc) #($BSONMapper.ToDocument($InputObject))) } else { $Documents.Add($doc) #$UpsertResult = $Collection.Insert($doc) #($BSONMapper.ToDocument($InputObject))) } } else { $Documents.Add($doc) #$UpsertResult = $Collection.Insert($doc) #($BSONMapper.ToDocument($InputObject))) } Write-Debug "Upsert result: $UpsertResult" If ($PassThru) { ConvertFrom-GW2DBDocument -Document $doc } } End { If ($Documents.count -gt 0) { $UpsertResult = $Collection.InsertBulk($Documents, $Documents.Count) Write-Debug "Upsert result: $UpsertResult" } } } Function Get-GW2DBEntryByQuery { [cmdletbinding()] param( [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName)] [string]$QueryString, [parameter(Mandatory)] [string]$CollectionName, [switch]$SingleResult, [parameter(ValueFromRemainingArguments)] $RemaingArgs ) Begin { $Connected = Connect-GW2LiteDB -PassThru #Ensure that if they past an endpoint name, we ensure its a proper collection name before we get the collection $CollectionName = Get-GW2DBCollectionName -EndPointName $CollectionName If (-not (Test-GW2DBCollection -CollectionName $CollectionName)) { $CollectionCreation = New-GW2DBCollection -CollectionName $CollectionName } $Collection = Get-GW2DBCollection -CollectionName $CollectionName } Process { If ($SingleResult) { $Documents = $Collection.FindOne($QueryString) } else { $Documents = $Collection.Find($QueryString) } $Results = $Documents | ForEach-Object { ConvertFrom-GW2DBDocument -Document $_ } return $results } End { If ($Connected) { Disconnect-GW2LiteDB } } } Function Find-GW2DBMissingEntries { param( $Reference, $Difference ) $CleanReference = $Reference -split ',' | ForEach-Object { $_ -replace "^'(.*)'$","`$1" } $CleanDiff = $Difference -split ',' | ForEach-Object { $_ -replace "^'(.*)'$","`$1" } $CleanDiff | Where-Object { $_ -notin $CleanReference } | Where-Object { $_ } } Function ConvertTo-GW2DBQueryArray { param( [parameter(Mandatory)] $Entries ) $FormatEntries = ForEach ( $E in ($Entries -split ",")) { If ($e -match "^'[^']*'$") { $e } else { "'$e'" } } ("[ {0} ]" -f ($FormatEntries -join ',')) } Function Get-GW2DBEntry { [cmdletbinding(DefaultParameterSetName="OnlyID")] param( [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName,ParameterSetName="AllEntries")] [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName,ParameterSetName="OnlyID")] [string[]]$Id, [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName,ParameterSetName="PropertyHashTable",Mandatory)] [hashtable]$PropertyValues, [parameter(ParameterSetName="AllEntries",Mandatory)] [switch]$All, [parameter(Mandatory)] [string]$CollectionName, [switch]$SkipOnlineLookup, [switch]$DkipDocumentConversion ) Begin { #Ensure that if they past an endpoint name, we ensure its a proper collection name before we get the collection $CollectionName = Get-GW2DBCollectionName -EndPointName $CollectionName If (-not (Test-GW2DBCollection -CollectionName $CollectionName)) { $CollectionCreation = New-GW2DBCollection -CollectionName $CollectionName } $Collection = Get-GW2DBCollection -CollectionName $CollectionName $MissingIds=@() } Process { switch ($PSCmdlet.ParameterSetName) { "AllEntries" { Write-Information "Looking for $($Id.count) IDs" $AllDocs = $Collection.FindAll() If ($SkipDocumentConversion) { $AllDocs } else { $AllEntries = $AllDocs | ForEach-Object { ConvertFrom-GW2DBDocument -Document $_ } If (($Id.Count -gt 0) -and ($AllEntries.Count -gt 0)) { $IdsNotInResults = Find-GW2DBMissingEntries -Reference ($AllEntries.Ids) -Difference $Id #-Comparison ($AllEntries.Ids) $MissingIds += @($IdsNotInResults) } $AllEntries } } "OnlyID" { Write-Debug "Database query of $CollectionName for IDs = $ID" If ($ID -match ","){ $QueryArray = ConvertTo-GW2DBQueryArray -Entries $Id Write-Debug "Querying $COllectionName for an array $QueryArray" $Documents = $Collection.Find("`$.Id in $QueryArray") If ($Documents) { Write-Debug "Converting documents..." If ($SkipDocumentConversion) { $Documents } else { $Results = $Documents | ForEach-Object { ConvertFrom-GW2DBDocument -Document $_ } $IdsNotInResults = Find-GW2DBMissingEntries -Reference ($Results.Id) -Difference $Id $MissingIds += @($IdsNotInResults) $Results } } } else { $Document = $Collection.FindOne("`$.Id = '$Id'") If ($Document) { ConvertFrom-GW2DBDocument -Document $Document } else { $MissingIds += @($Id) } } } default { $QueryElements=[System.Collections.ArrayList]@() ForEach ($Property in $PropertyValues.Keys) { $QueryElements.Add(("`$.{0} = '{1}'" -f $Property,$PropertyValues.$Property)) } $FullQuery = $QueryElements -join " and " Write-Debug "Attempting to query $CollectionName for $FullQuery" $Document = $Collection.FindOne($FullQuery) If ($SkipDocumentConversion) { $Document } else { ConvertFrom-GW2DBDocument -Document $Document } } } } End { If (($MissingIds.Count -gt 0) -and (-not $SkipOnlineLookup)) { Write-Debug "Couldn't find $($MissingIds.count) IDs in Database; looking up online ($($MissingIds -join ','))" $APIValue = Get-GW2DBAPIValue -CollectionName $CollectionName $MissingEntries = Get-GW2APIValue -APIValue $APIValue -APIParams @{ 'ids' = ($MissingIds -join ',') } -UseCache:$false -UseDB:$false $MissingEntries | Add-GW2DBEntry -CollectionName $CollectionName -PassThru } } } Function Get-GW2DBCollectionName { [cmdletbinding()] param( [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName)] [string]$EndPointName) Process { $EndpointName -replace "[\\/]","_" } } Function Get-GW2DBAPIValue { [cmdletbinding()] param( [parameter(ValueFromPipeline,ValueFromPipelineByPropertyName)] [string]$CollectionName) Process { $CollectionName -replace "_","/" } } Function Get-GW2DBValue { [cmdletbinding()] param( [string]$APIValue, [securestring]$SecureAPIKey, [hashtable]$APIParams ) Begin { $CollectionName = $APIValue | Get-GW2DBCollectionName $ConnectedInSession = Connect-GW2LiteDB -PassThru } Process { If ($APIParams.Ids) { Get-GW2DBEntry -CollectionName $CollectionName -Id $APIParams.Ids } elseIf ($APIParams.count -gt 0) { Get-GW2DBEntry -CollectionName $CollectionName -PropertyValues $APIParams } else { $WebResults = Get-GW2APIValue -APIValue $APIValue -SecureAPIKey $SecureAPIKey -APIParams $APIParams -UseCache:$false -UseDB:$false $WebResults } } ENd { If ($ConnectedInSession) { Disconnect-GW2LiteDB } } } |