I've got a couple of methods that use reflection to transform from one object type to another. I'm in the process of testing the transformation methods via Moq and have stumbled upon a behavior I don't know how to handle. When I reflect across a Moq object to obtain PropertyInfo's, I get two additional objects.
Moq.Mock``1[Namespace.Class+IElement] Mock
Moq.Mock Mock
The code to reproduce this is below:
public void Moq_Reflection() {
var realElement = new Stuff();
// Produces 2 items
PropertyInfo[] pInfo = realElement.GetType().GetProperties();
var mockElement = new Mock<IElement>();
mockElement.Setup(e => e.Property1).Returns(12);
mockElement.Setup(e => e.Property2).Returns(42);
// Produces 4 items
pInfo = mockElement.Object.GetType().GetProperties();
}
public interface IElement {
int Property1 { get; set; }
int Property2 { get; set; }
}
public class Stuff : IElement
{
public int Property1
{
get { return -1; }
set { }
}
public int Property2
{
get { return -2; }
set { }
}
}
Is there a way to Reflect on a Moq object and not retrieve these properties?
I was thinking about this more this afternoon, so here's another idea.
If I were coding this in my own project, I'd abstract out the reflection of the object. I'd create an interface that defines a contract for a class that will return the properties of an object, and then create a class that implements that interface by using reflection to return the set of properties. Same as what you're probably doing.
But then in the tests, I'd create a new implementation of the interface, but I'd add in whatever rules I needed to filter out unwanted properties on my mock objects. My live code wouldn't include any of the code necessary for testing.
I just had to get that idea out, just trying to help. Good luck!
I took a look at the code in LinqPad, and the only solution I could find to cut those two properties out was to exclude them based on whether PropertyType or Name included "Mock". For example:
pInfo.Where(item => item.PropertyType.ToString().Contains("Mock") == false);
pInfo.Where(item => item.Name.Contains("Mock") == false);
It's borderline hacky, but it's the only attribute I can find to filter. I don't think there's a way to filter the reflection itself.
Related
I'm using MoQ in C# to do some Unit tests/BDD tests, and I've often the need of generating the same object twice(because it will be potentially used in dictionary). Or something 99% the same but just with a different ID.
Is there a way to "clone" the Mock definition? Or to generate two objects with the same definition?
You should create a helper method that constructs that takes in some parameters to construct the Mock object.
[Test]
public void MyTest()
{
Mock<ITestObject> myMock = CreateObject(1);
ITestObject obj = myMock.Object;
}
private Mock<ITestObject> CreateObject(int id)
{
Mock<ITestObject> mock = new Mock<ITestObject>();
mock.SetupGet(o => o.ID).Returns(id);
return mock;
}
private interface ITestObject
{
int ID { get; set; }
}
If you just need a collection of data to unit test with, you may consider something like AutoFixture as well. It can work with Moq in the case of classes you want to mock. You teach AutoFixture how to create YourClass, and you can even set rules like "my IDs should be strings with capital letters and no more than X amount of them."
Then you'd just use autofixture.
var fixture = new Fixture();
var tetsClasses = fixture.CreateMany<TestClass>();
This is really just to give you an idea. You can do quite a but more with it, and it plays really well with Moq.
An alternative is to use a data builder pattern to create your data. So you could start with something simple and just keep adding onto it as you find new edge cases on how you need to build the data. Just build a fluent API on it and build the data however you want.
internal class TestClassBuilder<T> : where T : TestClass
{
int Id {get; set;}
public T WithId(int id)
{
this.Id = id;
return this;
}
public virtual T Build()
{
return new T()
{
if(this.Id)
Id = this.Id; // if you chose to set it, then assign it
else
Id = GetRandomId() // you can figure a solution here
}
}
}
Then call it like:
var stubOne = TestClassBuilder.WithId(1).Build();
You can extend it to build a list if you want.
I like fluent APIs on data builders, because you can start to tell your story with the methods you create, and it keeps your Arrange section neat and tidy.
Example:
var UnderAgeCustomer = new CustomerBuilder
.UnderAge
.WithFakeId
.InACrowd
.LooksYoung
.Build()
You could even add on
public static implicit operator T(TestClassBuilder<T> builder)
{
return builder.Build();
}
And you wouldn't need to use the .Build() part all the time (I think build adds unnecessary noise). Just don't try assigning that to a var, it won't work.
TestClass MockTwo = TestClassBuilder.WithId(2);
I would say you could also use a fixture pattern to track of all this ... but between that and the databuilder, you may as well use AutoFixture and Moq as I suggested :)
Update 1: for reasons I won't go into, I want to avoid having anything other than the properties to be persisted in my entity objects. This means no extra properties or methods...
I have an entity called Entity1 with (say) 10 public properties. In
one place in my code I want to output serialized JSON with (say) 3 of
those fields, in a second place I need to output 7 fields and in a
third place I might need to output (say) all 10 fields. How do I do
this using Newtonsoft's JSON library?
I can't use [JsonIgnore] or [DataMember] as that will apply to all
cases, so I won't be able to create "custom views" of the data (my own
terminology :-).
I tried to achieve this using an interface:
public interface Entity1View1
{
string Property1;
string Property2;
string Property5;
}
had Entity1 implement Entity1View1 and I passed an
IList<Entity1View1> to the JSON serializer (the objects were
actually just Entity1 objects). Didn't work: the serializer output
all the 10 public properties of Entity1.
The only other way I could think of was to implement
Entity1Wrapper1, Entity1Wrapper2 etc. type of classes where each
object would hold a corresponding instance of Entity1 and in turn
expose only those public properties that correspond to the properties
I want to show in "View1", "View2" etc. Then I pass lists of these
wrapper objects to the serializer (should work, haven't tried it yet).
Is there a better way?
If it matters, here's my configuration:
.Net 4.5
MVC 5
Don't know it that's the best way... but that's one.
One good point is that it will work either with json serialization or xml serialization, for example (which you may don't mind at all).
You can use ShouldSerialize<yourpropertyName> to manage what is serialized or not. <yourpropertyName> must match exactly the name of the property you wanna manage.
For example
public class Entity {
//assuming you want the default behavior to be "serialize all properties"
public Entity() {
ShouldSerializeProperty1 = true;
ShouldSerializeProperty2 = true;
ShouldSerializeProperty3 = true;
}
public string Property1 {get;set;}
public bool ShouldSerializeProperty1 {get;set;}
public string Property2 {get;set;}
public bool ShouldSerializeProperty2 {get;set;}
public int Property3 {get;set;}
public bool ShouldSerializeProperty3 {get;set;}
}
Then you could do, before all your serialization (of course, this could / should be extension methods).
var list = myListOfEntity;
//serialization1
foreach (var element in list) {
element.ShouldSerializeProperty3 = false;
}
//or serialization2
foreach (var element in list) {
element.ShouldSerializeProperty2 = false;
element.ShouldSerializeProperty3 = false;
}
I just wanted to make sure that this was the final step in processing.
You can create anonymous objects to serialize based on circumstance:
var json1Source1 = new {
Property1 = entityView1.Property1,
Property3 = entityView1.Property3
};
var json1Source2 = new {
Property2 = entityView1.Property2,
Property3 = entityView1.Property3
};
You can create jsonSource1 (or 2, 3, 4 etc) as anonymous objects that capture just what you need and then serialize them. The serializer will not care that they are anonymous.
Update 1:
To conditionally serialize a property, add a method that returns boolean with the same name as the property and then prefix the method name with ShouldSerialize..
This means that the solution suggested by Raphaël Althaus doesn't work as it relies on properties, whereas the serializer's documentation mentions that it has to be a method. I have verified that only a method returning a bool works as expected.
Original:
I finally went with a mix of Wrapper classes and the methodology suggested by Raphaël Althaus (with modifications): use Wrappers where some amount of sophistication may be required and use Raphaël's suggestion when simplicity will do.
Here's how I am using wrappers (intentionally left out null checks):
public class Entity1View1
{
protected Entity1 wrapped;
public Entity1View1(Entity1 entity)
{
wrapped = entity;
}
public String Property1
{
get { return wrapped.Property1; }
}
public String Property2
{
get { return wrapped.Property2; }
}
public String Property3
{
get { return wrapped.Property3.ToUpper(); }
}
}
This allows me to modify properties as their values are returned (as done with Property3 above) and lets me leverage inheritance to create new ways of serialization. For example, I can flatten the structure/hierarchy:
public class Entity1View2 : Entity1View1
{
pulic Entity1View2(Entity1 entity) : base(entity) { }
public long? SubEntityID
{
get { return wrapped.SubEntity.ID; }
}
}
For simpler cases where complexity/transformation of this sort is not required, I can simply use the ShouldSerialize* methods.
Same entity classes, different serialization outputs.
This page on the PostSharp website has the following teaser:
One of the common situations that you will encounter is the need to implement a specific interface on a large number of classes. This may be INotifyPropertyChanged, IDispose, IEquatable or some custom interface that you have created.
I'd like to write a custom aspect that implements a general version of IEquatable based on the properties of the class it's applied to (preferably at compile-time instead of by using reflection at runtime). It would be good to just be able to add an attribute to a simple class rather than having to implement a custom method each time. Is that possible? I'd hope so, since it's specifically called out in this introduction, but I haven't been able to track down any example code.
I've seen this example from the PostSharp website that includes an example of introducing the IIdentifiable interface. But it just returns a GUID that's independent of the class that the new interface is added to.
Is there a way to construct a custom attribute that implements IEquatable based on the properties of the type that it's applied to (i.e. making two instances equal if all of their properties are equal)?
I've found a solution using T4 templates but would like to know if the same can be achieved using PostSharp.
Edit:
To be clear, I'd like to be able to write something like this:
[AutoEquatable]
public class Thing
{
int Id { get; set; }
string Description { get; get; }
}
and have it automatically converted to this:
public class Thing
{
int Id { get; set; }
string Description { get; get; }
public override bool Equals(object other)
{
Thing o = other as Thing;
if (o == null) return false;
// generated in a loop based on the properties
if (!Id.Equals(o.Id)) return false;
if (!Description.Equals(o.Description)) return false;
return true;
}
}
This is possible with PostSharp 4.0 using the following code;
[PSerializable]
class EquatableAttribute : InstanceLevelAspect, IAdviceProvider
{
public List<ILocationBinding> Fields;
[ImportMember("Equals", IsRequired = true, Order = ImportMemberOrder.BeforeIntroductions)]
public Func<object, bool> EqualsBaseMethod;
[IntroduceMember(IsVirtual = true, OverrideAction = MemberOverrideAction.OverrideOrFail)]
public new bool Equals(object other)
{
// TODO: Define a smarter way to determine if base.Equals should be invoked.
if (this.EqualsBaseMethod.Method.DeclaringType != typeof(object) )
{
if (!this.EqualsBaseMethod(other))
return false;
}
object instance = this.Instance;
foreach (ILocationBinding binding in this.Fields)
{
// The following code is inefficient because it boxes all fields. There is currently no workaround.
object thisFieldValue = binding.GetValue(ref instance, Arguments.Empty);
object otherFieldValue = binding.GetValue(ref other, Arguments.Empty);
if (!object.Equals(thisFieldValue, otherFieldValue))
return false;
}
return true;
}
// TODO: Implement GetHashCode the same way.
public IEnumerable<AdviceInstance> ProvideAdvices(object targetElement)
{
Type targetType = (Type) targetElement;
FieldInfo bindingField = this.GetType().GetField("Fields");
foreach (
FieldInfo field in
targetType.GetFields(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Public |
BindingFlags.NonPublic))
{
yield return new ImportLocationAdviceInstance(bindingField, new LocationInfo(field));
}
}
}
I'm afraid this can not be done with PostSharp. PostSharp "injects" aspects code in your clases but you have to code the aspects. The key here is indetify common behavior and cross cutting concern in your system and model it as Aspects.
In the example of IIdentifiable you can see how GUID is a unique identifier that can be use by a lot of different classes in your system. It is common code, it is cross cutting concern and you find yourself REPEATING code in all your class entities so Identificable can be modeled as Aspect and get rid of repeating code.
As diferent classes has diferent Equals implementation you can not "deatach" (convert to aspect) the implementation of Equals. Equals is not a common behavior. Equals is not cross cutting concern. Equals can not be an Aspect (without reflection).
I'm looking to customize the creation-time behavior of AutoFixture such that I can set up some dependent objects after the properties of the fixture have been generated and assigned.
For example, suppose I have a method that customizes a User because its IsDeleted property always has to be false for a certain set of tests:
public class User
{
public int Id { get; set; }
public string Name { get; set; }
public bool IsDeleted { get; set; }
}
public static ObjectBuilder<User> BuildUser(this Fixture f)
{
return f.Build<User>().With(u => u.IsDeleted, false);
}
(I hand an ObjectBuilder back to the test so it can further customize the fixture if necessary.)
What I'd like to do is automatically associate that user with an anonymous collection by its Id at creation time, but I can't do this as-is because Id has not been generated by the time I hand the return value back to the unit test proper. Here's the sort of thing I'm trying to do:
public static ObjectBuilder<User> BuildUserIn(this Fixture f, UserCollection uc)
{
return f.Build<User>()
.With(u => u.IsDeleted, false);
.AfterCreation(u =>
{
var relation = f.Build<UserCollectionMembership>()
.With(ucm => ucm.UserCollectionId, uc.Id)
.With(ucm => ucm.UserId, u.Id)
.CreateAnonymous();
Repository.Install(relation);
}
}
Is something like this possible? Or perhaps there is a better way to accomplish my goal of creating an anonymous object graph?
For the Build method, this isn't possible, and probably never will be, because there are much better options available.
First of all, it should never be necessary to write static helper methods around the Build method. The Build method is for truly one-off initializations where one needs to define property or field values before the fact.
I.e. imagine a class like this:
public class MyClass
{
private string txt;
public string SomeWeirdText
{
get { return this.txt; }
set
{
if (value != "bar")
throw new ArgumentException();
this.txt = value;
}
}
}
In this (contrived) example, a straight fixture.CreateAnonymous<MyClass> is going to throw because it's going to attempt to assign something other than "bar" to the property.
In a one-off scenario, one can use the Build method to escape this problem. One example is simply to set the value explicitly to "bar":
var mc =
fixture.Build<MyClass>().With(x => x.SomeWeirdText, "bar").CreateAnonymous();
However, even easier would be to just omit that property:
var mc =
fixture.Build<MyClass>().Without(x => x.SomeWeirdText).CreateAnonymous();
However, once you start wanting to do this repeatedly, there are better options. AutoFixture has a very sophisticated and customizable engine for defining how things get created.
As a start, one could start by moving the omission of the property into a customization, like this:
fixture.Customize<MyClass>(c => c.Without(x => x.SomeWeirdText));
Now, whenever the fixture creates an instance of MyClass, it's just going to skip that property altogether. You can still assign a value afterwards:
var mc = fixture.CreateAnonymous<MyClass>();
my.SomeWeirdText = "bar";
If you want something more sophisticated, you can implement a custom ISpecimenBuilder. If you want to run some custom code after the instance has been created, you can decorate your own ISpecimenBuilder with a Postprocessor and supply a delegate. That might look something like this:
fixture.Customizations.Add(
new Postprocessor(yourCustomSpecimenBuilder, obj =>
{ */ do something to obj here */ }));
(BTW, are you still on AutoFixture 1.0? IIRC, there hasn't been an ObjectBuilder<T> around since then...)
There's a useful discussion on this topic on the AutoFixture CodePlex site.
I believe my postprocessor Customization linked over there should help you. Example usage:
class AutoControllerDataAttribute : AutoDataAttribute
{
public AutoControllerDataAttribute()
: this( new Fixture() )
{
}
public AutoControllerDataAttribute( IFixture fixture )
: base( fixture )
{
fixture.Customize( new AutoMoqCustomization() );
fixture.Customize( new ApplyControllerContextCustomization() );
}
class ApplyControllerContextCustomization : PostProcessWhereIsACustomization<Controller>
{
public ApplyControllerContextCustomization()
: base( PostProcess )
{
}
static void PostProcess( Controller controller )
{
controller.FakeControllerContext();
// etc. - add stuff you want to happen after the instance has been created
Background: I have a form ViewModel with 7 properties, each ViewModel representing sections of a wizard, and all implement IFormSection. I'm trying to use a single definition (i.e. DRY/SPoT) for these ViewModels between multi-section AJAX clients and single-section JavaScript-disabled clients.
It's important to have these accessible as properties so the automated serialization/deserialization works (i.e. ASP.NET MVC model binding), and those properties must also be individually nullable to indicate unsubmitted sections.
But I also have 6-10 occasions to iterate through these serializable properties with common IFormSection operations, in some cases in an ordered fashion. So how can I store this list of properties for reuse? EDIT: This includes batch new()ing them up in a full load operation.
For example, maybe the end result looks something like:
interface IFormSection {
void Load();
void Save();
bool Validate();
IFormSection GetNextSection(); // It's ok if this has to be done via ISectionManager
string DisplayName; // e.g. "Contact Information"
string AssociatedViewModelName; // e.g. "ContactInformation"
}
interface ISectionManager {
void LoadAllSections(); // EDIT: added this to clarify a desired use.
IFormSection GetRequestedSection(string name); // Users can navigate to a specific section
List<IFormSection> GetSections(bool? ValidityFilter = null);
// I'd use the above List to get the first invalid section
// (since a new user cannot proceed past an invalid section),
// also to get a list of sections to call .Save on,
// also to .Load and render all sections.
}
interface IFormTopLevel {
// Bindable properties
IFormSection ProfileContactInformation { get; set; }
IFormSection Page2 { get; set; }
IFormSection Page3 { get; set; }
IFormSection Page4 { get; set; }
IFormSection Page5 { get; set; }
IFormSection Page6 { get; set; }
IFormSection Page7 { get; set; }
}
I'm running into problems where I can't have abstract static methods, resulting in too many reflection calls or generics to do stupid stuff, and other problems that just make my whole thought process smell bad.
Help?
p.s.
I accept I may be overlooking a much simpler design involving delegates or something. I also realize I have SoC issues here, not all of which are a result of summarizing the problem for StackOverflow.
If the order is constant, you can have a property or method returning IEnumerable<object>; then yield return each property value... or IEnumerable<Tuple<string,object>>... which you can iterate over later.
Something super simple like:
private IEnumerable<Tuple<string,object>> GetProps1()
{
yield return Tuple.Create("Property1", Property1);
yield return Tuple.Create("Property2", Property2);
yield return Tuple.Create("Property3", Property3);
}
if you wanted a more generic approach doing the same thing, you can use reflection:
private IEnumerable<Tuple<string,object>> GetProps2(){
var properties = this.GetType().GetProperties();
return properties.Select(p=>Tuple.Create(p.Name, p.GetValue(this, null)));
}
or, idk? an extension method maybe?
private static IEnumerable<Tuple<string,object>> GetProps3(this object obj){
var properties = obj.GetType().GetProperties();
return properties.Select(p=>Tuple.Create(p.Name, p.GetValue(obj, null)));
}