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
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,282 @@ await GeneratorTest<AutoRegisterExportedCollectionsGenerator>.RunAsync(
("TestApp_Bootstrapper.AutoRegisterExportedCollections.g.cs", expected));
}

[Test]
public async Task Generates_Batch_Registration_Method_When_Register_Method_Comes_From_Inherited_Interface()
{
const string source = """
#nullable enable
using System;
using System.Collections.Generic;
using GFramework.Godot.SourceGenerators.Abstractions;

namespace GFramework.Godot.SourceGenerators.Abstractions
{
[AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)]
public sealed class AutoRegisterExportedCollectionsAttribute : Attribute { }

[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
public sealed class RegisterExportedCollectionAttribute : Attribute
{
public RegisterExportedCollectionAttribute(string registryMemberName, string registerMethodName) { }
}
}

namespace TestApp
{
public interface IKeyValue<TKey, TValue>
{
}

public interface IRegistry<TKey, TValue>
{
void Registry(IKeyValue<TKey, TValue> mapping);
}

public interface IAssetRegistry<TValue> : IRegistry<string, TValue>
{
}

public sealed class IntConfig : IKeyValue<string, int>
{
}

[AutoRegisterExportedCollections]
public partial class Bootstrapper
{
private readonly IAssetRegistry<int>? _registry = null;

[RegisterExportedCollection(nameof(_registry), "Registry")]
public List<IntConfig>? Values { get; } = new();
}
}
""";

const string expected = """
// <auto-generated />
#nullable enable

namespace TestApp;

partial class Bootstrapper
{
private void __RegisterExportedCollections_Generated()
{
if (this.Values is not null && this._registry is not null)
{
foreach (var __generatedItem in this.Values)
{
this._registry.Registry(__generatedItem);
}
}
}
}

""";

await GeneratorTest<AutoRegisterExportedCollectionsGenerator>.RunAsync(
source,
("TestApp_Bootstrapper.AutoRegisterExportedCollections.g.cs", expected));
}
Comment thread
GeWuYou marked this conversation as resolved.
Comment thread
coderabbitai[bot] marked this conversation as resolved.

[Test]
public async Task Reports_Diagnostic_When_Register_Method_Is_Only_Explicitly_Implemented_Interface_Member()
{
const string source = """
using System;
using System.Collections.Generic;
using GFramework.Godot.SourceGenerators.Abstractions;

namespace GFramework.Godot.SourceGenerators.Abstractions
{
[AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)]
public sealed class AutoRegisterExportedCollectionsAttribute : Attribute { }

[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
public sealed class RegisterExportedCollectionAttribute : Attribute
{
public RegisterExportedCollectionAttribute(string registryMemberName, string registerMethodName) { }
}
}

namespace TestApp
{
public interface IRegistry
{
void Register(int value);
}

public sealed class ExplicitRegistry : IRegistry
{
void IRegistry.Register(int value) { }
}

[AutoRegisterExportedCollections]
public partial class Bootstrapper
{
private readonly ExplicitRegistry _registry = new();

[RegisterExportedCollection(nameof(_registry), "Register")]
public List<int> {|#0:Values|} { get; } = new();
}
}
""";

var test = new CSharpSourceGeneratorTest<AutoRegisterExportedCollectionsGenerator, DefaultVerifier>
{
TestState =
{
Sources = { source }
},
DisabledDiagnostics = { "GF_Common_Trace_001" }
};
Comment thread
coderabbitai[bot] marked this conversation as resolved.

test.ExpectedDiagnostics.Add(new DiagnosticResult("GF_AutoExport_003", DiagnosticSeverity.Error)
.WithLocation(0)
.WithArguments("Register", "_registry", "Values"));

await test.RunAsync();
}

[Test]
public async Task Generates_Batch_Registration_Method_When_Register_Method_Comes_From_Base_Class()
{
const string source = """
#nullable enable
using System;
using System.Collections.Generic;
using GFramework.Godot.SourceGenerators.Abstractions;

namespace GFramework.Godot.SourceGenerators.Abstractions
{
[AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)]
public sealed class AutoRegisterExportedCollectionsAttribute : Attribute { }

[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
public sealed class RegisterExportedCollectionAttribute : Attribute
{
public RegisterExportedCollectionAttribute(string registryMemberName, string registerMethodName) { }
}
}

namespace TestApp
{
public class BaseRegistry
{
public void Register(int value) { }
}

public sealed class DerivedRegistry : BaseRegistry
{
}

[AutoRegisterExportedCollections]
public partial class Bootstrapper
{
private readonly DerivedRegistry? _registry = new();

[RegisterExportedCollection(nameof(_registry), nameof(BaseRegistry.Register))]
public List<int>? Values { get; } = new();
}
}
""";

const string expected = """
// <auto-generated />
#nullable enable

namespace TestApp;

partial class Bootstrapper
{
private void __RegisterExportedCollections_Generated()
{
if (this.Values is not null && this._registry is not null)
{
foreach (var __generatedItem in this.Values)
{
this._registry.Register(__generatedItem);
}
}
}
}

""";

await GeneratorTest<AutoRegisterExportedCollectionsGenerator>.RunAsync(
source,
("TestApp_Bootstrapper.AutoRegisterExportedCollections.g.cs", expected));
}

[Test]
public async Task Generates_Batch_Registration_Method_When_Registry_Member_Comes_From_Base_Class()
{
const string source = """
#nullable enable
using System;
using System.Collections.Generic;
using GFramework.Godot.SourceGenerators.Abstractions;

namespace GFramework.Godot.SourceGenerators.Abstractions
{
[AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)]
public sealed class AutoRegisterExportedCollectionsAttribute : Attribute { }

[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
public sealed class RegisterExportedCollectionAttribute : Attribute
{
public RegisterExportedCollectionAttribute(string registryMemberName, string registerMethodName) { }
}
}

namespace TestApp
{
public sealed class IntRegistry
{
public void Register(int value) { }
}

public abstract class BootstrapperBase
{
protected readonly IntRegistry? _registry = new();
}

[AutoRegisterExportedCollections]
public partial class Bootstrapper : BootstrapperBase
{
[RegisterExportedCollection(nameof(_registry), nameof(IntRegistry.Register))]
public List<int>? Values { get; } = new();
}
}
""";

const string expected = """
// <auto-generated />
#nullable enable

namespace TestApp;

partial class Bootstrapper
{
private void __RegisterExportedCollections_Generated()
{
if (this.Values is not null && this._registry is not null)
{
foreach (var __generatedItem in this.Values)
{
this._registry.Register(__generatedItem);
}
}
}
}

""";

await GeneratorTest<AutoRegisterExportedCollectionsGenerator>.RunAsync(
source,
("TestApp_Bootstrapper.AutoRegisterExportedCollections.g.cs", expected));
}

[Test]
public async Task Reports_Diagnostic_When_Collection_Member_Is_Not_Instance_Readable()
{
Expand Down
Loading
Loading