From ef7f55d58d60bd871aeb66eeae5e7f07cd7ed029 Mon Sep 17 00:00:00 2001 From: Nykolas Lima Date: Wed, 28 Jan 2015 19:39:53 -0200 Subject: [PATCH 1/3] fixing template where we want to override nested attribute value --- .../six2six/fixturefactory/ObjectFactory.java | 40 +++++++++++++++---- .../fixturefactory/FixtureImmutableTest.java | 10 +++++ 2 files changed, 43 insertions(+), 7 deletions(-) diff --git a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java index c13978b..a316d67 100755 --- a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java +++ b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java @@ -4,6 +4,7 @@ import java.util.Arrays; import java.util.Collection; import java.util.HashMap; +import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; @@ -88,7 +89,7 @@ public List gimme(int quantity, String label, Rule propertiesToOverride) } protected Object createObject(Rule rule) { - Map constructorArguments = new HashMap(); + Map constructorArguments = new HashMap(); List deferredProperties = new ArrayList(); Class clazz = templateHolder.getClazz(); @@ -96,8 +97,8 @@ protected Object createObject(Rule rule) { lookupConstructorParameterNames(clazz, rule.getProperties()) : new ArrayList(); for (Property property : rule.getProperties()) { - if (parameterNames.contains(property.getRootAttribute())) { - constructorArguments.put(property.getName(), generateConstructorParamValue(property)); + if(parameterNames.contains(property.getRootAttribute())) { + constructorArguments.put(property.getName(), property); } else { deferredProperties.add(property); } @@ -105,6 +106,11 @@ protected Object createObject(Rule rule) { Object result = ReflectionUtils.newInstance(clazz, processConstructorArguments(parameterNames, constructorArguments)); + Set propertiesNotUsedInConstructor = getPropertiesNotUsedInConstructor(constructorArguments, parameterNames); + if(propertiesNotUsedInConstructor.size() > 0) { + deferredProperties.addAll(propertiesNotUsedInConstructor); + } + for (Property property : deferredProperties) { ReflectionUtils.invokeRecursiveSetter(result, property.getName(), processPropertyValue(result, property)); } @@ -114,6 +120,16 @@ protected Object createObject(Rule rule) { } return result; } + + private Set getPropertiesNotUsedInConstructor(Map constructorArguments, List parameterNames) { + Set propertiesNotUsedInConstructor = new HashSet(constructorArguments.values()); + Set parameterProperties = new HashSet(); + for(String parameterName : parameterNames) { + parameterProperties.add(new Property(parameterName, "fakeValue")); + } + propertiesNotUsedInConstructor.removeAll(parameterProperties); + return propertiesNotUsedInConstructor; + } @SuppressWarnings("unchecked") protected List createObjects(int quantity, Rule rule) { @@ -166,25 +182,35 @@ private Object generateConstructorParamValue(Property property) { } } - protected List processConstructorArguments(List parameterNames, Map arguments) { + protected List processConstructorArguments(List parameterNames, Map arguments) { List values = new ArrayList(); + Map processedArguments = processArguments(arguments); if (owner != null && ReflectionUtils.isInnerClass(templateHolder.getClazz())) { values.add(owner); } - TransformerChain transformerChain = buildTransformerChain(new ParameterPlaceholderTransformer(arguments)); + TransformerChain transformerChain = buildTransformerChain(new ParameterPlaceholderTransformer(processedArguments)); for (String parameterName : parameterNames) { Class fieldType = ReflectionUtils.invokeRecursiveType(templateHolder.getClazz(), parameterName); - Object result = arguments.get(parameterName); + Object result = processedArguments.get(parameterName); if (result == null) { - result = processChainedProperty(parameterName, fieldType, arguments); + result = processChainedProperty(parameterName, fieldType, processedArguments); } values.add(transformerChain.transform(result, fieldType)); } return values; } + + private Map processArguments(Map arguments) { + Map processedArguments = new HashMap(); + for(String key : arguments.keySet()) { + processedArguments.put(key, generateConstructorParamValue(arguments.get(key))); + } + + return processedArguments; + } protected Object processChainedProperty(String parameterName, Class fieldType, Map arguments) { Rule rule = new Rule(); diff --git a/src/test/java/br/com/six2six/fixturefactory/FixtureImmutableTest.java b/src/test/java/br/com/six2six/fixturefactory/FixtureImmutableTest.java index 6d72ba4..976fd2d 100644 --- a/src/test/java/br/com/six2six/fixturefactory/FixtureImmutableTest.java +++ b/src/test/java/br/com/six2six/fixturefactory/FixtureImmutableTest.java @@ -96,4 +96,14 @@ public void shouldWorkWhenChainingInheritedProperty() { assertThat(child.getParentAttribute().getValue().length(), is(8)); assertThat(child.getChildAttribute().length(), is(16)); } + + @Test + public void shouldOverrideNestedObjectAttribute() { + Immutable result = Fixture.from(Immutable.class).gimme("fullConstructor", new Rule() {{ + add("address.street", "Rua do Nykolas"); + }}); + + assertThat(result.getAddress().getStreet(), equalTo("Rua do Nykolas")); + } + } From d4cb02e2fc474db5dff3507abf4d9296b29462b0 Mon Sep 17 00:00:00 2001 From: Nykolas Lima Date: Wed, 28 Jan 2015 21:16:34 -0200 Subject: [PATCH 2/3] improving code --- .../java/br/com/six2six/fixturefactory/ObjectFactory.java | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java index a316d67..f51daa8 100755 --- a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java +++ b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java @@ -122,13 +122,11 @@ protected Object createObject(Rule rule) { } private Set getPropertiesNotUsedInConstructor(Map constructorArguments, List parameterNames) { - Set propertiesNotUsedInConstructor = new HashSet(constructorArguments.values()); - Set parameterProperties = new HashSet(); + Map propertiesNotUsedInConstructor = new HashMap(constructorArguments); for(String parameterName : parameterNames) { - parameterProperties.add(new Property(parameterName, "fakeValue")); + propertiesNotUsedInConstructor.remove(parameterName); } - propertiesNotUsedInConstructor.removeAll(parameterProperties); - return propertiesNotUsedInConstructor; + return new HashSet(propertiesNotUsedInConstructor.values()); } @SuppressWarnings("unchecked") From d769370ec59ab03ebda889d3ab27149b2dccfb8b Mon Sep 17 00:00:00 2001 From: Nykolas Lima Date: Wed, 28 Jan 2015 22:33:13 -0200 Subject: [PATCH 3/3] improving map iteration --- .../java/br/com/six2six/fixturefactory/ObjectFactory.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java index f51daa8..a44d382 100755 --- a/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java +++ b/src/main/java/br/com/six2six/fixturefactory/ObjectFactory.java @@ -7,6 +7,7 @@ import java.util.HashSet; import java.util.List; import java.util.Map; +import java.util.Map.Entry; import java.util.Set; import org.apache.commons.lang.StringUtils; @@ -203,8 +204,8 @@ protected List processConstructorArguments(List parameterNames, private Map processArguments(Map arguments) { Map processedArguments = new HashMap(); - for(String key : arguments.keySet()) { - processedArguments.put(key, generateConstructorParamValue(arguments.get(key))); + for(Entry entry : arguments.entrySet()) { + processedArguments.put(entry.getKey(), generateConstructorParamValue(entry.getValue())); } return processedArguments;