Skip to content

Instantly share code, notes, and snippets.

@robashton
Created February 9, 2011 17:42
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save robashton/818875 to your computer and use it in GitHub Desktop.
Save robashton/818875 to your computer and use it in GitHub Desktop.
A working attempt at wrapping ActionCall
public class CommandHandlerUrlPolicy : IUrlPolicy
{
public bool Matches(ActionCall call, IConfigurationObserver log)
{
return call.Method.Name == "Handle";
}
public IRouteDefinition Build(ActionCall call)
{
call = WrapActionCall(call);
var route = call.ToRouteDefinition();
route.Append("Services");
route.Append("Commands");
route.Append(call.HandlerType.Name.Replace("CommandHandler", ""));
return route;
}
private ServiceActionCall WrapActionCall(ActionCall call)
{
var outerCall = new ServiceActionCall(call);
call.ReplaceWith(outerCall);
var validationType = typeof(ServiceValidationBehaviour<>).MakeGenericType(outerCall.InputType());
outerCall.WrapWith(validationType);
var jsonBehaviourType = typeof(ServiceOutputRenderBehaviour<>).MakeGenericType(typeof(ServiceCommandOutput));
var outputNode = new OutputNode(jsonBehaviourType);
outerCall.AddToEnd(outputNode);
return outerCall;
}
}
public class ServiceActionCall : ActionCall
{
private readonly ActionCall inner;
public ServiceActionCall(ActionCall inner) : base(inner.HandlerType, inner.Method)
{
this.inner = inner;
}
protected override ObjectDef buildObjectDef()
{
var originalDef = base.buildObjectDef();
originalDef.Type = typeof (ValidationAwareActionInvoker<,>)
.MakeGenericType(inner.HandlerType,
inner.Method.GetParameters().First().ParameterType);
return originalDef;
}
public override BehaviorCategory Category
{
get { return BehaviorCategory.Call; }
}
}
public class ServiceValidationBehaviour<T> : IActionBehavior where T : class
{
private readonly IFubuRequest fubuRequest;
private readonly IValidator<T> validator;
public IActionBehavior InsideBehavior { get; set; }
public ServiceValidationBehaviour(IFubuRequest fubuRequest, IValidator<T> validator)
{
this.fubuRequest = fubuRequest;
this.validator = validator;
}
public void Invoke()
{
var results = validator.Validate(fubuRequest.Get<T>());
var output = new ServiceCommandOutput()
{
Success = results.IsValid,
Messages = results.Errors
.Select(error=> new ServiceCommandOutputMessage()
{
Key = error.PropertyName,
Text = error.ErrorMessage
}).ToArray()
};
fubuRequest.Set(output);
if (InsideBehavior != null)
{
this.InsideBehavior.Invoke();
}
}
public void InvokePartial()
{
this.Invoke();
}
}
public class ValidationAwareActionInvoker<TController, TInput> : OneInZeroOutActionInvoker<TController, TInput> where TInput : class
{
private readonly IFubuRequest request;
public ValidationAwareActionInvoker(IFubuRequest request, TController controller, Action<TController, TInput> action) : base(request, controller, action)
{
this.request = request;
}
protected override FubuMVC.Core.DoNext performInvoke()
{
var result = request.Get<ServiceCommandOutput>();
if (result.Success)
{
base.performInvoke();
}
return FubuMVC.Core.DoNext.Continue;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment