08.02.2011, 19:07 | #1 |
Участник
|
Не срабатывает плагин
Добрый день!
Возникла такая ситуация: На событие create для salesorder зарегистрирован плагин счетчика (стандартный не подходит). Плагин корректно отрабатывает если заказ создается по умолчанию или из карточки клиента. Проблема возникает, когда создание заказа происходит из возможной сделки (ВС), плагин попросту не срабатывает и счетчик не увеличивает свое значение. Соответственно для заказа не устанавливается номер заказа При отладке через CRM Event Listener обнаружил что различия при создании обычным способом и из ВС есть, но они в значениях, которые нет возможности указать при регистрации плагина. Скорее всего они и влияют на то что в одной ситуации плагин срабатывает в а в другой нет. Обходной вариант сделал - подменил событие нажатия на кнопку создания заказа в ВС, заказ создался, плагин отработал, но продукты соответственно не добавились в заказ из ВС, так как был использован другой action(( (не подходит) Может кто-то уже решал подобную проблему? |
|
08.02.2011, 19:09 | #2 |
Чайный пьяница
|
Добрый день.
При создании salesorder из карточки opportunity, чтобы плагин запустился его необходимо зарегистрировать в child pipeline и всё получится.
__________________
Эмо разработчик, сначала пишу код, потом плачу над его несовершенством. Подписывайтесь на мой блог, twitter и YouTube канал. Пользуйтесь моим Ultimate Workflow Toolkit |
|
09.02.2011, 14:36 | #3 |
Участник
|
Цитата:
"Only SdkMessageProcessingStep in parent pipeline and in stages outside transaction can create CrmService to prevent deadlock. ". Дело в том что в плагине при входе в блок увеличения счетчика используется блокировка. Код: public class AutoNumber : IPlugin { private static object _sync = new object(); public void Execute(IPluginExecutionContext context) { ........... try{ lock (_sync) { // обработка } ........... } Параметры с которыми регистрирую: Message: Create PrimaryEntity: salesorder SecondaryEntity: none Запуск под пользователем, вызвавшим обработку плагина. ExecutionOrder: 1 Pre Stage (Пробовал и на Post, та же ошибка) Synhronous Server Child Pipeline Может некорректно зарегистрировал шаг? |
|
09.02.2011, 14:47 | #4 |
Участник
|
Заметил ещё такой момент, при регистрации шага с child pipeline сам счетчик увеличил свое значение, но по всем видимости не смог обновить заказ, так как он был заблокирован системой
|
|
09.02.2011, 14:55 | #5 |
Чайный пьяница
|
Покажите, пожалуйста, полный код плагина.
Что используете для работы с вебсервисом - ICrmService или CrmService? Если ICrmService, то необходимо ваш код переписать, чтобы он работал через CrmService.
__________________
Эмо разработчик, сначала пишу код, потом плачу над его несовершенством. Подписывайтесь на мой блог, twitter и YouTube канал. Пользуйтесь моим Ultimate Workflow Toolkit |
|
09.02.2011, 15:29 | #6 |
Участник
|
вот код:
Код: public void Execute(IPluginExecutionContext context) { DynamicEntity entity = null; if (context.InputParameters.Properties.Contains(ParameterName.Target) && context.InputParameters.Properties[ParameterName.Target] is DynamicEntity) { entity = (DynamicEntity)context.InputParameters.Properties[ParameterName.Target]; } else { return; } try { lock (_sync) { // simple query to get incremental settings for this entity using (ICrmService service = context.CreateCrmService(true)) { IncrementalNumbering setting = IncrementalNumbering.GetSettings(service, entity.Name); // system generated, if its assigned ignore this record if (setting != null && !entity.Properties.Contains(setting.PropertyName)) { int next = setting.CurrentPosition + 1; StringProperty increment = new StringProperty(setting.PropertyName,setting.Prefix.ToString()+ next.ToString()); entity.Properties.Add(increment); // keep track of the latest id inside the custom entity setting.Increment(service, next); } } } } catch (System.Web.Services.Protocols.SoapException ex) { ........ } } |
|
09.02.2011, 15:35 | #7 |
Чайный пьяница
|
Код: ICrmService service = context.CreateCrmService(true); Код: CrmAuthenticationToken token = new CrmAuthenticationToken(); token.AuthenticationType = AuthenticationType.AD; token.OrganizationName = context.OrganizationName; CrmService service = new CrmService(); service.UseDefaultCredentials = true; service.Url = (string)(Registry.LocalMachine.OpenSubKey("Software\\Microsoft\\MSCRM").GetValue("ServerUrl")) + "/2007/crmservice.asmx"; service.CrmAuthenticationTokenValue = token;
__________________
Эмо разработчик, сначала пишу код, потом плачу над его несовершенством. Подписывайтесь на мой блог, twitter и YouTube канал. Пользуйтесь моим Ultimate Workflow Toolkit |
|
10.02.2011, 10:00 | #8 |
Участник
|
Заменил код, ошибка исчезла, но при создании из возможной сделки при шаге зарегистрированном на child pipeline плагин счетчика все равно не срабатывает (увеличение не происходит и номер не присваивается)
|
|
10.02.2011, 12:57 | #9 |
Чайный пьяница
|
Код, покажите, пожалуйста. Только в этот раз полный (без троеточий, упущенных методов и т.п.).
__________________
Эмо разработчик, сначала пишу код, потом плачу над его несовершенством. Подписывайтесь на мой блог, twitter и YouTube канал. Пользуйтесь моим Ultimate Workflow Toolkit |
|
10.02.2011, 15:46 | #10 |
Участник
|
Код плагина:
Код: using System; using System.Collections.Generic; using Microsoft.Win32; using Microsoft.Crm.Sdk; using Microsoft.Crm.SdkTypeProxy; using Microsoft.Crm.SdkTypeProxy.Metadata; using Microsoft.Crm.Sdk.Query; namespace AKAutoNumber { public class AKAutoNumber : IPlugin { private string _secureInformation; private string _unsecureInformation; private static object _sync = new object(); public AKAutoNumber(string unsecureInfo, string secureInfo) { _secureInformation = secureInfo; _unsecureInformation = unsecureInfo; } // Related SDK topic: Writing a Plug-in public void Execute(IPluginExecutionContext context) { DynamicEntity entity = null; if (context.InputParameters.Properties.Contains(ParameterName.Target) && context.InputParameters.Properties[ParameterName.Target] is DynamicEntity) { entity = (DynamicEntity)context.InputParameters.Properties[ParameterName.Target]; } else { return; } try { lock (_sync) { // simple query to get incremental settings for this entity CrmAuthenticationToken token = new CrmAuthenticationToken(); token.AuthenticationType = AuthenticationType.AD; token.OrganizationName = context.OrganizationName; CrmService service = new CrmService(); service.UseDefaultCredentials = true; service.Url = (string)(Registry.LocalMachine.OpenSubKey("Software\\Microsoft\\MSCRM").GetValue("ServerUrl")) + "/2007/crmservice.asmx"; service.CrmAuthenticationTokenValue = token; IncrementalNumbering setting = IncrementalNumbering.GetSettings(service, entity.Name); if (setting != null && !entity.Properties.Contains(setting.PropertyName)) { int next = setting.CurrentPosition + 1; StringProperty increment = new StringProperty(setting.PropertyName,setting.Prefix.ToString()+ next.ToString()); entity.Properties.Add(increment); // keep track of the latest id inside the custom entity setting.Increment(service, next); } } } catch (System.Web.Services.Protocols.SoapException ex) { throw new InvalidPluginExecutionException( String.Format("An error occurred in the {0} plug-in.", this.GetType().ToString()), ex); } } } } Код: using System; using System.Collections.Generic; using System.Linq; using System.Text; using Microsoft.Crm.Sdk; using Microsoft.Crm.SdkTypeProxy; using Microsoft.Crm.Sdk.Query; namespace AKAutoNumber { public class IncrementalNumbering { public const string SchemaName = "do_universalnumber"; public class Fields { public const string Id = "do_universalnumberid"; public const string EntityName = "do_name"; public const string PropertyName = "do_attribute"; public const string CurrentPosition = "do_count"; public const string Prefix = "do_prefix"; } public Guid Id { get; set; } public string EntityName { get; set; } public string PropertyName { get; set; } public string Prefix { get; set; } public int CurrentPosition { get; set; } public IncrementalNumbering() { } public IncrementalNumbering(DynamicEntity entity) { this.Id = (entity.Properties[Fields.Id] as Key).Value; this.EntityName = entity.Properties[Fields.EntityName].ToString(); this.PropertyName = entity.Properties[Fields.PropertyName].ToString(); this.Prefix = entity.Properties[Fields.Prefix].ToString(); this.CurrentPosition = (entity.Properties[Fields.CurrentPosition] as CrmNumber).Value; } public void Increment(CrmService service, int next) { this.CurrentPosition = next; // set before calling ToDynamic TargetUpdateDynamic target = new TargetUpdateDynamic(); target.Entity = this.ToDynamic(); UpdateRequest request = new UpdateRequest(); request.Target = target; service.Execute(request); } // see if there are any increment settings for this entity public static IncrementalNumbering GetSettings(CrmService service, string entityName) { IncrementalNumbering setting = null; QueryExpression query = new QueryExpression(); query.EntityName = IncrementalNumbering.SchemaName; query.ColumnSet = new AllColumns(); query.Criteria = new FilterExpression(); query.Criteria.FilterOperator = LogicalOperator.And; ConditionExpression condition1 = new ConditionExpression(); condition1.AttributeName = IncrementalNumbering.Fields.EntityName; condition1.Operator = ConditionOperator.Equal; condition1.Values = new object[] { entityName }; query.Criteria.AddCondition(condition1); RetrieveMultipleRequest request = new RetrieveMultipleRequest(); request.Query = query; request.ReturnDynamicEntities = true; RetrieveMultipleResponse response = service.Execute(request) as RetrieveMultipleResponse; BusinessEntityCollection results = response.BusinessEntityCollection; if (results.BusinessEntities.Count > 0) // no error checkig to see if there are 2 incrementors set for the same entity { setting = new IncrementalNumbering(results.BusinessEntities[0] as DynamicEntity); } return setting; } // should include rest of the fields, but leave it for now public DynamicEntity ToDynamic() { DynamicEntity entity = new DynamicEntity(IncrementalNumbering.SchemaName); PropertyCollection properties = new PropertyCollection(); properties.Add(new KeyProperty(Fields.Id, new Key(this.Id))); properties.Add(new CrmNumberProperty(Fields.CurrentPosition, new CrmNumber(this.CurrentPosition))); entity.Properties = properties; return entity; } } } |
|
11.02.2011, 03:47 | #11 |
Чайный пьяница
|
На первый взгляд код - правильный, но есть какая то ошибочка. Проверил у себя точки входа в плагин - работает и для парен и для чайлд пайплайна. Так что совет вам - отладить плагин вооружившись Visual Studio...
__________________
Эмо разработчик, сначала пишу код, потом плачу над его несовершенством. Подписывайтесь на мой блог, twitter и YouTube канал. Пользуйтесь моим Ultimate Workflow Toolkit |
|
|
За это сообщение автора поблагодарили: Буденый (1). |
14.02.2011, 11:35 | #12 |
Участник
|
Спасибо a33ik,
проблема заключалась в том что обновлялось счетчиком поле "name". При создании из возможной сделки, это поле блокируется системой, соответственно при попытке обновления код автоматически переходит в конец ветки lock. Добавил свое поле, проблемы как и не было |
|
|
Похожие темы | ||||
Тема | Ответов | |||
Плагин на изменение подразделения пользователя | 6 | |||
не срабатывает плагин | 5 | |||
Плагин на создании Заказа | 4 | |||
Тип сущности, использующей плагин | 2 | |||
Как зарегить плагин на смену State? | 8 |
|