Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
32bc314
commit b2515d9
Showing
259 changed files
with
67,273 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Original file line | Diff line number | Diff line change |
---|---|---|---|
@@ -0,0 +1,31 @@ | |||
|
|||
Microsoft Visual Studio Solution File, Format Version 12.00 | |||
# Visual Studio 15 | |||
VisualStudioVersion = 15.0.27004.2009 | |||
MinimumVisualStudioVersion = 10.0.40219.1 | |||
Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "Odx.Xrm.Core", "Validation.Plugin\Odx.Xrm.Core\Odx.Xrm.Core.shproj", "{39F24847-66D9-474D-AB0A-9035274E8DC6}" | |||
EndProject | |||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Validation.Plugin.CoreLib", "Validation.Plugin\Validation.Plugin.CoreLib\Validation.Plugin.CoreLib.csproj", "{B22FC16A-6C94-4C73-8E9A-13DB1A70EC6D}" | |||
EndProject | |||
Global | |||
GlobalSection(SharedMSBuildProjectFiles) = preSolution | |||
Validation.Plugin\Odx.Xrm.Core\Odx.Xrm.Core.projitems*{39f24847-66d9-474d-ab0a-9035274e8dc6}*SharedItemsImports = 13 | |||
Validation.Plugin\Odx.Xrm.Core\Odx.Xrm.Core.projitems*{b22fc16a-6c94-4c73-8e9a-13db1a70ec6d}*SharedItemsImports = 4 | |||
EndGlobalSection | |||
GlobalSection(SolutionConfigurationPlatforms) = preSolution | |||
Debug|Any CPU = Debug|Any CPU | |||
Release|Any CPU = Release|Any CPU | |||
EndGlobalSection | |||
GlobalSection(ProjectConfigurationPlatforms) = postSolution | |||
{B22FC16A-6C94-4C73-8E9A-13DB1A70EC6D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |||
{B22FC16A-6C94-4C73-8E9A-13DB1A70EC6D}.Debug|Any CPU.Build.0 = Debug|Any CPU | |||
{B22FC16A-6C94-4C73-8E9A-13DB1A70EC6D}.Release|Any CPU.ActiveCfg = Release|Any CPU | |||
{B22FC16A-6C94-4C73-8E9A-13DB1A70EC6D}.Release|Any CPU.Build.0 = Release|Any CPU | |||
EndGlobalSection | |||
GlobalSection(SolutionProperties) = preSolution | |||
HideSolutionNode = FALSE | |||
EndGlobalSection | |||
GlobalSection(ExtensibilityGlobals) = postSolution | |||
SolutionGuid = {EFD477E1-E57D-485C-84B4-E160BEF7E285} | |||
EndGlobalSection | |||
EndGlobal |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Original file line | Diff line number | Diff line change |
---|---|---|---|
@@ -0,0 +1,36 @@ | |||
using System.Activities; | |||
using Microsoft.Xrm.Sdk; | |||
using Microsoft.Xrm.Sdk.Workflow; | |||
using Odx.Xrm.Core.DataAccess; | |||
|
|||
namespace Odx.Xrm.Core | |||
{ | |||
public class ActivityHandlerBase<T> : TraceableObject | |||
where T : CodeActivity | |||
{ | |||
private CodeActivityContext activityContext; | |||
public T ActivityData { get; private set; } | |||
protected IWorkflowContext WorkflowContext { get; private set; } | |||
private void InitializeInternal(CodeActivityContext context, T activity) | |||
{ | |||
this.activityContext = context; | |||
this.ActivityData = activity; | |||
this.tracingService = context.GetExtension<ITracingService>(); | |||
} | |||
|
|||
public void Initialize(CodeActivityContext context, CodeActivity activity) | |||
{ | |||
this.InitializeInternal(context, (T)activity); | |||
} | |||
|
|||
protected V GetContextProperty<V>(InArgument<V> inValue) | |||
{ | |||
return inValue.Get<V>(this.activityContext); | |||
} | |||
|
|||
protected void SetContextProperty<V>(OutArgument<V> outValue, V value) | |||
{ | |||
outValue.Set(this.activityContext, value); | |||
} | |||
} | |||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Original file line | Diff line number | Diff line change |
---|---|---|---|
@@ -0,0 +1,33 @@ | |||
using System; | |||
using System.Activities; | |||
using Microsoft.Xrm.Sdk; | |||
using Microsoft.Xrm.Sdk.Workflow; | |||
using Odx.Xrm.Core.DataAccess; | |||
|
|||
namespace Odx.Xrm.Core | |||
{ | |||
public abstract class BaseCustomActivity : CodeActivity | |||
{ | |||
protected override void Execute(CodeActivityContext context) | |||
{ | |||
var handler = this.GetActivityHandler(); | |||
handler.Initialize(context, this); | |||
var repositoryFactory = this.GetRepositoryFactory(context); | |||
var workflowContext = this.GetWorkflowContext(context); | |||
handler.Execute(workflowContext, repositoryFactory); | |||
} | |||
|
|||
private IWorkflowContext GetWorkflowContext(CodeActivityContext context) | |||
{ | |||
return context.GetExtension<IWorkflowContext>(); | |||
} | |||
|
|||
private IRepositoryFactory GetRepositoryFactory(CodeActivityContext context) | |||
{ | |||
var factory = context.GetExtension<IOrganizationServiceFactory>(); | |||
return new RepositoryFactory(factory); | |||
} | |||
|
|||
protected abstract IActivityHandler GetActivityHandler(); | |||
} | |||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Original file line | Diff line number | Diff line change |
---|---|---|---|
@@ -0,0 +1,169 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using Microsoft.Xrm.Sdk; | |||
using Odx.Xrm.Core.DataAccess; | |||
|
|||
namespace Odx.Xrm.Core | |||
{ | |||
public abstract class BasePlugin : IPlugin | |||
{ | |||
private string unsecureConfig; | |||
private string secureConfig; | |||
private HashSet<string> availableMessages; | |||
private bool disableRegisterCheck; | |||
|
|||
private enum PipelineStage | |||
{ | |||
PreValidation = 10, | |||
PreOperation = 20, | |||
PostOperation = 40 | |||
} | |||
|
|||
protected string UnsecureConfig | |||
{ | |||
get | |||
{ | |||
return this.unsecureConfig; | |||
} | |||
} | |||
|
|||
protected string SecureConfig | |||
{ | |||
get | |||
{ | |||
return this.secureConfig; | |||
} | |||
} | |||
|
|||
/// <summary> | |||
/// Register all messages that this plugin is registered on using fluent RegisterMessage method Example: | |||
/// RegisterMessage<CreateRequest>().RegisterMessage<UpdateRequest>() | |||
/// </summary> | |||
protected abstract void RegisterAvailableMessages(); | |||
|
|||
private BasePlugin RegisterMessage<TMessage>(PipelineStage stage) | |||
where TMessage : OrganizationRequest, new() | |||
{ | |||
var temp = new TMessage(); | |||
return this.RegisterMessage(stage, temp.RequestName); | |||
} | |||
|
|||
public void DisableRegisterCheck() | |||
{ | |||
this.disableRegisterCheck = true; | |||
} | |||
|
|||
private BasePlugin RegisterMessage(PipelineStage stage, string messageName) | |||
{ | |||
this.availableMessages.Add(stage + messageName); | |||
return this; | |||
} | |||
|
|||
public BasePlugin RegisterMessagePost(string messageName) | |||
{ | |||
return this.RegisterMessage(PipelineStage.PostOperation, messageName); | |||
} | |||
|
|||
public BasePlugin RegisterMessagePost<TMessage>() | |||
where TMessage : OrganizationRequest, new() | |||
{ | |||
return this.RegisterMessage<TMessage>(PipelineStage.PostOperation); | |||
} | |||
|
|||
public BasePlugin RegisterMessagePre(string messageName) | |||
{ | |||
return this.RegisterMessage(PipelineStage.PreOperation, messageName); | |||
} | |||
|
|||
public BasePlugin RegisterMessagePre<TMessage>() | |||
where TMessage : OrganizationRequest, new() | |||
{ | |||
return this.RegisterMessage<TMessage>(PipelineStage.PreOperation); | |||
} | |||
|
|||
public BasePlugin RegisterMessagePreValidation<TMessage>() | |||
where TMessage : OrganizationRequest, new() | |||
{ | |||
return this.RegisterMessage<TMessage>(PipelineStage.PreValidation); | |||
} | |||
|
|||
public BasePlugin RegisterMessagePreValidation(string messageName) | |||
{ | |||
return this.RegisterMessage(PipelineStage.PreValidation, messageName); | |||
} | |||
|
|||
|
|||
public BasePlugin(string unsecureConfig, string secureConfig) | |||
{ | |||
this.availableMessages = new HashSet<string>(); | |||
this.unsecureConfig = unsecureConfig; | |||
this.secureConfig = secureConfig; | |||
} | |||
|
|||
public virtual void Execute(IServiceProvider serviceProvider) | |||
{ | |||
this.RegisterAvailableMessages(); | |||
var context = this.GetPluginExecutionContext(serviceProvider); | |||
if (!this.disableRegisterCheck) | |||
{ | |||
if (!availableMessages.Contains((PipelineStage)context.Stage + context.MessageName)) | |||
{ | |||
throw new InvalidPluginExecutionException($"Plugin registered on bad message. Contact your system administrator"); | |||
} | |||
} | |||
} | |||
|
|||
protected IPluginExecutionContext GetPluginExecutionContext(IServiceProvider serviceProvider) | |||
{ | |||
return (IPluginExecutionContext)serviceProvider.GetService(typeof(IPluginExecutionContext)); | |||
} | |||
} | |||
|
|||
public abstract class BasePlugin<T> : BasePlugin, IPlugin | |||
where T : HandlerBase, IHandler, new() | |||
{ | |||
|
|||
public BasePlugin(string unsecureConfig, string secureConfig) : base(unsecureConfig, secureConfig) { } | |||
|
|||
public override void Execute(IServiceProvider serviceProvider) | |||
{ | |||
base.Execute(serviceProvider); | |||
|
|||
var localContext = this.GetLocalPluginContext(serviceProvider); | |||
var repositoryFactory = this.GetRepositoryFactory(serviceProvider); | |||
var tracingService = this.GetTracingService(serviceProvider); | |||
|
|||
var handler = new T(); | |||
handler.InitializeTracing(tracingService); | |||
handler.InitializeConfiguration(this.UnsecureConfig, this.SecureConfig); | |||
|
|||
try | |||
{ | |||
handler.Execute(localContext, repositoryFactory); | |||
} | |||
catch (Exception ex) | |||
{ | |||
handler.Trace(ex); | |||
handler.Trace($"Context: {localContext.Context.InputParameters.ToJSON()}"); | |||
throw; | |||
} | |||
} | |||
|
|||
private IRepositoryFactory GetRepositoryFactory(IServiceProvider serviceProvider) | |||
{ | |||
var factory = serviceProvider.GetService(typeof(IOrganizationServiceFactory)) as IOrganizationServiceFactory; | |||
return new RepositoryFactory(factory); | |||
} | |||
|
|||
private ILocalPluginExecutionContext GetLocalPluginContext(IServiceProvider serviceProvider) | |||
{ | |||
var context = this.GetPluginExecutionContext(serviceProvider); | |||
return new LocalPluginExecutionContext(context); | |||
} | |||
|
|||
private ITracingService GetTracingService(IServiceProvider serviceProvider) | |||
{ | |||
return (ITracingService)serviceProvider.GetService(typeof(ITracingService)); | |||
} | |||
} | |||
} |
Oops, something went wrong.