OK, back to two of my favorite topics, expression builders and SharePoint. This time I wanted to be able to retrieve a field value from the current page declaratively on the markup so that I can assign it to some control’s property, without the need for writing code. Of course, the most straight way to do it is through an expression builder. Here’s the code: 1: [ExpressionPrefix("SPField")]
2: public class SPFieldExpressionBuilder : ExpressionBuilder
3: {
4: #region Public static methods
5: public static Object GetFieldValue(String fieldName, PropertyInfo propertyInfo)
6: {
7: Object fieldValue = SPContext.Current.ListItem[fieldName];
8:
9: if (fieldValue != null)
10: {
11: if ((fieldValue is IConvertible) && (typeof(IConvertible).IsAssignableFrom(propertyInfo.PropertyType) == true))
12: {
13: if (propertyInfo.PropertyType.IsAssignableFrom(fieldValue.GetType()) != true)
14: {
15: fieldValue = Convert.ChangeType(fieldValue, propertyInfo.PropertyType);
16: }
17: }
18: }
19:
20: return (fieldValue);
21: }
22:
23: #endregion
24:
25: #region Public override methods
26: public override Object EvaluateExpression(Object target, BoundPropertyEntry entry, Object parsedData, ExpressionBuilderContext context)
27: {
28: return (GetFieldValue(entry.Expression, entry.PropertyInfo));
29: }
30:
31: public override CodeExpression GetCodeExpression(BoundPropertyEntry entry, Object parsedData, ExpressionBuilderContext context)
32: {
33: if (String.IsNullOrEmpty(entry.Expression) == true)
34: {
35: return (new CodePrimitiveExpression(String.Empty));
36: }
37: else
38: {
39: return (new CodeMethodInvokeExpression(new CodeMethodReferenceExpression(new CodeTypeReferenceExpression(this.GetType()), "GetFieldValue"), new CodePrimitiveExpression(entry.Expression), new CodePropertyReferenceExpression(new CodeArgumentReferenceExpression("entry"), "PropertyInfo")));
40: }
41: }
42:
43: #endregion
44:
45: #region Public override properties
46: public override Boolean SupportsEvaluate
47: {
48: get
49: {
50: return (true);
51: }
52: }
53: #endregion
54: }
You will notice that it will even try to convert the field value to the target property’s type, through the use of the IConvertible interface and the Convert.ChangeType method.
It must be placed on the Global Assembly Cache or you will get a security-related exception. The other alternative is to change the trust level of your web application to full trust.
Here’s how to register it on Web.config:
1: <expressionBuilders>
2: <!-- ... -->
3: <add expressionPrefix="SPField" type="MyNamespace.SPFieldExpressionBuilder, MyAssembly, Culture=neutral, Version=1.0.0.0, PublicKeyToken=29186a6b9e7b779f" />
4: </expressionBuilders>
And finally, here’s how to use it on an ASPX or ASCX file inside a publishing page:
1: <asp:Label runat="server" Text="<%$ SPField:Title %>"/>