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.");
                }
            }
        }