背景
我在某种程度上简化了这种情况,但这是一般性问题。
我使用Azure数据工厂将自定义API中的数据提取到Azure数据仓库中的表中。我正在使用IDotNetActivity来运行调用API的C#代码并将数据加载到数据仓库中。该活动在Azure Batch中运行。
在活动本身中,在调用自定义API之前,我从Azure Blob存储中的文件加载人员列表。 然后,我为文件中的每个人调用自定义API。 这些调用是一个接一个地顺序进行的。 问题是这种方法需要太长时间。 文件大小可能会增加,所以花费的时间只会变得更糟。
我试图改善效果的事情
主要问题
Azure Batch是否支持async / await?
其他问题
有人可以解释为什么MoreLinq的Batch在Azure Batch中不起作用吗? 以下是受影响代码的片段:
List<int> personIds = GetPersonIds(clientAddress, clientUsername, clientPassword);
var customResults = new List<CustomApiResult>();
foreach (var personIdsBatch in personIds.Batch(100))
{
customResults.AddRange(GetCustomResultsByBatch(address, username, password, personIdsBatch));
}
答案 0 :(得分:1)
根据我的理解,personIds.Batch(100)
只需将personIds
批量放入大小(100)的桶中。
//method1
foreach (var personIdsBatch in personIds.Batch(100))
{
customResults.AddRange(GetCustomResultsByBatch(address, username, password, personIdsBatch));
}
//method2
customResults.AddRange(GetCustomResultsByBatch(address, username, password, personIds));
上述两种方法都会按顺序为每个人调用自定义API,而method1
则为处理同一任务添加了额外的逻辑。
Azure Batch是否支持async / await?
根据您的代码,我将IDotNetActivity
实现定义如下,您可以参考它:
public class MyDotNetActivity : IDotNetActivity
{
public IDictionary<string, string> Execute(IEnumerable<LinkedService> linkedServices, IEnumerable<Dataset> datasets, Activity activity, IActivityLogger logger)
{
return ExecuteAsync(linkedServices, datasets, activity, logger).Result;
}
async Task<IDictionary<string, string>> ExecuteAsync(IEnumerable<LinkedService> linkedServices, IEnumerable<Dataset> datasets, Activity activity, IActivityLogger logger)
{
List<int> personIds = await GetPersonIds("{clientAddress}", "{clientUsername}", "{clientPassword}");
var tasks = new List<Task<List<CustomApiResult>>>();
foreach (var personIdsBatch in personIds.Batch(100))
{
tasks.AddRange(GetCustomResultsByBatch("{address}", "{username}", "{password}", "{personIdsBatch}"));
}
var taskResults = await Task.WhenAll(tasks);
List<CustomApiResult> customResults = taskResults.SelectMany(r=>r).ToList();
//process the custom api results
return new Dictionary<string, string>();
}
async Task<List<CustomApiResult>> GetCustomResultsByBatch(string address, string username, string password, IEnumerable<int> personIdsBatch)
{
//Get Custom Results By Batch
return new List<CustomApiResult>();
}
async Task<List<int>> GetPersonIds(string clientAddress, string clientUsername, string clientPassword)
{
//load a list of people from a file in Azure Blob storage
return new List<int>();
}
}
另外,我假设您可以按如下方式利用Parallel.ForEach并行执行同步作业:
List<int> personIds = GetPersonIds(clientAddress, clientUsername, clientPassword);
var customResults = new List<CustomApiResult>();
Parallel.ForEach(personIds.Batch(100),
new ParallelOptions()
{
MaxDegreeOfParallelism=5
},
(personIdsBatch) =>
{
var results = GetCustomResultsByBatch(address, username, password, personIdsBatch);
lock (customResults)
{
customResults.AddRange(results);
}
});