[CSHARP-743] ObjectId not getting returned Created: 17/May/13  Updated: 14/May/14  Resolved: 17/May/13

Status: Closed
Project: C# Driver
Component/s: None
Affects Version/s: 1.8.1
Fix Version/s: None

Type: Bug Priority: Major - P3
Reporter: James Goodale Assignee: Unassigned
Resolution: Duplicate Votes: 0
Labels: None
Remaining Estimate: Not Specified
Time Spent: Not Specified
Original Estimate: Not Specified
Environment:

Dev


Issue Links:
Duplicate
duplicates CSHARP-721 Insert fails to set SetIdMember inter... Closed
Backwards Compatibility: Minor Change

 Description   

We moved our driver from version 1.7.1 to 1.8.1 and now our objectId is not getting populated when inserting into the collection. Any thoughts as to what might have caused this?



 Comments   
Comment by James Goodale [ 17/May/13 ]

Great, thanks Craig.. that worked perfectly!

James.

Comment by Craig Wilson [ 17/May/13 ]

You got there quicker than I had time to post. You have definitely hit the regression I linked to above, although it is manifesting itself in a slightly different way. Previously, in 1.7.1, this would get set as a lazy side-effect of the way things were getting loaded. Now, any changes after AutoMap runs are all manual. So, setting the representation after AutoMap has run will not affect the id generator used. So, your solution here is absolutely correct. My apologies for the regression.

In the other ticket, I linked to a convention you could use rather than manually mapping this, although since it is your base class, it would likely introduce more code than this.

I believe this code is a little more concise and accomplishes the same thing:

if (!BsonClassMap.IsClassMapRegistered(typeof (MNetEntity)))
    {
        BsonClassMap.RegisterClassMap<MNetEntity>(cm =>
        {
            cm.AutoMap();
            // the id member should have already been mapped based on the default conventions...
            cm.IdMemberMap.SetRepresentation(BsonType.ObjectId).SetIdGenerator(new StringObjectIdGenerator()));
 
        });
    }

Comment by James Goodale [ 17/May/13 ]

So based on your other post I figured you would want to see our configuration for MNetEntity:

        public void Configure()
        {
            //http://stackoverflow.com/questions/8198304/idmembermap-is-null-using-representation-serialization-options
            if (!BsonClassMap.IsClassMapRegistered(typeof (MNetEntity)))
            {
                BsonClassMap.RegisterClassMap<MNetEntity>(cm =>
                {
                    cm.AutoMap();
	                cm.GetMemberMap(c => c.Id);
                    //.SetRepresentation(BsonType.ObjectId);
					cm.SetIdMember(cm.GetMemberMap(c => c.Id).SetRepresentation(BsonType.ObjectId).SetIdGenerator(new StringObjectIdGenerator()));
 
                });
            }
        }

I commented out the .SetRepresentation and added the the new Set as suggested in the other post and it works as expected. Is this correct?

Thanks!

Comment by James Goodale [ 17/May/13 ]

using MNet.Data;
 
namespace MNet.ServiceCore.Domain.Addresses
{
    public class BaseAddress : MNetEntity
    {
        public string Address1 { get; set; }
		public string Address2 { get; set; }
		public string Address3 { get; set; }
		public string City { get; set; }
        public string State { get; set; }
        public string Country { get; set; }
        public string ZipCode { get; set; }
    }
}
 
 
 
using System.ComponentModel.DataAnnotations.Schema;
using System.Runtime.Serialization;
 
namespace MNet.Data
{
  [DataContract(Name = "MNetEntity", Namespace = "")]
  public abstract class MNetEntity : IMNetEntity
  {
    [DataMember]
    [NotMapped]
    public string Id { get; set; }
  }
}

Comment by Craig Wilson [ 17/May/13 ]

And could you post your BaseAddress structure, at least a snippet that includes the identifier.

Comment by James Goodale [ 17/May/13 ]

So this is our configuration class:

    public class BaseAddressConfiguration : IEntityTypeConfiguration
    {
        public void Configure()
        {
            BsonEntityConfiguration.SetCollectionName<BaseAddress>("Address");
 
            if (!BsonClassMap.IsClassMapRegistered(typeof(BaseAddress)))
            {
                BsonClassMap.RegisterClassMap<BaseAddress>(cm =>
                {
                    cm.AutoMap();
                    cm.SetIsRootClass(true);
                });
            }
        }
       
    }

And here is a sample unit test that I created to test this:

		[Fact]
		public void BaseAddressConfigurationAddTest()
		{
			var baseAddress = new BaseAddress
				                  {
 
					                  Address1 = "123 Main st.",
					                  Address2 = "Suite 300",
					                  Address3 = "Attn: James",
					                  City = "Carlsbad",
					                  Country = "US",
					                  State = "CA",
					                  ZipCode = "920008"
				                  };
			var addressObj = _context.Database.GetCollection<BaseAddress>("Address").Insert(baseAddress);
 
			Assert.NotNull(addressObj);
 

and this is the response:

11000 duplicate key error index: ServiceCore.Address.$id dup key: { : null }'

Comment by Craig Wilson [ 17/May/13 ]

Could you post the code you are using to map your classes? There was a regression introduced in 1.8.0 regarding something similar (https://jira.mongodb.org/browse/CSHARP-721).

Comment by Sridhar Nanjundeswaran [ 17/May/13 ]

Can you add some sample code so I can try to reproduce. Also what version of the server are you running?

Generated at Wed Feb 07 21:37:42 UTC 2024 using Jira 9.7.1#970001-sha1:2222b88b221c4928ef0de3161136cc90c8356a66.