private async Task BuildModel(ProcessorModel model, AzureDevOpsEndpoint endpoint, bool warnOnMissing) { // Grab all the procs, then iterate over them looking for procs user has configured to be // sync'd. Then grab all Work Item Types for the given process and filter those by the ones user // wants to sync. Log.LogDebug($"Loading model for [{endpoint.Options.Name}]."); var rootFields = (await endpoint.GetApiDefinitionsAsync <WorkItemField>(queryForDetails: false)) .ToDictionary(x => x.ReferenceName, x => x); if (endpoint.Options.Name == Source.Options.Name) { SourceFields = rootFields; } else { TargetFields = rootFields; } var procs = await endpoint.GetApiDefinitionsAsync <ProcessDefinition>(); foreach (var processFilter in _Options.Processes.Keys) { string mappedProcName = processFilter; if (model == TargetModel && _Options.ProcessMaps.ContainsKey(processFilter)) { mappedProcName = _Options.ProcessMaps[processFilter]; } var proc = procs.FirstOrDefault(p => processFilter == "*" || p.Name.Equals(mappedProcName, StringComparison.OrdinalIgnoreCase)); if (proc != null) { //if (!isMapped) mappedProcName = proc.Name; if (!model.ProcessDefinitions.ContainsKey(proc.Id)) { model.ProcessDefinitions.Add(mappedProcName, new ProcessDefinitionModel() { Process = proc, MappedFrom = processFilter, WorkItemTypes = new List <WorkItemTypeModel>() }); } model.ProcessDefinitions[mappedProcName].WorkItemBehaviors = (await endpoint.GetApiDefinitionsAsync <WorkItemBehavior>(new object[] { proc.Id })).ToList(); model.ProcessDefinitions[mappedProcName].WorkItemBehaviors.ForEach(b => { if (!model.WorkItemBehaviors.ContainsKey(b.Id)) { model.WorkItemBehaviors.Add(b.Id, b); } }); #region Build Work Item Types data ... var procWits = (await endpoint.GetApiDefinitionsAsync <WorkItemType>(new object[] { proc.Id }, singleDefinitionQueryString: "$expand=All")); procWits = procWits.Where(x => _Options.Processes[processFilter].Any(a => a == "*" || x.Name.Equals(a, StringComparison.OrdinalIgnoreCase))); if (procWits != null && procWits.Count() > 0) { foreach (var wit in procWits) { if (!model.WorkItemTypes.ContainsKey(wit.Id)) { model.WorkItemTypes.Add(wit.Id, new WorkItemTypeModel() { WorkItemType = wit }); model.ProcessDefinitions[mappedProcName].WorkItemTypes.Add(model.WorkItemTypes[wit.Id]); } else { model.WorkItemTypes[wit.Id] = new WorkItemTypeModel() { WorkItemType = wit }; } #region --- Loading Wit Type Details --- await Task.WhenAll( Task.Run(async() => await LoadLayout(model, model.WorkItemTypes[wit.Id], endpoint, proc.Id)), Task.Run(async() => { model.WorkItemTypes[wit.Id].Fields = (await endpoint.GetApiDefinitionsAsync <WorkItemTypeField>(new object[] { proc.Id, wit.Id }, singleDefinitionQueryString: "$expand=All")).ToList(); model.WorkItemTypes[wit.Id].Fields.ForEach(field => model.WorkItemFields.Add(field.Id, field)); }), Task.Run(async() => { model.WorkItemTypes[wit.Id].States = (await endpoint.GetApiDefinitionsAsync <WorkItemState>(new object[] { proc.Id, wit.Id })).ToList(); model.WorkItemTypes[wit.Id].States.ForEach(state => model.WorkItemStates.Add(state.Name, state)); }), Task.Run(async() => { model.WorkItemTypes[wit.Id].Rules = (await endpoint.GetApiDefinitionsAsync <WorkItemRule>(new object[] { proc.Id, wit.Id })).ToList(); model.WorkItemTypes[wit.Id].Rules.ForEach(rule => model.WorkItemRules.Add(rule.Id, rule)); }), Task.Run(async() => { model.WorkItemTypes[wit.Id].Behaviors = (await endpoint.GetApiDefinitionsAsync <WorkItemTypeBehavior>(new object[] { proc.Id, wit.Id })).ToList(); model.WorkItemTypes[wit.Id].Behaviors.ForEach(rule => { if (!model.WorkItemTypeBehaviors.ContainsKey(rule.Id)) { model.WorkItemTypeBehaviors.Add(rule.Id, rule); } }); }) ); #endregion } } #endregion } else if (warnOnMissing) { Log.LogWarning($"Unable to locate {processFilter} process in {endpoint.Options.Name} organization."); } } }