0

I have a table with a column defined as an Identity column Incremented by 1. My problem is almost identical to this one... However, my code is a little different. I am writing my Entity Framework Code as Code First using Table-Per-Type (TPT) inheritance. I have a ContractHead table, a RentalContract table, and a StorageContract table in a SQL CE Database. The corresponding RentalContract and StorageContract entities derive from the ContractHead Entity.

[DataContract]
[Table("ContractHead")]
public class Contract
{
    [Key]
    [DataMember]
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Int64 Id { get; set; }

    [DataMember]
    [Column("ContactName")]
    [DataType(DataType.Text)]
    public String ContactName { get; set; }

    [DataMember]
    [DataType(DataType.EmailAddress)]
    [Column("ContactEmail")]
    public String ContactEmail { get; set; }

    [DataMember]
    [DataType(DataType.Text)]
    [Column("ContactAddress1")]
    public String ContactAddress1 { get; set; }
    //
    // ... MORE PROPERTIES

}


[DataContract]
[Table("ContractRental")]
public class RentalContract : Contract
{
    [DataMember]
    [Column("BoatMake")]
    public String BoatMake { get; set; }

    [DataMember]
    [Column("BoatYear")]
    public Int32? BoatYear { get; set; }

    [DataMember]
    [Column("BoatBeam")]
    public Decimal? BoatBeam { get; set; }

    [DataMember]
    [Column("BoatType")]
    [DataType(DataType.Text)]
    public String BoatType { get; set; }
    //
    // ... MORE PROPERTIES
}

[DataContract]
[Table("ContractStorage")]
public class StorageContract : Contract
{
    [DataMember]
    [Column("BoatMaxWidth")]
    public Decimal? BoatMaxWidth { get; set; }

    [DataMember]
    [ColumnAttribute("WidthUOM")]
    [DataType(DataType.Text)]
    public String WidthUOM { get; set; }

    [DataMember]
    [Column("LaunchDate")]
    [DataType(DataType.Date)]
    public DateTime? LaunchDate { get; set; }

    [DataMember]
    [Column("TotalCharge")]
    public Decimal? TotalCharge { get; set; }
    //
    // ... MORE PROPERTIES
}

I have, as you can see, decorated the primary Key property with the DatabaseGenerated Attribute. In fact when I first added this, in an effort to resolve this issue I was able to succesfully add a record ... just one ... after that, the error returned. When I create a new instance of a Contract the ID is assigned the value 0. Since it is a key field I assume that it is 1) required 2) populated with its default value since I do not explicitly set it. After the new Contract is defined it is passed to a method which implements the basic EF Add() method for adding a new Entity...

    private PikeMarine.Core.Models.RentalContract MapRentalContract()
    {
        PikeMarine.Core.Models.RentalContract contract = new Core.Models.RentalContract();

        //
        // (Code omitted) Fields are assigned values from form fields here ... The ID property is left unassigned
        //

        AddRentalContract(RentalContract contract);

    }


    public RentalContract AddRentalContract(RentalContract contract)
    {
        RentalContract ret = (RentalContract)base.db.Contracts.Add(contract);
        base.db.SaveChanges();
        return ret;
    }

It is on the call to SaveChanges() that the error is generated. When I attempt to insert the new record however I get the error ...

"The column cannot be modified [ColumnName = Id]"

I am confused on this because the ID field in the database (ContractHead table) is set as an identity column which is autogenerated and incremented by 1. Doesn't EF know this? Isn't that what the "DatabaseGenerated" attribute is telling the framework? Why is it attempting to set the value of that field?

Confused!

Community
  • 1
  • 1
Gary O. Stenstrom
  • 2,284
  • 9
  • 38
  • 59

1 Answers1

0

The problem was that the tables representing the derivative objects (StorageContract & RentakContract) each identified the ID field as an IDENTITY field, which was a problem. Once I redefined them so they were not IDENTITY columns the ADD function started working.

BEFORE

CREATE TABLE [ContractHead]
(
   [Id] BIGINT NOT NULL IDENTITY (1,1),
   -- Field definitions
);


CREATE TABLE [StorageContract]
(
   [Id] BIGINT NOT NULL IDENTITY (1,1),  -- unique constraint, foreign key to ContractHead.Id
   -- Field definitions
);


CREATE TABLE [RentalContract]
(
   [Id] BIGINT NOT NULL IDENTITY (1,1),  -- unique constraint, foreign key to ContractHead.Id
   -- Field definitions
);

AFTER

CREATE TABLE [ContractHead]
(
   [Id] BIGINT NOT NULL IDENTITY (1,1),
   -- Field definitions
);


CREATE TABLE [StorageContract]
(
   [Id] BIGINT NOT NULL,  -- unique constraint, foreign key to ContractHead.Id
   -- Field definitions
);


CREATE TABLE [RentalContract]
(
   [Id] BIGINT NOT NULL,  -- unique constraint, foreign key to ContractHead.Id
   -- Field definitions
);
Gary O. Stenstrom
  • 2,284
  • 9
  • 38
  • 59