多个网站优化怎么做,可视化网站后台管理系统,大型php网站系统,泉州网站建设哪家好前言上次#xff0c;我们虽然用代码实现了“异步 Request-Reply 模式”#xff0c;但是需要为每一个长时间操作 API 实现一个对应的 AsyncXXX 操作。其实#xff0c;可以尝试用 Source Generators 减少这种重复性劳动。实现思路Controller 类必须是partial,这样才能为它额外… 前言上次我们虽然用代码实现了“异步 Request-Reply 模式”但是需要为每一个长时间操作 API 实现一个对应的 AsyncXXX 操作。其实可以尝试用 Source Generators 减少这种重复性劳动。实现思路Controller 类必须是partial,这样才能为它额外增加新方法为每个长时间操作 API 声明一个 AsyncMethodAttribute这样 Source Generators 才知道为谁实现对应的同步操作;遍历所有声明了 AsyncMethodAttribute 的方法为其编写实现方法。具体代码1.添加 AsyncMethodAttribute向待编译项目加入 AsyncMethodAttribute 代码const string asyncMethodAttributeText using System;namespace AsyncMethodGenerator
{public sealed class AsyncMethodAttribute : Attribute{public AsyncMethodAttribute(){}}
}
;context.AddSource(AsyncMethodAttribute, SourceText.From(asyncMethodAttributeText, Encoding.UTF8));2.遍历 AsyncMethodAttribute 声明方法找到声明了 AsyncMethodAttribute 的所有方法private string GenerateMethods(SyntaxListMemberDeclarationSyntax members)
{StringBuilder stringBuilder new StringBuilder();foreach (var member in members){if(member is MethodDeclarationSyntax method HasAsyncMethodAttribute(method)){stringBuilder.Append(GenerateAsyncMethod(method));}}return stringBuilder.ToString();
}private bool HasAsyncMethodAttribute(MethodDeclarationSyntax method)
{var hasAttribute false;foreach (var attributeList in method.AttributeLists){foreach (var attribute in attributeList.Attributes){if (attribute.Name.ToString().Equals(AsyncMethod)){hasAttribute true;}}}return hasAttribute;
}3.生成 AsyncMethod 代码根据原方法定义生成 AsyncMethod 方法private string GenerateAsyncMethod(MethodDeclarationSyntax method)
{var stringBuilder new StringBuilder();foreach (var attributeList in method.AttributeLists){foreach (var attribute in attributeList.Attributes){if (attribute.Name.ToString().Equals(Route)){stringBuilder.Append($[Route(async/{attribute.ArgumentList.Arguments[0].ToString().Trim()})]);}else{stringBuilder.Append($[{attribute}]);stringBuilder.Append(\r\n);}}}stringBuilder.Append($public async TaskIActionResult Async{method.Identifier} );stringBuilder.Append($({method.ParameterList.Parameters}));stringBuilder.Append(\r\n);stringBuilder.Append(${{string id Guid.NewGuid().ToString();string responseValue $/status/{{id}};_cache.SetString(id, responseValue);Task.Factory.StartNew(() {{var result {GenerateCallingMethod(method)}.Result;_cache.SetString(id _result, JsonConvert.SerializeObject(result));}});return Accepted(responseValue);}});return stringBuilder.ToString();
}4.使用现在就可以在目标项目中使用 AsyncMethod 方法了:[ApiController]
[Route([controller])]
public partial class WeatherForecastController : ControllerBase
{...[HttpGet][Route(get)][AsyncMethod]public async TaskIEnumerableWeatherForecast Get(){...}
}注意 WeatherForecastController 是 partial class结论有了 Source Generators可以让编译器帮我们自动实现“异步 Request-Reply 模式”了想了解更多内容请关注我的个人公众号”My IO“