dem93
dem93

Reputation: 31

Save data using MSCRM Service

I am working on a project that intends to use crmservice in order to save data on existing database. The database is created by mscrm and I have to create an application that uses crmservice to store relevant information on db.

So far, I am receiving data from the viewModel and trying to save using crmservice.

method for saving below:

private void Initiate()
        {
            var serverConnect = new CrmConnector();
            CrmConnector.pubpassword = ConfigurationManager.AppSettings["crmpassword"].ToString();
            CrmConnector.pubuserName = ConfigurationManager.AppSettings["username"].ToString();
            CrmConnector.pubdomain = ConfigurationManager.AppSettings["domain"].ToString();
            CrmConnector.serveraddr = ConfigurationManager.AppSettings["server"].ToString();
            serverConfig = serverConnect.GetServerConfiguration();
        }

        public void SaveTimesheetLine(TimesheetViewModel timesheetLineVm)
        {
                string payrollId = Convert.ToString(Session["payroll"]);
                Initiate();
                using (_serviceProxy = CrmConnector.GetOrganizationProxy(serverConfig))
                {
                    // This statement is required to enable early-bound type support.
                    //_serviceProxy.EnableProxyTypes();
                    _service = (IOrganizationService) _serviceProxy;

                    var timesheetLineEntity = new Entity("new_timesheetlineitem");
                    timesheetLineEntity["new_billtoid"] = timesheetLineVm.TimesheetLineViewModels.BillToId;
                    timesheetLineEntity["new_timesheettimesheetlineitemid"] = timesheetLineVm.TimesheetId ;
                    timesheetLineEntity["new_slatimesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.SlaId;
                    timesheetLineEntity["new_billratetimesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.BillRateId;
                    timesheetLineEntity["new_stream3timesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.Stream3Id;
                    timesheetLineEntity["new_contracttypetimesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.ContractTypeId;
                    timesheetLineEntity["new_firstname"] = timesheetLineVm.TimesheetLineViewModels.EmployeeFirstName;
                    timesheetLineEntity["new_lastname"] = timesheetLineVm.TimesheetLineViewModels.EmployeeLastName;
                    timesheetLineEntity["new_accounttimesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.EmployerId;
                    timesheetLineEntity["new_payrollreference"] = payrollId;
                    timesheetLineEntity["new_timesheetdate"] = timesheetLineVm.TimesheetDate;
                    timesheetLineEntity["new_candidatetimesheetlineitemid"] = timesheetLineVm.TimesheetLineViewModels.CandidateId ;
                    // taken from user input 
                    timesheetLineEntity["new_startdatetime"] = timesheetLineVm.TimesheetLineViewModels.StartDate;
                    timesheetLineEntity["new_enddatetime"] = timesheetLineVm.TimesheetLineViewModels.EndDate;
                    timesheetLineEntity["new_paytypetimesheetlineitemidname"] = Convert.ToString(timesheetLineVm.TimesheetLineViewModels.PayType);
                    //timesheetLineEntity["new_lunchtime"] = 2;
                    timesheetLineEntity["new_submittedhours"] = timesheetLineVm.TimesheetLineViewModels.SubmittedHours;

                    _timesheetlineId = _service.Create(timesheetLineEntity);
                }
        }

The error I am receiving:

[FaultException`1: System.NullReferenceException: Microsoft Dynamics CRM has experienced an error. Reference number for administrators or support: #E28869A7]
System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg) +11080899
System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type) +336
Microsoft.Xrm.Sdk.IOrganizationService.Create(Entity entity) +0
Microsoft.Xrm.Sdk.Client.OrganizationServiceProxy.CreateCore(Entity entity) +425
Microsoft.Xrm.Sdk.Client.OrganizationServiceProxy.Create(Entity entity) +13

I have researched and not yet found any similar issue. Would anyone have gone through this before?

----------------- EDITED I think this approach should be done differently, so I done some small changes. Instead of trying to add a new timesheetLine (is related to timesheet - one timesheet can have 0 or more timesheetLines), I am trying to retrieve a timesheet and instantiate a list of timesheetines to id, then update.

Below updated code:

using (_serviceProxy = CrmConnector.GetOrganizationProxy(serverConfig))
                {
                    // This statement is required to enable early-bound type support.
                    _serviceProxy.EnableProxyTypes();
                    _service = (IOrganizationService) _serviceProxy;

                    var context = new CRMService(_serviceProxy);

                    var timesheetLineEntity = new New_timesheetlineitem()
                    {

                        // taken from user input 
                        New_startdatetime = timesheetLineVm.TimesheetLineViewModels.StartDate,
                        New_EndDateTime = timesheetLineVm.TimesheetLineViewModels.EndDate,
                        //new_paytypetimesheetlineitemid = Convert.ToString(timesheetLineVm.TimesheetLineViewModels.PayType),
                        //timesheetLineEntity["new_lunchtime"] = 2;
                        New_SubmittedHours = timesheetLineVm.TimesheetLineViewModels.SubmittedHours

                        //_timesheetlineId = _service.Create(timesheetLineEntity);
                    };


                    var timesheetLineItemList = new List<New_timesheetlineitem>();
                    timesheetLineItemList.Add(timesheetLineEntity);

                    var retrievedTimesheet = _serviceProxy.Retrieve("new_timesheet", new Guid(timesheetLineVm.TimesheetId.ToString()), new ColumnSet(new string[] {"new_firstname", "new_lastname", "new_name", "new_payrollreference", "new_timesheetdate", "new_timesheetid", "new_slatimesheetid", "new_stream3timesheetid", "new_candidatetimesheetid", "new_accounttimesheetid", "new_billtoid", "new_contracttypetimesheetid", "new_billratetimesheetid", "new_status", "new_timesheet_new_approverid", "new_invoiced"})) as New_timesheet;

                    if (retrievedTimesheet != null)
                    {
                        retrievedTimesheet.new_new_timesheet_new_timesheetlineitem = timesheetLineItemList;

                        _serviceProxy.Update(retrievedTimesheet);
                    }
                    //context.AddObject(timesheetLineEntity);
                    // context.SaveChanges();
                }

I am now getting the following error:

System.ServiceModel.FaultException1 was unhandled by user code
HResult=-2146233087 Message=Entity Id must be specified for Update
Source=mscorlib
Action=http://schemas.microsoft.com/xrm/2011/Contracts/Services/IOrganizationService/UpdateOrganizationServiceFaultFault StackTrace: Server stack trace: at System.ServiceModel.Channels.ServiceChannel.HandleReply(ProxyOperationRuntime operation, ProxyRpc& rpc) at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout) at System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation) at System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message) Exception rethrown at [0]: at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg) at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type) at Microsoft.Xrm.Sdk.IOrganizationService.Update(Entity entity) at Microsoft.Xrm.Sdk.Client.OrganizationServiceProxy.UpdateCore(Entity entity) at Microsoft.Xrm.Sdk.Client.OrganizationServiceProxy.Update(Entity entity) at TimesheetSample.Controllers.TimesheetController.SaveTimesheetLine(TimesheetViewModel timesheetLineVm) in c:\Users\Demerson.Herculano\Documents\AES Projects\TimesheetSample\TimesheetSample\Controllers\TimesheetController.cs:line 159 at TimesheetSample.Controllers.TimesheetController.New(TimesheetViewModel timesheetVm) in c:\Users\Demerson.Herculano\Documents\AES Projects\TimesheetSample\TimesheetSample\Controllers\TimesheetController.cs:line 110 at lambda_method(Closure , ControllerBase , Object[] ) at System.Web.Mvc.ActionMethodDispatcher.Execute(ControllerBase controller, Object[] parameters) at System.Web.Mvc.ReflectedActionDescriptor.Execute(ControllerContext controllerContext, IDictionary
2 parameters) at System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary2 parameters) at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass42.<BeginInvokeSynchronousActionMethod>b__41() at System.Web.Mvc.Async.AsyncResultWrapper.<>c__DisplayClass81.b__7(IAsyncResult _) at System.Web.Mvc.Async.AsyncResultWrapper.WrappedAsyncResult`1.End() at System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeActionMethod(IAsyncResult asyncResult) at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass37.<>c__DisplayClass39.b__33() at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass4f.b__49() InnerException:

Thanks in advance, Dem

Upvotes: 0

Views: 992

Answers (2)

Ankit Singh
Ankit Singh

Reputation: 51

I am not clear about the approach but as it looks like you are using mvc approach or website where you are using CRM service to CRUD crm records.
So I am putting my points on that basis:


 1. First of all you have to check whether you are connected to CRM service or Not (I think you are connected to CRM service thats why are are getting those error message on create or update record but anyway you can check like this below) 

public void SaveTimesheetLine(TimesheetViewModel timesheetLineVm)
{
    string payrollId = Convert.ToString(Session["payroll"]);
    Initiate();
    using (_serviceProxy = CrmConnector.GetOrganizationProxy(serverConfig))
    {
        // This statement is required to enable early-bound type support.
        //_serviceProxy.EnableProxyTypes();
        _service = (IOrganizationService) _serviceProxy;


        WhoAmIRequest request = new WhoAmIRequest();
        WhoAmIResponse response = (WhoAmIResponse)_service.Execute(request);
        Guid userId= response.UserId;

        If(userId==null || userId==Guid.Empty)
            return; // if userid is null or empty then ur crm service is not connected.



 2. SaveTimesheetLine(TimesheetViewModel timesheetLineVm) you are passing timesheetlineVM, this indicates that you you are creating TimeSheetLine for a TimeSheet. I have reviewed you code and found some errors:
This is of EnntityReference (LookUp) Type and you are passing string value 

    timesheetLineEntity["new_payrollreference"] = new EntityReference("entitylogicalname",new Guid(payrollId));

You are not passing the TimeSheet for which this TimeSheetLine will create

    timesheetLineEntity["timesheeetid"]=new EntityReference("timesheet",new Guid(timesheetid));


3. [FaultException`1: System.NullReferenceException: Microsoft Dynamics CRM has experienced an error.
This type of error will come on those case when we are passing null value in CRM. Please check all the values in code and look which is null and required.


4. I have also looked on the Update Code ,this is wrong because in every case you don't have `timesheetLineVm.TimesheetId.ToString()` this will be null or blank.



    var timesheetLineEntity = new New_timesheetlineitem()
                        {

                            // taken from user input 
                            New_startdatetime = timesheetLineVm.TimesheetLineViewModels.StartDate,
                            New_EndDateTime = timesheetLineVm.TimesheetLineViewModels.EndDate,
                            //new_paytypetimesheetlineitemid = Convert.ToString(timesheetLineVm.TimesheetLineViewModels.PayType),
                            //timesheetLineEntity["new_lunchtime"] = 2;
                            New_SubmittedHours = timesheetLineVm.TimesheetLineViewModels.SubmittedHours

                            //_timesheetlineId = _service.Create(timesheetLineEntity);
                        };


                        var timesheetLineItemList = new List<New_timesheetlineitem>();
                        timesheetLineItemList.Add(timesheetLineEntity);

                        var retrievedTimesheet = _serviceProxy.Retrieve("new_timesheet", new Guid(timesheetLineVm.TimesheetId.ToString()), new ColumnSet(new string[] {"new_firstname", "new_lastname", "new_name", "new_payrollreference", "new_timesheetdate", "new_timesheetid", "new_slatimesheetid", "new_stream3timesheetid", "new_candidatetimesheetid", "new_accounttimesheetid", "new_billtoid", "new_contracttypetimesheetid", "new_billratetimesheetid", "new_status", "new_timesheet_new_approverid", "new_invoiced"})) as New_timesheet;

you are declaring `var timesheetLineEntity` and using `timesheetLineVm.TimesheetId.ToString()` in the next line. timesheetLineEntity will only contain these three `New_startdatetime,New_EndDateTime,New_SubmittedHours`


I think you have to review this and in case you need my help I'll glad to support you.

Please ignore if this is not helpful for you.

Upvotes: 0

Guido Preite
Guido Preite

Reputation: 15128

The problem is that you are not considering the field types for Dynamics CRM.

Let's check this line:

timesheetLineEntity["new_firstname"] = timesheetLineVm.TimesheetLineViewModels.EmployeeFirstName;

probably new_firstname inside CRM is a single line of text field, so if EmployerFistName is a string you have no problem setting the value.

Now check this line:

timesheetLineEntity["new_billtoid"] = timesheetLineVm.TimesheetLineViewModels.BillToId;

The field new_billtoid probably inside CRM is a Lookup pointing to an entity called new_billto or new_bill. Lookup fields in C# are mapped as EntityReference so the correct way (assuming the entity name is new_bill and BillToId is a GUID) is:

 timesheetLineEntity["new_billtoid"] =
 new EntityReference("new_bill", timesheetLineVm.TimesheetLineViewModels.BillToId);

Bottom line: you need to check the exact types of all the fields you need to set and convert them to the right type if necessary.

Upvotes: 3

Related Questions