Wednesday, March 7, 2012

Meta Data Web Service in CRM with Example in 4.0.


Metadata Web Service

This Web Service is the one that provides access to the entire CRM metadata.
A new feature with this version of Microsoft CRM, the metadata can now be used to create, update, or delete entities, as well as create or delete relationships within entities. You can also use it to add, delete, or modify attributes to an existing entity programmatically.
This Web Service can be very useful for ISVs to look up entities on a setup installer to see if the product was already installed or to check whether any conflict exists with the entities of the CRM system on which a customization would be deployed.

The URL for this Web Service reference is
http://<servername>:<portnumber>/MSCrmServices/2007/MetadataService.asmx

For example:
http://crm4:5555/MSCrmServices/2007/MetadataService.asmx

To add a Web Reference for this Web Service, go to Visual Studio 2005 and, using the new console application project you created, right-click the project name in the Solution Explorer and choose Add Web Reference from the menu. Enter the URL of the metadata Web Service, click GO, and then enter CrmSdk.Metadata as the Web Reference Name

Click Add Reference to finally add the Web Service reference to your project.
This Web Service exposes only one method, the Execute method.
Execute Method
This method accepts the following submethods:

CreateAttribute
CreateEntity
CreateManyToMany
CreateOneToMany
DeleteAttribute
DeleteEntity
DeleteOptionValue
DeleteStatusValue
DeleteRelationship
InsertOptionValue
InsertStatusValue
OrderOption
OrderStatus
RetrieveAllEntities
RetrieveAttribute
RetrieveEntity
RetrieveRelationship
RetrieveTimestamp
UpdateAttribute
UpdateEntity
UpdateOptionValue
UpdateStatusValue
UpdateRelationship

Each of these submethods has its own Request and Response classes.
To use the CreateAttribute method, for example, you must create an instance of CreateAttributeRequest, and the Execute method would return an instance of CreateAttributeResponse.
For example, you might use the following code to find out whether the custom entity new_MyNewCustomEntity already exists in a CRM implementation. As with the Main Data Web Service, you will generate a common method to retrieve the Metadata Web Service URL for the organization by using the Discovery Web Service. You will use this method throughout the samples related to the Metadata Web Service.

Example:
namespace MetadataWebService
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine(CheckEntity("ORGNAME","account"));
            Console.ReadKey();
        }
        private static bool CheckEntity(string organizationName, string entityName)
        {
            try
            {
                CrmSdk.Metadata.MetadataService myCrm = new CrmSdk.Metadata.MetadataService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.Metadata.CrmAuthenticationToken myToken = new CrmSdk.Metadata.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

                CrmSdk.Metadata.RetrieveEntityRequest myRequest = new CrmSdk.Metadata.RetrieveEntityRequest();
                myRequest.LogicalName = entityName.ToLower();
                CrmSdk.Metadata.RetrieveEntityResponse myResponse;
                myResponse = (CrmSdk.Metadata.RetrieveEntityResponse)myCrm.Execute(myRequest);
                return true;
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText + "  " + soapEx.ToString());
                return false;
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return false;
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "password";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }
    }
}

Above code check that account entity is exist or not.Now Lets see another Example.

private static bool CreateCustomEntity(string organizationName, string entityName)
{
   try
   {

       CrmSdk.Metadata.MetadataService myCrm = new CrmSdk.Metadata.MetadataService();
       myCrm.Url = GetCrmMetadataServiceForOrganization(organizationName);
       CrmSdk.Metadata.CrmAuthenticationToken myToken = new CrmSdk.Metadata.CrmAuthenticationToken();
       myToken.AuthenticationType = 0;
       myToken.OrganizationName = organizationName;
       myCrm.CrmAuthenticationTokenValue = myToken;
       myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

       // Creates new entity
       CrmSdk.Metadata.EntityMetadata myNewEntity = new CrmSdk.Metadata.EntityMetadata();
       myNewEntity.Description = CreateLabel(entityName);
       myNewEntity.DisplayCollectionName = CreateLabel(entityName);
       myNewEntity.DisplayName = CreateLabel(entityName);

       myNewEntity.IsAvailableOffline = new CrmSdk.Metadata.CrmBoolean();
       myNewEntity.IsAvailableOffline.Value = true;
       myNewEntity.DuplicateDetection = new CrmSdk.Metadata.CrmBoolean();
       myNewEntity.DuplicateDetection.Value = true;
       myNewEntity.SchemaName = entityName;
       myNewEntity.LogicalName = entityName;
       myNewEntity.OwnershipType = new CrmSdk.Metadata.CrmOwnershipTypes();
       myNewEntity.OwnershipType.Value = CrmSdk.Metadata.OwnershipTypes.UserOwned;

       // creates primary attribute
       CrmSdk.Metadata.StringAttributeMetadata myPrimaryAttr = new CrmSdk.Metadata.StringAttributeMetadata();
       myPrimaryAttr.DisplayName = CreateLabel("Name");
       myPrimaryAttr.Description = CreateLabel("this is the Name");
       myPrimaryAttr.AttributeType = new CrmSdk.Metadata.CrmAttributeType();
       myPrimaryAttr.AttributeType.Value = CrmSdk.Metadata.AttributeType.String;
       myPrimaryAttr.MaxLength = new CrmSdk.Metadata.CrmNumber();       myPrimaryAttr.MaxLength.Value = 100;
       myPrimaryAttr.SchemaName = "new_Name";
       myPrimaryAttr.Format = new CrmSdk.Metadata.CrmStringFormat();
       myPrimaryAttr.Format.Value = CrmSdk.Metadata.StringFormat.Text;
       myPrimaryAttr.RequiredLevel = new CrmSdk.Metadata.CrmAttributeRequiredLevel();
       myPrimaryAttr.RequiredLevel.Value = CrmSdk.Metadata.AttributeRequiredLevel.Required;
       myPrimaryAttr.DisplayMask = new CrmSdk.Metadata.CrmDisplayMasks();
       myPrimaryAttr.DisplayMask.Value = CrmSdk.Metadata.DisplayMasks.PrimaryName;
       myPrimaryAttr.LogicalName = "new_name";

       // prepare request
       CrmSdk.Metadata.CreateEntityRequest myRequest = new CrmSdk.Metadata.CreateEntityRequest();
       myRequest.Entity = myNewEntity;
       myRequest.HasActivities = true;
       myRequest.HasNotes = true;
       myRequest.PrimaryAttribute = myPrimaryAttr;

       CrmSdk.Metadata.CreateEntityResponse myResponse;
       myResponse = (CrmSdk.Metadata.CreateEntityResponse)myCrm.Execute(myRequest);
       return true;
   }
   catch (System.Web.Services.Protocols.SoapException soapEx)
   {
       Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText + "  " + soapEx.ToString());
       return false;
   }
   catch (Exception ex)
   {
       Console.WriteLine("General exception: " + ex.ToString());
       return false;
   }
}

                                        

Note

The code uses a custom method called CreateLabel to simplify the code used to set up the labels; they must be managed in a collection because of the Multilanguage feature. This sample uses only the English language for the strings, but you can easily customize it to use other languages.

private static CrmSdk.Metadata.CrmLabel CreateLabel(string myString)
{
   CrmSdk.Metadata.CrmLabel myLabel = new CrmSdk.Metadata.CrmLabel();
   CrmSdk.Metadata.LocLabel[] myLabels = new CrmSdk.Metadata.LocLabel[1];
   myLabels[0] = new CrmSdk.Metadata.LocLabel();
   myLabels[0].Label = myString;
   myLabels[0].LanguageCode = new CrmSdk.Metadata.CrmNumber();
   myLabels[0].LanguageCode.Value = 1033; // English code
   myLabel.LocLabels = myLabels;
   return myLabel;
}

Now if you want to create a new entity with the name of new_MyNewCustomEntity on the organization with the name Webfortis, you could use the following code:
static void Main(string[] args)
{
        CreateCustomEntity("Webfortis", "new_MyNewCustomEntity");

        Console.ReadKey();
}

Note

Be sure the entity name doesn't already exist in the CRM system, or the Execute method will raise an exception. To be sure, you could use the CheckEntity method you created before and use a code as follows:
static void Main(string[] args)
{
   if (!CheckEntity("Webfortis", "new_MyNewCustomEntity"))
         {
             CreateCustomEntity("Webfortis", "new_MyNewCustomEntity");
         }
    Console.ReadKey();
}

In addition, you must set at least the primary attribute on the request, and this one must be required.

You can also use this Web Service if you want to show all the options from a Picklist attribute on another application.
As another example, imagine that you needed to retrieve all possible values for the Shipping Method property for Accounts. Because the Shipping Method is a Picklist, you would have to query the MetaData to get the values.
This method can be used as follows:
Code View:
private static void GetShippingMethod(string organizationName)
{
    CrmSdk.Metadata.MetadataService myCrm = new CrmSdk.Metadata.MetadataService();
    myCrm.Url = GetCrmMetadataServiceForOrganization(organizationName);
    CrmSdk.Metadata.CrmAuthenticationToken myToken = new CrmSdk.Metadata.CrmAuthenticationToken();
    myToken.AuthenticationType = 0;
    myToken.OrganizationName = organizationName;
    myCrm.CrmAuthenticationTokenValue = myToken;
    myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

    CrmSdk.Metadata.RetrieveAttributeRequest myRequest = new CrmSdk.Metadata.RetrieveAttributeRequest();
    myRequest.EntityLogicalName = CrmSdk.EntityName.account.ToString();
    myRequest.LogicalName = "address1_shippingmethodcode";

    CrmSdk.Metadata.RetrieveAttributeResponse myResponse;
    myResponse = (CrmSdk.Metadata.RetrieveAttributeResponse)
    myCrm.Execute(myRequest);
    foreach (CrmSdk.Metadata.Option myOption in ((CrmSdk.Metadata.PicklistAttributeMetadata)(myResponse.AttributeMetadata)).Options)
    {
        Console.WriteLine(myOption.Label.LocLabels[0].Label);
    }
}

Now if you want to test this method on the organization with the name Webfortis, you could use the following code:
static void Main(string[] args)
{
        GetShippingMethod("Webfortis");
        Console.ReadKey();
}

Tuesday, March 6, 2012

Main Data Web Service in CRM 4.0.


Main Data Service

The other Web Service reference that is necessary for a custom application is the Main Data Web Service:
http://<servername>:<portnumber>/MSCRMServices/2007/CrmServiceWsdl.aspx

For example:
http://crm4:5555/MSCRMServices/2007/CrmServiceWsdl.aspx

To add a Web Reference for this Web Service, Follow same Procedure as Discuss above. Then enter CrmSdk as the Web Reference Name.
Click Add Reference to add the Web Service reference to your project.

This Web Service has the following methods:

Create
Retrieve
RetrieveMultiple
Delete
Execute
Fetch
Update

Create Method

This method is used to create new instances of an existing entity, such as a new Account or Contact.
This method has only one implementation: It returns a Global Unique Identifier (GUID), which is the unique identifier of the new entity record to be created; it accepts one parameter of type BusinessEntity. Because all entities in CRM inherit from the BusinessEntity base class, you can pass any entity class to this input parameter.
This is an example of how to create a new Account record programmatically in Visual Studio 2005 with C#:
Code View:

namespace ConsoleWebService
{
    class MainDataService
    {
        static void Main(string[] args)
        {
            Console.WriteLine("New Account GUID="+CreateAccount("ORGNAME","New Account"));
            Console.ReadKey();
        }

        private static string CreateAccount(string organizationName, string accountName)
        {
            try
            {
            
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;
              
              
                CrmSdk.account newAccount = new CrmSdk.account();
              
                newAccount.name = accountName;
                newAccount.address1_country = "India";
                newAccount.address1_city = "Mumbai";

                CrmSdk.Lookup objLookup=new CrmSdk.Lookup();
                objLookup.type= "account";
                objLookup.Value= new Guid("A8A58DB6-5364-E111-9493-00E04C39161E");
            
                newAccount.parentaccountid = objLookup;
                CrmSdk.Lookup objLookup1 = new CrmSdk.Lookup();
                objLookup1.type = "contact";
                objLookup1.Value = new Guid("1EDE79DD-FC5D-E111-9493-00E04C39161E");

                newAccount.primarycontactid = objLookup1;
                CrmSdk.Picklist pl = new CrmSdk.Picklist();
                pl.name = "address1_addresstypecode";
                pl.Value = 1;
                newAccount.address1_addresstypecode = pl;

            
              
                Guid newAccountId = myCrm.Create(newAccount);
                return newAccountId.ToString();
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText + " " + soapEx.ToString());
                return soapEx.Detail.InnerText + "  " + soapEx.ToString();
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return "General exception: " + ex.ToString();
            }

        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "domainname";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "password";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }

    }
}


 Retrieve Method

This method gets an instance of an entity object. To get more than one instance of an entity, use the RetrieveMultiple method (explained in the next section).
This method returns a class type of BusinessEntity, so it is necessary to cast the returned value to the entity you want to retrieve.
The input parameters are the string of the entity name, the GUID of the instance of the entity, and a set of columns or fields you want to retrieve.
It is important to define the columns you want to retrieve in the last parameter, or you will get null values even though the instance in the CRM system has values.
This is an example of the Retrieve method and Using that I am Retriving the Information of one Account:

Code View:

namespace ConsoleWebService
{
    public class Retrive
    {
        static void Main(string[] args)
        {
            string newAccountId = "A003B5FA-7F67-E111-9493-00E04C39161E";
            Console.WriteLine("Account GUID = " + newAccountId);
            CrmSdk.account acc = new CrmSdk.account();
            acc=RetrieveAccount("ORGNAME", new Guid(newAccountId));
            Console.WriteLine("Name="+acc.name);
            Console.WriteLine("City="+acc.address1_city);
            Console.WriteLine("Country="+acc.address1_country);
        
            Console.ReadKey(); //added for debugging purposes only

        }
      
        private static CrmSdk.account RetrieveAccount(string organizationName, Guid accountId)
        {
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;
                CrmSdk.ColumnSet columns = new CrmSdk.ColumnSet();
                // add more attributes if you want separated by coma below
                columns.Attributes = new string[] { "name", "accountid", "address1_city", "address1_country" };
                Guid myAccountId = accountId;
                CrmSdk.account myAccount =
                (CrmSdk.account)myCrm.Retrieve(CrmSdk.EntityName.account.ToString(),
                                               myAccountId, columns);
                return myAccount;
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                                  + "  " + soapEx.ToString());
                return null;
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return null;
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "gtl12@";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }
    }
}

RetrieveMultiple Method

This method gets one or more than one instance of an entity.
For example, you can use this method to retrieve all the Accounts for an organization, as illustrated here:

namespace ConsoleWebService
{
    class GetAllAccount
    {
        static void Main(string[] args)
        {
            GetAllAccounts("ORGNAME");
            Console.ReadKey(); //added for debugging purposes only
        }
        private static void GetAllAccounts(string organizationName)
        {
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

                // Creates a column set holding the names of the columns to be retreived
                CrmSdk.ColumnSet colsPrincipal = new CrmSdk.ColumnSet();
                // Sets the Column Set's Properties
                colsPrincipal.Attributes = new string[] { "accountid", "name" };

                // Create the Query Expression
                CrmSdk.QueryExpression queryPrincipal = new CrmSdk.QueryExpression();

                // Set the QueryExpression's Properties
                queryPrincipal.EntityName = CrmSdk.EntityName.account.ToString();
                queryPrincipal.ColumnSet = colsPrincipal;

                /// Retrieve the accounts.
                CrmSdk.BusinessEntityCollection myAccounts = myCrm.RetrieveMultiple(
                                                            queryPrincipal);
                Console.WriteLine("\nGetAllAccounts found {0} accounts\n", myAccounts.BusinessEntities.Length);
                foreach (CrmSdk.BusinessEntity myEntity in myAccounts.BusinessEntities)
                {
                    CrmSdk.account myAccount = (CrmSdk.account)myEntity;
                    Console.WriteLine(myAccount.name);
                }
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText + "  " + soapEx.ToString());
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "password";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }
    }
}

Now Lets Take another Example For example, to retrieve all the Accounts whose names match or start with a selected first letter, use this code:


namespace ConsoleWebService
{
    class MatchAccount
    {
        static void Main(string[] args)
        {
            List<CrmSdk.account> accounts;
            Console.WriteLine("Accounts that starts with the letter N");
            accounts = GetAllAccountsByName("ORGNAME", "N%",
                ConsoleWebService.CrmSdk.ConditionOperator.Like);
            if (accounts == null)
            {
                Console.WriteLine("No accounts found");
            }

            Console.WriteLine("Accounts equal to 'Test Account'");
            accounts = GetAllAccountsByName("ORGNAME", "Test Account",
            ConsoleWebService.CrmSdk.ConditionOperator.Equal);
            if (accounts == null)
            {
                Console.WriteLine("No accounts found");
            }
            Console.ReadKey(); //added for debugging purposes only
        }
        private static List<CrmSdk.account> GetAllAccountsByName(string organizationName,
        string accountName, CrmSdk.ConditionOperator conditionalOperator)
        {
            List<CrmSdk.account> accounts = null;
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

                // Creates a column set holding the names of the columns to be retreived
                CrmSdk.ColumnSet colsPrincipal = new CrmSdk.ColumnSet();
                // Sets the Column Set's Properties
                colsPrincipal.Attributes = new string[] { "accountid", "name" };

                // Create a ConditionExpression
                CrmSdk.ConditionExpression conditionPrincipal =
                                        new CrmSdk.ConditionExpression();

                // Sets the ConditionExpressions Properties so that the condition
                // is true when the ownerid of the account Equals the principalId
                conditionPrincipal.AttributeName = "name";
                conditionPrincipal.Operator = conditionalOperator;
                conditionPrincipal.Values = new object[1];
                conditionPrincipal.Values[0] = accountName;

                // Create the FilterExpression
                CrmSdk.FilterExpression filterPrincipal = new CrmSdk.FilterExpression();

                // Set the FilterExpression's Properties
                filterPrincipal.FilterOperator = CrmSdk.LogicalOperator.And;
                filterPrincipal.Conditions = new CrmSdk.ConditionExpression[] { conditionPrincipal };

                // Create the Query Expression
                CrmSdk.QueryExpression queryPrincipal = new CrmSdk.QueryExpression();

                // Set the QueryExpression's Properties
                queryPrincipal.EntityName = CrmSdk.EntityName.account.ToString();
                queryPrincipal.ColumnSet = colsPrincipal;
                queryPrincipal.Criteria = filterPrincipal;

                /// Retrieve the accounts.
                CrmSdk.BusinessEntityCollection myAccounts = myCrm.RetrieveMultiple(queryPrincipal);
                accounts = new List<ConsoleWebService.CrmSdk.account>();
                Console.WriteLine("\nGetAllAccountsByName found {0} accounts\n", myAccounts.BusinessEntities.Length);
                foreach (CrmSdk.BusinessEntity myEntity in myAccounts.BusinessEntities)
                {
                    CrmSdk.account myAccount = (CrmSdk.account)myEntity;
                    accounts.Add(myAccount);
                    Console.WriteLine(myAccount.name);
                }
                return accounts;
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                                + "  " + soapEx.ToString());
                return null;
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return null;
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "gtl12@";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }

    }
}

Delete Method

This method deletes an existing instance of an entity. This method doesn't return any value and accepts two inputs parameters. The first parameter is a string containing the entity type (you can use the EntityName enumerator here), and the second parameter is the GUID of the instance of the entity you will delete.
This is an example of how to delete a new Account programmatically in Visual Studio 2005 with C#:

Code View:


namespace ConsoleWebService
{
    class Delete
    {
        static void Main(string[] args)
        {
            List<CrmSdk.account> accounts;
            Console.WriteLine("Accounts equal to 'test'");
            accounts = GetAllAccountsByName("ORGNAME", "test",
            ConsoleWebService.CrmSdk.ConditionOperator.Equal);
            if (accounts == null)
            {
                Console.WriteLine("No accounts found");
            }
            else
            {
                foreach (CrmSdk.account myAccount in accounts)
                {

                    Console.WriteLine(
                    DeleteAccount("ORGNAME", myAccount.accountid.Value));
                }
            }
            Console.ReadKey(); //added for debugging purposes only
        }
        private static List<CrmSdk.account> GetAllAccountsByName(string organizationName,
     string accountName, CrmSdk.ConditionOperator conditionalOperator)
        {
            List<CrmSdk.account> accounts = null;
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

                // Creates a column set holding the names of the columns to be retreived
                CrmSdk.ColumnSet colsPrincipal = new CrmSdk.ColumnSet();
                // Sets the Column Set's Properties
                colsPrincipal.Attributes = new string[] { "accountid", "name" };

                // Create a ConditionExpression
                CrmSdk.ConditionExpression conditionPrincipal =
                                        new CrmSdk.ConditionExpression();

                // Sets the ConditionExpressions Properties so that the condition
                // is true when the ownerid of the account Equals the principalId
                conditionPrincipal.AttributeName = "name";
                conditionPrincipal.Operator = conditionalOperator;
                conditionPrincipal.Values = new object[1];
                conditionPrincipal.Values[0] = accountName;

                // Create the FilterExpression
                CrmSdk.FilterExpression filterPrincipal = new CrmSdk.FilterExpression();

                // Set the FilterExpression's Properties
                filterPrincipal.FilterOperator = CrmSdk.LogicalOperator.And;
                filterPrincipal.Conditions = new CrmSdk.ConditionExpression[] { conditionPrincipal };

                // Create the Query Expression
                CrmSdk.QueryExpression queryPrincipal = new CrmSdk.QueryExpression();

                // Set the QueryExpression's Properties
                queryPrincipal.EntityName = CrmSdk.EntityName.account.ToString();
                queryPrincipal.ColumnSet = colsPrincipal;
                queryPrincipal.Criteria = filterPrincipal;

                /// Retrieve the accounts.
                CrmSdk.BusinessEntityCollection myAccounts = myCrm.RetrieveMultiple(queryPrincipal);
                accounts = new List<ConsoleWebService.CrmSdk.account>();
                Console.WriteLine("\nGetAllAccountsByName found {0} accounts\n", myAccounts.BusinessEntities.Length);
                foreach (CrmSdk.BusinessEntity myEntity in myAccounts.BusinessEntities)
                {
                    CrmSdk.account myAccount = (CrmSdk.account)myEntity;
                    accounts.Add(myAccount);
                    Console.WriteLine(myAccount.name);
                }
                return accounts;
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                                + "  " + soapEx.ToString());
                return null;
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return null;
            }
        }
      
      
        private static string DeleteAccount(string organizationName, Guid accountToDelete)
        {
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;
                myCrm.Delete(CrmSdk.EntityName.account.ToString(), accountToDelete);
                return "Account successfully deleted";
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                                + "  " + soapEx.ToString());
                return "SOAP exception: " + soapEx.Detail.InnerText
                                + "  " + soapEx.ToString();
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return "General exception: " + ex.ToString();
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "gtl12@";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }

    }

}


Execute Method

This method executes business logic.

It returns a Response object and accepts a parameter as the input of the Request type.
You can use this method as a wildcard for all the other methods. This means that you can create an Account by using this method because the class called CreateRequest derives from Request and can be used as the input parameter; you receive a CreateResponse as the result. The same happens for UpdateRequest, UpdateResponse, RetrieveRequest, and RetrieveResponse.


However, this method is usually used for things you can't do with the other methods. A good example is to use this method, close a CRM Case. Although the Case entity can be updated, you can't update the status by using the Update method. To close a Case, you need to use this method:

Code View:

private static bool CloseCase(string organizationName, Guid caseId)
{
   try
   {
       CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
       myCrm.Url = GetCrmServiceForOrganization(organizationName);
       CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
       myToken.AuthenticationType = 0;
       myToken.OrganizationName = organizationName;
       myCrm.CrmAuthenticationTokenValue = myToken;
       myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

       CrmSdk.incident myIncident = new CrmSdk.incident();
       myIncident.incidentid = new CrmSdk.Key();
       myIncident.incidentid.Value = caseId;

       CrmSdk.incidentresolution myIncidentResolution = new CrmSdk.incidentresolution();
       myIncidentResolution.incidentid = new CrmSdk.Lookup();
       myIncidentResolution.incidentid.type = CrmSdk.EntityName.incident.ToString();
       myIncidentResolution.incidentid.Value = myIncident.incidentid.Value;

       CrmSdk.CloseIncidentRequest closeIncident = new CrmSdk.CloseIncidentRequest();
       closeIncident.IncidentResolution = myIncidentResolution;
       closeIncident.Status = -1;
       myCrm.Execute(closeIncident);
       Console.WriteLine("Case successfully closed ");
       return true;
   }
   catch (System.Web.Services.Protocols.SoapException soapEx)
   {
       Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                         + "  " + soapEx.ToString());
       return false;
   }
   catch (Exception ex)
   {
       Console.WriteLine("General exception: " + ex.ToString());
        return false;
   }
}

                                        
Fetch Method

This method executes a query defined by the FetchXML language.
This method is similar to the RetrieveMultiple method, but it returns a string containing the XML representation of the entities result set.
A few points to remember about the Fetch method:
Fetch does not support a Union join. To view all the tasks for an account by checking all the contacts of a Contact, you need to perform separate Fetch methods—one on the contact tasks and the one on the account contacts—and then merge the results.
The result set of records depends on the user privilege that invokes the Web Service.
Performance is lower than when using Retrieve or RetrieveMultiple methods.
The following code example shows how to use this method to retrieve all contacts with all their properties:

Code View:

private static void GetAllContacts(string organizationName)
{
    try
    {
        CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
        myCrm.Url = GetCrmServiceForOrganization(organizationName);
        CrmSdk.CrmAuthenticationToken myToken = new
CrmSdk.CrmAuthenticationToken();
        myToken.AuthenticationType = 0;
        myToken.OrganizationName = organizationName;
        myCrm.CrmAuthenticationTokenValue = myToken;
        myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

        // Retrieve all Contacts.
        StringBuilder fetchStr = new StringBuilder();
        fetchStr.Append(@"<fetch mapping='logical'>");
        fetchStr.Append(@"<entity name='contact'><all-attributes/>");
        fetchStr.Append(@"</entity></fetch>");

        // Fetch the results.
        String resultXML = myCrm.Fetch(fetchStr.ToString());

        System.Xml.XmlDocument myXMLDoc = new System.Xml.XmlDocument();
        myXMLDoc.LoadXml(resultXML);
        System.Xml.XmlNodeList myNodeList = myXMLDoc.GetElementsByTagName ("fullname");
        Console.WriteLine("\nGetAllContacts found {0} contacts\n", myNodeList.Count);
        foreach (System.Xml.XmlNode myNode in myNodeList)
        {
            Console.WriteLine("Contact fullname = {0}", myNode.InnerText);
        }
    }
    catch (System.Web.Services.Protocols.SoapException soapEx)
    {
        Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                         + "  " + soapEx.ToString());
    }
    catch (Exception ex)
    {
        Console.WriteLine("General exception: " + ex.ToString());
    }
}



Update Method

This method updates data related to an instance of an entity.
This method has only one implementation and doesn't return a value. In the same way as the Create method, it accepts one parameter of type BusinessEntity. Because all the entities in CRM inherit from the BusinessEntity base class, you can pass any entity class to this input parameter. To use this method, you must set at least the ID property of the entity to be updated. For example, you would set the accountid property if you wanted to update an account.
This is an example of how to update an existing Account programmatically in Visual Studio 2005 with C#:

Code View

namespace ConsoleWebService
{
    class Update
    {
        static void Main(string[] args)
        {
            UpdateAccountName("GTLDEV", new Guid("B4C606E9-9067-E111-9493-00E04C39161E"), "test");
            Console.ReadKey(); //added for debugging purposes only
        }
        private static string UpdateAccountName(string organizationName, Guid accountId, string newName)
        {
            try
            {
                CrmSdk.CrmService myCrm = new CrmSdk.CrmService();
                myCrm.Url = GetCrmServiceForOrganization(organizationName);
                CrmSdk.CrmAuthenticationToken myToken = new CrmSdk.CrmAuthenticationToken();
                myToken.AuthenticationType = 0;
                myToken.OrganizationName = organizationName;
                myCrm.CrmAuthenticationTokenValue = myToken;
                myCrm.Credentials = System.Net.CredentialCache.DefaultCredentials;

                CrmSdk.account myAcoount = new CrmSdk.account();
                myAcoount.accountid = new CrmSdk.Key();
                myAcoount.accountid.Value = accountId;
                myAcoount.name = newName;
                myCrm.Update(myAcoount);
   Console.WriteLine("Account successfully updated");

                return "Account successfully updated ";
            }
            catch (System.Web.Services.Protocols.SoapException soapEx)
            {
                Console.WriteLine("SOAP exception: " + soapEx.Detail.InnerText
                               + "  " + soapEx.ToString());
                return "SOAP exception: " + soapEx.Detail.InnerText
                               + "  " + soapEx.ToString();
            }
            catch (Exception ex)
            {
                Console.WriteLine("General exception: " + ex.ToString());
                return "General exception: " + ex.ToString();
            }
        }
        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();

            //myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "kartik.patel";
            System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
            System.Net.CredentialCache.DefaultNetworkCredentials.Password = "gtl12@";
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();

            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute(myRequest);
            foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) == 0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;

        }

    }
}
Note that only the properties you set are updated. This means that, in the previous example, only the company name property will be changed and the other properties will keep their values. This happens even though they are not set and they have null values when sending them to the Update method.


Note
Remember to always replace ORGNAME with your organization name.

The Meta Data WebService will be Discuss in my Next Post.

Web Services in CRM 4.0.


-Web Services Fundamentals

Microsoft Dynamics CRM uses the Service Oriented Architecture (SOA) concept, which implements a series of Web Services to provide extensibility support.

Web Services are language- and platform-independent, so basically they can be consumed by an application written in Java, Visual Basic, or C#. They also can be used on a Microsoft Windows–based OS, as well as UNIX and Macintosh platforms.

The Microsoft CRM Web Services are divided and defined into three main groups:
Discovery Web Service
Main Data Web Service
Metadata Web Service

To easily see these Web Services' definitions and get the URL addresses of the Web Services Description Language (WSDL) documents within Microsoft CRM, follow these steps:

1. Go to Settings, Customizations.

2. Select the option Download Web Services Description Files (see Figure

As you can see in you can download the definitions for two main Web Services—the Main Data and the Metadata Web Services. The Discovery Web Service is not shown because it is not organization-dependent.
To understand how to use these Web Services, you need to create a new console application in C# to follow the examples of this chapter. To do so, open Visual Studio 2005 and go to File, New, Project. From the project types, go to Visual C#/Windows and select the Console Application on the right side where the templates are.If You are using 2010 then  you may need to use the compatibility feature to add a Web Reference (instead of a Service Reference):Right click on the project and choose "Add Service Reference"
1. Click on the "Advanced..." button
2. Click on the "Add Web Reference..." button
3. Paste your URL in the URL box, e.g., http://MyServer/_vti_bin/excelservice.asmx
4. Click on the "Add Reference" button

The Web Services definition files are explained next.


Discovery Web Service
As we explained previously, one of the new features of Microsoft CRM is the multitenancy capability, which is support for more than one organization on the same server. In previous versions, the Microsoft CRM product was limited to only one Organization per server.
Because of that, you need to query a general Web Service called CRMDiscoveryService that will give you the right Web Service for the organization you want to work with. You can find the query by navigating here:

Code View:
http://<servername>:<portnumber>/MSCRMServices/2007/AD/CrmDiscoveryService.asmx?WSDL

For example:

http://crm4:5555/MSCRMServices/2007/AD/CrmDiscoveryService.asmx?WSDL

To add a Web Reference for this Web Service go to Visual Studio 2005, and using the new console application project you created, right-click the project name in the Solution Explorer and choose Add Web Reference from the menu. Enter the URL of the discovery service, click GO, and then enter CrmSdk.Discovery as the Web Reference Name
Click Add Reference to finally add the Web Service reference to your project.
Note:If u are using vs 2010 Then u have Follow following step to Add web Reference.
you may need to use the compatibility feature to add a Web Reference (instead of a Service Reference):Right click on the project and choose "Add Service Reference"
5. Click on the "Advanced..." button
6. Click on the "Add Web Reference..." button
7. Paste your URL in the URL box, e.g., http://MyServer/_vti_bin/excelservice.asmx
Click on the "Add Reference" button

Note
Visual Studio must be run from a computer connected to the same domain and LAN as the CRM Server for all the samples in this chapter or you will be prompted to enter the Windows credentials when adding the Web Service reference.

By querying this Web Service, you can retrieve all the organizations that a specific user belongs to and get the right Web Service location. An example of this follows:

Code View:
namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine(GetCrmServiceForOrganization("ORGNAME"));
            Console.ReadKey();
        }

        private static string GetCrmServiceForOrganization(string organizationName)
        {
            string urlResult = "";
            CrmSdk.Discovery.CrmDiscoveryService myCrm = new CrmSdk.Discovery.CrmDiscoveryService();
            myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            CrmSdk.Discovery.RetrieveOrganizationsRequest myRequest = new CrmSdk.Discovery.RetrieveOrganizationsRequest();
            CrmSdk.Discovery.RetrieveOrganizationsResponse myResponse = (CrmSdk.Discovery.RetrieveOrganizationsResponse)myCrm.Execute (myRequest); foreach (CrmSdk.Discovery.OrganizationDetail tDetail in myResponse.OrganizationDetails)
            {
                Console.WriteLine("Organization = " + tDetail.OrganizationName);
                if (String.Compare(tDetail.OrganizationName, organizationName, true) ==0)
                {
                    return tDetail.CrmServiceUrl;
                }
            }
            return urlResult;
        }
    }
}

If your CRM Site is not Configured in your  local machine than you have to specify the UserName,Password and Domain Name.So you have to replace the Line
myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials; with below Four Lines.

 System.Net.CredentialCache.DefaultNetworkCredentials.UserName = "username";
 System.Net.CredentialCache.DefaultNetworkCredentials.Domain = "server";
 System.Net.CredentialCache.DefaultNetworkCredentials.Password = "password";
 myCrm.Credentials = System.Net.CredentialCache.DefaultNetworkCredentials;
            
Note

Remember to always replace ORGNAME with your organization name.
                        

This function illustrates how to get the correct Web Service address to use for the organization you want to work with.

Main Data Service and Meta Data Service will be Discuss in my Next Post.

Monday, March 5, 2012

Create a Plug Ins With Pre Method in 4.0.

Example: Change the quotenumber in the Pre-Stage for the Create of a Quote.

The quotenumber is a field that the CRM web service will not allow you to change after it is written to the database so you need to use the Pre-Stage and modify the context Entity before the end of the Execute method as shown below.


Create a Class Library and write as below


namespace CRMPlugIn
{
    public class PreClass:IPlugin
    {
        #region IPlugin Members
        public void Execute(IPluginExecutionContext context)
        {
            var entity = (DynamicEntity)context.InputParameters.Properties[ParameterName.Target];

            // . . . retrieve data to populate number . . .

            // Set value before it is written to the database

            if (entity.Properties.Contains("quotenumber"))
            {
                entity.Properties.Remove("quotenumber");
            }
            Random r = new Random();
            var prop = new StringProperty("quotenumber", "Q"+r.Next(1,1000));
            entity.Properties.Add(prop);
        }
        #endregion

    }
}

This example will create a Quote Number whatever Format You want.....

Plug Ins in CRM in 4.0.


A Plug-Ins is a .NET assembly that can be used to intercept events generated from the CRM system to perform a variety of actions. An example of event interception is an entity that will be created, updated, or deleted; an action can be virtually anything. Some common Plug-In uses might include these:
Performing a complicated update routine on CRM entities and/or attributes when it might be impractical to use JavaScript or Workflow
Grabbing data from another system and updating CRM when an entity instance is created or updated
Updating another system programmatically from CRM (such as an accounting system)

-Using Plug-Ins, you can fire a custom action or event on an Account, for example, either before or after it has been created, updated, or deleted. Additionally, other events can be handled from a Plug-In, such as Assign, Merge, and Handle.

When Is It Recommended to Use a Plug-In?
Use a Plug-In when you need to integrate Microsoft Dynamics CRM with another legacy system or when you want to extend or customize the original functionality or behaviors of Microsoft Dynamics CRM.

Modes
You can set up Plug-Ins in synchronous or asynchronous mode.
Synchronous mode starts the execution of the Plug-In when the event is fired and blocks the CRM application process until the executed method finishes. This option is not recommended if you perform a process that might take a long time to execute.

Asynchronous mode can't be combined with the Pre stage.

Stages
Plug-Ins can be set up in the Pre or Post stages:

The Pre stage sends control to the Plug-In before the real event is executed in the core system. As an example, you might attach a Plug-In to the Create event of the Account entity; your code would execute before the Account is actually created in the CRM system. With this method, you could prevent the Account or the entity record from being created, if desired.

The Post stage is executed after the real event has executed in the core system. So following the example just described, your code would be executed only after the Account record is created.

Plug-In Development
-To develop a Plug-In, you must download the Microsoft Dynamics CRM 4.0 SDK from the Microsoft website. The SDK can be found at http://www.microsoft.com/downloads/details.aspx?familyid=82E632A7-FAF9-41E0-8EC1-A2662AAE9DFB&displaylang=en or by searching for CRM 4.0 at SDK at http://msdn2.microsoft.com/en-us/default.aspx.

-Download the CRMSdk4.exe file, save it, and execute it to choose the folder where you want to decompress the files.

-To create a Plug-In, you must create a new Class Library project in Visual Studio 2005 by going to the File Menu, New, Project. Then select Visual C#/Windows in the project types on the left and Class Library on the right. Enter a name for the project and select the location and a Solution Name
(The Purpose of this is when we create the New account in CRM the  Description Field in Account Page is generated through our class Library code after Creating the New Account.)


Now Look at the Extracted Files where You set up  CRMSdk4.exe.In that Find Microsoft.Crm.Sdk.dll file to your project as well as add another reference to Microsoft.Crm.SdkTypeProxy.dll. These DLL files are located inside the SDK\Bin subfolder

After you create the project, you must add a reference to the Microsoft.Crm.Sdk.dll file to your project as well as add another reference to Microsoft.Crm.SdkTypeProxy.dll. These DLL files are located inside the SDK\Bin subfolder. To add these references follow these steps:

1. Go to the Solution Explorer and select the Solution name (the root node of the tree), right-click, and select the Add Reference menu option (see Figure).



2.Move to the Browse tab 

3.Locate the SDK\Bin directory on your local drive and select both Microsoft.Crm.Sdk.dll and Microsoft.Crm.SdkTypeProxy.dll files. (To select more than one file hold the Ctrl key.)

4.Click OK to add the references to your project. You see these files inside the References folder of your project in the Solution Explorer (see Figure )


As with any other interface, you must explicitly implement methods. In the case of the IPlugin interface, you must implement the Execute method, as shown in the following code:
namespace myPlugIn
{
  public class Class1 :IPlugin
  {
    #region IPlugin Members
    public void Execute(IPluginExecutionContext context)
    {
      throw new Exception("The method or operation is not implemented.");
    }
    #endregion
  }

}

The previous code implements the method but it only acts to throw an exception. We update the Account description field with the unique identifier value that is assigned when the Account is created to illustrate a more useful example.

To perform this sample, delete the line that is inside the Execute method:
throw new Exception("The method or operation is not implemented.");

and enter the following code instead:
        DynamicEntity entity =
(DynamicEntity)context.InputParameters.Properties["Target"];
        if (entity.Name == EntityName.account.ToString())
        {
            Guid id = (Guid)context.OutputParameters.Properties["Id"];
            Key myKey = new Key(id);

            if (!entity.Properties.Contains("accountid"))
            {
            entity.Properties["accountid"] = myKey;
            }
            if (!entity.Properties.Contains("description"))
            {
            entity.Properties["description"] = "GUID = " + id.ToString();
            ICrmService service = context.CreateCrmService(true);
            service.Update(entity);
            }
        }
- Now Debug the class Library and copy the dll of it and put it some Place.
   Now You have to Register the Plug In

- Download the Plugin Registration tool. (In that download    PluginRegistration.exe(http://archive.msdn.microsoft.com/crmplugin/Release/ProjectReleases.aspx?ReleaseId=2010) )

- Run this and Fill Server,Port,Domain,UserName and Try to connect  then it will ask for   password and   insert the password and then Press OK and then select organization and click on connect
   Now click on Register New Assembly.



-Click on Browse and Specify the Assembly(dll) and select database radio button and click on Register Selected Plugins.

-Now Locate the Plug-In you just registered in the Steps registered and You will see (Plugin) CRMPlugIn.Class1

-Expand the assembly and you will see the Plug Ins with its class Name.and select that PlugIns.  
Now Right Click On it and select Register New Step.

-The Dialog box will shown as below.

-Now Write Create in general Configuration Information Message.

-Write Account in Primary Entity and None to secondary Entity.and then you have to select Execution mode and Eventing Pipeline stage of Execution.and Press Register New Step.

-And Now Go to the CRM Site and create a Account and then Open Newly created Account check description Field You will see "Guid + some id(Guid) that generated "


Plug-In Debugging

There are two ways to debug your Plug-In. The first is attaching the debugger to the w3p.exe process, and the other is forcing the add-in to call the debugger. For either of these methods, it is recommended to try them on a testing environment as these methods use Visual Studio and will interrupt users jobs if attempted on a production environment.

Before trying any of these methods, you need to build your Plug-In with Debug mode and put the PDB (project data base) file generated by the compiler in the following directory (assuming you have the CRM server installed on C:\Program Files\Microsoft Dynamics CRM\):

C:\Program Files\Microsoft Dynamics CRM\Server\bin\assembly


Unfortunately, you must restart the IIS after copying the PDB file. This is something that can be done via the command prompt by running the following command at a command line prompt:

Iisreset


Note

You must copy the PDB file every time you rebuild the solution and restart the IIS.



Attaching the Debugger to the w3wp.exe Process
With this mode, you have to open your Plug-In solution in Visual Studio 2005 first and put in breakpoints where you want to stop and debug your code. To put a breakpoint, press F9 or go to the Debut menu and select the Toggle Breakpoint option

You must start the debugger by attaching the Visual Studio debugger to the w3wp.exe process. To do that, go to the Debug menu and select the Attach to Process option


When the Attach to Process dialog box appears, be sure to check the check boxes that say Show Processes from All Users and Show Processes in All Sessions. Locate the w3wp.exe process, and select it

Note

If you don't find the w3wp.exe process, it is probably because you must first open an Internet Explorer window and browse to your CRM organization URL, so the IIS will load the application pool represented by the w3wp.exe. You might also see more than one instance of this process depending on the application pools configured in the server. To be sure you select all the instances you find, hold the CTRL key before pressing the Attach button.

Press the Attach button to start debugging the Plug-In.

Assuming you registered a Plug-In with a step associated to the Account entity on the Create event (as our example did), when you go to the CRM web application and try to create a new Account, you will be automatically switched to the Visual Studio 2005 application after you click Save or Save and Close on the Account Form

When you finish the debugging, you can stop the debugger by going to the Debug menu and clicking either the Stop Debugging or Detach All menu options