Skip to content

Commit

Permalink
update compile 优化对非公成员的脚本功能
Browse files Browse the repository at this point in the history
  • Loading branch information
NMSAzulX committed Jul 9, 2024
1 parent 725bc8d commit 58d8b30
Show file tree
Hide file tree
Showing 15 changed files with 227 additions and 7 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
using Microsoft.AspNetCore.Mvc;

namespace WebapiWIthController.Controllers
{
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
private static readonly string[] Summaries = new[]
{
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};

private readonly ILogger<WeatherForecastController> _logger;

public WeatherForecastController(ILogger<WeatherForecastController> logger)
{
_logger = logger;
}

[HttpGet(Name = "GetWeatherForecast")]
public IEnumerable<WeatherForecast> Get()
{
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateTime.Now.AddDays(index),
TemperatureC = Random.Shared.Next(-20, 55),
Summary = Summaries[Random.Shared.Next(Summaries.Length)]
})
.ToArray();
}
}
}
54 changes: 54 additions & 0 deletions samples/HE/NET6.0/WebapiWIthController/Program.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
using Microsoft.AspNetCore.Mvc.ModelBinding;
using Microsoft.AspNetCore.Mvc.ModelBinding.Metadata;

namespace WebapiWIthController
{
public class Program
{
public static void Main(string[] args)
{
NatashaManagement.RegistDomainCreator<NatashaDomainCreator>();

var builder = WebApplication.CreateBuilder(args);

// Add services to the container.

builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();

var app = builder.Build();


var action = @"
var modelMetadataProvider = arg1.Services.GetService<IModelMetadataProvider>();
var controllerActivatorProvider = arg1.Services.GetService<IControllerPropertyActivator>();
((DefaultModelMetadataProvider)modelMetadataProvider).ClearCache();
((DefaultControllerPropertyActivator)controllerActivatorProvider).ClearCache();
Console.WriteLine(1111);"
.WithSlimMethodBuilder()
.WithMetadata(typeof(Console))
.WithUsings("Microsoft.AspNetCore.Mvc.Controllers")
//.WithMetadata(typeof(IgnoresAccessChecksToAttribute))
.WithMetadata(typeof(IModelMetadataProvider))
.WithPrivateAccess(typeof(DefaultModelMetadataProvider))
.ToAction<WebApplication>()!;
action(app);

// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}

app.UseAuthorization();


app.MapControllers();

app.Run();
}
}
}
13 changes: 13 additions & 0 deletions samples/HE/NET6.0/WebapiWIthController/WeatherForecast.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
namespace WebapiWIthController
{
public class WeatherForecast
{
public DateTime Date { get; set; }

public int TemperatureC { get; set; }

public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);

public string? Summary { get; set; }
}
}
13 changes: 13 additions & 0 deletions samples/HE/NET6.0/WebapiWIthController/WebapiWIthController.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<Project Sdk="Microsoft.NET.Sdk.Web">

<PropertyGroup>
<TargetFramework>net6.0</TargetFramework>
<Nullable>enable</Nullable>
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
</ItemGroup>

</Project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
}
}
9 changes: 9 additions & 0 deletions samples/HE/NET6.0/WebapiWIthController/appsettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
},
"AllowedHosts": "*"
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text;

namespace Natasha.CSharp.Extension.MethodCreator
{
Expand Down Expand Up @@ -99,6 +97,7 @@ public T ToDelegate<T>(string modifier = "") where T : Delegate
var fullScript = $"{usingCode} public static class {className} {{ public static {(modifier ?? string.Empty)} {returnTypeScript} Invoke({parameterScript}){{ {Script} }} }}";
if (PrivateObjects!=null)
{
Builder.WithPrivateAccess();
Builder.Add(fullScript.ToAccessPrivateTree(PrivateObjects));
}
else
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
using Natasha.CSharp.Compiler.Component;
using Natasha.CSharp.Compiler.Utils;
using System;
using System.Collections.Generic;
using System.Collections.Immutable;
Expand Down Expand Up @@ -45,7 +46,7 @@ public AssemblyCSharpBuilder ConfigCompilerOption(Action<NatashaCSharpCompilerOp
/// 输出文件包含私有字段信息.
/// </summary>
/// <returns>链式对象(调用方法的实例本身).</returns>
public AssemblyCSharpBuilder WithPrivateMembers()
public AssemblyCSharpBuilder WithPrivateMembersOutput()
{
_includePrivateMembers = true;
return this;
Expand All @@ -57,7 +58,7 @@ public AssemblyCSharpBuilder WithPrivateMembers()
/// 注:选项状态会被缓存,复用时无需重复调用.
/// </remarks>
/// <returns>链式对象(调用方法的实例本身).</returns>
public AssemblyCSharpBuilder WithoutPrivateMembers()
public AssemblyCSharpBuilder WithoutPrivateMembersOutput()
{
_includePrivateMembers = false;
return this;
Expand Down Expand Up @@ -172,6 +173,11 @@ public AssemblyCSharpBuilder WithReleasePlusCompile()
public CSharpCompilation GetAvailableCompilation(Func<CSharpCompilationOptions, CSharpCompilationOptions>? initOptionsFunc = null)
{

if (_allowCompileWithPrivate)
{
NatashaAccessHelper.AccessHandle(this);
}

#if DEBUG
Stopwatch stopwatch = new();
stopwatch.Start();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
using Natasha.CSharp.Compiler.Utils;
using System;
using System.IO;
using System.Reflection;

/// <summary>
/// 程序集编译构建器-输出
Expand All @@ -20,7 +21,6 @@ public sealed partial class AssemblyCSharpBuilder
public static readonly string GlobalOutputFolder;
static AssemblyCSharpBuilder()
{

GlobalOutputFolder = Path.Combine(AppDomain.CurrentDomain.BaseDirectory!, "DynamicLibraryFolders");
if (!Directory.Exists(GlobalOutputFolder))
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Natasha.CSharp.Compiler.SemanticAnalaysis;
using Natasha.CSharp.Compiler.Utils;
using System;
using System.Runtime.CompilerServices;

Expand All @@ -11,6 +12,7 @@
[assembly: InternalsVisibleTo("Natasha.CSharp.UnitTest.Base, PublicKey=002400000480000094000000060200000024000052534131000400000100010069acb31dd0d9918441d6ed2b49cd67ae17d15fd6ded4ccd2f99b4a88df8cddacbf72d5897bb54f406b037688d99f482ff1c3088638b95364ef614f01c3f3f2a2a75889aa53286865463fb1803876056c8b98ec57f0b3cf2b1185de63d37041ba08f81ddba0dccf81efcdbdc912032e8d2b0efa21accc96206c386b574b9d9cb8")]
public sealed partial class AssemblyCSharpBuilder
{

private NatashaException? _exception;

public NatashaException? GetException()
Expand Down Expand Up @@ -42,6 +44,29 @@ public AssemblyCSharpBuilder(string assemblyName)
}

internal static bool HasInitialized;


private bool _allowCompileWithPrivate;

/// <summary>
/// 该方法允许编译单元导入私有成员并进行编译
/// </summary>
/// <returns></returns>
public AssemblyCSharpBuilder WithPrivateAccess()
{
_allowCompileWithPrivate = true;
return this;
}
/// <summary>
/// 该方法不允许编译私有成员
/// </summary>
/// <returns></returns>
public AssemblyCSharpBuilder WithoutPrivateAccess()
{
_allowCompileWithPrivate = false;
return this;
}

/// <summary>
/// 清空编译载体信息, 下次编译重组 Compilation .
/// </summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -199,9 +199,13 @@ public NatashaCSharpCompilerOptions WithCompilerFlag(CompilerBinderFlags flags)
/// <returns></returns>
public NatashaCSharpCompilerOptions AppendCompilerFlag(params CompilerBinderFlags[] flags)
{

for (int i = 0; i < flags.Length; i++)
{
_compileFlags |= flags[i];
if (!_compileFlags.HasFlag(flags[i]))
{
_compileFlags |= flags[i];
}
}
return this;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using Microsoft.CodeAnalysis.CSharp.Syntax;
using Natasha.CSharp.Compiler.Utils;
using System.Collections.Generic;
using System.Diagnostics;

public static class NatashaStringExtension
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

public static partial class NatashaManagement
{

public static NatashaInitializeHelper GetInitializer()
{
return new NatashaInitializeHelper();
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Reflection.Metadata;
using System.Text;

namespace Natasha.CSharp.Compiler.Utils
{
public static class NatashaAccessHelper
{
public readonly static Action<AssemblyCSharpBuilder> AccessHandle;

static NatashaAccessHelper()
{
var accessType = Assembly.GetEntryAssembly().GetType("System.Runtime.CompilerServices.IgnoresAccessChecksToAttribute", throwOnError: false);
if (accessType == null)
{
AssemblyCSharpBuilder builder = new();
builder.UseDefaultLoadContext();
builder.UseSimpleMode();
builder.ConfigLoadContext(opt => opt
.AddReferenceAndUsingCode(typeof(object))
.AddReferenceAndUsingCode(typeof(AssemblyName))
);

builder.Add(@"
namespace System.Runtime.CompilerServices
{
[AttributeUsage(AttributeTargets.Assembly, AllowMultiple = true)]
public class IgnoresAccessChecksToAttribute : Attribute
{
public IgnoresAccessChecksToAttribute(string assemblyName)
{
AssemblyName = assemblyName;
}
public string AssemblyName { get; }
}
}");
var assembly = builder.GetAssembly();
accessType = assembly.GetTypeFromShortName("IgnoresAccessChecksToAttribute");
}

AccessHandle = builder =>
builder
.ConfigCompilerOption(opt => opt
.WithAllMetadata()
.AppendCompilerFlag(CompilerBinderFlags.IgnoreAccessibility)
)
.ConfigLoadContext(ctx => ctx.AddReferenceAndUsingCode(accessType));

}
}
}

0 comments on commit 58d8b30

Please sign in to comment.