Skip to content

Instantly share code, notes, and snippets.

@ajai8085
Last active November 20, 2015 00:24
Show Gist options
  • Save ajai8085/0a1f297e141fc790f3e1 to your computer and use it in GitHub Desktop.
Save ajai8085/0a1f297e141fc790f3e1 to your computer and use it in GitHub Desktop.
Prepare dynamic parameters for dapper on the fly , use parameter name as expressions to retrieve the values etc .
static public class DapperExtensions
{
public static MemberInfo GetMemberInfo(this Expression expression)
{
LambdaExpression lambdaExpression = (LambdaExpression)expression;
MemberExpression memberExpression;
if (lambdaExpression.Body is UnaryExpression)
{
UnaryExpression unaryExpression = (UnaryExpression)lambdaExpression.Body;
memberExpression = (MemberExpression)unaryExpression.Operand;
}
else
{
memberExpression = (MemberExpression)lambdaExpression.Body;
}
return memberExpression.Member;
}
public static TReturn GetValue<TReturn, TProperty>(this DynamicParameters dynamicParameters, Expression<Func<TProperty>> property)
{
return dynamicParameters.Get<TReturn>("@"+ property.GetMemberInfo().Name);
}
//Feel free to use this as you want
public static DynamicParameters PrepareParams<T>(this IDbConnection connection, T entity) where T : class
{
var dynamicParameters = new DynamicParameters();
var type = typeof(T);
var props = type.GetProperties();
foreach (var prop in props)
{
ParameterTypeAttribute[] attributes = (ParameterTypeAttribute[])prop.GetCustomAttributes(
typeof(ParameterTypeAttribute), false);
ParameterTypeAttribute metadata;
if (attributes != null && attributes.Length > 0)
{
metadata = attributes.Single();//make sure that there are no multiple attributes
}
else
{
metadata = new ParameterTypeAttribute();
}
if (!metadata.IgnoreField)
{
object value = prop.GetValue(entity);
dynamicParameters.Add("@"+ prop.Name, value, null, metadata.Direction);
}
}
return dynamicParameters;
}
}
using System;
using System.Data;
namespace Impos.Common.DataServices.Model
{
[System.AttributeUsage(AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
sealed class ParameterTypeAttribute : Attribute
{
//Overloaded constructors are done purposefully , changing it to ParameterTypeAttribute(ParameterDirection direction= ParameterDirection.Input, bool ignoreField=false ) makes to look the place where the attribute is used funny. more over , I do not want to recompile the target assemblies if the signature changes
public ParameterTypeAttribute() : this(ParameterDirection.Input, false)
{
}
public ParameterTypeAttribute(bool ignoreField) : this(ParameterDirection.Input, ignoreField)
{
}
public ParameterTypeAttribute(ParameterDirection direction) : this(direction, false)
{
}
public ParameterTypeAttribute(ParameterDirection direction, bool ignoreField)
{
Direction = direction;
IgnoreField = ignoreField;
}
public ParameterDirection Direction { get; set; }
public bool IgnoreField { get; set; }
}
}
using Dapper;
Public class Test
{
sqlConnection.PrepareParams(_stockInputInstance);
sqlConnection.Exxx()
int b = p.Get<int>(()=>_stockInputInstance.Status);
int c = p.Get<int>(()=>_stockInputInstance.StockFound);
}
class StockInput
{
public int DepartmentId { get; set; }
public int? EmployeeId { get; set; }
[ParameterType(ParameterDirection.Output)]
public int StockFound { get; set; }
[ParameterType(ParameterDirection.ReturnValue)]
public int Status { get; set; }
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment