Public/Caching.ps1
<#
.SYNOPSIS Return the value of a key from the cache. You can use "$value = $cache:key" as well. .DESCRIPTION Return the value of a key from the cache, or returns the value plus metadata such as expiry time if required. You can use "$value = $cache:key" as well. .PARAMETER Key The Key to be retrieved. .PARAMETER Storage An optional cache Storage name. (Default: in-memory) .PARAMETER Metadata If supplied, and if supported by the cache storage, an metadata such as expiry times will also be returned. .EXAMPLE $value = Get-PodeCache -Key 'ExampleKey' .EXAMPLE $value = Get-PodeCache -Key 'ExampleKey' -Storage 'ExampleStorage' .EXAMPLE $value = Get-PodeCache -Key 'ExampleKey' -Metadata .EXAMPLE $value = $cache:ExampleKey #> function Get-PodeCache { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Key, [Parameter()] [string] $Storage = $null, [switch] $Metadata ) # inmem or custom storage? if ([string]::IsNullOrEmpty($Storage)) { $Storage = $PodeContext.Server.Cache.DefaultStorage } # use inmem cache if ([string]::IsNullOrEmpty($Storage)) { return (Get-PodeCacheInternal -Key $Key -Metadata:$Metadata) } # used custom storage if (Test-PodeCacheStorage -Key $Storage) { return (Invoke-PodeScriptBlock -ScriptBlock $PodeContext.Server.Cache.Storage[$Storage].Get -Arguments @($Key, $Metadata.IsPresent) -Splat -Return) } # storage not found! # Cache storage with name not found when attempting to retrieve cached item throw ($PodeLocale.cacheStorageNotFoundForRetrieveExceptionMessage -f $Storage, $Key) } <# .SYNOPSIS Set (create/update) a key in the cache. You can use "$cache:key = 'value'" as well. .DESCRIPTION Set (create/update) a key in the cache, with an optional TTL value. You can use "$cache:key = 'value'" as well. .PARAMETER Key The Key to be set. .PARAMETER InputObject The value of the key to be set, can be any object type. .PARAMETER Ttl An optional TTL value, in seconds. The default is whatever "Get-PodeCacheDefaultTtl" retuns, which will be 3600 seconds when not set. .PARAMETER Storage An optional cache Storage name. (Default: in-memory) .EXAMPLE Set-PodeCache -Key 'ExampleKey' -InputObject 'ExampleValue' .EXAMPLE Set-PodeCache -Key 'ExampleKey' -InputObject 'ExampleValue' -Storage 'ExampleStorage' .EXAMPLE Set-PodeCache -Key 'ExampleKey' -InputObject 'ExampleValue' -Ttl 300 .EXAMPLE Set-PodeCache -Key 'ExampleKey' -InputObject @{ Value = 'ExampleValue' } .EXAMPLE @{ Value = 'ExampleValue' } | Set-PodeCache -Key 'ExampleKey' .EXAMPLE $cache:ExampleKey = 'ExampleValue' #> function Set-PodeCache { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Key, [Parameter(Mandatory = $true, Position = 0, ValueFromPipeline = $true)] [object] $InputObject, [Parameter()] [int] $Ttl = 0, [Parameter()] [string] $Storage = $null ) begin { # Initialize an array to hold piped-in values $pipelineValue = @() } process { # Add the current piped-in value to the array $pipelineValue += $_ } end { # If there are multiple piped-in values, set InputObject to the array of values if ($pipelineValue.Count -gt 1) { $InputObject = $pipelineValue } # use the global settable default here if ($Ttl -le 0) { $Ttl = $PodeContext.Server.Cache.DefaultTtl } # inmem or custom storage? if ([string]::IsNullOrEmpty($Storage)) { $Storage = $PodeContext.Server.Cache.DefaultStorage } # use inmem cache if ([string]::IsNullOrEmpty($Storage)) { Set-PodeCacheInternal -Key $Key -InputObject $InputObject -Ttl $Ttl } # used custom storage elseif (Test-PodeCacheStorage -Key $Storage) { $null = Invoke-PodeScriptBlock -ScriptBlock $PodeContext.Server.Cache.Storage[$Storage].Set -Arguments @($Key, $InputObject, $Ttl) -Splat } # storage not found! else { # Cache storage with name not found when attempting to set cached item throw ($PodeLocale.cacheStorageNotFoundForSetExceptionMessage -f $Storage, $Key) } } } <# .SYNOPSIS Test if a key exists in the cache. .DESCRIPTION Test if a key exists in the cache, and isn't expired. .PARAMETER Key The Key to test. .PARAMETER Storage An optional cache Storage name. (Default: in-memory) .EXAMPLE Test-PodeCache -Key 'ExampleKey' .EXAMPLE Test-PodeCache -Key 'ExampleKey' -Storage 'ExampleStorage' #> function Test-PodeCache { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Key, [Parameter()] [string] $Storage = $null ) # inmem or custom storage? if ([string]::IsNullOrEmpty($Storage)) { $Storage = $PodeContext.Server.Cache.DefaultStorage } # use inmem cache if ([string]::IsNullOrEmpty($Storage)) { return (Test-PodeCacheInternal -Key $Key) } # used custom storage if (Test-PodeCacheStorage -Key $Storage) { return (Invoke-PodeScriptBlock -ScriptBlock $PodeContext.Server.Cache.Storage[$Storage].Test -Arguments @($Key) -Splat -Return) } # storage not found! # Cache storage with name not found when attempting to check if cached item exists throw ($PodeLocale.cacheStorageNotFoundForExistsExceptionMessage -f $Storage, $Key) } <# .SYNOPSIS Remove a key from the cache. .DESCRIPTION Remove a key from the cache. .PARAMETER Key The Key to be removed. .PARAMETER Storage An optional cache Storage name. (Default: in-memory) .EXAMPLE Remove-PodeCache -Key 'ExampleKey' .EXAMPLE Remove-PodeCache -Key 'ExampleKey' -Storage 'ExampleStorage' #> function Remove-PodeCache { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Key, [Parameter()] [string] $Storage = $null ) # inmem or custom storage? if ([string]::IsNullOrEmpty($Storage)) { $Storage = $PodeContext.Server.Cache.DefaultStorage } # use inmem cache if ([string]::IsNullOrEmpty($Storage)) { Remove-PodeCacheInternal -Key $Key } # used custom storage elseif (Test-PodeCacheStorage -Key $Storage) { $null = Invoke-PodeScriptBlock -ScriptBlock $PodeContext.Server.Cache.Storage[$Storage].Remove -Arguments @($Key) -Splat } # storage not found! else { # Cache storage with name not found when attempting to remove cached item throw ($PodeLocale.cacheStorageNotFoundForRemoveExceptionMessage -f $Storage, $Key) } } <# .SYNOPSIS Clear all keys from the cache. .DESCRIPTION Clear all keys from the cache. .PARAMETER Storage An optional cache Storage name. (Default: in-memory) .EXAMPLE Clear-PodeCache .EXAMPLE Clear-PodeCache -Storage 'ExampleStorage' #> function Clear-PodeCache { [CmdletBinding()] param( [Parameter()] [string] $Storage = $null ) # inmem or custom storage? if ([string]::IsNullOrEmpty($Storage)) { $Storage = $PodeContext.Server.Cache.DefaultStorage } # use inmem cache if ([string]::IsNullOrEmpty($Storage)) { Clear-PodeCacheInternal } # used custom storage elseif (Test-PodeCacheStorage -Key $Storage) { $null = Invoke-PodeScriptBlock -ScriptBlock $PodeContext.Server.Cache.Storage[$Storage].Clear } # storage not found! else { # Cache storage with name not found when attempting to clear the cache throw ($PodeLocale.cacheStorageNotFoundForClearExceptionMessage -f $Storage) } } <# .SYNOPSIS Add a cache storage. .DESCRIPTION Add a cache storage. .PARAMETER Name The Name of the cache storage. .PARAMETER Get A Get ScriptBlock, to retrieve a key's value from the cache, or the value plus metadata if required. Supplied parameters: Key, Metadata. .PARAMETER Set A Set ScriptBlock, to set/create/update a key's value in the cache. Supplied parameters: Key, Value, TTL. .PARAMETER Remove A Remove ScriptBlock, to remove a key from the cache. Supplied parameters: Key. .PARAMETER Test A Test ScriptBlock, to test if a key exists in the cache. Supplied parameters: Key. .PARAMETER Clear A Clear ScriptBlock, to remove all keys from the cache. Use an empty ScriptBlock if not supported. .PARAMETER Default If supplied, this cache storage will be set as the default storage. .EXAMPLE Add-PodeCacheStorage -Name 'ExampleStorage' -Get {} -Set {} -Remove {} -Test {} -Clear {} #> function Add-PodeCacheStorage { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [ValidateNotNullOrEmpty()] [string] $Name, [Parameter(Mandatory = $true)] [scriptblock] $Get, [Parameter(Mandatory = $true)] [scriptblock] $Set, [Parameter(Mandatory = $true)] [scriptblock] $Remove, [Parameter(Mandatory = $true)] [scriptblock] $Test, [Parameter(Mandatory = $true)] [scriptblock] $Clear, [switch] $Default ) # test if storage already exists if (Test-PodeCacheStorage -Name $Name) { # Cache Storage with name already exists throw ($PodeLocale.cacheStorageAlreadyExistsExceptionMessage -f $Name) } # add cache storage $PodeContext.Server.Cache.Storage[$Name] = @{ Name = $Name Get = $Get Set = $Set Remove = $Remove Test = $Test Clear = $Clear Default = $Default.IsPresent } # is default storage? if ($Default) { $PodeContext.Server.Cache.DefaultStorage = $Name } } <# .SYNOPSIS Remove a cache storage. .DESCRIPTION Remove a cache storage. .PARAMETER Name The Name of the cache storage. .EXAMPLE Remove-PodeCacheStorage -Name 'ExampleStorage' #> function Remove-PodeCacheStorage { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Name ) $null = $PodeContext.Server.Cache.Storage.Remove($Name) } <# .SYNOPSIS Returns a cache storage. .DESCRIPTION Returns a cache storage. .PARAMETER Name The Name of the cache storage. .EXAMPLE $storage = Get-PodeCacheStorage -Name 'ExampleStorage' #> function Get-PodeCacheStorage { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Name ) return $PodeContext.Server.Cache.Storage[$Name] } <# .SYNOPSIS Test if a cache storage has been added/exists. .DESCRIPTION Test if a cache storage has been added/exists. .PARAMETER Name The Name of the cache storage. .EXAMPLE if (Test-PodeCacheStorage -Name 'ExampleStorage') { } #> function Test-PodeCacheStorage { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Name ) return $PodeContext.Server.Cache.Storage.ContainsKey($Name) } <# .SYNOPSIS Set a default cache storage. .DESCRIPTION Set a default cache storage. .PARAMETER Name The Name of the default storage to use for caching. .EXAMPLE Set-PodeCacheDefaultStorage -Name 'ExampleStorage' #> function Set-PodeCacheDefaultStorage { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [string] $Name ) $PodeContext.Server.Cache.DefaultStorage = $Name } <# .SYNOPSIS Returns the current default cache Storage name. .DESCRIPTION Returns the current default cache Storage name. Empty/null if one isn't set. .EXAMPLE $storageName = Get-PodeCacheDefaultStorage #> function Get-PodeCacheDefaultStorage { [CmdletBinding()] param() return $PodeContext.Server.Cache.DefaultStorage } <# .SYNOPSIS Set a default cache TTL. .DESCRIPTION Set a default cache TTL. .PARAMETER Value A default TTL value, in seconds, to use when setting cache key expiries. .EXAMPLE Set-PodeCacheDefaultTtl -Value 3600 #> function Set-PodeCacheDefaultTtl { [CmdletBinding()] param( [Parameter(Mandatory = $true)] [int] $Value ) if ($Value -le 0) { return } $PodeContext.Server.Cache.DefaultTtl = $Value } <# .SYNOPSIS Returns the current default cache TTL value. .DESCRIPTION Returns the current default cache TTL value. 3600 seconds is the default TTL if not set. .EXAMPLE $ttl = Get-PodeCacheDefaultTtl #> function Get-PodeCacheDefaultTtl { [CmdletBinding()] param() return $PodeContext.Server.Cache.DefaultTtl } |