This is a migrated thread and some comments may be shown as answers.

Foreign key update problem

1 Answer 132 Views
Development (API, general questions)
This is a migrated thread and some comments may be shown as answers.
This question is locked. New answers and comments are not allowed.
Kristof
Top achievements
Rank 1
Kristof asked on 21 Mar 2011, 09:22 PM
I have an entity Aspnet_Users and have a link in my UserExtend Entity --> foreign key = UserId of type Guid.
Now when I copy the UserExtend in a ViewModel for MVC using EmitMapper, then I do some changes through the view and hit save.
After the save button is clicked I copy the viewmodel back to UserExtend and try to update it with the following code:

                 try
            {
                IObjectId id = Database.OID.GetObjectId(entity);
                var existingEntity = Context.GetObject<T>(new ObjectKey(id));
 
                //ExecuteCopy(entity, existingEntity);
                ObjectMapperManager.DefaultInstance.GetMapper<T, T>().Map(entity, existingEntity);
                Context.SaveChanges();
 
                return id.ToString();
            }
            catch (OpenAccessException ex)
            {
                Context.ClearChanges();
                throw ex;
            }


I get an error that UserId cannot be null: but the value is not null. I think because of the Telerik SQL optimalizations the UserId is null because it is not changed. And because the UserId is a foreign key, it is still included in the generated SQL.

Telerik.OpenAccess.Exceptions.DataStoreException was unhandled by user code
  Message=Update failed: Telerik.OpenAccess.RT.sql.SQLException: Cannot insert the value NULL into column 'UserId', table 'Ecommerce.dbo.UserExtend'; column does not allow nulls. UPDATE fails.
The statement has been terminated.
   at Telerik.OpenAccess.RT.Adonet2Generic.Impl.PreparedStatementImp.executeUpdate()
   at OpenAccessRuntime.Relational.conn.PooledPreparedStatement.executeUpdate()
   at OpenAccessRuntime.Relational.RelationalStorageManager.generateUpdates(OID oid, Int32 index, ClassMetaData cmd, PersistGraph graph, Int32[] fieldNos, Boolean haveNewObjects, CharBuf s)
Row: GenericOID@a UserExtend Id=5
UPDATE [UserExtend] SET [UserId]=?, [CustomerName]=? WHERE [Id] = ? AND [UserId]=? AND [CustomerName]=?
(set event logging to all to see parameter values) Telerik.OpenAccess.RT.sql.SQLException: Cannot insert the value NULL into column 'UserId', table 'Ecommerce.dbo.UserExtend'; column does not allow nulls. UPDATE fails.
The statement has been terminated.
   at Telerik.OpenAccess.RT.Adonet2Generic.Impl.PreparedStatementImp.executeUpdate()
   at OpenAccessRuntime.Relational.conn.PooledPreparedStatement.executeUpdate()
   at OpenAccessRuntime.Relational.RelationalStorageManager.generateUpdates(OID oid, Int32 index, ClassMetaData cmd, PersistGraph graph, Int32[] fieldNos, Boolean haveNewObjects, CharBuf s)
  Source=Telerik.OpenAccess
  CanRetry=false
  StackTrace:
       at eCommerce.DataAccess.Common.EntityManager`1.UpdateEntity[T](T entity) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.DataAccess\Common\EntityManager.cs:line 81
       at eCommerce.DataAccess.Common.Manager`1.Update(T entity) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.DataAccess\Common\Manager.cs:line 26
       at eCommerce.BusinessLogic.Customers.UserExtendLogic.Update(UserExtend userExtend) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.BusinessLogic\Customers\UserExtendLogic.cs:line 32
       at eCommerce.Facade.Customers.UserExtendFacade.Update(UserExtend userExtend) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.Facade\Customers\UserExtendFacade.cs:line 37
       at eCommerce.Facade.Customers.MembershipFacade.HandleUserExtend(String internalUserName, UserExtend userExtend, Boolean insert) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.Facade\Customers\MembershipFacade.cs:line 117
       at eCommerce.Facade.Customers.MembershipFacade.CreateOrUpdateUser(UserExtend userExtend) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.Facade\Customers\MembershipFacade.cs:line 75
       at eCommerce.Webshop.Controllers.AccountController.UpdateRegistration(RegisterModel model) in C:\Projects\Dev-xp\Marlimat\trunk\src\eCommerce.Webshop\Controllers\AccountController.cs:line 164
       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, IDictionary`2 parameters)
       at System.Web.Mvc.ControllerActionInvoker.<>c__DisplayClass15.<InvokeActionMethodWithFilters>b__12()
       at System.Web.Mvc.ControllerActionInvoker.InvokeActionMethodFilter(IActionFilter filter, ActionExecutingContext preContext, Func`1 continuation)
  InnerException: Telerik.OpenAccess.RT.sql.SQLException
       Message=Cannot insert the value NULL into column 'UserId', table 'Ecommerce.dbo.UserExtend'; column does not allow nulls. UPDATE fails.
The statement has been terminated.
       Source=Telerik.OpenAccess.Adonet2
       Description=SQLState=;Cannot insert the value NULL into column 'UserId', table 'Ecommerce.dbo.UserExtend'; column does not allow nulls. UPDATE fails.
The statement has been terminated.
       ErrorCode=515
       Number=515
       StackTrace:
            at Telerik.OpenAccess.RT.Adonet2Generic.Impl.PreparedStatementImp.executeUpdate()
            at OpenAccessRuntime.Relational.conn.PooledPreparedStatement.executeUpdate()
            at OpenAccessRuntime.Relational.RelationalStorageManager.generateUpdates(OID oid, Int32 index, ClassMetaData cmd, PersistGraph graph, Int32[] fieldNos, Boolean haveNewObjects, CharBuf s)
       InnerException:

only when I manually map the fields and SKIP the UserId field, the update is successful...
Is there a solution for this behavior? I don't want to maintain all mappings by hand.

1 Answer, 1 is accepted

Sort by
0
Serge
Telerik team
answered on 24 Mar 2011, 01:22 PM
Hi Kristof,

 Unfortunately I am unable to reproduce this exact behaviour on my side, however there are a few thing that you can do. First of all you can modify the concurrency control strategy to all which will ensure that all field are checked for changes. Also make sure that prior to saving the changes to the database the value of this foreign key primitive field is not set to null, your emit mapper might be setting the wrong value.

If that does not help it would be very valuable for us if you could provide a sample project that reproduces this behaviour so that we can debug it locally and find the cause of the issue faster.

I hope this is helpful. 

Kind regards,
Serge
the Telerik team
Tags
Development (API, general questions)
Asked by
Kristof
Top achievements
Rank 1
Answers by
Serge
Telerik team
Share this question
or