diff --git a/src/SmartCode.App/PluginManager.cs b/src/SmartCode.App/PluginManager.cs index c0128a6..498911f 100644 --- a/src/SmartCode.App/PluginManager.cs +++ b/src/SmartCode.App/PluginManager.cs @@ -56,19 +56,23 @@ private IEnumerable ResolvePlugins() where TPlugin : IPlugin var plugins = _serviceProvider.GetServices(); foreach (var plugin in plugins) { - if (!plugin.Initialized) + lock (this) { - var pluginType = plugin.GetType(); - var names = pluginType.AssemblyQualifiedName.Split(','); - var typeName = names[0].Trim(); - var assName = names[1].Trim(); - var pluginConfig = _smartCodeOptions - .Plugins - .FirstOrDefault(m => m.ImplAssemblyName == assName && m.ImplTypeName == typeName); - plugin.Initialize(pluginConfig.Parameters); + if (!plugin.Initialized) + { + var pluginType = plugin.GetType(); + var names = pluginType.AssemblyQualifiedName.Split(','); + var typeName = names[0].Trim(); + var assName = names[1].Trim(); + var pluginConfig = _smartCodeOptions + .Plugins + .FirstOrDefault(m => m.ImplAssemblyName == assName && m.ImplTypeName == typeName); + plugin.Initialize(pluginConfig.Parameters); + } } } return plugins; + } } } diff --git a/src/SmartCode.CLI/Program.cs b/src/SmartCode.CLI/Program.cs index fa00641..e54f256 100644 --- a/src/SmartCode.CLI/Program.cs +++ b/src/SmartCode.CLI/Program.cs @@ -12,9 +12,11 @@ namespace SmartCode.CLI { class Program { - static async Task Main(string[] args) + static async Task Main(string[] args) { - await CommandLineApplication.ExecuteAsync(args); + ThreadPool.SetMinThreads(1000, 1000); + ThreadPool.SetMaxThreads(1000, 1000); + await CommandLineApplication.ExecuteAsync(args); } } } diff --git a/src/SmartCode.Generator/BuildTasks/TableBuildTask.cs b/src/SmartCode.Generator/BuildTasks/TableBuildTask.cs index 92ff6ed..42dc537 100644 --- a/src/SmartCode.Generator/BuildTasks/TableBuildTask.cs +++ b/src/SmartCode.Generator/BuildTasks/TableBuildTask.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using System.Linq; +using System.Threading; using System.Threading.Tasks; namespace SmartCode.Generator.BuildTasks diff --git a/src/SmartCode.Generator/GeneratorProjectBuilder.cs b/src/SmartCode.Generator/GeneratorProjectBuilder.cs index 7944eb3..d43ac21 100644 --- a/src/SmartCode.Generator/GeneratorProjectBuilder.cs +++ b/src/SmartCode.Generator/GeneratorProjectBuilder.cs @@ -1,3 +1,7 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Threading; using System.Threading.Tasks; using Microsoft.Extensions.Logging; using SmartCode.Configuration; @@ -20,28 +24,118 @@ Project project _logger = logger; } + CountdownEvent countdown = new CountdownEvent(1); + public async Task Build() { - BuildContext buildContext = null; var dataSource = _pluginManager.Resolve(_project.DataSource.Name); await dataSource.InitData(); + + if (_project.AllowParallel) + { + await this.ParallelBuild(dataSource); + } + else + { + await this.SerialBuild(dataSource); + } + } + + public async Task SerialBuild(IDataSource dataSource) + { foreach (var buildKV in _project.BuildTasks) { _logger.LogInformation($"-------- BuildTask:{buildKV.Key} Start! ---------"); - var output = buildKV.Value.Output; - buildContext = new BuildContext + var context = new BuildContext { PluginManager = _pluginManager, Project = _project, DataSource = dataSource, BuildKey = buildKV.Key, Build = buildKV.Value, - Output = output?.Copy() + Output = buildKV.Value.Output?.Copy(), }; - await _pluginManager.Resolve(buildKV.Value.Type).Build(buildContext); + + //ִ���������� + await _pluginManager.Resolve(context.Build.Type).Build(context); + _logger.LogInformation($"-------- BuildTask:{buildKV.Key} End! ---------"); } } + + private Task ParallelBuild(IDataSource dataSource) + { + + IList allContexts = _project.BuildTasks.Select(d => new BuildContext + { + PluginManager = _pluginManager, + Project = _project, + DataSource = dataSource, + BuildKey = d.Key, + Build = d.Value, + Output = d.Value.Output?.Copy(), + }).ToArray(); + foreach (var context in allContexts) + { + if (context.Build.DependOn != null && context.Build.DependOn.Count() > 0) + { + context.DependOn = allContexts.Where(d => context.Build.DependOn.Contains(d.BuildKey)).ToArray(); + } + } + countdown.Reset(); + countdown.AddCount(allContexts.Count); + foreach (var context in allContexts) + { + context.CountDown.Reset(); + if (context.DependOn != null && context.DependOn.Count > 0) + { + context.CountDown.AddCount(context.DependOn.Count); + } + + ThreadPool.QueueUserWorkItem((obj) => _ = this.BuildTask(obj), (context, allContexts)); + } + + foreach (var context in allContexts) + { + context.CountDown.Signal(); + } + + countdown.Signal(); + countdown.Wait(); + + return Task.CompletedTask; + } + + private async Task BuildTask(object obj) + { + var p = ((BuildContext context, IList allContexts))obj; + + if (p.context.DependOn != null && p.context.DependOn.Count > 0) + { + _logger.LogInformation($"-------- BuildTask:{p.context.BuildKey} Wait [{string.Join(",", p.context.DependOn?.Select(d => d.BuildKey)?.ToArray())}]---------"); + } + //�ȴ��������� + p.context.CountDown.Wait(); + + _logger.LogInformation($"-------- BuildTask:{p.context.BuildKey} Start! ---------"); + //ִ���������� + await _pluginManager.Resolve(p.context.Build.Type).Build(p.context); + + foreach (var c in p.allContexts) + { + if (c.DependOn == null || c.DependOn.Count == 0) + { + continue; + } + if (c.DependOn.Contains(p.context)) + { + c.CountDown.Signal(); + } + } + + countdown.Signal(); + _logger.LogInformation($"-------- BuildTask:{p.context.BuildKey} End! ---------"); + } } } \ No newline at end of file diff --git a/src/SmartCode/BuildContext.cs b/src/SmartCode/BuildContext.cs index 3abddaa..9746c0d 100644 --- a/src/SmartCode/BuildContext.cs +++ b/src/SmartCode/BuildContext.cs @@ -1,12 +1,15 @@ using System; using System.Collections.Generic; using System.Text; +using System.Threading; +using System.Threading.Tasks; using SmartCode.Configuration; namespace SmartCode { public class BuildContext { + public Project Project { get; set; } public IDataSource DataSource { get; set; } public IPluginManager PluginManager { get; set; } @@ -26,5 +29,9 @@ public void SetItem(string key, object item) { Items[key] = item; } + + public IList DependOn { get; set; } + //public Task BuildTask { get; set; } + public CountdownEvent CountDown { get; } = new CountdownEvent(1); } } diff --git a/src/SmartCode/Configuration/Build.cs b/src/SmartCode/Configuration/Build.cs index 72a75aa..f00f859 100644 --- a/src/SmartCode/Configuration/Build.cs +++ b/src/SmartCode/Configuration/Build.cs @@ -13,7 +13,7 @@ public class Build /// public String Type { get; set; } public String Module { get; set; } - public TemplateEngine TemplateEngine { get; set; } + public TemplateEngine TemplateEngine { get; set; } public Output Output { get; set; } public IEnumerable IncludeTables { get; set; } public IEnumerable IgnoreTables { get; set; } @@ -21,6 +21,10 @@ public class Build public bool? IgnoreView { get; set; } public NamingConverter NamingConverter { get; set; } /// + /// 依赖于 + /// + public IEnumerable DependOn { get; set; } + /// /// 自定义构建参数 /// public IDictionary Parameters { get; set; } diff --git a/src/SmartCode/Configuration/Project.cs b/src/SmartCode/Configuration/Project.cs index ed9d7d2..92deb0b 100644 --- a/src/SmartCode/Configuration/Project.cs +++ b/src/SmartCode/Configuration/Project.cs @@ -11,6 +11,7 @@ public class Project public String ConfigPath { get; set; } public String Module { get; set; } public String Author { get; set; } + public bool AllowParallel { get; set; } = false; public ProjectMode? Mode { get; set; } public DataSource DataSource { get; set; } public TemplateEngine TemplateEngine { get; set; } = TemplateEngine.Default;