PipeScript.types.ps1xml

<?xml version="1.0" encoding="utf-16"?>
<!-- Generated with EZOut 1.8.8: Install-Module EZOut or https://github.com/StartAutomating/EZOut -->
<Types>
  <Type>
    <Name>System.Management.Automation.Language.Ast</Name>
    <Members>
      <ScriptMethod>
        <Name>ConvertFromAST</Name>
        <Script>
                        param()

return $this

                    </Script>
      </ScriptMethod>
      <ScriptMethod>
        <Name>GetLineage</Name>
        <Script>
                        $thisParent = $this.Parent
while ($thisParent) {
    $thisParent
    $thisParent = $thisParent.Parent
}

                    </Script>
      </ScriptMethod>
      <ScriptProperty>
        <Name>Tokens</Name>
        <GetScriptBlock>
                        $text = $this.Extent.ToString()
    
$previousToken = $null
$tokenCount = 0
@(foreach ($token in [Management.Automation.PSParser]::Tokenize($text, [ref]$null)) {
    Add-Member NoteProperty Text $text -Force -InputObject $token
    Add-Member NoteProperty PreviousToken $previousToken -Force -InputObject $token
    if ($token.Type -in 'Variable', 'String') {
        $realContent = $text.Substring($token.Start, $token.Length)
        Add-Member NoteProperty Content $realContent -Force -InputObject $token
    }
    $previousToken = $token
    $tokenCount++
    $token
})
                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.AttributeAst</Name>
    <Members>
      <ScriptProperty>
        <Name>ArgumentList</Name>
        <GetScriptBlock>
                        $Parameter = [Ordered]@{}
$ArgumentList = @()
# Collect all of the arguments of the attribute, in the order they were specified.
$argsInOrder = @(
    @($this.PositionalArguments) + @($this.NamedArguments) |
    Sort-Object { $_.Extent.StartOffset}
)


# Now we need to map each of those arguments into either named or positional arguments.
foreach ($attributeArg in $argsInOrder) {
    # Named arguments are fairly straightforward:
    if ($attributeArg -is [Management.Automation.Language.NamedAttributeArgumentAst]) {
        $argName = $attributeArg.ArgumentName
        $argAst = $attributeArg.Argument
        $parameter[$argName] =
            if ($argName -eq $argAst) { # If the argument is the name,
                $true # treat it as a [switch] parameter.
            }
            # If the argument value was an ScriptBlockExpression
            else {
                $argAst
            }
    } else {
        # If we are a positional parameter, for the moment:
        if ($parameter.Count) {
            # add it to the last named parameter.
            $parameter[@($parameter.Keys)[-1]] =
                @() + $parameter[@($parameter.Keys)[-1]] + $argAst
        } else {
            # Or add it to the list of string arguments.
            $ArgumentList +=
                $attributeArg.ConvertFromAst()
        }
    }
}

return $ArgumentList

                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>Parameter</Name>
        <GetScriptBlock>
                        $Parameter = [Ordered]@{}
# Collect all of the arguments of the attribute, in the order they were specified.
$argsInOrder = @(
    @($this.PositionalArguments) + @($this.NamedArguments) |
    Sort-Object { $_.Extent.StartOffset}
)

# Now we need to map each of those arguments into either named or positional arguments.
foreach ($attributeArg in $argsInOrder) {
    # Named arguments are fairly straightforward:
    if ($attributeArg -is [Management.Automation.Language.NamedAttributeArgumentAst]) {
        $argName = $attributeArg.ArgumentName
        $argAst = $attributeArg.Argument
        $parameter[$argName] =
            if ($argName -eq $argAst) { # If the argument is the name,
                $true # treat it as a [switch] parameter.
            }
            # If the argument value was an ScriptBlockExpression
            else {
                $argAst.ConvertFromAst()
            }
    } else {
        # If we are a positional parameter, for the moment:
        if ($parameter.Count) {
            # add it to the last named parameter.
            $parameter[@($parameter.Keys)[-1]] =
                @() + $parameter[@($parameter.Keys)[-1]] + $attributeArg.ConvertFromAst()
        }
    }
}

return $Parameter
                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>ResolvedCommand</Name>
        <GetScriptBlock>
                        &lt;#
.SYNOPSIS
    Resolves an Attribute to a CommandInfo
.DESCRIPTION
    Resolves an Attribute to one or more CommandInfo.
.EXAMPLE
    {
        [InvokePipeScript()]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [Microsoft.PowerShell.Core.GetCommand()]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [Get_Command()]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [GetCommand()]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [cmd()]$null
    }.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
#&gt;
# Get the name of the transpiler.
$transpilerStepName =
    if ($this.TypeName.IsGeneric) {
        $this.TypeName.TypeName.Name
    } else {
        $this.TypeName.Name
    }
$decamelCase = [Regex]::new('(?&lt;=[a-z])(?=[A-Z])')
@(
    # If a Transpiler exists by that name, it will be returned first.
    Get-Transpiler -TranspilerName $transpilerStepName
    # Then, any periods in the attribute name will be converted to slashes,
    $fullCommandName = $transpilerStepName -replace '\.','\' -replace
        '_','-' # and any underscores to dashes.

    # Then, the first CamelCased code will have a - injected in between the CamelCase.
    $fullCommandName = $decamelCase.Replace($fullCommandName, '-', 1)
    # Now we will try to find the command.
    $ExecutionContext.SessionState.InvokeCommand.GetCommand($fullCommandName, 'All')
)
                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.CommandAst</Name>
    <Members>
      <ScriptProperty>
        <Name>ArgumentList</Name>
        <GetScriptBlock>
                        $parameterAstType = [Management.Automation.Language.CommandParameterAst]
@(
for (
    $commandElementIndex = 1
    $commandElementIndex -lt $this.CommandElements.Count
    $commandElementIndex++
)
{
    $commandElement = $this.CommandElements[$commandElementIndex]
    $nextElement = $this.CommandElements[$commandElementIndex + 1]
    if ($commandElement -is $parameterAstType) {
        if (-not $commandElement.Argument -and
            $nextElement -and
            $nextElement -isnot $parameterAstType) {
            $commandElementIndex++
        }
    } else {
        $commandElement.ConvertFromAst()
    }
}
)
                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>IsAssigned</Name>
        <GetScriptBlock>
                        $this.Parent.Parent -is [Management.Automation.Language.AssignmentStatementAST]
                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>IsPiped</Name>
        <GetScriptBlock>
                        ($this.Parent -is [Management.Automation.Language.PipelineAst]) -and
($this.Parent.PipelineElements.Count -gt 1)

                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>Parameter</Name>
        <GetScriptBlock>
                        $NamedParameters = [Ordered]@{}
$parameterAstType = [Management.Automation.Language.CommandParameterAst]

for (
    $commandElementIndex = 1
    $commandElementIndex -lt $this.CommandElements.Count
    $commandElementIndex++
)
{
    $commandElement = $this.CommandElements[$commandElementIndex]
    $nextElement = $this.CommandElements[$commandElementIndex + 1]
    if ($commandElement -is $parameterAstType) {
        if ($commandElement.Argument) {
            $NamedParameters[$commandElement.ParameterName] =
                $commandElement.Argument.ConvertFromAst()
        } elseif ($nextElement -and $nextElement -isnot $parameterAstType) {
            $NamedParameters[$commandElement.ParameterName] =
                $nextElement.Argument.ConvertFromAst()
            $commandElementIndex++
        } else {
            $NamedParameters[$commandElement.ParameterName] = $true
        }
    }
}

$NamedParameters
                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>PipelineLength</Name>
        <GetScriptBlock>
                        if ($this.Parent -isnot [Management.Automation.Language.PipelineAst]) { return $null }
$this.Parent.PipelineElements.Count



                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>PipelinePosition</Name>
        <GetScriptBlock>
                        if ($this.Parent -isnot [Management.Automation.Language.PipelineAst]) { return $null }
$this.Parent.PipelineElements.IndexOf($this)


                    </GetScriptBlock>
      </ScriptProperty>
      <ScriptProperty>
        <Name>ResolvedCommand</Name>
        <GetScriptBlock>
                        $ExecutionContext.SessionState.InvokeCommand.GetCommand($this.CommandElements[0].ToString(), 'All')
                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.ConstantExpressionAst</Name>
    <Members>
      <ScriptMethod>
        <Name>ConvertFromAST</Name>
        <Script>
                        $this.Value

                    </Script>
      </ScriptMethod>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.PipelineAST</Name>
    <Members>
      <ScriptProperty>
        <Name>IsAssigned</Name>
        <GetScriptBlock>
                        $this.Parent -is [Management.Automation.Language.AssignmentStatementAST]

                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>PipeScript</Name>
    <Members>
      <ScriptProperty>
        <Name>PipeScriptType</Name>
        <GetScriptBlock>
                        if ($this.Source -match '\.psx\.ps1{0,1}$') {
    "Transpiler"
}
elseif ($this.Source -match "\.ps1{0,1}\.(?&lt;ext&gt;[^.]+$)") {
    "SourceGenerator"
}
elseif ($this.Source) {
    "PipeScriptFile"
}
else {
    "Function"
}

                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.ScriptBlock</Name>
    <Members>
      <ScriptMethod>
        <Name>Transpile</Name>
        <Script>
                        $this | .&gt;PipeScript

                    </Script>
      </ScriptMethod>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.ScriptBlockExpressionAst</Name>
    <Members>
      <ScriptMethod>
        <Name>ConvertFromAST</Name>
        <Script>
                        $this.GetScriptBlock()

                    </Script>
      </ScriptMethod>
      <ScriptMethod>
        <Name>GetScriptBlock</Name>
        <Script>
                        [ScriptBlock]::create($this -replace '^\{' -replace '\}$')

                    </Script>
      </ScriptMethod>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.ScriptBlockAst</Name>
    <Members>
      <ScriptMethod>
        <Name>ConvertFromAST</Name>
        <Script>
                        $this.GetScriptBlock()

                    </Script>
      </ScriptMethod>
      <ScriptMethod>
        <Name>GetScriptBlock</Name>
        <Script>
                        [ScriptBlock]::create($this -replace '^\{' -replace '\}$')

                    </Script>
      </ScriptMethod>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.TypeConstraintAst</Name>
    <Members>
      <ScriptProperty>
        <Name>ResolvedCommand</Name>
        <GetScriptBlock>
                        &lt;#
.SYNOPSIS
    Resolves an TypeConstraintAST to a CommandInfo
.DESCRIPTION
    Resolves an TypeConstraintAST to one or more CommandInfo Objects.
.EXAMPLE
    {
        [InvokePipeScript[a]]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [Microsoft.PowerShell.Core.GetCommand]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [Get_Command]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [GetCommand]$null
    }.Ast.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
.EXAMPLE
    {
        [cmd]$null
    }.EndBlock.Statements[0].PipelineElements[0].Expression.Attribute.ResolvedCommand
#&gt;
# Get the name of the transpiler.
$transpilerStepName =
    if ($this.TypeName.IsGeneric) {
        $this.TypeName.TypeName.Name
    } else {
        $this.TypeName.Name
    }
$decamelCase = [Regex]::new('(?&lt;=[a-z])(?=[A-Z])')
@(
    # If a Transpiler exists by that name, it will be returned first.
    Get-Transpiler -TranspilerName $transpilerStepName
    # Then, any periods in the attribute name will be converted to slashes,
    $fullCommandName = $transpilerStepName -replace '\.','\' -replace
        '_','-' # and any underscores to dashes.

    # Then, the first CamelCased code will have a - injected in between the CamelCase.
    $fullCommandName = $decamelCase.Replace($fullCommandName, '-', 1)
    # Now we will try to find the command.
    $ExecutionContext.SessionState.InvokeCommand.GetCommand($fullCommandName, 'All')
)
                    </GetScriptBlock>
      </ScriptProperty>
    </Members>
  </Type>
  <Type>
    <Name>System.Management.Automation.Language.VariableExpressionAst</Name>
    <Members>
      <ScriptMethod>
        <Name>ConvertFromAST</Name>
        <Script>
                        # Most variables we will not know the value of until we have run.
# the exceptions to the rule are: $true, $false, and $null
if ($this.variablePath.userPath -in 'true', 'false', 'null') {
    $ExecutionContext.SessionState.PSVariable.Get($this.variablePath).Value
} else {
    $this
}

                    </Script>
      </ScriptMethod>
      <ScriptMethod>
        <Name>GetAssignments</Name>
        <Script>
                        &lt;#
.SYNOPSIS
    Gets assignments of a variable
.DESCRIPTION
    Searches the abstract syntax tree for assignments of the variable.
.EXAMPLE
    {
        $x = 1
        $y = 2
        $x * $y
    }.Ast.EndBlock.Statements[-1].PipelineElements[0].Expression.Left.GetAssignments()
.EXAMPLE
    {
        [int]$x, [int]$y = 1, 2
        $x * $y
    }.Ast.EndBlock.Statements[-1].PipelineElements[0].Expression.Left.GetAssignments()
.EXAMPLE
    {
        param($x, $y)
        $x * $y
    }.Ast.EndBlock.Statements[-1].PipelineElements[0].Expression.Left.GetAssignments()
#&gt;
param()

$astVariableName = "$this"
$variableFoundAt = @{}
foreach ($parent in $this.GetLineage()) {
    $parent.FindAll({
        param($ast)
        $IsAssignment =
            (
                $ast -is [Management.Automation.Language.AssignmentStatementAst] -and
                $ast.Left.Find({
                    param($leftAst)
                    $leftAst -is [Management.Automation.Language.VariableExpressionAST] -and
                    $leftAst.Extent.ToString() -eq $astVariableName
                }, $false)
            ) -or (
                $ast -is [Management.Automation.Language.ParameterAst] -and
                $ast.Name.ToString() -eq $astVariableName
            )

        if ($IsAssignment -and -not $variableFoundAt[$ast.Extent.StartOffset]) {
            $variableFoundAt[$ast.Extent.StartOffset] = $ast
            $ast
        }
    }, $false)
}

                    </Script>
      </ScriptMethod>
      <ScriptMethod>
        <Name>GetVariableType</Name>
        <Script>
                        &lt;#
.SYNOPSIS
    Gets a Variable's Likely Type
.DESCRIPTION
    Determines the type of a variable.

    This looks for the closest assignment statement and uses this to determine what type the variable is likely to be.
.NOTES
    Subject to revision and improvement. While this covers many potential scenarios, it does not always
.EXAMPLE
    {
        [int]$x = 1
        $y = 2
        $x + $y
    }.Ast.EndBlock.Statements[-1].PipelineElements[0].Expression.Left.GetVariableType()
.EXAMPLE
    {
        $x = Get-Process
        $x + $y
    }.Ast.EndBlock.Statements[-1].PipelineElements[0].Expression.Left.GetVariableType()
#&gt;
if ($this.VariablePath.userPath -eq 'psBoundParmeters') {
    return [Management.Automation.PSBoundParametersDictionary]
}
$assignments = $this.GetAssignments()
$closestAssignment = $assignments[0]

# Our easiest scenario is that the variable is assigned in a parameter
if ($closestAssignment -is [Management.Automation.Language.ParameterAst]) {
    # If so, the .StaticType will give us our variable type.
    return $closestAssignment.StaticType
}

# Our next simple scenario is that the closest assignment is declaring a hashtable
if ($closestAssignment.Right.Expression -is [Management.Automation.Language.HashtableAst]) {
    return [hashtable]
}

# The left can be a convert expression.
if ($closestAssignment.Left -is [Management.Automation.Language.ConvertExpressionAst]) {
    # If the left was [ordered]
    if ($closestAssignment.Left.Type.Tostring() -eq '[ordered]') {
        return [Collections.specialized.OrderedDictionary] # return an OrderedDictionary
    } else {
        # If the left side's type can be reflected
        $reflectedType = $closestAssignment.Left.Type.TypeName.GetReflectionType()
        if ($reflectedType) {
            return $reflectedType # return it.
        }
        else {
            # otherwise, return the left's static type.
            return $closestAssignment.Left.StaticType
        }
    }
}

# Determine if the left side is multiple assignment
$isMultiAssignment =$closestAssignment.Left -is [Management.Automation.Language.ArrayLiteralAst]

# If the left side is not multiple assignment, but the right side is an array
if (-not $isMultiAssignment -and
    $closestAssignment.Right.Expression -is [Management.Automation.ArrayExpressionAst]) {
    # then the object is an array.
    return [Object[]]
}

# Next, if the right as a convert expression
if ($closestAssignment.Right.Expression -is [Management.Automation.Language.ConvertExpressionAst]) {
    # If it was '[ordered]'
    if ($closestAssignment.Right.Expression.Type.Tostring() -eq '[ordered]') {
        # return an ordered dictionary
        return [Collections.specialized.OrderedDictionary]
    } else {
        # Otherwise, see if we have a reflected type.
        $reflectedType = $closestAssignment.Right.Expression.Type.TypeName.GetReflectionType()
        if ($reflectedType) {
            return $reflectedType # If we do, return it.
        }
        else {
            # If we don't, return the static type of the expression
            return $closestAssignment.Right.Expression.StaticType
        }
    }
}




# The right side could be a pipeline
if ($closestAssignment.Right -is [Management.Automation.Language.PipelineAst]) {
    # If so, walk backwards thru the pipeline
    for ($pipelineElementIndex = $closestAssignment.Right.PipelineElements.Count - 1;
        $pipelineElementIndex -ge 0;
        $pipelineElementIndex--) {
        $commandInfo = $closestAssignment.Right.PipelineElements[$pipelineElementIndex].ResolvedCommand
        # If the command had an output type, return it.
        if ($commandInfo.OutputType) {
            return $commandInfo.OutputType.Type
        }
    }
}






# If we don't know, return nothing
return





                    </Script>
      </ScriptMethod>
    </Members>
  </Type>
</Types>