Ошибка, когда 2 проверки работали вместе на форме
У меня есть кредитный лимит субъекта с тремя полями: кредитный рейтинг, кредитный лимит и конфигурация, конфигурация - это поле поиска, поле кредитного лимита - валюта, а кредитный рейтинг - опция (A, B, C). поэтому при обновлении он будет проверяться 2 раза, во-первых, кредитный рейтинг не может совпадать с кредитным рейтингом, который уже имеется в конфигурации поля
Пример: мой предварительный рейтинг кредитоспособности B, и моя конфигурация уже имеет лимит кредитования 2, который равен A и B, когда я обновляю кредитный рейтинг до A, это будет ошибкой, потому что у конфигурации не может быть 2 одинакового кредитного рейтинга.
и вторая проверка выполняется при обновлении поля кредитного лимита, поэтому текущий кредитный лимит не может превышать поле кредитного лимита для предварительного изображения, мое изображение кредитного изображения для предварительного изображения составляет 500 долларов, при попытке обновить до 550 долларов будут отображаться сообщения об ошибках.
Поэтому я создаю 2 плагина для проверки обоих условий, и для обоих этапов выполнения моего конвейера событий установлено значение PreOperation.
, вот проверка кредитного рейтинга
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Sdk.Query;
using System;
using System.Collections.Generic;
using TrainingConfiguration.Plugins.Model;
namespace TrainingConfiguration.Plugins
{
public class CreditRatingUpdateValidation : IPlugin
{
public void Execute(IServiceProvider serviceProvider)
{
IPluginExecutionContext context = (IPluginExecutionContext)serviceProvider.GetService(typeof(IPluginExecutionContext));
Entity entity = (Entity)context.InputParameters["Target"];
IOrganizationServiceFactory serviceFactory = (IOrganizationServiceFactory)serviceProvider.GetService(typeof(IOrganizationServiceFactory));
IOrganizationService service = (IOrganizationService)serviceFactory.CreateOrganizationService(context.UserId);
if (entity.LogicalName.Contains("ita_creditlimit"))
{
Entity preImage = (Entity)context.PreEntityImages["CreditImage"];
EntityReference configuration = (EntityReference)(preImage.Attributes["ita_configuration"]);
string configurationId = configuration.Id.ToString();
string fetchXml = @"<fetch version='1.0' output-format='xml-platform' mapping='logical' distinct='false'>
<entity name='ita_creditlimit'>
<attribute name='ita_creditlimitid' />
<attribute name='ita_name' />
<attribute name='ita_creditrating' />
<attribute name='ita_configuration' />
<order attribute='ita_name' descending='false' />
<filter type='and'>
<condition attribute='ita_configuration' operator='eq' value=""{0}"" />
</filter>
</entity>
</fetch>";
fetchXml = string.Format(fetchXml, configurationId);
var qe = new FetchExpression(fetchXml);
var result = service.RetrieveMultiple(qe);
var preRating = ((OptionSetValue)preImage.Attributes["ita_creditrating"]).Value;
var postRating = ((OptionSetValue)entity.Attributes["ita_creditrating"]).Value;
if (result.Entities.Count > 0)
{
List<String> listCreditRating = new List<string>();
for (int i = 0; i < result.Entities.Count; i++)
{
string creditRating = ((OptionSetValue)result.Entities[i].Attributes["ita_creditrating"]).Value.ToString();
listCreditRating.Add(creditRating);
}
if (postRating.ToString() != preRating.ToString())
{
bool alreadyExist = listCreditRating.Contains(postRating.ToString());
if (alreadyExist == true)
{
throw new InvalidPluginExecutionException("Can't have 2 same rating");
}
}
}
}
}
}
}
здесь для проверки кредитного лимита
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Sdk.Query;
using System;
using System.Collections.Generic;
using System.Linq;
using TrainingConfiguration.Plugins.Model;
namespace TrainingConfiguration.Plugins
{
public class CreditUpdateValidation : IPlugin
{
public void Execute(IServiceProvider serviceProvider)
{
IPluginExecutionContext context = (IPluginExecutionContext)serviceProvider.GetService(typeof(IPluginExecutionContext));
ITracingService tracingService = (ITracingService)serviceProvider.GetService(typeof(ITracingService));
IOrganizationServiceFactory serviceFactory =
(IOrganizationServiceFactory)serviceProvider.GetService(typeof(IOrganizationServiceFactory));
IOrganizationService service = serviceFactory.CreateOrganizationService(context.UserId);
Entity entity = (Entity)context.InputParameters["Target"];
if (entity.LogicalName.Equals("ita_creditlimit"))
{
decimal parseInt1 = 0;
decimal parseInt2 = 0;
Entity preImage = (Entity)context.PreEntityImages["CreditImage"];
if (context.PreEntityImages.Contains("CreditImage"))
{
Money preValue = (Money)preImage.Attributes["ita_creditlimit"];
parseInt1 = preValue.Value;
}
Money postValue = (Money)entity.Attributes["ita_creditlimit"];
parseInt2 = postValue.Value;
if (parseInt2 > parseInt1)
{
throw new InvalidPluginExecutionException("Can't Exceed the credit limit");
}
}
}
}
}
сначала оба плагина работают нормально. прежде чем я попытаюсь запустить его вместе, я не знаю, почему, когда я пытался запустить его вместе, у него будет странное исключение, иногда он скажет, что атрибут ita_rating key не найден или ita_creditlimit не найден, даже если я уже добавляю его на моем фильтрующем атрибуте при регистрации плагина я пытался решить эту проблему в течение дня, но я до сих пор не знаю, почему происходят эти странные поведения, потому что, когда я пытался отключить один из плагинов, другой плагин будет работать, может кто-нибудь дать некоторые просветление Что это за причина? Это из моего кода или что-то еще? и я уже пытался использовать попробовать и поймать, и вот исключение, которое я получил
System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary.
at System.Collections.Generic.Dictionary`2.get_Item(TKey key)
at TrainingConfiguration.Plugins.CreditUpdateValidation.Execute(IServiceProvider serviceProvider)
1 ответ
Я думаю, что я уже знаю, что здесь не так, так что либо Money postValue = (Money)entity.Attributes["ita_creditlimit"];
или же var value1 = (OptionSetValue)entity.Attributes["ita_creditrating"];
имеют атрибут только когда значение меняется. Пример, когда мой кредитный лимит составляет 500 долларов, и я просто оставляю его там, не обновляя свой кредитный лимит, то есть, когда появляется ошибка, поэтому я исправляю ее с помощью try and catch, когда ее ошибка, я буду использовать PreImage для моего кредитного лимита при вылове.