public static bool IsActive(out AmbientObserver observer) { var current = AmbientObserver.current; observer = current; return(current != null); }
public static EventWithTarget GetEventWithTarget <TMock>(this Action <TMock> eventExpression, TMock mock) where TMock : class { Guard.NotNull(eventExpression, nameof(eventExpression)); MethodBase addRemove; Mock target; using (var observer = AmbientObserver.Activate()) { eventExpression(mock); if (!observer.LastIsInvocation(out target, out var invocation, out _)) { throw new ArgumentException(Resources.ExpressionIsNotEventAttachOrDetachOrIsNotVirtual); } addRemove = invocation.Method; } var ev = addRemove.DeclaringType.GetEvent( addRemove.Name.Replace("add_", string.Empty).Replace("remove_", string.Empty)); if (ev == null) { throw new ArgumentException(string.Format( CultureInfo.CurrentCulture, Resources.EventNotFound, addRemove)); } return(new EventWithTarget(ev, target)); }
public static bool IsMatch(this Expression expression, out Match match) { using (var observer = AmbientObserver.Activate()) { Expression.Lambda <Action>(expression).CompileUsingExpressionCompiler().Invoke(); return(observer.LastIsMatch(out match)); } }
public void Dispose() { if (this.observations != null) { for (var i = this.observations.Count - 1; i >= 0; --i) { this.observations[i].Dispose(); } } current = null; }
public override InterceptionAction Handle(Invocation invocation, Mock mock) { if (AmbientObserver.IsActive(out _)) { return(InterceptionAction.Continue); } var matchedSetup = mock.Setups.FindMatchFor(invocation); if (matchedSetup != null) { matchedSetup.Condition?.EvaluatedSuccessfully(); if (matchedSetup.IsVerifiable) { invocation.MarkAsMatchedByVerifiableSetup(); } else { invocation.MarkAsMatchedBySetup(); } matchedSetup.SetOutParameters(invocation); // We first execute, as there may be a Throws // and therefore we might never get to the // next line. matchedSetup.Execute(invocation); return(InterceptionAction.Stop); } else if (mock.Behavior == MockBehavior.Strict) { throw MockException.NoSetup(invocation); } else { return(InterceptionAction.Continue); } }
private static SetupSetImplResult SetupSetImpl(Mock mock, Delegate setterExpression) { Mock target; Invocation invocation; AmbientObserver.Matches matches; using (var observer = AmbientObserver.Activate()) { setterExpression.DynamicInvoke(mock.Object); if (!observer.LastIsInvocation(out target, out invocation, out matches)) { throw new ArgumentException(string.Format( CultureInfo.InvariantCulture, Resources.SetupOnNonVirtualMember, string.Empty)); } } var setter = invocation.Method; if (!setter.IsPropertySetter()) { throw new ArgumentException(Resources.SetupNotSetter); } // No need to call ThrowIfCantOverride as non-overridable would have thrown above already. // Get the variable name as used in the actual delegate :) // because of delegate currying, look at the last parameter for the Action's backing method, not the first var setterExpressionParameters = setterExpression.GetMethodInfo().GetParameters(); var parameterName = setterExpressionParameters[setterExpressionParameters.Length - 1].Name; var x = Expression.Parameter(invocation.Method.DeclaringType, parameterName); var arguments = invocation.Arguments; var parameters = setter.GetParameters(); var values = new Expression[arguments.Length]; if (matches.Count == 0) { // Length == 1 || Length == 2 (Indexer property) for (int i = 0; i < arguments.Length; i++) { values[i] = GetValueExpression(arguments[i], parameters[i].ParameterType); } var lambda = Expression.Lambda( typeof(Action <>).MakeGenericType(x.Type), Expression.Call(x, invocation.Method, values), x); return(new SetupSetImplResult(target, lambda, invocation.Method, values)); } else { // TODO: Use all observed matchers, not just the last one! var lastMatch = matches[matches.Count - 1]; var matchers = new Expression[arguments.Length]; var valueIndex = arguments.Length - 1; var propertyType = setter.GetParameters()[valueIndex].ParameterType; // If the value matcher is not equal to the property // type (i.e. prop is int?, but you use It.IsAny<int>()) // add a cast. if (lastMatch.RenderExpression.Type != propertyType) { values[valueIndex] = Expression.Convert(lastMatch.RenderExpression, propertyType); } else { values[valueIndex] = lastMatch.RenderExpression; } matchers[valueIndex] = new MatchExpression(lastMatch); for (int i = 0; i < arguments.Length - 1; i++) { // Add the index value for the property indexer values[i] = GetValueExpression(arguments[i], parameters[i].ParameterType); // TODO: No matcher supported now for the index matchers[i] = values[i]; } var lambda = Expression.Lambda( typeof(Action <>).MakeGenericType(x.Type), Expression.Call(x, invocation.Method, values), x); return(new SetupSetImplResult(target, lambda, invocation.Method, matchers)); } }
public static AmbientObserver Activate() { Debug.Assert(current == null); return(current = new AmbientObserver()); }
public Matches(AmbientObserver observer, int offset, int count) { this.observer = observer; this.offset = offset; this.count = count; }