title: how to use Attribute.IsDefined in entity framework 5?
body: <p>I am using the entity framework to create an audit trail.  Rather than audit every property, I thought I would create a custom attribute</p>
  
  <pre><code>  [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)]
      public class DoNotAudit : Attribute
      {
      }
  </code></pre>
  
  <p>Then I would apply this to my model</p>
  
  <pre><code> [Table("AuditZone")]
      public class AuditZone
      {
          public AuditZone()
          {
              AuditZoneUploadedCOESDetails = new List&lt;UploadedCOESDetails&gt;();
              AuditZonePostcode = new List&lt;Postcodes&gt;();
          }
  
          [Key]
          public int Id { get; set; }
          public string Description { get; set; }     
          public bool Valid { get; set; }       
  
          public DateTime CreatedDate { get; set; }
          public int? CreatedBy { get; set; }
          [DoNotAudit]
          public DateTime? ModifiedDate { get; set; }
          public int? ModifiedBy { get; set; }
  
          public virtual UserProfile CreatedByUser { get; set; }
          public virtual UserProfile ModifiedByUser { get; set; }
  
          public virtual ICollection&lt;UploadedCOESDetails&gt; AuditZoneUploadedCOESDetails { get; set; }
          public virtual ICollection&lt;Postcodes&gt; AuditZonePostcode { get; set; }
      }
  </code></pre>
  
  <p>Then in my code for the audit trail</p>
  
  <pre><code>  // This is overridden to prevent someone from calling SaveChanges without specifying the user making the change
          public override int SaveChanges()
          {
              throw new InvalidOperationException("User ID must be provided");
          }
          public int SaveChanges(int userId)
          {
              // Get all Added/Deleted/Modified entities (not Unmodified or Detached)
              foreach (var ent in this.ChangeTracker.Entries().Where(p =&gt; p.State == System.Data.EntityState.Added || p.State == System.Data.EntityState.Deleted || p.State == System.Data.EntityState.Modified))
              {
                  // For each changed record, get the audit record entries and add them
                  foreach (AuditLog x in GetAuditRecordsForChange(ent, userId))
                  {
                      this.AuditLogs.Add(x);
                  }
              }
  
              // Call the original SaveChanges(), which will save both the changes made and the audit records
              return base.SaveChanges();
          }
  
          private List&lt;AuditLog&gt; GetAuditRecordsForChange(DbEntityEntry dbEntry, int userId)
          {
              List&lt;AuditLog&gt; result = new List&lt;AuditLog&gt;();
  
              DateTime changeTime = DateTime.UtcNow;
  
              // Get the Table() attribute, if one exists
              //TableAttribute tableAttr = dbEntry.Entity.GetType().GetCustomAttributes(typeof(TableAttribute), false).SingleOrDefault() as TableAttribute;
  
              TableAttribute tableAttr = dbEntry.Entity.GetType().GetCustomAttributes(typeof(TableAttribute), true).SingleOrDefault() as TableAttribute;
  
              // Get table name (if it has a Table attribute, use that, otherwise get the pluralized name)
              string tableName = tableAttr != null ? tableAttr.Name : dbEntry.Entity.GetType().Name;
  
              // Get primary key value (If you have more than one key column, this will need to be adjusted)
              var keyNames = dbEntry.Entity.GetType().GetProperties().Where(p =&gt; p.GetCustomAttributes(typeof(KeyAttribute), false).Count() &gt; 0).ToList();
  
              string keyName = keyNames[0].Name;
  
              var test = dbEntry.Entity.GetType().GetProperties().Where(p =&gt; p.GetCustomAttributes(typeof(DoNotAudit), false).Count() &gt; 0).ToList();
  
  
  
              // //dbEntry.Entity.GetType().GetProperties().Single(p =&gt; p.GetCustomAttributes(typeof(KeyAttribute), false).Count() &gt; 0).Name;
  
              if (dbEntry.State == System.Data.EntityState.Added)
              {
                  // For Inserts, just add the whole record
                  // If the entity implements IDescribableEntity, use the description from Describe(), otherwise use ToString()
  
                  foreach (string propertyName in dbEntry.CurrentValues.PropertyNames)
                  {
  
  
                      result.Add(new AuditLog()
                      {
                          AuditLogId = Guid.NewGuid(),
                          UserId = userId,
                          EventDateUTC = changeTime,
                          EventType = "A",    // Added
                          TableName = tableName,
                          RecordId = dbEntry.CurrentValues.GetValue&lt;object&gt;(keyName).ToString(),
                          ColumnName = propertyName,
                          NewValue = dbEntry.CurrentValues.GetValue&lt;object&gt;(propertyName) == null ? null : dbEntry.CurrentValues.GetValue&lt;object&gt;(propertyName).ToString()
                      }
                              );
                  }
              }
              else if (dbEntry.State == System.Data.EntityState.Deleted)
              {
                  // Same with deletes, do the whole record, and use either the description from Describe() or ToString()
                  result.Add(new AuditLog()
                  {
                      AuditLogId = Guid.NewGuid(),
                      UserId = userId,
                      EventDateUTC = changeTime,
                      EventType = "D", // Deleted
                      TableName = tableName,
                      RecordId = dbEntry.OriginalValues.GetValue&lt;object&gt;(keyName).ToString(),
                      ColumnName = "*ALL"//,
                     // NewValue = (dbEntry.OriginalValues.ToObject() is IDescribableEntity) ? (dbEntry.OriginalValues.ToObject() as IDescribableEntity).Describe() : dbEntry.OriginalValues.ToObject().ToString()
                  }
                      );
              }
              else if (dbEntry.State == System.Data.EntityState.Modified)
              {
                  foreach (string propertyName in dbEntry.OriginalValues.PropertyNames)
                  {
  
                      var doNotAUditDefined = dbEntry.Property(propertyName).GetType().GetCustomAttributes(typeof(DoNotAudit), false);
  
                     // var test1 = dbEntry.Property(propertyName).GetType().Where(p =&gt; p.GetCustomAttributes(typeof(DoNotAudit), false).Count() &gt; 0).ToList();
  
                  //    var test = dbEntry.Entity.GetType().GetProperties().Where(p =&gt; p.GetCustomAttributes(typeof(DoNotAudit), false).Count() &gt; 0).ToList();
  
  
                      // For updates, we only want to capture the columns that actually changed
                      if (!object.Equals(dbEntry.OriginalValues.GetValue&lt;object&gt;(propertyName), dbEntry.CurrentValues.GetValue&lt;object&gt;(propertyName)))
                      {
                          result.Add(new AuditLog()
                          {
                              AuditLogId = Guid.NewGuid(),
                              UserId = userId,
                              EventDateUTC = changeTime,
                              EventType = "M",    // Modified
                              TableName = tableName,
                              RecordId = dbEntry.OriginalValues.GetValue&lt;object&gt;(keyName).ToString(),
                              ColumnName = propertyName,
                              OriginalValue = dbEntry.OriginalValues.GetValue&lt;object&gt;(propertyName) == null ? null : dbEntry.OriginalValues.GetValue&lt;object&gt;(propertyName).ToString(),
                              NewValue = dbEntry.CurrentValues.GetValue&lt;object&gt;(propertyName) == null ? null : dbEntry.CurrentValues.GetValue&lt;object&gt;(propertyName).ToString()
                          }
                              );
                      }
                  }
              }
              // Otherwise, don't do anything, we don't care about Unchanged or Detached entities
  
              return result;
          }
  </code></pre>
  
  <p>In the modified section I have the following line of code</p>
  
  <pre><code>  var doNotAUditDefined = dbEntry.Property(propertyName).GetType().GetCustomAttributes(typeof(DoNotAudit), false);
  </code></pre>
  
  <p>WHen I step through the code, even for the modifiedDate property this is shown as empty.  How can that be?  any help is appreciated</p>
  
  <p>Thanks</p>