PSModuleUtils/Functions/FormatFileContent.ps1
# =========================================================================== # FormatFileContent.ps1 --------------------------------------------------- # =========================================================================== # function ---------------------------------------------------------------- # --------------------------------------------------------------------------- function Format-IniContent { <# .DESCRIPTION Searches for pattern '%(value)s' in specified content of a config file and replaces this pattern with the value of the referenced field or with the value of the corresponding system environment. [section] field-reference = value field-with-pattern-reference = %(field-reference)s\file-name field-with-pattern-environment = %(HOME)s\file-name Field 'field-with-pattern-reference' will be assigned the value 'value/file-name' and 'field-with-pattern-environment' gets the value 'C:\Users\User\file-name'. .PARAMETER Content .OUTPUTS System.Object. Formatted config content. #> [CmdletBinding(PositionalBinding)] [OutputType([System.Object])] Param( [Parameter(Position=1, Mandatory, ValueFromPipeline, HelpMessage="Content from config file.")] [System.Object] $Content, [Parameter(Position=2, HelpMessage="Object with values for substitution.")] [System.Object] $Substitution ) Process { # loop over all sections in config object $keys = $Content.Keys -split " " for($i=0; $i -lt $keys.Count; $i++ ) { $Content.($keys[$i]) = Format-FileContent -Content $Content.($keys[$i]) -Substitution $Substitution } return $Content } } # function ---------------------------------------------------------------- # --------------------------------------------------------------------------- function Format-JsonContent { <# .DESCRIPTION Searches for pattern '%(value)s' in specified content of a json file and replaces this pattern with the value of a referenced field or with the value of the corresponding system environment. { 'field-reference' : 'value' 'field-with-pattern-reference' = '%(field-reference)s\file-name' 'field-with-pattern-environment' = '%(HOME)s\file-name' } Field 'field-with-pattern-reference' will be assigned the value 'value/file-name' and 'field-with-pattern-environment' gets the value 'C:\Users\User\file-name'. .PARAMETER Content .OUTPUTS System.Object. Formatted json content. #> [CmdletBinding(PositionalBinding)] [OutputType([System.Object])] Param( [Parameter(Position=1, Mandatory, ValueFromPipeline, HelpMessage="Content from json file.")] [System.Object[]] $Content, [Parameter(Position=2, HelpMessage="Object with values for substitution.")] [System.Object] $Substitution ) Process { # loop over all elements in json object for($i=0; $i -lt $Content.Length; $i++) { $hashtable = ConvertTo-HashtableFromObject $Content[$i] $result = Format-FileContent -Content $hashtable -Substitution $Substitution $Content[$i] = ConvertTo-ObjectFromHashtable $result } return $Content } } # function ---------------------------------------------------------------- # --------------------------------------------------------------------------- function Format-FileContent { <# .DESCRIPTION .PARAMETER Content .OUTPUTS System.Object. Formatted config content. #> [CmdletBinding(PositionalBinding)] [OutputType([System.Object])] Param( [Parameter(Position=1, Mandatory, ValueFromPipeline, HelpMessage="Content of a arbitrary file.")] [System.Object] $Content, [Parameter(Position=2, HelpMessage="Object with values for substitution.")] [System.Object] $Substitution ) Process { # loop over all fields in a specific config section $default_keys = ($Substitution | Get-Member | Where-Object {$_.MemberType -eq "NoteProperty" -or $_.MemberType -eq "Property"} | Select-Object -ExpandProperty Name) -split " " $default = $False if ($default_keys) { $default = $True } $keys_sec = $Content.Keys -split " " for($j=0; $j -lt $keys_sec.Count; $j++ ) { # if there are matches each result will be stored and replaced with referenced field or corresponding environment variable $Content.($keys_sec[$j]) = Get-FormattedString -String $Content.($keys_sec[$j]) -Keys $keys_sec -Object $Content -Default:$default -DefaultKeys $default_keys -DefaultObject $Substitution } return $Content } } # function ---------------------------------------------------------------- # --------------------------------------------------------------------------- function Get-FormattedString { <# .DESCRIPTION .PARAMETER String .OUTPUTS System.Object. Object which contains all values inside ini pattern. #> [CmdletBinding(PositionalBinding)] [OutputType([System.Object])] Param ( [Parameter(HelpMessage="Search string.")] [System.String] $String, [Parameter(HelpMessage="Keys for substitution.")] [System.Object] $Keys, [Parameter(HelpMessage="Object with elements for substitution.")] [System.Object] $Object, [Parameter(HelpMessage="Use default object for substitution.")] [Switch] $Default, [Parameter(HelpMessage="Default keys for substitution.")] [System.Object] $DefaultKeys, [Parameter(HelpMessage= "Default object with elements for substitution.")] [System.Object] $DefaultObject ) Process{ $string_backup = $String $pattern = "\%\(([a-z-_]+)\)s" # if there are matches each result will be stored and replaced with referenced field or corresponding environment variable Get-RegexMatchResultList -String $String -Pattern $pattern | ForEach-Object { # search for reference field and corresponding environment variable $value = $Null if ($Keys -contains $_){ $value = $Object.($_) } elseif ($Default) { if ($DefaultKeys -contains $_){ $value = $DefaultObject.($_) } } if (-not $value) { $value = [System.Environment]::GetEnvironmentVariable($_) } if ($value) { # replace the pattern in given field as well as return formatted string $String = [Regex]::Replace( $String, "\%\(($_)\)s", $value, "IgnoreCase") } } # if the search pattern was found and string was modified, perform a recursive proceeding, else return the string if ($string_backup -eq $String){ return $String } else { return Get-FormattedString -String $String -Keys $Keys -Object $Object -Default:$Default -DefaultKeys $DefaultKeys -DefaultObject $DefaultObject } } } # function ---------------------------------------------------------------- # --------------------------------------------------------------------------- function Get-RegexMatchResultList { Param( [Parameter(HelpMessage="Search string.")] [System.String] $String, [Parameter(HelpMessage="Search patterm.")] [System.String] $Pattern ) return [Regex]::Matches($String, $Pattern, "IgnoreCase").Groups | Where-Object { $_.Name -eq 1} | Select-Object -ExpandProperty Value } |