Skip to content

Commit c597849

Browse files
author
Kapil Borle
committed
Fix severity filtering while invoking script analyzer
Filters the rules based on their severity before passing them the AST for analysis. Prior to the fix, the severity filter was applied on diagnostic records. This was inefficient as Invoke-ScriptAnalyzer would run all the rules irrespective of the given severity and then filter the diagnostic records to extract the results that corresponded to the given severity.
1 parent 3571167 commit c597849

File tree

1 file changed

+63
-72
lines changed

1 file changed

+63
-72
lines changed

Engine/ScriptAnalyzer.cs

Lines changed: 63 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -1320,6 +1320,64 @@ private IEnumerable<DiagnosticRecord> AnalyzeFile(string filePath)
13201320
return this.AnalyzeSyntaxTree(scriptAst, scriptTokens, filePath);
13211321
}
13221322

1323+
private bool IsSeverityAllowed(IEnumerable<uint> allowedSeverities, IRule rule)
1324+
{
1325+
return severity == null
1326+
|| (allowedSeverities != null
1327+
&& rule != null
1328+
&& HasGetSeverity(rule)
1329+
&& allowedSeverities.Contains((uint)rule.GetSeverity()));
1330+
}
1331+
1332+
IEnumerable<uint> GetAllowedSeveritiesInInt()
1333+
{
1334+
return severity != null
1335+
? severity.Select(item => (uint)Enum.Parse(typeof(DiagnosticSeverity), item, true))
1336+
: null;
1337+
}
1338+
1339+
bool HasMethod<T>(T obj, string methodName)
1340+
{
1341+
var type = obj.GetType();
1342+
return type.GetMethod(methodName) != null;
1343+
}
1344+
1345+
bool HasGetSeverity<T>(T obj)
1346+
{
1347+
return HasMethod<T>(obj, "GetSeverity");
1348+
}
1349+
1350+
bool IsRuleAllowed(IRule rule)
1351+
{
1352+
IEnumerable<uint> allowedSeverities = GetAllowedSeveritiesInInt();
1353+
bool includeRegexMatch = false;
1354+
bool excludeRegexMatch = false;
1355+
foreach (Regex include in includeRegexList)
1356+
{
1357+
if (include.IsMatch(rule.GetName()))
1358+
{
1359+
includeRegexMatch = true;
1360+
break;
1361+
}
1362+
}
1363+
1364+
foreach (Regex exclude in excludeRegexList)
1365+
{
1366+
if (exclude.IsMatch(rule.GetName()))
1367+
{
1368+
excludeRegexMatch = true;
1369+
break;
1370+
}
1371+
}
1372+
1373+
bool helpRule = String.Equals(rule.GetName(), "PSUseUTF8EncodingForHelpFile", StringComparison.OrdinalIgnoreCase);
1374+
bool includeSeverity = IsSeverityAllowed(allowedSeverities, rule);
1375+
1376+
return (includeRule == null || includeRegexMatch)
1377+
&& (excludeRule == null || !excludeRegexMatch)
1378+
&& IsSeverityAllowed(allowedSeverities, rule);
1379+
}
1380+
13231381
/// <summary>
13241382
/// Analyzes the syntax tree of a script file that has already been parsed.
13251383
/// </summary>
@@ -1373,39 +1431,17 @@ public IEnumerable<DiagnosticRecord> AnalyzeSyntaxTree(
13731431

13741432
Helper.Instance.Tokens = scriptTokens;
13751433
}
1376-
1434+
13771435
#region Run ScriptRules
13781436
//Trim down to the leaf element of the filePath and pass it to Diagnostic Record
13791437
string fileName = filePathIsNullOrWhiteSpace ? String.Empty : System.IO.Path.GetFileName(filePath);
1380-
13811438
if (this.ScriptRules != null)
13821439
{
13831440
var tasks = this.ScriptRules.Select(scriptRule => Task.Factory.StartNew(() =>
13841441
{
1385-
bool includeRegexMatch = false;
1386-
bool excludeRegexMatch = false;
1387-
1388-
foreach (Regex include in includeRegexList)
1389-
{
1390-
if (include.IsMatch(scriptRule.GetName()))
1391-
{
1392-
includeRegexMatch = true;
1393-
break;
1394-
}
1395-
}
1396-
1397-
foreach (Regex exclude in excludeRegexList)
1398-
{
1399-
if (exclude.IsMatch(scriptRule.GetName()))
1400-
{
1401-
excludeRegexMatch = true;
1402-
break;
1403-
}
1404-
}
1405-
14061442
bool helpRule = String.Equals(scriptRule.GetName(), "PSUseUTF8EncodingForHelpFile", StringComparison.OrdinalIgnoreCase);
14071443

1408-
if ((includeRule == null || includeRegexMatch) && (excludeRule == null || !excludeRegexMatch))
1444+
if (IsRuleAllowed(scriptRule))
14091445
{
14101446
List<object> result = new List<object>();
14111447

@@ -1475,25 +1511,7 @@ public IEnumerable<DiagnosticRecord> AnalyzeSyntaxTree(
14751511
{
14761512
foreach (ITokenRule tokenRule in this.TokenRules)
14771513
{
1478-
bool includeRegexMatch = false;
1479-
bool excludeRegexMatch = false;
1480-
foreach (Regex include in includeRegexList)
1481-
{
1482-
if (include.IsMatch(tokenRule.GetName()))
1483-
{
1484-
includeRegexMatch = true;
1485-
break;
1486-
}
1487-
}
1488-
foreach (Regex exclude in excludeRegexList)
1489-
{
1490-
if (exclude.IsMatch(tokenRule.GetName()))
1491-
{
1492-
excludeRegexMatch = true;
1493-
break;
1494-
}
1495-
}
1496-
if ((includeRule == null || includeRegexMatch) && (excludeRule == null || !excludeRegexMatch))
1514+
if (IsRuleAllowed(tokenRule))
14971515
{
14981516
this.outputWriter.WriteVerbose(string.Format(CultureInfo.CurrentCulture, Strings.VerboseRunningMessage, tokenRule.GetName()));
14991517

@@ -1592,24 +1610,7 @@ public IEnumerable<DiagnosticRecord> AnalyzeSyntaxTree(
15921610
// Run all DSC Rules
15931611
foreach (IDSCResourceRule dscResourceRule in this.DSCResourceRules)
15941612
{
1595-
bool includeRegexMatch = false;
1596-
bool excludeRegexMatch = false;
1597-
foreach (Regex include in includeRegexList)
1598-
{
1599-
if (include.IsMatch(dscResourceRule.GetName()))
1600-
{
1601-
includeRegexMatch = true;
1602-
break;
1603-
}
1604-
}
1605-
foreach (Regex exclude in excludeRegexList)
1606-
{
1607-
if (exclude.IsMatch(dscResourceRule.GetName()))
1608-
{
1609-
excludeRegexMatch = true;
1610-
}
1611-
}
1612-
if ((includeRule == null || includeRegexMatch) && (excludeRule == null || !excludeRegexMatch))
1613+
if (IsRuleAllowed(dscResourceRule))
16131614
{
16141615
this.outputWriter.WriteVerbose(string.Format(CultureInfo.CurrentCulture, Strings.VerboseRunningMessage, dscResourceRule.GetName()));
16151616

@@ -1646,8 +1647,7 @@ public IEnumerable<DiagnosticRecord> AnalyzeSyntaxTree(
16461647

16471648
foreach (ExternalRule exRule in this.ExternalRules)
16481649
{
1649-
if ((includeRule == null || includeRule.Contains(exRule.GetName(), StringComparer.OrdinalIgnoreCase)) &&
1650-
(excludeRule == null || !excludeRule.Contains(exRule.GetName(), StringComparer.OrdinalIgnoreCase)))
1650+
if (IsRuleAllowed(exRule))
16511651
{
16521652
string ruleName = string.Format(CultureInfo.CurrentCulture, "{0}\\{1}", exRule.GetSourceName(), exRule.GetName());
16531653
this.outputWriter.WriteVerbose(string.Format(CultureInfo.CurrentCulture, Strings.VerboseRunningMessage, ruleName));
@@ -1676,15 +1676,6 @@ public IEnumerable<DiagnosticRecord> AnalyzeSyntaxTree(
16761676
// Need to reverse the concurrentbag to ensure that results are sorted in the increasing order of line numbers
16771677
IEnumerable<DiagnosticRecord> diagnosticsList = diagnostics.Reverse();
16781678

1679-
if (severity != null)
1680-
{
1681-
var diagSeverity = severity.Select(item => Enum.Parse(typeof(DiagnosticSeverity), item, true));
1682-
if (diagSeverity.Count() != 0)
1683-
{
1684-
diagnosticsList = diagnostics.Where(item => diagSeverity.Contains(item.Severity));
1685-
}
1686-
}
1687-
16881679
return this.suppressedOnly ?
16891680
suppressed.OfType<DiagnosticRecord>() :
16901681
diagnosticsList;

0 commit comments

Comments
 (0)