Skip to content

Commit a379e1f

Browse files
liamjpetersandyleejordan
authored andcommitted
Check whether each scriptblock being analysed has a process block that directly contains variable usage of $_ or $PSItem. Then when we encounted a parameter with ValueFromPipeline set, we consider whether we saw usage within a process block by automatic variable.
1 parent b09c4e8 commit a379e1f

File tree

1 file changed

+19
-10
lines changed

1 file changed

+19
-10
lines changed

Rules/ReviewUnusedParameter.cs

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,19 @@ public IEnumerable<DiagnosticRecord> AnalyzeScript(Ast ast, string fileName)
9898
// find all declared parameters
9999
IEnumerable<Ast> parameterAsts = scriptBlockAst.FindAll(oneAst => oneAst is ParameterAst, false);
100100

101+
// does the scriptblock have a process block where either $PSItem or $_ is referenced
102+
bool hasProcessBlockWithPSItemOrUnderscore = false;
103+
if (scriptBlockAst.ProcessBlock != null)
104+
{
105+
IDictionary<string, int> processBlockVariableCount = GetVariableCount(scriptBlockAst.ProcessBlock);
106+
processBlockVariableCount.TryGetValue("_", out int underscoreVariableCount);
107+
processBlockVariableCount.TryGetValue("psitem", out int psitemVariableCount);
108+
if (underscoreVariableCount > 0 || psitemVariableCount > 0)
109+
{
110+
hasProcessBlockWithPSItemOrUnderscore = true;
111+
}
112+
}
113+
101114
// list all variables
102115
IDictionary<string, int> variableCount = GetVariableCount(scriptBlockAst);
103116

@@ -108,18 +121,14 @@ public IEnumerable<DiagnosticRecord> AnalyzeScript(Ast ast, string fileName)
108121
valFromPipelineAst => valFromPipelineAst is NamedAttributeArgumentAst namedAttrib && string.Equals(
109122
namedAttrib.ArgumentName, "ValueFromPipeline",
110123
StringComparison.OrdinalIgnoreCase
111-
),
124+
),
112125
false
113126
);
114-
// If the parameter has the ValueFromPipeline attribute, check for usages of $_ or $PSItem
115-
if (valueFromPipeline?.GetValue() == true)
127+
// If the parameter has the ValueFromPipeline attribute and the scriptblock has a process block with
128+
// $_ or $PSItem usage, then the parameter is considered used
129+
if (valueFromPipeline?.GetValue() == true && hasProcessBlockWithPSItemOrUnderscore)
116130
{
117-
variableCount.TryGetValue("_", out int underscoreVariableCount);
118-
variableCount.TryGetValue("psitem", out int psitemVariableCount);
119-
if (underscoreVariableCount > 0 || psitemVariableCount > 0)
120-
{
121-
continue;
122-
}
131+
continue;
123132
}
124133

125134
// there should be at least two usages of the variable since the parameter declaration counts as one
@@ -240,7 +249,7 @@ public string GetSourceName()
240249
/// <param name="ast">The scriptblock ast to scan</param>
241250
/// <param name="data">Previously generated data. New findings are added to any existing dictionary if present</param>
242251
/// <returns>a dictionary including all variables in the scriptblock and their count</returns>
243-
IDictionary<string, int> GetVariableCount(ScriptBlockAst ast, Dictionary<string, int> data = null)
252+
IDictionary<string, int> GetVariableCount(Ast ast, Dictionary<string, int> data = null)
244253
{
245254
Dictionary<string, int> content = data;
246255
if (null == data)

0 commit comments

Comments
 (0)