From 481c28206e22113682ae41f96f0818629525a2f2 Mon Sep 17 00:00:00 2001
From: Bradley Grainger <bgrainger@gmail.com>
Date: Fri, 24 Nov 2023 10:41:37 -0800
Subject: [PATCH] Fix trim warnings.

Add an app to test publishing with trimming.

Signed-off-by: Bradley Grainger <bgrainger@gmail.com>
---
 MySqlConnector.sln                            |  7 +++++++
 src/MySqlConnector/Core/DbTypeMapping.cs      | 10 ++++++++-
 src/MySqlConnector/Core/ResultSet.cs          |  4 ++++
 .../MySqlConnectionStringBuilder.cs           |  3 +++
 src/MySqlConnector/MySqlConnector.csproj      |  2 ++
 src/MySqlConnector/MySqlDataReader.cs         |  8 +++++++
 tools/TrimTestApp/Program.cs                  | 21 +++++++++++++++++++
 tools/TrimTestApp/TrimTestApp.csproj          | 17 +++++++++++++++
 8 files changed, 71 insertions(+), 1 deletion(-)
 create mode 100644 tools/TrimTestApp/Program.cs
 create mode 100644 tools/TrimTestApp/TrimTestApp.csproj

diff --git a/MySqlConnector.sln b/MySqlConnector.sln
index c3646c415..7042dbe98 100644
--- a/MySqlConnector.sln
+++ b/MySqlConnector.sln
@@ -28,6 +28,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MySqlConnector.DependencyIn
 EndProject
 Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MySqlConnector.DependencyInjection.Tests", "tests\MySqlConnector.DependencyInjection.Tests\MySqlConnector.DependencyInjection.Tests.csproj", "{E41AD8B7-2F67-444F-A8DC-51C3C8B1FD16}"
 EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TrimTestApp", "tools\TrimTestApp\TrimTestApp.csproj", "{51AD5CD4-88C6-4066-AEFD-09487C6D67E0}"
+EndProject
 Global
 	GlobalSection(SolutionConfigurationPlatforms) = preSolution
 		Debug|Any CPU = Debug|Any CPU
@@ -82,12 +84,17 @@ Global
 		{E41AD8B7-2F67-444F-A8DC-51C3C8B1FD16}.Debug|Any CPU.Build.0 = Debug|Any CPU
 		{E41AD8B7-2F67-444F-A8DC-51C3C8B1FD16}.Release|Any CPU.ActiveCfg = Release|Any CPU
 		{E41AD8B7-2F67-444F-A8DC-51C3C8B1FD16}.Release|Any CPU.Build.0 = Release|Any CPU
+		{51AD5CD4-88C6-4066-AEFD-09487C6D67E0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+		{51AD5CD4-88C6-4066-AEFD-09487C6D67E0}.Debug|Any CPU.Build.0 = Debug|Any CPU
+		{51AD5CD4-88C6-4066-AEFD-09487C6D67E0}.Release|Any CPU.ActiveCfg = Release|Any CPU
+		{51AD5CD4-88C6-4066-AEFD-09487C6D67E0}.Release|Any CPU.Build.0 = Release|Any CPU
 	EndGlobalSection
 	GlobalSection(SolutionProperties) = preSolution
 		HideSolutionNode = FALSE
 	EndGlobalSection
 	GlobalSection(NestedProjects) = preSolution
 		{2C8FA08E-755D-454D-B98E-10A122673ABE} = {D0EDA522-FB29-4C44-B4EC-0D3AF72C016D}
+		{51AD5CD4-88C6-4066-AEFD-09487C6D67E0} = {D0EDA522-FB29-4C44-B4EC-0D3AF72C016D}
 	EndGlobalSection
 	GlobalSection(ExtensibilityGlobals) = postSolution
 		SolutionGuid = {4784EA55-5DE0-404F-8BEC-E14C202F01FA}
diff --git a/src/MySqlConnector/Core/DbTypeMapping.cs b/src/MySqlConnector/Core/DbTypeMapping.cs
index f72611ee7..b1c3e1bd8 100644
--- a/src/MySqlConnector/Core/DbTypeMapping.cs
+++ b/src/MySqlConnector/Core/DbTypeMapping.cs
@@ -1,9 +1,17 @@
+using System.Diagnostics.CodeAnalysis;
 using System.Globalization;
 
 namespace MySqlConnector.Core;
 
-internal sealed class DbTypeMapping(Type clrType, DbType[] dbTypes, Func<object, object>? convert = null)
+internal sealed class DbTypeMapping(
+#if NET6_0_OR_GREATER
+	[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicProperties | DynamicallyAccessedMemberTypes.PublicFields)]
+#endif
+	Type clrType, DbType[] dbTypes, Func<object, object>? convert = null)
 {
+#if NET6_0_OR_GREATER
+	[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicProperties | DynamicallyAccessedMemberTypes.PublicFields)]
+#endif
 	public Type ClrType { get; } = clrType;
 	public DbType[] DbTypes { get; } = dbTypes;
 
diff --git a/src/MySqlConnector/Core/ResultSet.cs b/src/MySqlConnector/Core/ResultSet.cs
index c3704b826..a8ee4ad41 100644
--- a/src/MySqlConnector/Core/ResultSet.cs
+++ b/src/MySqlConnector/Core/ResultSet.cs
@@ -1,5 +1,6 @@
 using System.Buffers;
 using System.Diagnostics;
+using System.Diagnostics.CodeAnalysis;
 using System.Globalization;
 using System.Runtime.ExceptionServices;
 using MySqlConnector.Protocol;
@@ -304,6 +305,9 @@ public string GetDataTypeName(int ordinal)
 		return TypeMapper.Instance.GetColumnTypeMetadata(mySqlDbType).SimpleDataTypeName;
 	}
 
+#if NET6_0_OR_GREATER
+	[return: DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicProperties | DynamicallyAccessedMemberTypes.PublicFields)]
+#endif
 	public Type GetFieldType(int ordinal)
 	{
 		if (!HasResultSet)
diff --git a/src/MySqlConnector/MySqlConnectionStringBuilder.cs b/src/MySqlConnector/MySqlConnectionStringBuilder.cs
index b82352596..9f00d941d 100644
--- a/src/MySqlConnector/MySqlConnectionStringBuilder.cs
+++ b/src/MySqlConnector/MySqlConnectionStringBuilder.cs
@@ -871,6 +871,9 @@ internal string GetConnectionString(bool includePassword)
 	/// Fills in <paramref name="propertyDescriptors"/> with information about the available properties on this object.
 	/// </summary>
 	/// <param name="propertyDescriptors">The collection of <see cref="PropertyDescriptor"/> objects to populate.</param>
+#if NET6_0_OR_GREATER
+	[RequiresUnreferencedCode("Calls DbConnectionStringBuilder.GetProperties")]
+#endif
 	protected override void GetProperties(Hashtable propertyDescriptors)
 	{
 		base.GetProperties(propertyDescriptors);
diff --git a/src/MySqlConnector/MySqlConnector.csproj b/src/MySqlConnector/MySqlConnector.csproj
index 536f437c3..a7bf2e43d 100644
--- a/src/MySqlConnector/MySqlConnector.csproj
+++ b/src/MySqlConnector/MySqlConnector.csproj
@@ -13,6 +13,8 @@
     <Nullable>enable</Nullable>
     <CheckEolTargetFramework>false</CheckEolTargetFramework>
     <ImplicitUsings>enable</ImplicitUsings>
+    <IsTrimmable>true</IsTrimmable>
+    <IsAotCompatible>true</IsAotCompatible>
   </PropertyGroup>
 
   <ItemGroup>
diff --git a/src/MySqlConnector/MySqlDataReader.cs b/src/MySqlConnector/MySqlDataReader.cs
index 4bdc9c8ac..1995fa603 100644
--- a/src/MySqlConnector/MySqlDataReader.cs
+++ b/src/MySqlConnector/MySqlDataReader.cs
@@ -1,6 +1,7 @@
 using System.Collections;
 using System.Collections.ObjectModel;
 using System.Diagnostics;
+using System.Diagnostics.CodeAnalysis;
 using System.Globalization;
 using MySqlConnector.Core;
 using MySqlConnector.Logging;
@@ -245,7 +246,14 @@ public override long GetChars(int ordinal, long dataOffset, char[]? buffer, int
 
 	public override string GetDataTypeName(int ordinal) => GetResultSet().GetDataTypeName(ordinal);
 
+#if NET6_0_OR_GREATER
+	[return: DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicProperties | DynamicallyAccessedMemberTypes.PublicFields)]
+#endif
 	public Type GetFieldType(string name) => GetFieldType(GetOrdinal(name));
+
+#if NET6_0_OR_GREATER
+	[return: DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicProperties | DynamicallyAccessedMemberTypes.PublicFields)]
+#endif
 	public override Type GetFieldType(int ordinal) => GetResultSet().GetFieldType(ordinal);
 
 	public override object GetValue(int ordinal) => GetResultSet().GetCurrentRow().GetValue(ordinal);
diff --git a/tools/TrimTestApp/Program.cs b/tools/TrimTestApp/Program.cs
new file mode 100644
index 000000000..f5c2e9e1c
--- /dev/null
+++ b/tools/TrimTestApp/Program.cs
@@ -0,0 +1,21 @@
+using MySqlConnector;
+
+var connectionStringBuilder = new MySqlConnectionStringBuilder
+{
+	Server = "localhost",
+	UserID = "root",
+	Password = "pass",
+};
+
+await using var dataSource = new MySqlDataSourceBuilder(connectionStringBuilder.ConnectionString)
+	.UseName("test")
+	.Build();
+
+await using var connection = await dataSource.OpenConnectionAsync();
+await using var command = connection.CreateCommand();
+command.CommandText = "SELECT 1";
+await using var reader = await command.ExecuteReaderAsync();
+while (await reader.ReadAsync())
+{
+	Console.WriteLine(reader.GetValue(0));
+}
diff --git a/tools/TrimTestApp/TrimTestApp.csproj b/tools/TrimTestApp/TrimTestApp.csproj
new file mode 100644
index 000000000..f1aa76bbf
--- /dev/null
+++ b/tools/TrimTestApp/TrimTestApp.csproj
@@ -0,0 +1,17 @@
+﻿<Project Sdk="Microsoft.NET.Sdk">
+
+  <PropertyGroup>
+    <OutputType>Exe</OutputType>
+    <TargetFrameworks>net6.0;net7.0;net8.0</TargetFrameworks>
+    <ImplicitUsings>enable</ImplicitUsings>
+    <Nullable>enable</Nullable>
+    <PublishTrimmed>true</PublishTrimmed>
+    <NoWarn>$(NoWarn);IL2026;IL2111;IL2112</NoWarn>
+  </PropertyGroup>
+
+  <ItemGroup>
+    <ProjectReference Include="..\..\src\MySqlConnector\MySqlConnector.csproj" />
+    <TrimmerRootAssembly Include="MySqlConnector" />
+  </ItemGroup>
+
+</Project>
