3.5 question: PropertyInfo(Of T) and custom attributes

3.5 question: PropertyInfo(Of T) and custom attributes

Old forum URL: forums.lhotka.net/forums/t/4483.aspx


stefan posted on Sunday, March 09, 2008

Hi Rocky,

I want to integrate an auditing mechanism in my base class using the new  FieldManager.GetRegisteredProperties(), which returns a List(Of IPropertyInfo).

I know that this way I only can control members that were declared like this:

    Private Shared NameProperty As PropertyInfo(Of String) = _
    RegisterProperty(Of String)(GetType(TestAuditableBase), New PropertyInfo(Of String)("Name", "friendly name of property", String.Empty))

I just pull out a new List(Of Object) using ReadProperty(info) for each registered member
each time I need to make a snapshot of the current values.
My tests seem to work.

Now I want to use a custom attribute 'NotAuditedAttribute' to indicate that certain members
should be ignored in the auditing process. Just like with NotUndoable.

How can I use custom attributes together with the new way of registering the members?
Am I then forced to use a local backing field, or is there another possible way?

Stefan


 

RockfordLhotka replied on Sunday, March 09, 2008

I think there are a couple options.

One is to put the custom attribute on the Shared PropertyInfo declaration. Another is to put the custom attribute on the property itself. Either way you need to use reflection to see if the attribute is present - it is just a matter of choosing what to reflect against.

A way that would avoid reflection is to extend PropertyInfo<T>. The purpose of PropertyInfo<T> is to provide metadata about each property, and you can subclass PropertyInfo<T> and extend it with extra metadata. So rather than using a custom attribute, you could just have an extra property in your custom extension that indicates whether the property is audited.

stefan replied on Monday, March 10, 2008

Thank you for your advice.
I will as well have to extend PropertyInfo<T> for my custom authorization to work. Formerly I had attributes on each property indicating the appropriate permission entry in my auth table.
Now I will be able to maintain these infos using the framework's infrastructure. That's pretty cool!

Thanks,

Stefan

rsbaker0 replied on Sunday, March 09, 2008

This doesn't specifically address your question of attributes, but it seems to me that if you use attributes your auditing fields would be determined at compile time (unless you are using ICustomTypeDescriptor, which has its own warts).

Our application also supports field level auditing, but our users get to decide what fields get audited, so I don't know until runtime which fields will be audited. I implemented it with a static dictionary that maintains a list of the fields audited for each object, and load the dictionary on the first database connection. It seems to work well and is also reasonably fast.

stefan replied on Monday, March 10, 2008

You are right - deciding which properties are audited should be the user's choice.
How did you determine the first database connection - or do you fill the dictionary with the entire information that's available for all types on the first login?

Stefan

rsbaker0 replied on Monday, March 10, 2008

In our case, we have a set of bridge classes that sit between CSLA and the ORM we use for database access, so it provides a natural place for doing initialization of this type. (Getting the plumbing set up properly for this was a serious "chicken versus the egg" problem, but I finally got it sorted out... ;)

I think your idea of doing it on the first login would also work fine and is basically equivalent.

Copyright (c) Marimer LLC