locked
Code First: string Id. Always getting "The Id field is required" DbValidationError RRS feed

  • Question

  • Hello,

    I have one-many relationship. I have followed this tutorial and then add some data annotation attributes. So have the following entities:

    public class Machine
    {
        [Key]
        [Required]
        [StringLength(15)]
        public string Imei { get; set; }
    
        // More properties
    
        public virtual ICollection<ApplicationUser> Users { get; set; }
        public virtual ICollection<AlarmEntry> AlarmsEntries { get; set; }
    
        public Machine()
        {
            this.AlarmsEntries = new List<AlarmEntry>();
        }
    }
    
    public class AlarmEntry
    {
        [Key]
        [Required]
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public string Id { get; set; }
    
        // More properties
    
        [StringLength(15)]
        public string MachineImei { get; set; }
    
        [ForeignKey("MachineImei")]
        public virtual Machine Machine { get; set; }
    
        public AlarmEntry()
        {
        }
    }

    I set DatabaseGenerated attribute to Identity (The database generates a value when a row is inserted). Then I create new AlarmEntry entities to Machine:

    using (ApplicationDbContext context = new ApplicationDbContext())
    {
        foreach (Machine machine in context.Machines)
        {
            MachineChecking ic = new MachineChecking(machine);
            ic.Check();
    
            if (ic.NewAlarmas != null)
            {
                foreach (AlarmEntry alarm in ic.NewAlarmas)
                {
                    AlarmEntry alarmEntry = context.AlarmEntries.Create();
                    alarmEntry.Address = alarm.Address;
                    alarmEntry.DateAndTime = alarm.DateAndTime;
                    alarmEntry.MachineImei = alarm.MachineImei;
                    alarmEntry.Message = alarm.Message;
                    alarmEntry.Name = alarm.Name;
                    alarmEntry.Type = alarm.Type;
                    machine.AlarmsEntries.Add(alarmEntry);
                }
            }
        }
        context.SaveChanges();
    }

    When SaveChanges(), for each new AlarmEntry I get one DbValidationError with this message: The Id field is required. I don't know why, because the DB would create new id with [DatabaseGenerated(DatabaseGeneratedOption.Identity)], isn't it?

    Can anyone help me? Thanks.

    Jon.

    Wednesday, September 30, 2015 2:54 PM

Answers

  • Hi Jon,

    Identity for string column types are not supported. To work around, you have to change Id column to Int type.

     [Key]
        [Required]
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public int Id { get; set; }
    
    

    I hope it helps.

    Regards,


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place.
    Click HERE to participate the survey.

    • Marked as answer by Jon 123 Friday, October 2, 2015 8:06 AM
    Thursday, October 1, 2015 2:48 AM
  • Well, I've undone all changes up to the initial migration. Then I added again the AlarmEntry with int Id and works. Thank you Herro wong for your time!
    • Marked as answer by Jon 123 Friday, October 2, 2015 8:06 AM
    Friday, October 2, 2015 8:05 AM

All replies

  • Hi Jon,

    Identity for string column types are not supported. To work around, you have to change Id column to Int type.

     [Key]
        [Required]
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public int Id { get; set; }
    
    

    I hope it helps.

    Regards,


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place.
    Click HERE to participate the survey.

    • Marked as answer by Jon 123 Friday, October 2, 2015 8:06 AM
    Thursday, October 1, 2015 2:48 AM
  • I changed the Id to int (Add-Migration and Update-Database), but now I get an SqlException:

    Cannot insert the value NULL into column 'Id', table '8000SeriesDB.dbo.AlarmEntries'; column does not allow nulls. INSERT fails.
    The statement has been terminated.

    It seems that it doesn't create new Id...


    • Edited by Jon 123 Thursday, October 1, 2015 1:38 PM
    Thursday, October 1, 2015 1:38 PM
  • Hi Jon,

    Everything works well on my side. I used your code as the following snippet.

     public class Machine
        {
            [Key]
            [Required]
            [StringLength(15)]
            public string Imei { get; set; }
    
            // More properties
            
            public virtual ICollection<AlarmEntry> AlarmsEntries { get; set; }
    
            public Machine()
            {
                this.AlarmsEntries = new List<AlarmEntry>();
            }
        }
    
        public class AlarmEntry
        {
            [Key]
            [Required]
            [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
            public int Id { get; set; }
    
            // More properties
    
            [StringLength(15)]
            public string MachineImei { get; set; }
    
            [ForeignKey("MachineImei")]
            public virtual Machine Machine { get; set; }
    
            public AlarmEntry()
            {
            }
        }
    
        public class ApplicationDbContext : DbContext
        {
            public ApplicationDbContext()
                : base("name=DefaultContext")
            {
            }
            public System.Data.Entity.DbSet<Machine> Machines { get; set; }
            public System.Data.Entity.DbSet<AlarmEntry> AlarmEntrys { get; set; }
        }
     using (ApplicationDbContext db = new ApplicationDbContext())
                {
                    Machine machine = new Machine();
                    machine.Imei = "machine001";
                    AlarmEntry entry1 = new AlarmEntry();
                    entry1.Machine = machine;
                    machine.AlarmsEntries.Add(entry1);
                    AlarmEntry entry2 = new AlarmEntry();
                    entry2.Machine = machine;
                    machine.AlarmsEntries.Add(entry2);
                    AlarmEntry entry3 = new AlarmEntry();
                    entry3.Machine = machine;
                    machine.AlarmsEntries.Add(entry3);
                    db.Machines.Add(machine);
                    db.SaveChanges();
                }

    Can you share a repro project here to describe your issue in detail.

    Regards,


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place.
    Click HERE to participate the survey.

    Friday, October 2, 2015 6:12 AM
  • Could this be Migrations problem?
    Friday, October 2, 2015 7:25 AM
  • Well, I've undone all changes up to the initial migration. Then I added again the AlarmEntry with int Id and works. Thank you Herro wong for your time!
    • Marked as answer by Jon 123 Friday, October 2, 2015 8:06 AM
    Friday, October 2, 2015 8:05 AM