using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Sdk.Query;
namespace AutoNumber
{
public class AutoNumberPlugin : IPlugin
{
public void Execute(IServiceProvider serviceProvider)
{
System.Threading.Mutex mtx = null;
String debugText = "Inside
Execute \n";
try
{
Microsoft.Xrm.Sdk.IPluginExecutionContext context =
(Microsoft.Xrm.Sdk.IPluginExecutionContext)
serviceProvider.GetService(typeof(Microsoft.Xrm.Sdk.IPluginExecutionContext));
if (context.InputParameters.Contains("Target") &&
context.InputParameters["Target"]
is Entity)
{
Entity entity = (Entity)context.InputParameters["Target"];
debugText = debugText + "Inside if loop
- targe \n";
IOrganizationServiceFactory serviceFactory =
(IOrganizationServiceFactory)serviceProvider.GetService(typeof(IOrganizationServiceFactory));
IOrganizationService service =
serviceFactory.CreateOrganizationService(context.UserId);
string fetchXml = @"<fetch mapping='logical'>
<entity name='ssb_autonumber'><all-attributes/>
<filter type=""and"">
<condition
attribute=""ssb_entityname""
operator=""eq"" value='" + entity.LogicalName + "'"
+ "
/></filter></entity></fetch>";
string mutextName = string.Format("{0}{1}",
entity.LogicalName, "Autonumber");
mtx = new System.Threading.Mutex(false,
mutextName);
mtx.WaitOne();
//get hold on the mutex and only release it
after update was done ot the ssb_counter entity
// not
sure if this will work in a multi server environment
debugText = debugText + "Before
executing fetch \n";
EntityCollection result = service.RetrieveMultiple(new FetchExpression(fetchXml));
debugText = debugText + "After executing fetch \n";
string nextIncrementNumber = string.Empty;
if (result.Entities.Count == 1)
{
debugText = debugText +
"inside the if loop - enitities \n";
//retrieve the counter
Entity autoNumber =
result.Entities[0];
if (!autoNumber.Attributes.Contains("ssb_counter"))
throw new
InvalidPluginExecutionException("ssb_counter
must contain a value");
if (!autoNumber.Attributes.Contains("ssb_incrementunit"))
throw new
InvalidPluginExecutionException("ssb_incrementunit
must contain a value");
debugText = debugText +
"get values \n";
int counter = Int32.Parse(autoNumber.Attributes["ssb_counter"].ToString());
int incrementUnit = Int32.Parse(autoNumber.Attributes["ssb_incrementunit"].ToString());
string prefix = autoNumber.Attributes.Contains("ssb_prefix") ? autoNumber.Attributes["ssb_prefix"].ToString() : string.Empty;
string prefixSeparator = autoNumber.Attributes.Contains("ssb_prefixseparator") ?
autoNumber.Attributes["ssb_prefixseparator"].ToString()
: string.Empty;
string suffix = autoNumber.Attributes.Contains("ssb_suffix") ? autoNumber.Attributes["ssb_suffix"].ToString() : string.Empty;
string
suffixseparator = autoNumber.Attributes.Contains("ssb_suffixseparator")
? autoNumber.Attributes["ssb_suffixseparator"].ToString()
: string.Empty;
string numberFormatter = autoNumber.Attributes.Contains("ssb_numberformatter") ?
autoNumber.Attributes["ssb_numberformatter"].ToString()
: string.Empty;
string fieldToUpdate;
if (autoNumber.Attributes.Contains("ssb_entityautonumberfield"))
fieldToUpdate = autoNumber.Attributes["ssb_entityautonumberfield"].ToString();
else
throw new
InvalidPluginExecutionException("ssb_entityautonumberfield
should not be emplty");
debugText = debugText + "before calling buld number \n";
nextIncrementNumber =
BuildAutoNumber(prefix, prefixSeparator,
suffix,
suffixseparator, counter, incrementUnit, numberFormatter);
debugText = debugText + "after calling build number \n" +
nextIncrementNumber;
//increment the autonumber entity
//and update it to record the counter
debugText = debugText +
"before calling update (autonumber)\n";
autoNumber.Attributes["ssb_counter"] = counter +
incrementUnit;
service.Update(autoNumber);
debugText = debugText +
"before calling update (entity) \n";
entity.Attributes.Add(fieldToUpdate, nextIncrementNumber);
//entity.Attributes[fieldToUpdate] = nextIncrementNumber;
// service.Update(entity);
}
}
}
catch (Exception
ex)
{
if (mtx != null)
{
mtx.ReleaseMutex();
mtx = null;
}
//
throw new InvalidPluginExecutionException("An error occured in Autonumber
plugin", ex);
throw new
InvalidPluginExecutionException("An error
occured in Autonumber plugin" + ex + "\n"
+ debugText);
}
finally
{
debugText = null;
if (mtx != null)
mtx.ReleaseMutex();
}
}
private string
BuildAutoNumber(string prefix, string prefixSeparator, string
suffix, string suffixSeparator, int counter, int
incrementUnit, string numberFormatter)
{
bool hasPrefix = false,
hasSuffix = false;
string returnNumber = string.Empty;
if (!string.IsNullOrEmpty(prefix))
{
hasPrefix = true;
}
if (!string.IsNullOrEmpty(suffix))
{
hasSuffix = true;
}
counter = counter + incrementUnit;
returnNumber = (hasPrefix ? prefix + prefixSeparator : "") + counter.ToString(numberFormatter)
+ (hasSuffix ? suffixSeparator + suffix : "");
return returnNumber;
}
}
}