Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions src/Microsoft.Unity.Analyzers.Tests/ConsistencyTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -129,4 +129,46 @@ public async Task CheckHelpLinks()
}
}

[SkippableFact]
public void CheckCodeFixTestsHaveTriviaTests()
{
var assembly = typeof(ConsistencyTests).Assembly;

var codeFixTestClasses = assembly
.GetTypes()
.Where(t => t is { IsClass: true, IsAbstract: false } && IsBaseCodeFixVerifierTest(t))
.ToArray();

List<string> missingTriviaTests = [];

foreach (var testClass in codeFixTestClasses)
{
if (testClass
.GetMethods(BindingFlags.Public | BindingFlags.Instance)
.Where(m => m.GetCustomAttributes(typeof(FactAttribute), true).Any() ||
m.GetCustomAttributes(typeof(TheoryAttribute), true).Any())
.Any(m => m.Name.Contains("Trivia", StringComparison.OrdinalIgnoreCase)))
continue;

missingTriviaTests.Add(testClass.Name);
}

Skip.If(missingTriviaTests.Any(), $"The following CodeFix test classes ({(float)missingTriviaTests.Count / codeFixTestClasses.Length:0.00%}) are missing a Trivia test:\n\n{string.Join("\n", missingTriviaTests)}");
}

private static bool IsBaseCodeFixVerifierTest(Type type)
{
// IsAssignableFrom cannot be used with open generic types
var baseType = type.BaseType;
while (baseType != null)
{
if (baseType.IsGenericType && baseType.GetGenericTypeDefinition() == typeof(BaseCodeFixVerifierTest<,>))
return true;

baseType = baseType.BaseType;
}

return false;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ public void Method(Foo foo) {


[Fact]
public async Task CreateComponentInstanceComments()
public async Task CreateComponentInstanceTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ namespace Microsoft.Unity.Analyzers.Tests;
public class EmptyUnityMessageTests : BaseCodeFixVerifierTest<EmptyUnityMessageAnalyzer, EmptyUnityMessageCodeFix>
{
[Fact]
public async Task EmptyFixedUpdate()
public async Task EmptyFixedUpdateTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -115,4 +115,52 @@ void Update()

await VerifyCSharpDiagnosticAsync(test);
}

[SkippableFact]
public async Task UseGetLocalPositionAndRotationMethodTrivia()
{
const string test = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Quaternion rotation;
// rotation comment
rotation = transform.localRotation;
// position comment
var position = transform.localPosition;
// trailing comment
}
}
";

var method = GetCSharpDiagnosticAnalyzer().ExpressionContext.PositionAndRotationMethodName;
var type = typeof(UnityEngine.Transform);

Skip.IfNot(MethodExists("UnityEngine", type.FullName!, method), $"This Unity version does not support {type}.{method}");

var diagnostic = ExpectDiagnostic().WithLocation(10, 9);

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Quaternion rotation;
// rotation comment
// position comment
transform.GetLocalPositionAndRotation(out var position, out rotation);
// trailing comment
}
}
";

await VerifyCSharpFixAsync(test, fixedTest);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -242,4 +242,49 @@ void Update()
// Implicit conversion incompatible with 'out'
await VerifyCSharpDiagnosticAsync(test);
}

[Fact]
public async Task UseGetPositionAndRotationMethodAssignmentTrivia()
{
const string test = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Vector3 position;
Quaternion rotation;
// position comment
position = transform.position;
// rotation comment
rotation = transform.rotation;
// trailing comment
}
}
";

var diagnostic = ExpectDiagnostic().WithLocation(11, 9);

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Vector3 position;
Quaternion rotation;
// position comment
// rotation comment
transform.GetPositionAndRotation(out position, out rotation);
// trailing comment
}
}
";

await VerifyCSharpFixAsync(test, fixedTest);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ private static void Menu1()
}

[Fact]
public async Task MissingStaticDeclarationComments()
public async Task MissingStaticDeclarationTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
37 changes: 37 additions & 0 deletions src/Microsoft.Unity.Analyzers.Tests/ImproperMessageCaseTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -287,6 +287,43 @@ static void OnPostprocessAllAssets(string[] importedAssets, string[] deletedAsse
{
}
}
";
await VerifyCSharpFixAsync(test, fixedTest);
}

[Fact]
public async Task ImproperlyCasedUpdateTrivia()
{
const string test = @"
using UnityEngine;

class Camera : MonoBehaviour
{
// comment
private void /* inner */ UPDATE /* outer */ ()
{
}
/* comment */
}
";

var diagnostic = ExpectDiagnostic()
.WithLocation(7, 30)
.WithArguments("UPDATE");

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;

class Camera : MonoBehaviour
{
// comment
private void /* inner */ Update /* outer */ ()
{
}
/* comment */
}
";
await VerifyCSharpFixAsync(test, fixedTest);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ class Camera : MonoBehaviour
}

[Fact]
public async Task RedundantSerializeFieldComments()
public async Task RedundantSerializeFieldTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ private void Method(GameObject argument)
}

[Fact]
public async Task RemoveGameObjectPropertyComments()
public async Task RemoveGameObjectPropertyTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,47 @@ static Camera()

public static readonly int willGenerateImplicitStaticCtor = 666;
}
";
await VerifyCSharpFixAsync(test, fixedTest);
}

[Fact]
public async Task InitializeOnLoadWithoutStaticCtorTrivia()
{
const string test = @"
using UnityEngine;
using UnityEditor;

[InitializeOnLoad]
class Camera : MonoBehaviour
{
// comment
private int field = 0;
/* comment */
}
";

var diagnostic = ExpectDiagnostic()
.WithLocation(6, 7)
.WithArguments("Camera");

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;
using UnityEditor;

[InitializeOnLoad]
class Camera : MonoBehaviour
{
static Camera()
{
}

// comment
private int field = 0;
/* comment */
}
";
await VerifyCSharpFixAsync(test, fixedTest);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ private static void OnLoad()
}

[Fact]
public async Task InitializeOnLoadMethodFixModifiersComments()
public async Task InitializeOnLoadMethodFixModifiersTrivia()
{
const string test = @"
using UnityEditor;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -631,4 +631,53 @@ void Update()
// The lambda is not considered inside the loop
await VerifyCSharpDiagnosticAsync(test);
}

[Fact]
public async Task VerticesInForLoopConditionTrivia()
{
const string test = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Mesh mesh = GetComponent<MeshFilter>().mesh;
// loop start
for (int i = 0; i < /* vertices access */ mesh.vertices.Length /* end access */; i++)
{
// some work
}
// loop end
}
}
";

var diagnostic = ExpectDiagnostic()
.WithLocation(10, 51)
.WithArguments("vertices");

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;

class Camera : MonoBehaviour
{
void Update()
{
Mesh mesh = GetComponent<MeshFilter>().mesh;
Vector3[] meshVertices = mesh.vertices;
// loop start
for (int i = 0; i < /* vertices access */ meshVertices.Length /* end access */; i++)
{
// some work
}
// loop end
}
}
";

await VerifyCSharpFixAsync(test, fixedTest);
}
}
35 changes: 35 additions & 0 deletions src/Microsoft.Unity.Analyzers.Tests/MessageSignatureTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -409,4 +409,39 @@ private void OnSceneGUI(object foo)
// In this special case, we do not provide a codefix, given it would break the code as the message is -wrongly- used elsewhere
await VerifyCSharpFixAsync(test, test);
}

[Fact]
public async Task MessageSignatureTrivia()
{
const string test = @"
using UnityEngine;

class Camera : MonoBehaviour
{
// leading comment
private void OnApplicationPause(int foo, bool pause, string[] bar) // trailing comment
{
}
}
";

var diagnostic = ExpectDiagnostic()
.WithLocation(7, 18)
.WithArguments("OnApplicationPause");

await VerifyCSharpDiagnosticAsync(test, diagnostic);

const string fixedTest = @"
using UnityEngine;

class Camera : MonoBehaviour
{
// leading comment
private void OnApplicationPause(bool pause) // trailing comment
{
}
}
";
await VerifyCSharpFixAsync(test, fixedTest);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ private IEnumerator InvokeMe()
}

[Fact]
public async Task TestStartCoroutineComments()
public async Task TestStartCoroutineTrivia()
{
const string test = @"
using UnityEngine;
Expand Down
Loading
Loading