Of Code and Me

Somewhere to write down all the stuff I'm going to forget and then need

An Implementation of Fold for C# August 20, 2009

Filed under: C#,Coding,Functional programming,Uncategorized — Rupert Bates @ 9:22 am

I expect there are a number of implementations of this around, but I couldn’t find one so I wrote this. It is an extension method which implements Fold on IEnumerable


public static class Extensions
{
  public delegate TDestination FoldOperation<TSource, TDestination>(TSource item, TDestination acc);
  public static TDestination Fold<TSource, TDestination>(this IEnumerable<TSource> list, FoldOperation<TSource, TDestination> foldOperation, TDestination acc)
  {
     foreach(TSource item in list)
     {
       acc = foldOperation(item, acc);
     }
     return acc;
  }
 }

I can then use this Fold function for something like this which takes an object with a number of properties and creates a querystring with the name/value pairs of all of those properties which are non-null:

public class UrlConstructor
{
  //Takes a RequestParameter object with a number of properties which
  //if their value is set should be translated into querystring parameters
  public static string ConstructUrl(RequestParameters rp)
  {
    //Get all the properties where the value is not null
    var values = typeof(RequestParameters).GetProperties().Where(p => (p.GetValue(rp, null) != null));

    //Fold these values up into a string
    var querystring = values.Fold(((p, acc) => acc + p.Name + "=" + p.GetValue(rp, null) + "&"), "").TrimEnd('&');

    return "http://mybaseurl.com/default.aspx?" + querystring;
  }
} 
 

Find and run aspnet_regsql.exe with powershell August 18, 2009

Filed under: Uncategorized — Rupert Bates @ 4:47 pm

gci -Recurse -Path c:\windows\ -Include aspnet_regsql.exe | Invoke-Item

 

Enumeration model binder for asp.net mvc August 8, 2009

Filed under: C#,MVC,Uncategorized — Rupert Bates @ 9:06 pm

We were recently working on an asp.net MVC app and I noticed that in a lot of places actions were taking strings as parameters and then converting them to enum values with the action. The reason for doing this rather than just typing the parameter as the enum type was because they were optional and so when the value didn’t exist an error was thrown:

screenshot of error page

screenshot of error page

Because enums are not nullable types they can’t be used as optional parameters.

What was needed then was a way to provide a default parameter for when the parameter didn’t exist in the url. To do this I wrote a custom model binder and it solved the problem pretty well.

Here is the code for the binder

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace EnumTest.Helpers
{
public class EnumBinder<T> : IModelBinder
{
private T DefaultValue { get; set; }
public EnumBinder(T defaultValue)
{
DefaultValue = defaultValue;
}

#region IModelBinder Members
public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
return bindingContext.ValueProvider[bindingContext.ModelName] == null
? DefaultValue
: GetEnumValue(DefaultValue, bindingContext.ValueProvider[bindingContext.ModelName].AttemptedValue);
}

#endregion

public static T GetEnumValue<T>(T defaultValue, string value)
{
T enumType = defaultValue;

if ((!String.IsNullOrEmpty(value)) && (Contains(typeof(T), value)))
enumType = (T)Enum.Parse(typeof(T), value, true);

return enumType;
}
public static bool Contains(Type enumType, string value)
{
return Enum.GetNames(enumType).Contains(value, StringComparer.OrdinalIgnoreCase);
}
}
}

And to use it in your project you just register it in your Global.asax, specifying the type of your enum and the default value you want when there is no value available in the input.

protected void Application_Start()
        {
            RegisterRoutes(RouteTable.Routes);
            ModelBinders.Binders.Add(typeof(TestEnum), new EnumBinder<TestEnum>(TestEnum.rupert));
        }