Auto.ps1
#Set-StrictMode -Version Latest ##################################################### # Auto ##################################################### <#PSScriptInfo .VERSION 0.21 .GUID 602bc07e-a621-4738-8c27-0edf4a4cea8e .AUTHOR David Walker, Sitecore Dave, Radical Dave .COMPANYNAME David Walker, Sitecore Dave, Radical Dave .COPYRIGHT David Walker, Sitecore Dave, Radical Dave .TAGS sitecore powershell local install iis solr .LICENSEURI https://github.com/SitecoreDave/SharedSitecore.SitecoreLocal/blob/main/LICENSE .PROJECTURI https://github.com/SitecoreDave/SharedSitecore.SitecoreLocal .ICONURI .EXTERNALMODULEDEPENDENCIES .REQUIREDSCRIPTS .EXTERNALSCRIPTDEPENDENCIES .RELEASENOTES - see README.md #> <# .SYNOPSIS Auto All The Things! .DESCRIPTION PowerShell script that helps you Automate All The Things! .EXAMPLE PS> Auto 'name' PS> Auto az armtemplate.json .EXAMPLE PS> Auto 'name' 'template' .EXAMPLE PS> Auto 'name' 'template' 'd:\repos' .Link https://github.com/Radical-Dave/Auto .OUTPUTS System.String #> [CmdletBinding(SupportsShouldProcess=$true)] Param( [Parameter(Mandatory = $false, Position=0)] [string] $action = 'help', [Parameter(Mandatory = $false, Position=1)] [string] $data = '', [Parameter(Mandatory = $false, Position=2)] [string] $path = '', [string] $adApp = 'DevOps', [switch] $Force = $false ) begin { $Global:ErrorActionPreference = 'Stop' $PSScriptName = ($MyInvocation.MyCommand.Name.Replace(".ps1","")) $PSScriptVersion = (Test-ScriptFileInfo -Path $MyInvocation.MyCommand.Path | Select-Object -ExpandProperty Version) $PSCallingScript = if ($MyInvocation.PSCommandPath) { $MyInvocation.PSCommandPath | Split-Path -Parent } else { $null } Write-Verbose "#####################################################" Write-Host "# $PSScriptRoot/$PSScriptName $($PSScriptVersion):$action $data $path called by:$PSCallingScript" -ForegroundColor White $StopWatch = New-Object -TypeName System.Diagnostics.Stopwatch $StopWatch.Start() Write-Verbose "path:$path" if (@('az','tf') -contains $action -and $data -ne "") { if (Test-Path "$PSScriptRoot\data\$action\$data\tasks\$data.json") { $path = "$PSScriptRoot\data\$action\tasks.json"; } elseif (Test-Path "$PSScriptPath\data\$action\tasks\$data\$data.json") { $path = "$PSScriptPath\data\$action\$data\tasks.json"; } $tasks = $path } else { if (!$path -and $action -ne 'az') { if (Test-Path "$PSScriptRoot/$PSScriptName.json") { $path = "$PSScriptRoot/$PSScriptName.json" } else { $profileParent =Split-Path $profile -Parent if (Test-Path "$profileParent/$($PSScriptName).json") { $path = "$profileParent/$($PSScriptName).json" } } } } Write-Verbose "path:$path" #if (!(Test-Path $path)) { # throw "ERROR invalid path:$($path)" #} if ($path) { try { #$tasks = Get-Content .\auto.json | Out-String | Invoke-Expression $configFile = (Get-Content $path -Raw) | ConvertFrom-Json #Write-Host "config:$($config)" } catch { throw $_ } Write-Verbose "logs:$($configFile.logs)" try { #Write-Verbose "checking tasks" $tasksNode = $configFile.psobject.properties["tasks"].value #Write-Verbose "checking props" #Write-Host "tasksNode:$($tasksNode)" $tasks = $tasksNode.PSObject.Properties #Write-Host "tasks:$($tasks)" } catch { Write-Verbose "NON-Critical? Error parsing task(s): $_" } } if (!$path) { if ((Test-Path "$PSScriptPath\data\$action\$data\tasks.json")) { $path = "$PSScriptPath\data\$action\$data\tasks.json"; } } Write-Verbose "path:$path" } process { if ($action -eq 'add' -and $data.IndexOf('=') -gt -1) { Write-Host "add task:$data" $ds = $data.split('=') #if ($config.tasks["$data"]) { #if (!Force) { # throw "ERROR Task:$action already exists. Use -Force to overwrite." #} else { # $config.tasks | Add-Member -MemberType NoteProperty -Name "$($ds[0])" -Value "$($ds[1])" -PassThru -Force #} #} else { $configFile.tasks | Add-Member -MemberType NoteProperty -Name "$($ds[0])" -Value "$($ds[1])" -PassThru -Force #} $configFile | ConvertTo-Json | Out-File $path } elseif ($action -eq 'del' -or $action -eq 'delete' -and $data) { if (!$configFile -or !$configFile.tasks) { throw 'ERROR no config or config.tasks?' } Write-Host "delete task:$data" $configFile.tasks.PSObject.Properties.Remove("$data") $configFile | ConvertTo-Json | Out-File $path } else { $task = @() Write-Verbose "action:$action" if ($tasks -and $action -ne 'help') { $taskProperty = $tasks[$action] Write-Verbose "taskProperty:$taskProperty" if ($taskProperty) { $task = $taskProperty.value } } if ($task) { Write-Verbose "task:$task" if ($task -like '*$(data)*') { Write-Verbose "data:$data" $task = $task.replace('$(data)', "$($data)") #$task = $task -replace '$(data)', "$($data)" } Write-Verbose "task:$task" $cmd = $task Write-Verbose "cmd:$cmd" if ($cmd -like '~\*') { $cmd = (Join-Path (Split-Path $profile -Parent) ($task.Remove(0,2))) } elseif ($cmd -like '.\*') { $cmd = (Join-Path $PSScriptRoot ($task.Remove(0,2))) } elseif ($cmd.Substring(0,2) -eq '*\') { $name = $cmd.Remove(0,2) Write-Host "name:$name" $checkPath = $data if (!$checkPath) { #$cmd = (Join-Path $PSScriptRoot ($task.Remove(0,2))) $checkPath = "$(Split-Path $path -Parent)\data\tests\nested" } Write-Host "checkPath:$checkPath" $cmd = Get-ChildItem "$checkPath\$name*" -Recurse | Select-Object FullName if (!$cmd) { throw "ERROR could not find item $name in $checkPath -Recurse" } } Write-Host "Invoke:$cmd" -ForegroundColor White if (!$data) { Invoke-Expression -Command $cmd -OutVariable $results } else { Invoke-Expression -Command "$cmd $data" -OutVariable $results } Write-Host "RESULTS:$results" } else { #if ($action -ne 'help' -and $action -ne 'az' -and $action -ne 'tf') { if (@('help','az','tf','tfd','sql') -notcontains $action) { Write-Host "Task not found in $PSScriptName.json: $action, to add use: -addTask 'AutoScript'" -ForegroundColor White } if ($action -eq 'sql') { if(!$data) {$data = 'SELECT @@version'} #* FROM SYS.DATABASES #SYS_TABLES if ($path -notlike ';') { #use config $path = "Data Source=(local);Initial Catalog=.;Integrated Security=SSPI;" } Write-Host "RUN:$data" Write-Host "AGAINST:$path" Write-Host "path:$path" try { $connection = New-Object system.data.sqlclient.sqlconnection Write-Verbose "[BEGIN ] Creating the SQL Command object" $cmd = New-Object system.Data.SqlClient.SqlCommand $connection.connectionstring = $path $connection.open() #join the connection to the command object $cmd.connection = $connection $cmd.CommandText = $data Write-Verbose "[PROCESS] Invoking $data" if ($PSCmdlet.ShouldProcess($data)) { #determine what method to invoke based on the query Switch -regex ($data) { "^Select (\w+|\*)|(@@\w+ AS)" { $reader = $cmd.executereader() $out=@() #convert datarows to a custom object while ($reader.read()) { $h = [ordered]@{} for ($i=0;$i -lt $reader.FieldCount;$i++) { $col = $reader.getname($i) $h.add($col,$reader.getvalue($i)) } #for $out += new-object -TypeName psobject -Property $h } #while $out $reader.close() Break } "@@" { $cmd.ExecuteScalar() Break } Default { $cmd.ExecuteNonQuery() | Out-Null } } } } catch { throw "ERROR $PSScriptName sql $data - $_" #-InformationVariable results } } elseif (@('az','tf','tfd') -contains $action) { Write-Host "RUN:$path" $envPrefix = '' #if ($action -eq 'tf') { $envPrefix = 'TF_VAR_'} if (@('tf','tfd') -contains $action) { $envPrefix = 'TF_VAR_'} #todo: finish working with Nick to use set-env (otherwise use set-envs) @((Split-Path $profile -Parent),$PSScriptRoot,("$currLocation" -ne "$PSScriptRoot" ? $currLocation : ''),$data |