View Javadoc
1   /*
2    * Copyright 2002-2015 the original author or authors.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  
17  package org.springframework.beans.factory;
18  
19  import java.io.Closeable;
20  import java.lang.reflect.Field;
21  import java.net.MalformedURLException;
22  import java.security.AccessControlContext;
23  import java.security.AccessController;
24  import java.security.Principal;
25  import java.security.PrivilegedAction;
26  import java.text.NumberFormat;
27  import java.text.ParseException;
28  import java.util.Arrays;
29  import java.util.Iterator;
30  import java.util.List;
31  import java.util.Locale;
32  import java.util.Map;
33  import java.util.Properties;
34  import java.util.Set;
35  import javax.annotation.Priority;
36  import javax.security.auth.Subject;
37  
38  import org.apache.commons.logging.Log;
39  import org.apache.commons.logging.LogFactory;
40  import org.junit.Ignore;
41  import org.junit.Rule;
42  import org.junit.Test;
43  import org.junit.rules.ExpectedException;
44  import org.mockito.Matchers;
45  
46  import org.springframework.beans.BeansException;
47  import org.springframework.beans.MutablePropertyValues;
48  import org.springframework.beans.NotWritablePropertyException;
49  import org.springframework.beans.PropertyEditorRegistrar;
50  import org.springframework.beans.PropertyEditorRegistry;
51  import org.springframework.beans.PropertyValue;
52  import org.springframework.beans.TypeConverter;
53  import org.springframework.beans.TypeMismatchException;
54  import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
55  import org.springframework.beans.factory.config.BeanDefinition;
56  import org.springframework.beans.factory.config.BeanExpressionContext;
57  import org.springframework.beans.factory.config.BeanExpressionResolver;
58  import org.springframework.beans.factory.config.BeanPostProcessor;
59  import org.springframework.beans.factory.config.ConfigurableBeanFactory;
60  import org.springframework.beans.factory.config.ConstructorArgumentValues;
61  import org.springframework.beans.factory.config.InstantiationAwareBeanPostProcessorAdapter;
62  import org.springframework.beans.factory.config.PropertiesFactoryBean;
63  import org.springframework.beans.factory.config.RuntimeBeanReference;
64  import org.springframework.beans.factory.config.TypedStringValue;
65  import org.springframework.beans.factory.support.AbstractBeanDefinition;
66  import org.springframework.beans.factory.support.AbstractBeanFactory;
67  import org.springframework.beans.factory.support.BeanDefinitionBuilder;
68  import org.springframework.beans.factory.support.ChildBeanDefinition;
69  import org.springframework.beans.factory.support.DefaultListableBeanFactory;
70  import org.springframework.beans.factory.support.ManagedList;
71  import org.springframework.beans.factory.support.PropertiesBeanDefinitionReader;
72  import org.springframework.beans.factory.support.RootBeanDefinition;
73  import org.springframework.beans.factory.xml.ConstructorDependenciesBean;
74  import org.springframework.beans.propertyeditors.CustomNumberEditor;
75  import org.springframework.core.MethodParameter;
76  import org.springframework.core.annotation.AnnotationAwareOrderComparator;
77  import org.springframework.core.convert.converter.Converter;
78  import org.springframework.core.convert.support.DefaultConversionService;
79  import org.springframework.core.convert.support.GenericConversionService;
80  import org.springframework.core.io.Resource;
81  import org.springframework.core.io.UrlResource;
82  import org.springframework.tests.Assume;
83  import org.springframework.tests.TestGroup;
84  import org.springframework.tests.sample.beans.DependenciesBean;
85  import org.springframework.tests.sample.beans.DerivedTestBean;
86  import org.springframework.tests.sample.beans.ITestBean;
87  import org.springframework.tests.sample.beans.LifecycleBean;
88  import org.springframework.tests.sample.beans.NestedTestBean;
89  import org.springframework.tests.sample.beans.SideEffectBean;
90  import org.springframework.tests.sample.beans.TestBean;
91  import org.springframework.tests.sample.beans.factory.DummyFactory;
92  import org.springframework.util.StopWatch;
93  import org.springframework.util.StringValueResolver;
94  
95  import static org.hamcrest.Matchers.*;
96  import static org.junit.Assert.*;
97  import static org.mockito.BDDMockito.*;
98  
99  /**
100  * Tests properties population and autowire behavior.
101  *
102  * @author Rod Johnson
103  * @author Juergen Hoeller
104  * @author Rick Evans
105  * @author Sam Brannen
106  * @author Chris Beams
107  * @author Phillip Webb
108  * @author Stephane Nicoll
109  */
110 public class DefaultListableBeanFactoryTests {
111 
112 	private static final Log factoryLog = LogFactory.getLog(DefaultListableBeanFactory.class);
113 
114 
115 	@Rule
116 	public ExpectedException thrown = ExpectedException.none();
117 
118 
119 	@Test
120 	public void testUnreferencedSingletonWasInstantiated() {
121 		KnowsIfInstantiated.clearInstantiationRecord();
122 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
123 		Properties p = new Properties();
124 		p.setProperty("x1.(class)", KnowsIfInstantiated.class.getName());
125 		assertTrue("singleton not instantiated", !KnowsIfInstantiated.wasInstantiated());
126 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
127 		lbf.preInstantiateSingletons();
128 		assertTrue("singleton was instantiated", KnowsIfInstantiated.wasInstantiated());
129 	}
130 
131 	@Test
132 	public void testLazyInitialization() {
133 		KnowsIfInstantiated.clearInstantiationRecord();
134 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
135 		Properties p = new Properties();
136 		p.setProperty("x1.(class)", KnowsIfInstantiated.class.getName());
137 		p.setProperty("x1.(lazy-init)", "true");
138 		assertTrue("singleton not instantiated", !KnowsIfInstantiated.wasInstantiated());
139 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
140 		assertTrue("singleton not instantiated", !KnowsIfInstantiated.wasInstantiated());
141 		lbf.preInstantiateSingletons();
142 
143 		assertTrue("singleton not instantiated", !KnowsIfInstantiated.wasInstantiated());
144 		lbf.getBean("x1");
145 		assertTrue("singleton was instantiated", KnowsIfInstantiated.wasInstantiated());
146 	}
147 
148 	@Test
149 	public void testFactoryBeanDidNotCreatePrototype() {
150 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
151 		Properties p = new Properties();
152 		p.setProperty("x1.(class)", DummyFactory.class.getName());
153 		// Reset static state
154 		DummyFactory.reset();
155 		p.setProperty("x1.singleton", "false");
156 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
157 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
158 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
159 		assertEquals(TestBean.class, lbf.getType("x1"));
160 		lbf.preInstantiateSingletons();
161 
162 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
163 		lbf.getBean("x1");
164 		assertEquals(TestBean.class, lbf.getType("x1"));
165 		assertTrue(lbf.containsBean("x1"));
166 		assertTrue(lbf.containsBean("&x1"));
167 		assertTrue("prototype was instantiated", DummyFactory.wasPrototypeCreated());
168 	}
169 
170 	@Test
171 	public void testPrototypeFactoryBeanIgnoredByNonEagerTypeMatching() {
172 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
173 		Properties p = new Properties();
174 		p.setProperty("x1.(class)", DummyFactory.class.getName());
175 		// Reset static state
176 		DummyFactory.reset();
177 		p.setProperty("x1.(singleton)", "false");
178 		p.setProperty("x1.singleton", "false");
179 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
180 
181 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
182 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
183 		assertEquals(0, beanNames.length);
184 		beanNames = lbf.getBeanNamesForAnnotation(SuppressWarnings.class);
185 		assertEquals(0, beanNames.length);
186 
187 		assertFalse(lbf.containsSingleton("x1"));
188 		assertTrue(lbf.containsBean("x1"));
189 		assertTrue(lbf.containsBean("&x1"));
190 		assertFalse(lbf.isSingleton("x1"));
191 		assertFalse(lbf.isSingleton("&x1"));
192 		assertTrue(lbf.isPrototype("x1"));
193 		assertTrue(lbf.isPrototype("&x1"));
194 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
195 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
196 		assertTrue(lbf.isTypeMatch("&x1", DummyFactory.class));
197 		assertEquals(TestBean.class, lbf.getType("x1"));
198 		assertEquals(DummyFactory.class, lbf.getType("&x1"));
199 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
200 	}
201 
202 	@Test
203 	public void testSingletonFactoryBeanIgnoredByNonEagerTypeMatching() {
204 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
205 		Properties p = new Properties();
206 		p.setProperty("x1.(class)", DummyFactory.class.getName());
207 		// Reset static state
208 		DummyFactory.reset();
209 		p.setProperty("x1.(singleton)", "false");
210 		p.setProperty("x1.singleton", "true");
211 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
212 
213 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
214 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
215 		assertEquals(0, beanNames.length);
216 		beanNames = lbf.getBeanNamesForAnnotation(SuppressWarnings.class);
217 		assertEquals(0, beanNames.length);
218 
219 		assertFalse(lbf.containsSingleton("x1"));
220 		assertTrue(lbf.containsBean("x1"));
221 		assertTrue(lbf.containsBean("&x1"));
222 		assertFalse(lbf.isSingleton("x1"));
223 		assertFalse(lbf.isSingleton("&x1"));
224 		assertTrue(lbf.isPrototype("x1"));
225 		assertTrue(lbf.isPrototype("&x1"));
226 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
227 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
228 		assertTrue(lbf.isTypeMatch("&x1", DummyFactory.class));
229 		assertEquals(TestBean.class, lbf.getType("x1"));
230 		assertEquals(DummyFactory.class, lbf.getType("&x1"));
231 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
232 	}
233 
234 	@Test
235 	public void testNonInitializedFactoryBeanIgnoredByNonEagerTypeMatching() {
236 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
237 		Properties p = new Properties();
238 		p.setProperty("x1.(class)", DummyFactory.class.getName());
239 		// Reset static state
240 		DummyFactory.reset();
241 		p.setProperty("x1.singleton", "false");
242 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
243 
244 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
245 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
246 		assertEquals(0, beanNames.length);
247 		beanNames = lbf.getBeanNamesForAnnotation(SuppressWarnings.class);
248 		assertEquals(0, beanNames.length);
249 
250 		assertFalse(lbf.containsSingleton("x1"));
251 		assertTrue(lbf.containsBean("x1"));
252 		assertTrue(lbf.containsBean("&x1"));
253 		assertFalse(lbf.isSingleton("x1"));
254 		assertTrue(lbf.isSingleton("&x1"));
255 		assertTrue(lbf.isPrototype("x1"));
256 		assertFalse(lbf.isPrototype("&x1"));
257 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
258 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
259 		assertTrue(lbf.isTypeMatch("&x1", DummyFactory.class));
260 		assertEquals(TestBean.class, lbf.getType("x1"));
261 		assertEquals(DummyFactory.class, lbf.getType("&x1"));
262 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
263 	}
264 
265 	@Test
266 	public void testInitializedFactoryBeanFoundByNonEagerTypeMatching() {
267 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
268 		Properties p = new Properties();
269 		p.setProperty("x1.(class)", DummyFactory.class.getName());
270 		// Reset static state
271 		DummyFactory.reset();
272 		p.setProperty("x1.singleton", "false");
273 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
274 		lbf.preInstantiateSingletons();
275 
276 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
277 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
278 		assertEquals(1, beanNames.length);
279 		assertEquals("x1", beanNames[0]);
280 		assertTrue(lbf.containsSingleton("x1"));
281 		assertTrue(lbf.containsBean("x1"));
282 		assertTrue(lbf.containsBean("&x1"));
283 		assertTrue(lbf.containsLocalBean("x1"));
284 		assertTrue(lbf.containsLocalBean("&x1"));
285 		assertFalse(lbf.isSingleton("x1"));
286 		assertTrue(lbf.isSingleton("&x1"));
287 		assertTrue(lbf.isPrototype("x1"));
288 		assertFalse(lbf.isPrototype("&x1"));
289 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
290 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
291 		assertTrue(lbf.isTypeMatch("&x1", DummyFactory.class));
292 		assertTrue(lbf.isTypeMatch("x1", Object.class));
293 		assertTrue(lbf.isTypeMatch("&x1", Object.class));
294 		assertEquals(TestBean.class, lbf.getType("x1"));
295 		assertEquals(DummyFactory.class, lbf.getType("&x1"));
296 		assertTrue("prototype not instantiated", !DummyFactory.wasPrototypeCreated());
297 
298 		lbf.registerAlias("x1", "x2");
299 		assertTrue(lbf.containsBean("x2"));
300 		assertTrue(lbf.containsBean("&x2"));
301 		assertTrue(lbf.containsLocalBean("x2"));
302 		assertTrue(lbf.containsLocalBean("&x2"));
303 		assertFalse(lbf.isSingleton("x2"));
304 		assertTrue(lbf.isSingleton("&x2"));
305 		assertTrue(lbf.isPrototype("x2"));
306 		assertFalse(lbf.isPrototype("&x2"));
307 		assertTrue(lbf.isTypeMatch("x2", TestBean.class));
308 		assertFalse(lbf.isTypeMatch("&x2", TestBean.class));
309 		assertTrue(lbf.isTypeMatch("&x2", DummyFactory.class));
310 		assertTrue(lbf.isTypeMatch("x2", Object.class));
311 		assertTrue(lbf.isTypeMatch("&x2", Object.class));
312 		assertEquals(TestBean.class, lbf.getType("x2"));
313 		assertEquals(DummyFactory.class, lbf.getType("&x2"));
314 		assertEquals(1, lbf.getAliases("x1").length);
315 		assertEquals("x2", lbf.getAliases("x1")[0]);
316 		assertEquals(1, lbf.getAliases("&x1").length);
317 		assertEquals("&x2", lbf.getAliases("&x1")[0]);
318 		assertEquals(1, lbf.getAliases("x2").length);
319 		assertEquals("x1", lbf.getAliases("x2")[0]);
320 		assertEquals(1, lbf.getAliases("&x2").length);
321 		assertEquals("&x1", lbf.getAliases("&x2")[0]);
322 	}
323 
324 	@Test
325 	public void testStaticFactoryMethodFoundByNonEagerTypeMatching() {
326 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
327 		RootBeanDefinition rbd = new RootBeanDefinition(TestBeanFactory.class);
328 		rbd.setFactoryMethodName("createTestBean");
329 		lbf.registerBeanDefinition("x1", rbd);
330 
331 		TestBeanFactory.initialized = false;
332 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
333 		assertEquals(1, beanNames.length);
334 		assertEquals("x1", beanNames[0]);
335 		assertFalse(lbf.containsSingleton("x1"));
336 		assertTrue(lbf.containsBean("x1"));
337 		assertFalse(lbf.containsBean("&x1"));
338 		assertTrue(lbf.isSingleton("x1"));
339 		assertFalse(lbf.isSingleton("&x1"));
340 		assertFalse(lbf.isPrototype("x1"));
341 		assertFalse(lbf.isPrototype("&x1"));
342 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
343 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
344 		assertEquals(TestBean.class, lbf.getType("x1"));
345 		assertEquals(null, lbf.getType("&x1"));
346 		assertFalse(TestBeanFactory.initialized);
347 	}
348 
349 	@Test
350 	public void testStaticPrototypeFactoryMethodFoundByNonEagerTypeMatching() {
351 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
352 		RootBeanDefinition rbd = new RootBeanDefinition(TestBeanFactory.class);
353 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
354 		rbd.setFactoryMethodName("createTestBean");
355 		lbf.registerBeanDefinition("x1", rbd);
356 
357 		TestBeanFactory.initialized = false;
358 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
359 		assertEquals(1, beanNames.length);
360 		assertEquals("x1", beanNames[0]);
361 		assertFalse(lbf.containsSingleton("x1"));
362 		assertTrue(lbf.containsBean("x1"));
363 		assertFalse(lbf.containsBean("&x1"));
364 		assertFalse(lbf.isSingleton("x1"));
365 		assertFalse(lbf.isSingleton("&x1"));
366 		assertTrue(lbf.isPrototype("x1"));
367 		assertFalse(lbf.isPrototype("&x1"));
368 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
369 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
370 		assertEquals(TestBean.class, lbf.getType("x1"));
371 		assertEquals(null, lbf.getType("&x1"));
372 		assertFalse(TestBeanFactory.initialized);
373 	}
374 
375 	@Test
376 	public void testNonStaticFactoryMethodFoundByNonEagerTypeMatching() {
377 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
378 		RootBeanDefinition factoryBd = new RootBeanDefinition(TestBeanFactory.class);
379 		lbf.registerBeanDefinition("factory", factoryBd);
380 		RootBeanDefinition rbd = new RootBeanDefinition(TestBeanFactory.class);
381 		rbd.setFactoryBeanName("factory");
382 		rbd.setFactoryMethodName("createTestBeanNonStatic");
383 		lbf.registerBeanDefinition("x1", rbd);
384 
385 		TestBeanFactory.initialized = false;
386 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
387 		assertEquals(1, beanNames.length);
388 		assertEquals("x1", beanNames[0]);
389 		assertFalse(lbf.containsSingleton("x1"));
390 		assertTrue(lbf.containsBean("x1"));
391 		assertFalse(lbf.containsBean("&x1"));
392 		assertTrue(lbf.isSingleton("x1"));
393 		assertFalse(lbf.isSingleton("&x1"));
394 		assertFalse(lbf.isPrototype("x1"));
395 		assertFalse(lbf.isPrototype("&x1"));
396 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
397 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
398 		assertEquals(TestBean.class, lbf.getType("x1"));
399 		assertEquals(null, lbf.getType("&x1"));
400 		assertFalse(TestBeanFactory.initialized);
401 	}
402 
403 	@Test
404 	public void testNonStaticPrototypeFactoryMethodFoundByNonEagerTypeMatching() {
405 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
406 		RootBeanDefinition factoryBd = new RootBeanDefinition(TestBeanFactory.class);
407 		lbf.registerBeanDefinition("factory", factoryBd);
408 		RootBeanDefinition rbd = new RootBeanDefinition();
409 		rbd.setFactoryBeanName("factory");
410 		rbd.setFactoryMethodName("createTestBeanNonStatic");
411 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
412 		lbf.registerBeanDefinition("x1", rbd);
413 
414 		TestBeanFactory.initialized = false;
415 		String[] beanNames = lbf.getBeanNamesForType(TestBean.class, true, false);
416 		assertEquals(1, beanNames.length);
417 		assertEquals("x1", beanNames[0]);
418 		assertFalse(lbf.containsSingleton("x1"));
419 		assertTrue(lbf.containsBean("x1"));
420 		assertFalse(lbf.containsBean("&x1"));
421 		assertTrue(lbf.containsLocalBean("x1"));
422 		assertFalse(lbf.containsLocalBean("&x1"));
423 		assertFalse(lbf.isSingleton("x1"));
424 		assertFalse(lbf.isSingleton("&x1"));
425 		assertTrue(lbf.isPrototype("x1"));
426 		assertFalse(lbf.isPrototype("&x1"));
427 		assertTrue(lbf.isTypeMatch("x1", TestBean.class));
428 		assertFalse(lbf.isTypeMatch("&x1", TestBean.class));
429 		assertTrue(lbf.isTypeMatch("x1", Object.class));
430 		assertFalse(lbf.isTypeMatch("&x1", Object.class));
431 		assertEquals(TestBean.class, lbf.getType("x1"));
432 		assertEquals(null, lbf.getType("&x1"));
433 		assertFalse(TestBeanFactory.initialized);
434 
435 		lbf.registerAlias("x1", "x2");
436 		assertTrue(lbf.containsBean("x2"));
437 		assertFalse(lbf.containsBean("&x2"));
438 		assertTrue(lbf.containsLocalBean("x2"));
439 		assertFalse(lbf.containsLocalBean("&x2"));
440 		assertFalse(lbf.isSingleton("x2"));
441 		assertFalse(lbf.isSingleton("&x2"));
442 		assertTrue(lbf.isPrototype("x2"));
443 		assertFalse(lbf.isPrototype("&x2"));
444 		assertTrue(lbf.isTypeMatch("x2", TestBean.class));
445 		assertFalse(lbf.isTypeMatch("&x2", TestBean.class));
446 		assertTrue(lbf.isTypeMatch("x2", Object.class));
447 		assertFalse(lbf.isTypeMatch("&x2", Object.class));
448 		assertEquals(TestBean.class, lbf.getType("x2"));
449 		assertEquals(null, lbf.getType("&x2"));
450 		assertEquals(1, lbf.getAliases("x1").length);
451 		assertEquals("x2", lbf.getAliases("x1")[0]);
452 		assertEquals(1, lbf.getAliases("&x1").length);
453 		assertEquals("&x2", lbf.getAliases("&x1")[0]);
454 		assertEquals(1, lbf.getAliases("x2").length);
455 		assertEquals("x1", lbf.getAliases("x2")[0]);
456 		assertEquals(1, lbf.getAliases("&x2").length);
457 		assertEquals("&x1", lbf.getAliases("&x2")[0]);
458 	}
459 
460 	@Test
461 	public void testEmpty() {
462 		ListableBeanFactory lbf = new DefaultListableBeanFactory();
463 		assertTrue("No beans defined --> array != null", lbf.getBeanDefinitionNames() != null);
464 		assertTrue("No beans defined after no arg constructor", lbf.getBeanDefinitionNames().length == 0);
465 		assertTrue("No beans defined after no arg constructor", lbf.getBeanDefinitionCount() == 0);
466 	}
467 
468 	@Test
469 	public void testEmptyPropertiesPopulation() {
470 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
471 		Properties p = new Properties();
472 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
473 		assertTrue("No beans defined after ignorable invalid", lbf.getBeanDefinitionCount() == 0);
474 	}
475 
476 	@Test
477 	public void testHarmlessIgnorableRubbish() {
478 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
479 		Properties p = new Properties();
480 		p.setProperty("foo", "bar");
481 		p.setProperty("qwert", "er");
482 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p, "test");
483 		assertTrue("No beans defined after harmless ignorable rubbish", lbf.getBeanDefinitionCount() == 0);
484 	}
485 
486 	@Test
487 	public void testPropertiesPopulationWithNullPrefix() {
488 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
489 		Properties p = new Properties();
490 		p.setProperty("test.(class)", TestBean.class.getName());
491 		p.setProperty("test.name", "Tony");
492 		p.setProperty("test.age", "48");
493 		int count = (new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
494 		assertTrue("1 beans registered, not " + count, count == 1);
495 		testSingleTestBean(lbf);
496 	}
497 
498 	@Test
499 	public void testPropertiesPopulationWithPrefix() {
500 		String PREFIX = "beans.";
501 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
502 		Properties p = new Properties();
503 		p.setProperty(PREFIX + "test.(class)", TestBean.class.getName());
504 		p.setProperty(PREFIX + "test.name", "Tony");
505 		p.setProperty(PREFIX + "test.age", "0x30");
506 		int count = (new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p, PREFIX);
507 		assertTrue("1 beans registered, not " + count, count == 1);
508 		testSingleTestBean(lbf);
509 	}
510 
511 	@Test
512 	public void testSimpleReference() {
513 		String PREFIX = "beans.";
514 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
515 		Properties p = new Properties();
516 
517 		p.setProperty(PREFIX + "rod.(class)", TestBean.class.getName());
518 		p.setProperty(PREFIX + "rod.name", "Rod");
519 
520 		p.setProperty(PREFIX + "kerry.(class)", TestBean.class.getName());
521 		p.setProperty(PREFIX + "kerry.name", "Kerry");
522 		p.setProperty(PREFIX + "kerry.age", "35");
523 		p.setProperty(PREFIX + "kerry.spouse(ref)", "rod");
524 
525 		int count = (new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p, PREFIX);
526 		assertTrue("2 beans registered, not " + count, count == 2);
527 
528 		TestBean kerry = lbf.getBean("kerry", TestBean.class);
529 		assertTrue("Kerry name is Kerry", "Kerry".equals(kerry.getName()));
530 		ITestBean spouse = kerry.getSpouse();
531 		assertTrue("Kerry spouse is non null", spouse != null);
532 		assertTrue("Kerry spouse name is Rod", "Rod".equals(spouse.getName()));
533 	}
534 
535 	@Test
536 	public void testPropertiesWithDotsInKey() {
537 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
538 		Properties p = new Properties();
539 
540 		p.setProperty("tb.(class)", TestBean.class.getName());
541 		p.setProperty("tb.someMap[my.key]", "my.value");
542 
543 		int count = (new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
544 		assertTrue("1 beans registered, not " + count, count == 1);
545 		assertEquals(1, lbf.getBeanDefinitionCount());
546 
547 		TestBean tb = lbf.getBean("tb", TestBean.class);
548 		assertEquals("my.value", tb.getSomeMap().get("my.key"));
549 	}
550 
551 	@Test
552 	public void testUnresolvedReference() {
553 		String PREFIX = "beans.";
554 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
555 		Properties p = new Properties();
556 
557 		try {
558 			p.setProperty(PREFIX + "kerry.(class)", TestBean.class.getName());
559 			p.setProperty(PREFIX + "kerry.name", "Kerry");
560 			p.setProperty(PREFIX + "kerry.age", "35");
561 			p.setProperty(PREFIX + "kerry.spouse(ref)", "rod");
562 
563 			(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p, PREFIX);
564 
565 			lbf.getBean("kerry");
566 			fail("Unresolved reference should have been detected");
567 		}
568 		catch (BeansException ex) {
569 			// cool
570 		}
571 	}
572 
573 	@Test
574 	public void testSelfReference() {
575 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
576 		MutablePropertyValues pvs = new MutablePropertyValues();
577 		pvs.add("spouse", new RuntimeBeanReference("self"));
578 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
579 		bd.setPropertyValues(pvs);
580 		lbf.registerBeanDefinition("self", bd);
581 		TestBean self = (TestBean) lbf.getBean("self");
582 		assertEquals(self, self.getSpouse());
583 	}
584 
585 	@Test
586 	public void testPossibleMatches() {
587 		try {
588 			DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
589 			MutablePropertyValues pvs = new MutablePropertyValues();
590 			pvs.add("ag", "foobar");
591 			RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
592 			bd.setPropertyValues(pvs);
593 			lbf.registerBeanDefinition("tb", bd);
594 			lbf.getBean("tb");
595 			fail("Should throw exception on invalid property");
596 		}
597 		catch (BeanCreationException ex) {
598 			assertTrue(ex.getCause() instanceof NotWritablePropertyException);
599 			NotWritablePropertyException cause = (NotWritablePropertyException) ex.getCause();
600 			// expected
601 			assertEquals(1, cause.getPossibleMatches().length);
602 			assertEquals("age", cause.getPossibleMatches()[0]);
603 		}
604 	}
605 
606 	@Test
607 	public void testPrototype() {
608 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
609 		Properties p = new Properties();
610 		p.setProperty("kerry.(class)", TestBean.class.getName());
611 		p.setProperty("kerry.age", "35");
612 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
613 		TestBean kerry1 = (TestBean) lbf.getBean("kerry");
614 		TestBean kerry2 = (TestBean) lbf.getBean("kerry");
615 		assertTrue("Non null", kerry1 != null);
616 		assertTrue("Singletons equal", kerry1 == kerry2);
617 
618 		lbf = new DefaultListableBeanFactory();
619 		p = new Properties();
620 		p.setProperty("kerry.(class)", TestBean.class.getName());
621 		p.setProperty("kerry.(scope)", "prototype");
622 		p.setProperty("kerry.age", "35");
623 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
624 		kerry1 = (TestBean) lbf.getBean("kerry");
625 		kerry2 = (TestBean) lbf.getBean("kerry");
626 		assertTrue("Non null", kerry1 != null);
627 		assertTrue("Prototypes NOT equal", kerry1 != kerry2);
628 
629 		lbf = new DefaultListableBeanFactory();
630 		p = new Properties();
631 		p.setProperty("kerry.(class)", TestBean.class.getName());
632 		p.setProperty("kerry.(scope)", "singleton");
633 		p.setProperty("kerry.age", "35");
634 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
635 		kerry1 = (TestBean) lbf.getBean("kerry");
636 		kerry2 = (TestBean) lbf.getBean("kerry");
637 		assertTrue("Non null", kerry1 != null);
638 		assertTrue("Specified singletons equal", kerry1 == kerry2);
639 	}
640 
641 	@Test
642 	public void testPrototypeCircleLeadsToException() {
643 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
644 		Properties p = new Properties();
645 		p.setProperty("kerry.(class)", TestBean.class.getName());
646 		p.setProperty("kerry.(singleton)", "false");
647 		p.setProperty("kerry.age", "35");
648 		p.setProperty("kerry.spouse", "*rod");
649 		p.setProperty("rod.(class)", TestBean.class.getName());
650 		p.setProperty("rod.(singleton)", "false");
651 		p.setProperty("rod.age", "34");
652 		p.setProperty("rod.spouse", "*kerry");
653 
654 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
655 		try {
656 			lbf.getBean("kerry");
657 			fail("Should have thrown BeanCreationException");
658 		}
659 		catch (BeanCreationException ex) {
660 			// expected
661 			assertTrue(ex.contains(BeanCurrentlyInCreationException.class));
662 		}
663 	}
664 
665 	@Test
666 	public void testPrototypeExtendsPrototype() {
667 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
668 		Properties p = new Properties();
669 		p.setProperty("wife.(class)", TestBean.class.getName());
670 		p.setProperty("wife.name", "kerry");
671 
672 		p.setProperty("kerry.(parent)", "wife");
673 		p.setProperty("kerry.age", "35");
674 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
675 		TestBean kerry1 = (TestBean) lbf.getBean("kerry");
676 		TestBean kerry2 = (TestBean) lbf.getBean("kerry");
677 		assertEquals("kerry", kerry1.getName());
678 		assertNotNull("Non null", kerry1);
679 		assertTrue("Singletons equal", kerry1 == kerry2);
680 
681 		lbf = new DefaultListableBeanFactory();
682 		p = new Properties();
683 		p.setProperty("wife.(class)", TestBean.class.getName());
684 		p.setProperty("wife.name", "kerry");
685 		p.setProperty("wife.(singleton)", "false");
686 		p.setProperty("kerry.(parent)", "wife");
687 		p.setProperty("kerry.(singleton)", "false");
688 		p.setProperty("kerry.age", "35");
689 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
690 		assertFalse(lbf.isSingleton("kerry"));
691 		kerry1 = (TestBean) lbf.getBean("kerry");
692 		kerry2 = (TestBean) lbf.getBean("kerry");
693 		assertTrue("Non null", kerry1 != null);
694 		assertTrue("Prototypes NOT equal", kerry1 != kerry2);
695 
696 		lbf = new DefaultListableBeanFactory();
697 		p = new Properties();
698 		p.setProperty("kerry.(class)", TestBean.class.getName());
699 		p.setProperty("kerry.(singleton)", "true");
700 		p.setProperty("kerry.age", "35");
701 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
702 		kerry1 = (TestBean) lbf.getBean("kerry");
703 		kerry2 = (TestBean) lbf.getBean("kerry");
704 		assertTrue("Non null", kerry1 != null);
705 		assertTrue("Specified singletons equal", kerry1 == kerry2);
706 	}
707 
708 	@Test
709 	public void testCanReferenceParentBeanFromChildViaAlias() {
710 		final String EXPECTED_NAME = "Juergen";
711 		final int EXPECTED_AGE = 41;
712 
713 		RootBeanDefinition parentDefinition = new RootBeanDefinition(TestBean.class);
714 		parentDefinition.setAbstract(true);
715 		parentDefinition.getPropertyValues().add("name", EXPECTED_NAME);
716 		parentDefinition.getPropertyValues().add("age", new Integer(EXPECTED_AGE));
717 
718 		ChildBeanDefinition childDefinition = new ChildBeanDefinition("alias");
719 
720 		DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
721 		factory.registerBeanDefinition("parent", parentDefinition);
722 		factory.registerBeanDefinition("child", childDefinition);
723 		factory.registerAlias("parent", "alias");
724 
725 		TestBean child = (TestBean) factory.getBean("child");
726 		assertEquals(EXPECTED_NAME, child.getName());
727 		assertEquals(EXPECTED_AGE, child.getAge());
728 
729 		assertEquals("Use cached merged bean definition",
730 				factory.getMergedBeanDefinition("child"), factory.getMergedBeanDefinition("child"));
731 	}
732 
733 	@Test
734 	public void testGetTypeWorksAfterParentChildMerging() {
735 		RootBeanDefinition parentDefinition = new RootBeanDefinition(TestBean.class);
736 		ChildBeanDefinition childDefinition = new ChildBeanDefinition("parent", DerivedTestBean.class, null, null);
737 
738 		DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
739 		factory.registerBeanDefinition("parent", parentDefinition);
740 		factory.registerBeanDefinition("child", childDefinition);
741 		factory.freezeConfiguration();
742 
743 		assertEquals(TestBean.class, factory.getType("parent"));
744 		assertEquals(DerivedTestBean.class, factory.getType("child"));
745 	}
746 
747 	@Test
748 	public void testNameAlreadyBound() {
749 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
750 		Properties p = new Properties();
751 		p.setProperty("kerry.(class)", TestBean.class.getName());
752 		p.setProperty("kerry.age", "35");
753 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
754 		try {
755 			(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
756 		}
757 		catch (BeanDefinitionStoreException ex) {
758 			assertEquals("kerry", ex.getBeanName());
759 			// expected
760 		}
761 	}
762 
763 	private void testSingleTestBean(ListableBeanFactory lbf) {
764 		assertTrue("1 beans defined", lbf.getBeanDefinitionCount() == 1);
765 		String[] names = lbf.getBeanDefinitionNames();
766 		assertTrue("Array length == 1", names.length == 1);
767 		assertTrue("0th element == test", names[0].equals("test"));
768 		TestBean tb = (TestBean) lbf.getBean("test");
769 		assertTrue("Test is non null", tb != null);
770 		assertTrue("Test bean name is Tony", "Tony".equals(tb.getName()));
771 		assertTrue("Test bean age is 48", tb.getAge() == 48);
772 	}
773 
774 	@Test
775 	public void testAliasCircle() {
776 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
777 		lbf.registerAlias("test", "test2");
778 		lbf.registerAlias("test2", "test3");
779 		try {
780 			lbf.registerAlias("test3", "test");
781 			fail("Should have thrown IllegalStateException");
782 		}
783 		catch (IllegalStateException ex) {
784 			// expected
785 		}
786 	}
787 
788 	@Test
789 	public void testBeanDefinitionOverriding() {
790 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
791 		lbf.registerBeanDefinition("test", new RootBeanDefinition(TestBean.class));
792 		lbf.registerBeanDefinition("test", new RootBeanDefinition(NestedTestBean.class));
793 		lbf.registerAlias("otherTest", "test2");
794 		lbf.registerAlias("test", "test2");
795 		assertTrue(lbf.getBean("test") instanceof NestedTestBean);
796 		assertTrue(lbf.getBean("test2") instanceof NestedTestBean);
797 	}
798 
799 	@Test
800 	public void testBeanDefinitionRemoval() {
801 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
802 		lbf.setAllowBeanDefinitionOverriding(false);
803 		lbf.registerBeanDefinition("test", new RootBeanDefinition(TestBean.class));
804 		lbf.registerAlias("test", "test2");
805 		lbf.preInstantiateSingletons();
806 		lbf.removeBeanDefinition("test");
807 		lbf.removeAlias("test2");
808 		lbf.registerBeanDefinition("test", new RootBeanDefinition(NestedTestBean.class));
809 		lbf.registerAlias("test", "test2");
810 		assertTrue(lbf.getBean("test") instanceof NestedTestBean);
811 		assertTrue(lbf.getBean("test2") instanceof NestedTestBean);
812 	}
813 
814 	@Test
815 	public void testBeanDefinitionOverridingNotAllowed() {
816 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
817 		lbf.setAllowBeanDefinitionOverriding(false);
818 		lbf.registerBeanDefinition("test", new RootBeanDefinition(TestBean.class));
819 		try {
820 			lbf.registerBeanDefinition("test", new RootBeanDefinition(NestedTestBean.class));
821 			fail("Should have thrown BeanDefinitionStoreException");
822 		}
823 		catch (BeanDefinitionStoreException ex) {
824 			assertEquals("test", ex.getBeanName());
825 			// expected
826 		}
827 	}
828 
829 	@Test
830 	public void testBeanDefinitionOverridingWithAlias() {
831 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
832 		lbf.registerBeanDefinition("test", new RootBeanDefinition(TestBean.class));
833 		lbf.registerAlias("test", "testAlias");
834 		lbf.registerBeanDefinition("test", new RootBeanDefinition(NestedTestBean.class));
835 		lbf.registerAlias("test", "testAlias");
836 		assertTrue(lbf.getBean("test") instanceof NestedTestBean);
837 		assertTrue(lbf.getBean("testAlias") instanceof NestedTestBean);
838 	}
839 
840 	@Test
841 	public void testAliasChaining() {
842 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
843 		lbf.registerBeanDefinition("test", new RootBeanDefinition(NestedTestBean.class));
844 		lbf.registerAlias("test", "testAlias");
845 		lbf.registerAlias("testAlias", "testAlias2");
846 		lbf.registerAlias("testAlias2", "testAlias3");
847 		Object bean = lbf.getBean("test");
848 		assertSame(bean, lbf.getBean("testAlias"));
849 		assertSame(bean, lbf.getBean("testAlias2"));
850 		assertSame(bean, lbf.getBean("testAlias3"));
851 	}
852 
853 	@Test
854 	public void testBeanReferenceWithNewSyntax() {
855 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
856 		Properties p = new Properties();
857 		p.setProperty("r.(class)", TestBean.class.getName());
858 		p.setProperty("r.name", "rod");
859 		p.setProperty("k.(class)", TestBean.class.getName());
860 		p.setProperty("k.name", "kerry");
861 		p.setProperty("k.spouse", "*r");
862 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
863 		TestBean k = (TestBean) lbf.getBean("k");
864 		TestBean r = (TestBean) lbf.getBean("r");
865 		assertTrue(k.getSpouse() == r);
866 	}
867 
868 	@Test
869 	public void testCanEscapeBeanReferenceSyntax() {
870 		String name = "*name";
871 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
872 		Properties p = new Properties();
873 		p.setProperty("r.(class)", TestBean.class.getName());
874 		p.setProperty("r.name", "*" + name);
875 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
876 		TestBean r = (TestBean) lbf.getBean("r");
877 		assertTrue(r.getName().equals(name));
878 	}
879 
880 	@Test
881 	public void testCustomEditor() {
882 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
883 		lbf.addPropertyEditorRegistrar(new PropertyEditorRegistrar() {
884 			@Override
885 			public void registerCustomEditors(PropertyEditorRegistry registry) {
886 				NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
887 				registry.registerCustomEditor(Float.class, new CustomNumberEditor(Float.class, nf, true));
888 			}
889 		});
890 		MutablePropertyValues pvs = new MutablePropertyValues();
891 		pvs.add("myFloat", "1,1");
892 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
893 		bd.setPropertyValues(pvs);
894 		lbf.registerBeanDefinition("testBean", bd);
895 		TestBean testBean = (TestBean) lbf.getBean("testBean");
896 		assertTrue(testBean.getMyFloat().floatValue() == 1.1f);
897 	}
898 
899 	@Test
900 	public void testCustomConverter() {
901 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
902 		GenericConversionService conversionService = new DefaultConversionService();
903 		conversionService.addConverter(new Converter<String, Float>() {
904 			@Override
905 			public Float convert(String source) {
906 				try {
907 					NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
908 					return nf.parse(source).floatValue();
909 				}
910 				catch (ParseException ex) {
911 					throw new IllegalArgumentException(ex);
912 				}
913 			}
914 		});
915 		lbf.setConversionService(conversionService);
916 		MutablePropertyValues pvs = new MutablePropertyValues();
917 		pvs.add("myFloat", "1,1");
918 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
919 		bd.setPropertyValues(pvs);
920 		lbf.registerBeanDefinition("testBean", bd);
921 		TestBean testBean = (TestBean) lbf.getBean("testBean");
922 		assertTrue(testBean.getMyFloat().floatValue() == 1.1f);
923 	}
924 
925 	@Test
926 	public void testCustomEditorWithBeanReference() {
927 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
928 		lbf.addPropertyEditorRegistrar(new PropertyEditorRegistrar() {
929 			@Override
930 			public void registerCustomEditors(PropertyEditorRegistry registry) {
931 				NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
932 				registry.registerCustomEditor(Float.class, new CustomNumberEditor(Float.class, nf, true));
933 			}
934 		});
935 		MutablePropertyValues pvs = new MutablePropertyValues();
936 		pvs.add("myFloat", new RuntimeBeanReference("myFloat"));
937 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
938 		bd.setPropertyValues(pvs);
939 		lbf.registerBeanDefinition("testBean", bd);
940 		lbf.registerSingleton("myFloat", "1,1");
941 		TestBean testBean = (TestBean) lbf.getBean("testBean");
942 		assertTrue(testBean.getMyFloat().floatValue() == 1.1f);
943 	}
944 
945 	@Test
946 	public void testCustomTypeConverter() {
947 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
948 		NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
949 		lbf.setTypeConverter(new CustomTypeConverter(nf));
950 		MutablePropertyValues pvs = new MutablePropertyValues();
951 		pvs.add("myFloat", "1,1");
952 		ConstructorArgumentValues cav = new ConstructorArgumentValues();
953 		cav.addIndexedArgumentValue(0, "myName");
954 		cav.addIndexedArgumentValue(1, "myAge");
955 		lbf.registerBeanDefinition("testBean", new RootBeanDefinition(TestBean.class, cav, pvs));
956 		TestBean testBean = (TestBean) lbf.getBean("testBean");
957 		assertEquals("myName", testBean.getName());
958 		assertEquals(5, testBean.getAge());
959 		assertTrue(testBean.getMyFloat().floatValue() == 1.1f);
960 	}
961 
962 	@Test
963 	public void testCustomTypeConverterWithBeanReference() {
964 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
965 		NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
966 		lbf.setTypeConverter(new CustomTypeConverter(nf));
967 		MutablePropertyValues pvs = new MutablePropertyValues();
968 		pvs.add("myFloat", new RuntimeBeanReference("myFloat"));
969 		ConstructorArgumentValues cav = new ConstructorArgumentValues();
970 		cav.addIndexedArgumentValue(0, "myName");
971 		cav.addIndexedArgumentValue(1, "myAge");
972 		lbf.registerBeanDefinition("testBean", new RootBeanDefinition(TestBean.class, cav, pvs));
973 		lbf.registerSingleton("myFloat", "1,1");
974 		TestBean testBean = (TestBean) lbf.getBean("testBean");
975 		assertEquals("myName", testBean.getName());
976 		assertEquals(5, testBean.getAge());
977 		assertTrue(testBean.getMyFloat().floatValue() == 1.1f);
978 	}
979 
980 	@Test
981 	public void testRegisterExistingSingletonWithReference() {
982 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
983 		Properties p = new Properties();
984 		p.setProperty("test.(class)", TestBean.class.getName());
985 		p.setProperty("test.name", "Tony");
986 		p.setProperty("test.age", "48");
987 		p.setProperty("test.spouse(ref)", "singletonObject");
988 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
989 		Object singletonObject = new TestBean();
990 		lbf.registerSingleton("singletonObject", singletonObject);
991 
992 		assertTrue(lbf.isSingleton("singletonObject"));
993 		assertEquals(TestBean.class, lbf.getType("singletonObject"));
994 		TestBean test = (TestBean) lbf.getBean("test");
995 		assertEquals(singletonObject, lbf.getBean("singletonObject"));
996 		assertEquals(singletonObject, test.getSpouse());
997 
998 		Map<?, ?> beansOfType = lbf.getBeansOfType(TestBean.class, false, true);
999 		assertEquals(2, beansOfType.size());
1000 		assertTrue(beansOfType.containsValue(test));
1001 		assertTrue(beansOfType.containsValue(singletonObject));
1002 
1003 		beansOfType = lbf.getBeansOfType(null, false, true);
1004 		assertEquals(2, beansOfType.size());
1005 
1006 		Iterator<String> beanNames = lbf.getBeanNamesIterator();
1007 		assertEquals("test", beanNames.next());
1008 		assertEquals("singletonObject", beanNames.next());
1009 		assertFalse(beanNames.hasNext());
1010 
1011 		assertTrue(lbf.containsSingleton("test"));
1012 		assertTrue(lbf.containsSingleton("singletonObject"));
1013 		assertTrue(lbf.containsBeanDefinition("test"));
1014 		assertFalse(lbf.containsBeanDefinition("singletonObject"));
1015 	}
1016 
1017 	@Test
1018 	public void testRegisterExistingSingletonWithNameOverriding() {
1019 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1020 		Properties p = new Properties();
1021 		p.setProperty("test.(class)", TestBean.class.getName());
1022 		p.setProperty("test.name", "Tony");
1023 		p.setProperty("test.age", "48");
1024 		p.setProperty("test.spouse(ref)", "singletonObject");
1025 		(new PropertiesBeanDefinitionReader(lbf)).registerBeanDefinitions(p);
1026 		lbf.registerBeanDefinition("singletonObject", new RootBeanDefinition(PropertiesFactoryBean.class));
1027 		Object singletonObject = new TestBean();
1028 		lbf.registerSingleton("singletonObject", singletonObject);
1029 		lbf.preInstantiateSingletons();
1030 
1031 		assertTrue(lbf.isSingleton("singletonObject"));
1032 		assertEquals(TestBean.class, lbf.getType("singletonObject"));
1033 		TestBean test = (TestBean) lbf.getBean("test");
1034 		assertEquals(singletonObject, lbf.getBean("singletonObject"));
1035 		assertEquals(singletonObject, test.getSpouse());
1036 
1037 		Map<?, ?>  beansOfType = lbf.getBeansOfType(TestBean.class, false, true);
1038 		assertEquals(2, beansOfType.size());
1039 		assertTrue(beansOfType.containsValue(test));
1040 		assertTrue(beansOfType.containsValue(singletonObject));
1041 
1042 		beansOfType = lbf.getBeansOfType(null, false, true);
1043 
1044 		Iterator<String> beanNames = lbf.getBeanNamesIterator();
1045 		assertEquals("test", beanNames.next());
1046 		assertEquals("singletonObject", beanNames.next());
1047 		assertFalse(beanNames.hasNext());
1048 		assertEquals(2, beansOfType.size());
1049 
1050 		assertTrue(lbf.containsSingleton("test"));
1051 		assertTrue(lbf.containsSingleton("singletonObject"));
1052 		assertTrue(lbf.containsBeanDefinition("test"));
1053 		assertTrue(lbf.containsBeanDefinition("singletonObject"));
1054 	}
1055 
1056 	@Test
1057 	public void testRegisterExistingSingletonWithAutowire() {
1058 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1059 		MutablePropertyValues pvs = new MutablePropertyValues();
1060 		pvs.add("name", "Tony");
1061 		pvs.add("age", "48");
1062 		RootBeanDefinition bd = new RootBeanDefinition(DependenciesBean.class);
1063 		bd.setPropertyValues(pvs);
1064 		bd.setDependencyCheck(RootBeanDefinition.DEPENDENCY_CHECK_OBJECTS);
1065 		bd.setAutowireMode(RootBeanDefinition.AUTOWIRE_BY_TYPE);
1066 		lbf.registerBeanDefinition("test", bd);
1067 		Object singletonObject = new TestBean();
1068 		lbf.registerSingleton("singletonObject", singletonObject);
1069 
1070 		assertTrue(lbf.containsBean("singletonObject"));
1071 		assertTrue(lbf.isSingleton("singletonObject"));
1072 		assertEquals(TestBean.class, lbf.getType("singletonObject"));
1073 		assertEquals(0, lbf.getAliases("singletonObject").length);
1074 		DependenciesBean test = (DependenciesBean) lbf.getBean("test");
1075 		assertEquals(singletonObject, lbf.getBean("singletonObject"));
1076 		assertEquals(singletonObject, test.getSpouse());
1077 	}
1078 
1079 	@Test
1080 	public void testRegisterExistingSingletonWithAlreadyBound() {
1081 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1082 		Object singletonObject = new TestBean();
1083 		lbf.registerSingleton("singletonObject", singletonObject);
1084 		try {
1085 			lbf.registerSingleton("singletonObject", singletonObject);
1086 			fail("Should have thrown IllegalStateException");
1087 		}
1088 		catch (IllegalStateException ex) {
1089 			// expected
1090 		}
1091 	}
1092 
1093 	@Test
1094 	public void testReregisterBeanDefinition() {
1095 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1096 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1097 		bd1.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1098 		lbf.registerBeanDefinition("testBean", bd1);
1099 		assertTrue(lbf.getBean("testBean") instanceof TestBean);
1100 		RootBeanDefinition bd2 = new RootBeanDefinition(NestedTestBean.class);
1101 		bd2.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1102 		lbf.registerBeanDefinition("testBean", bd2);
1103 		assertTrue(lbf.getBean("testBean") instanceof NestedTestBean);
1104 	}
1105 
1106 	@Test
1107 	public void testArrayPropertyWithAutowiring() throws MalformedURLException {
1108 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1109 		bf.registerSingleton("resource1", new UrlResource("http://localhost:8080"));
1110 		bf.registerSingleton("resource2", new UrlResource("http://localhost:9090"));
1111 
1112 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1113 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_BY_TYPE);
1114 		bf.registerBeanDefinition("arrayBean", rbd);
1115 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1116 
1117 		assertEquals(new UrlResource("http://localhost:8080"), ab.getResourceArray()[0]);
1118 		assertEquals(new UrlResource("http://localhost:9090"), ab.getResourceArray()[1]);
1119 	}
1120 
1121 	@Test
1122 	public void testArrayPropertyWithOptionalAutowiring() throws MalformedURLException {
1123 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1124 
1125 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1126 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_BY_TYPE);
1127 		bf.registerBeanDefinition("arrayBean", rbd);
1128 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1129 
1130 		assertNull(ab.getResourceArray());
1131 	}
1132 
1133 	@Test
1134 	public void testArrayConstructorWithAutowiring() {
1135 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1136 		bf.registerSingleton("integer1", new Integer(4));
1137 		bf.registerSingleton("integer2", new Integer(5));
1138 
1139 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1140 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
1141 		bf.registerBeanDefinition("arrayBean", rbd);
1142 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1143 
1144 		assertEquals(new Integer(4), ab.getIntegerArray()[0]);
1145 		assertEquals(new Integer(5), ab.getIntegerArray()[1]);
1146 	}
1147 
1148 	@Test
1149 	public void testArrayConstructorWithOptionalAutowiring() {
1150 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1151 
1152 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1153 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
1154 		bf.registerBeanDefinition("arrayBean", rbd);
1155 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1156 
1157 		assertNull(ab.getIntegerArray());
1158 	}
1159 
1160 	@Test
1161 	public void testDoubleArrayConstructorWithAutowiring() throws MalformedURLException {
1162 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1163 		bf.registerSingleton("integer1", new Integer(4));
1164 		bf.registerSingleton("integer2", new Integer(5));
1165 		bf.registerSingleton("resource1", new UrlResource("http://localhost:8080"));
1166 		bf.registerSingleton("resource2", new UrlResource("http://localhost:9090"));
1167 
1168 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1169 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
1170 		bf.registerBeanDefinition("arrayBean", rbd);
1171 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1172 
1173 		assertEquals(new Integer(4), ab.getIntegerArray()[0]);
1174 		assertEquals(new Integer(5), ab.getIntegerArray()[1]);
1175 		assertEquals(new UrlResource("http://localhost:8080"), ab.getResourceArray()[0]);
1176 		assertEquals(new UrlResource("http://localhost:9090"), ab.getResourceArray()[1]);
1177 	}
1178 
1179 	@Test
1180 	public void testDoubleArrayConstructorWithOptionalAutowiring() throws MalformedURLException {
1181 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1182 		bf.registerSingleton("resource1", new UrlResource("http://localhost:8080"));
1183 		bf.registerSingleton("resource2", new UrlResource("http://localhost:9090"));
1184 
1185 		RootBeanDefinition rbd = new RootBeanDefinition(ArrayBean.class);
1186 		rbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
1187 		bf.registerBeanDefinition("arrayBean", rbd);
1188 		ArrayBean ab = (ArrayBean) bf.getBean("arrayBean");
1189 
1190 		assertNull(ab.getIntegerArray());
1191 		assertNull(ab.getResourceArray());
1192 	}
1193 
1194 	@Test
1195 	public void testExpressionInStringArray() {
1196 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
1197 		BeanExpressionResolver beanExpressionResolver = mock(BeanExpressionResolver.class);
1198 		when(beanExpressionResolver.evaluate(eq("#{foo}"), Matchers.any(BeanExpressionContext.class)))
1199 				.thenReturn("classpath:/org/springframework/beans/factory/xml/util.properties");
1200 		bf.setBeanExpressionResolver(beanExpressionResolver);
1201 
1202 		RootBeanDefinition rbd = new RootBeanDefinition(PropertiesFactoryBean.class);
1203 		MutablePropertyValues pvs = new MutablePropertyValues();
1204 		pvs.add("locations", new String[] {"#{foo}"});
1205 		rbd.setPropertyValues(pvs);
1206 		bf.registerBeanDefinition("myProperties", rbd);
1207 		Properties properties = (Properties) bf.getBean("myProperties");
1208 		assertEquals("bar", properties.getProperty("foo"));
1209 	}
1210 
1211 	@Test
1212 	public void testAutowireWithNoDependencies() {
1213 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1214 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1215 		lbf.registerBeanDefinition("rod", bd);
1216 		assertEquals(1, lbf.getBeanDefinitionCount());
1217 		Object registered = lbf.autowire(NoDependencies.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, false);
1218 		assertEquals(1, lbf.getBeanDefinitionCount());
1219 		assertTrue(registered instanceof NoDependencies);
1220 	}
1221 
1222 	@Test
1223 	public void testAutowireWithSatisfiedJavaBeanDependency() {
1224 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1225 		MutablePropertyValues pvs = new MutablePropertyValues();
1226 		pvs.add("name", "Rod");
1227 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1228 		bd.setPropertyValues(pvs);
1229 		lbf.registerBeanDefinition("rod", bd);
1230 		assertEquals(1, lbf.getBeanDefinitionCount());
1231 		// Depends on age, name and spouse (TestBean)
1232 		Object registered = lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1233 		assertEquals(1, lbf.getBeanDefinitionCount());
1234 		DependenciesBean kerry = (DependenciesBean) registered;
1235 		TestBean rod = (TestBean) lbf.getBean("rod");
1236 		assertSame(rod, kerry.getSpouse());
1237 	}
1238 
1239 	@Test
1240 	public void testAutowireWithSatisfiedConstructorDependency() {
1241 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1242 		MutablePropertyValues pvs = new MutablePropertyValues();
1243 		pvs.add("name", "Rod");
1244 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1245 		bd.setPropertyValues(pvs);
1246 		lbf.registerBeanDefinition("rod", bd);
1247 		assertEquals(1, lbf.getBeanDefinitionCount());
1248 		Object registered = lbf.autowire(ConstructorDependency.class, AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, false);
1249 		assertEquals(1, lbf.getBeanDefinitionCount());
1250 		ConstructorDependency kerry = (ConstructorDependency) registered;
1251 		TestBean rod = (TestBean) lbf.getBean("rod");
1252 		assertSame(rod, kerry.spouse);
1253 	}
1254 
1255 	@Test
1256 	public void testAutowireWithTwoMatchesForConstructorDependency() {
1257 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1258 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1259 		lbf.registerBeanDefinition("rod", bd);
1260 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1261 		lbf.registerBeanDefinition("rod2", bd2);
1262 		try {
1263 			lbf.autowire(ConstructorDependency.class, AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, false);
1264 			fail("Should have thrown UnsatisfiedDependencyException");
1265 		}
1266 		catch (UnsatisfiedDependencyException ex) {
1267 			// expected
1268 			assertTrue(ex.getMessage().contains("rod"));
1269 			assertTrue(ex.getMessage().contains("rod2"));
1270 		}
1271 	}
1272 
1273 	@Test
1274 	public void testAutowireWithUnsatisfiedConstructorDependency() {
1275 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1276 		MutablePropertyValues pvs = new MutablePropertyValues();
1277 		pvs.addPropertyValue(new PropertyValue("name", "Rod"));
1278 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1279 		bd.setPropertyValues(pvs);
1280 		lbf.registerBeanDefinition("rod", bd);
1281 		assertEquals(1, lbf.getBeanDefinitionCount());
1282 		try {
1283 			lbf.autowire(UnsatisfiedConstructorDependency.class, AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, true);
1284 			fail("Should have unsatisfied constructor dependency on SideEffectBean");
1285 		}
1286 		catch (UnsatisfiedDependencyException ex) {
1287 			// expected
1288 		}
1289 	}
1290 
1291 	@Test
1292 	public void testAutowireConstructor() {
1293 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1294 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1295 		lbf.registerBeanDefinition("spouse", bd);
1296 		ConstructorDependenciesBean bean = (ConstructorDependenciesBean)
1297 				lbf.autowire(ConstructorDependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, true);
1298 		Object spouse = lbf.getBean("spouse");
1299 		assertTrue(bean.getSpouse1() == spouse);
1300 		assertTrue(BeanFactoryUtils.beanOfType(lbf, TestBean.class) == spouse);
1301 	}
1302 
1303 	@Test
1304 	public void testAutowireBeanByName() {
1305 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1306 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1307 		lbf.registerBeanDefinition("spouse", bd);
1308 		DependenciesBean bean = (DependenciesBean)
1309 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, true);
1310 		TestBean spouse = (TestBean) lbf.getBean("spouse");
1311 		assertEquals(spouse, bean.getSpouse());
1312 		assertTrue(BeanFactoryUtils.beanOfType(lbf, TestBean.class) == spouse);
1313 	}
1314 
1315 	@Test
1316 	public void testAutowireBeanByNameWithDependencyCheck() {
1317 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1318 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1319 		lbf.registerBeanDefinition("spous", bd);
1320 		try {
1321 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, true);
1322 			fail("Should have thrown UnsatisfiedDependencyException");
1323 		}
1324 		catch (UnsatisfiedDependencyException ex) {
1325 			// expected
1326 		}
1327 	}
1328 
1329 	@Test
1330 	public void testAutowireBeanByNameWithNoDependencyCheck() {
1331 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1332 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1333 		lbf.registerBeanDefinition("spous", bd);
1334 		DependenciesBean bean = (DependenciesBean)
1335 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, false);
1336 		assertNull(bean.getSpouse());
1337 	}
1338 
1339 	@Test
1340 	public void testDependsOnCycle() {
1341 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1342 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1343 		bd1.setDependsOn("tb2");
1344 		lbf.registerBeanDefinition("tb1", bd1);
1345 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1346 		bd2.setDependsOn("tb1");
1347 		lbf.registerBeanDefinition("tb2", bd2);
1348 		try {
1349 			lbf.preInstantiateSingletons();
1350 			fail("Should have thrown BeanCreationException");
1351 		}
1352 		catch (BeanCreationException ex) {
1353 			// expected
1354 			assertTrue(ex.getMessage().contains("Circular"));
1355 			assertTrue(ex.getMessage().contains("'tb2'"));
1356 			assertTrue(ex.getMessage().contains("'tb1'"));
1357 		}
1358 	}
1359 
1360 	@Test
1361 	public void testImplicitDependsOnCycle() {
1362 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1363 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1364 		bd1.setDependsOn("tb2");
1365 		lbf.registerBeanDefinition("tb1", bd1);
1366 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1367 		bd2.setDependsOn("tb3");
1368 		lbf.registerBeanDefinition("tb2", bd2);
1369 		RootBeanDefinition bd3 = new RootBeanDefinition(TestBean.class);
1370 		bd3.setDependsOn("tb1");
1371 		lbf.registerBeanDefinition("tb3", bd3);
1372 		try {
1373 			lbf.preInstantiateSingletons();
1374 			fail("Should have thrown BeanCreationException");
1375 		}
1376 		catch (BeanCreationException ex) {
1377 			// expected
1378 			assertTrue(ex.getMessage().contains("Circular"));
1379 			assertTrue(ex.getMessage().contains("'tb3'"));
1380 			assertTrue(ex.getMessage().contains("'tb1'"));
1381 		}
1382 	}
1383 
1384 	@Test(expected = NoSuchBeanDefinitionException.class)
1385 	public void testGetBeanByTypeWithNoneFound() {
1386 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1387 		lbf.getBean(TestBean.class);
1388 	}
1389 
1390 	@Test
1391 	public void testGetBeanByTypeDefinedInParent() {
1392 		DefaultListableBeanFactory parent = new DefaultListableBeanFactory();
1393 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1394 		parent.registerBeanDefinition("bd1", bd1);
1395 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory(parent);
1396 		TestBean bean = lbf.getBean(TestBean.class);
1397 		assertThat(bean.getBeanName(), equalTo("bd1"));
1398 	}
1399 
1400 	@Test(expected = NoUniqueBeanDefinitionException.class)
1401 	public void testGetBeanByTypeWithAmbiguity() {
1402 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1403 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1404 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1405 		lbf.registerBeanDefinition("bd1", bd1);
1406 		lbf.registerBeanDefinition("bd2", bd2);
1407 		lbf.getBean(TestBean.class);
1408 	}
1409 
1410 	@Test
1411 	public void testGetBeanByTypeWithPrimary() throws Exception {
1412 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1413 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1414 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1415 		bd2.setPrimary(true);
1416 		lbf.registerBeanDefinition("bd1", bd1);
1417 		lbf.registerBeanDefinition("bd2", bd2);
1418 		TestBean bean = lbf.getBean(TestBean.class);
1419 		assertThat(bean.getBeanName(), equalTo("bd2"));
1420 	}
1421 
1422 	@Test
1423 	public void testGetBeanByTypeWithMultiplePrimary() throws Exception {
1424 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1425 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1426 		bd1.setPrimary(true);
1427 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1428 		bd2.setPrimary(true);
1429 		lbf.registerBeanDefinition("bd1", bd1);
1430 		lbf.registerBeanDefinition("bd2", bd2);
1431 		thrown.expect(NoUniqueBeanDefinitionException.class);
1432 		thrown.expectMessage(containsString("more than one 'primary'"));
1433 		lbf.getBean(TestBean.class);
1434 	}
1435 
1436 	@Test
1437 	public void testGetBeanByTypeWithPriority() throws Exception {
1438 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1439 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1440 		RootBeanDefinition bd1 = new RootBeanDefinition(HighPriorityTestBean.class);
1441 		RootBeanDefinition bd2 = new RootBeanDefinition(LowPriorityTestBean.class);
1442 		lbf.registerBeanDefinition("bd1", bd1);
1443 		lbf.registerBeanDefinition("bd2", bd2);
1444 		TestBean bean = lbf.getBean(TestBean.class);
1445 		assertThat(bean.getBeanName(), equalTo("bd1"));
1446 	}
1447 
1448 	@Test
1449 	public void testGetBeanByTypeWithMultiplePriority() throws Exception {
1450 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1451 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1452 		RootBeanDefinition bd1 = new RootBeanDefinition(HighPriorityTestBean.class);
1453 		RootBeanDefinition bd2 = new RootBeanDefinition(HighPriorityTestBean.class);
1454 		lbf.registerBeanDefinition("bd1", bd1);
1455 		lbf.registerBeanDefinition("bd2", bd2);
1456 		thrown.expect(NoUniqueBeanDefinitionException.class);
1457 		thrown.expectMessage(containsString("Multiple beans found with the same priority"));
1458 		thrown.expectMessage(containsString("5")); // conflicting priority
1459 		lbf.getBean(TestBean.class);
1460 	}
1461 
1462 	@Test
1463 	public void testGetBeanByTypeWithPriorityAndNullInstance() throws Exception {
1464 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1465 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1466 		RootBeanDefinition bd1 = new RootBeanDefinition(HighPriorityTestBean.class);
1467 		RootBeanDefinition bd2 = new RootBeanDefinition(NullTestBeanFactoryBean.class);
1468 		lbf.registerBeanDefinition("bd1", bd1);
1469 		lbf.registerBeanDefinition("bd2", bd2);
1470 		TestBean bean = lbf.getBean(TestBean.class);
1471 		assertThat(bean.getBeanName(), equalTo("bd1"));
1472 	}
1473 
1474 	@Test
1475 	public void testGetBeanByTypePrimaryHasPrecedenceOverPriority() throws Exception {
1476 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1477 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1478 		RootBeanDefinition bd1 = new RootBeanDefinition(HighPriorityTestBean.class);
1479 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1480 		bd2.setPrimary(true);
1481 		lbf.registerBeanDefinition("bd1", bd1);
1482 		lbf.registerBeanDefinition("bd2", bd2);
1483 		TestBean bean = lbf.getBean(TestBean.class);
1484 		assertThat(bean.getBeanName(), equalTo("bd2"));
1485 	}
1486 
1487 	@Test
1488 	public void testGetBeanByTypeFiltersOutNonAutowireCandidates() {
1489 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1490 		RootBeanDefinition bd1 = new RootBeanDefinition(TestBean.class);
1491 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1492 		RootBeanDefinition na1 = new RootBeanDefinition(TestBean.class);
1493 		na1.setAutowireCandidate(false);
1494 
1495 		lbf.registerBeanDefinition("bd1", bd1);
1496 		lbf.registerBeanDefinition("na1", na1);
1497 		TestBean actual = lbf.getBean(TestBean.class); // na1 was filtered
1498 		assertSame(lbf.getBean("bd1", TestBean.class), actual);
1499 
1500 		lbf.registerBeanDefinition("bd2", bd2);
1501 		try {
1502 			lbf.getBean(TestBean.class);
1503 			fail("Should have thrown NoSuchBeanDefinitionException");
1504 		}
1505 		catch (NoSuchBeanDefinitionException ex) {
1506 			// expected
1507 		}
1508 	}
1509 
1510 	@Test(expected = NoSuchBeanDefinitionException.class)
1511 	public void testGetBeanByTypeInstanceWithNoneFound() {
1512 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1513 		lbf.getBean(ConstructorDependency.class, 42);
1514 	}
1515 
1516 	@Test
1517 	public void testGetBeanByTypeInstanceDefinedInParent() {
1518 		DefaultListableBeanFactory parent = new DefaultListableBeanFactory();
1519 		RootBeanDefinition bd1 = createConstructorDependencyBeanDefinition(99);
1520 		parent.registerBeanDefinition("bd1", bd1);
1521 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory(parent);
1522 		ConstructorDependency bean = lbf.getBean(ConstructorDependency.class, 42);
1523 		assertThat(bean.beanName, equalTo("bd1"));
1524 		assertThat(bean.spouseAge, equalTo(42));
1525 	}
1526 
1527 	@Test
1528 	public void testGetBeanByTypeInstanceWithAmbiguity() {
1529 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1530 		RootBeanDefinition bd1 = createConstructorDependencyBeanDefinition(99);
1531 		RootBeanDefinition bd2 = new RootBeanDefinition(ConstructorDependency.class);
1532 		bd2.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1533 		bd2.getConstructorArgumentValues().addGenericArgumentValue("43");
1534 
1535 		lbf.registerBeanDefinition("bd1", bd1);
1536 		lbf.registerBeanDefinition("bd2", bd2);
1537 
1538 		thrown.expect(NoUniqueBeanDefinitionException.class);
1539 		lbf.getBean(ConstructorDependency.class, 42);
1540 	}
1541 
1542 	@Test
1543 	public void testGetBeanByTypeInstanceWithPrimary() {
1544 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1545 		RootBeanDefinition bd1 = createConstructorDependencyBeanDefinition(99);
1546 		RootBeanDefinition bd2 = createConstructorDependencyBeanDefinition(43);
1547 		bd2.setPrimary(true);
1548 		lbf.registerBeanDefinition("bd1", bd1);
1549 		lbf.registerBeanDefinition("bd2", bd2);
1550 		ConstructorDependency bean = lbf.getBean(ConstructorDependency.class, 42);
1551 		assertThat(bean.beanName, equalTo("bd2"));
1552 		assertThat(bean.spouseAge, equalTo(42));
1553 	}
1554 
1555 	@Test
1556 	public void testGetBeanByTypeInstanceWithMultiplePrimary() {
1557 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1558 		RootBeanDefinition bd1 = createConstructorDependencyBeanDefinition(99);
1559 		RootBeanDefinition bd2 = createConstructorDependencyBeanDefinition(43);
1560 		bd1.setPrimary(true);
1561 		bd2.setPrimary(true);
1562 
1563 		lbf.registerBeanDefinition("bd1", bd1);
1564 		lbf.registerBeanDefinition("bd2", bd2);
1565 		thrown.expect(NoUniqueBeanDefinitionException.class);
1566 		thrown.expectMessage(containsString("more than one 'primary'"));
1567 		lbf.getBean(ConstructorDependency.class, 42);
1568 	}
1569 
1570 	@Test
1571 	public void testGetBeanByTypeInstanceFiltersOutNonAutowireCandidates() {
1572 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1573 		RootBeanDefinition bd1 = createConstructorDependencyBeanDefinition(99);
1574 		RootBeanDefinition bd2 = createConstructorDependencyBeanDefinition(43);
1575 		RootBeanDefinition na1 = createConstructorDependencyBeanDefinition(21);
1576 		na1.setAutowireCandidate(false);
1577 
1578 		lbf.registerBeanDefinition("bd1", bd1);
1579 		lbf.registerBeanDefinition("na1", na1);
1580 		ConstructorDependency actual = lbf.getBean(ConstructorDependency.class, 42); // na1 was filtered
1581 		assertThat(actual.beanName, equalTo("bd1"));
1582 
1583 		lbf.registerBeanDefinition("bd2", bd2);
1584 		try {
1585 			lbf.getBean(TestBean.class, 67);
1586 			fail("Should have thrown NoSuchBeanDefinitionException");
1587 		}
1588 		catch (NoSuchBeanDefinitionException ex) {
1589 			// expected
1590 		}
1591 	}
1592 
1593 	@Test
1594 	public void testGetBeanWithArgsNotCreatedForFactoryBeanChecking() {
1595 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1596 		RootBeanDefinition bd1 = new RootBeanDefinition(ConstructorDependency.class);
1597 		bd1.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1598 		lbf.registerBeanDefinition("bd1", bd1);
1599 		RootBeanDefinition bd2 = new RootBeanDefinition(ConstructorDependencyFactoryBean.class);
1600 		bd2.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1601 		lbf.registerBeanDefinition("bd2", bd2);
1602 
1603 		ConstructorDependency bean = lbf.getBean(ConstructorDependency.class, 42);
1604 		assertThat(bean.beanName, equalTo("bd1"));
1605 		assertThat(bean.spouseAge, equalTo(42));
1606 
1607 		assertEquals(1, lbf.getBeanNamesForType(ConstructorDependency.class).length);
1608 		assertEquals(1, lbf.getBeanNamesForType(ConstructorDependencyFactoryBean.class).length);
1609 	}
1610 
1611 	private RootBeanDefinition createConstructorDependencyBeanDefinition(int age) {
1612 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependency.class);
1613 		bd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
1614 		bd.getConstructorArgumentValues().addGenericArgumentValue(String.valueOf(age));
1615 		return bd;
1616 	}
1617 
1618 	@Test
1619 	public void testAutowireBeanByType() {
1620 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1621 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1622 		lbf.registerBeanDefinition("test", bd);
1623 		DependenciesBean bean = (DependenciesBean)
1624 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1625 		TestBean test = (TestBean) lbf.getBean("test");
1626 		assertEquals(test, bean.getSpouse());
1627 	}
1628 
1629 	/**
1630 	 * Verifies that a dependency on a {@link FactoryBean} can be autowired
1631 	 * <em>by type</em>, specifically addressing the JIRA issue raised in <a
1632 	 * href="http://opensource.atlassian.com/projects/spring/browse/SPR-4040"
1633 	 * target="_blank">SPR-4040</a>.
1634 	 */
1635 	@Test
1636 	public void testAutowireBeanWithFactoryBeanByType() {
1637 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1638 		RootBeanDefinition bd = new RootBeanDefinition(LazyInitFactory.class);
1639 		lbf.registerBeanDefinition("factoryBean", bd);
1640 		LazyInitFactory factoryBean = (LazyInitFactory) lbf.getBean("&factoryBean");
1641 		assertNotNull("The FactoryBean should have been registered.", factoryBean);
1642 		FactoryBeanDependentBean bean = (FactoryBeanDependentBean) lbf.autowire(FactoryBeanDependentBean.class,
1643 				AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1644 		assertEquals("The FactoryBeanDependentBean should have been autowired 'by type' with the LazyInitFactory.",
1645 				factoryBean, bean.getFactoryBean());
1646 	}
1647 
1648 	@Test
1649 	public void testGetTypeForAbstractFactoryBean() {
1650 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1651 		RootBeanDefinition bd = new RootBeanDefinition(FactoryBeanThatShouldntBeCalled.class);
1652 		bd.setAbstract(true);
1653 		lbf.registerBeanDefinition("factoryBean", bd);
1654 		assertNull(lbf.getType("factoryBean"));
1655 	}
1656 
1657 	/**
1658 	 * Verifies that a dependency on a {@link FactoryBean} can <strong>not</strong>
1659 	 * be autowired <em>by name</em>, as &amp; is an illegal character in
1660 	 * Java method names. In other words, you can't name a method
1661 	 * {@code set&amp;FactoryBean(...)}.
1662 	 */
1663 	@Test(expected = TypeMismatchException.class)
1664 	public void testAutowireBeanWithFactoryBeanByName() {
1665 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1666 		RootBeanDefinition bd = new RootBeanDefinition(LazyInitFactory.class);
1667 		lbf.registerBeanDefinition("factoryBean", bd);
1668 		LazyInitFactory factoryBean = (LazyInitFactory) lbf.getBean("&factoryBean");
1669 		assertNotNull("The FactoryBean should have been registered.", factoryBean);
1670 		lbf.autowire(FactoryBeanDependentBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, true);
1671 	}
1672 
1673 	@Test
1674 	public void testAutowireBeanByTypeWithTwoMatches() {
1675 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1676 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1677 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1678 		lbf.registerBeanDefinition("test", bd);
1679 		lbf.registerBeanDefinition("spouse", bd2);
1680 		try {
1681 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1682 			fail("Should have thrown UnsatisfiedDependencyException");
1683 		}
1684 		catch (UnsatisfiedDependencyException ex) {
1685 			// expected
1686 			assertTrue(ex.getMessage().contains("test"));
1687 			assertTrue(ex.getMessage().contains("spouse"));
1688 		}
1689 	}
1690 
1691 	@Test
1692 	public void testAutowireBeanByTypeWithTwoMatchesAndParameterNameDiscovery() {
1693 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1694 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1695 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1696 		lbf.registerBeanDefinition("test", bd);
1697 		lbf.registerBeanDefinition("spouse", bd2);
1698 		try {
1699 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1700 			fail("Should have thrown UnsatisfiedDependencyException");
1701 		}
1702 		catch (UnsatisfiedDependencyException ex) {
1703 			// expected
1704 			assertTrue(ex.getMessage().contains("test"));
1705 			assertTrue(ex.getMessage().contains("spouse"));
1706 		}
1707 	}
1708 
1709 	@Test
1710 	public void testAutowireBeanByTypeWithDependencyCheck() {
1711 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1712 		try {
1713 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1714 			fail("Should have thrown UnsatisfiedDependencyException");
1715 		}
1716 		catch (UnsatisfiedDependencyException ex) {
1717 			// expected
1718 		}
1719 	}
1720 
1721 	@Test
1722 	public void testAutowireBeanByTypeWithNoDependencyCheck() {
1723 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1724 		DependenciesBean bean = (DependenciesBean)
1725 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, false);
1726 		assertNull(bean.getSpouse());
1727 	}
1728 
1729 	@Test
1730 	public void testAutowireBeanByTypeWithTwoMatchesAndOnePrimary() {
1731 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1732 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1733 		bd.setPrimary(true);
1734 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1735 		lbf.registerBeanDefinition("test", bd);
1736 		lbf.registerBeanDefinition("spouse", bd2);
1737 
1738 		DependenciesBean bean = (DependenciesBean)
1739 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1740 		assertThat(bean.getSpouse(), equalTo(lbf.getBean("test")));
1741 	}
1742 
1743 	@Test
1744 	public void testAutowireBeanByTypeWithTwoPrimaryCandidates() {
1745 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1746 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1747 		bd.setPrimary(true);
1748 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1749 		bd2.setPrimary(true);
1750 		lbf.registerBeanDefinition("test", bd);
1751 		lbf.registerBeanDefinition("spouse", bd2);
1752 
1753 		try {
1754 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1755 			fail("Should have thrown UnsatisfiedDependencyException");
1756 		}
1757 		catch (UnsatisfiedDependencyException ex) {
1758 			// expected
1759 			assertNotNull("Exception should have cause", ex.getCause());
1760 			assertEquals("Wrong cause type", NoUniqueBeanDefinitionException.class, ex.getCause().getClass());
1761 		}
1762 	}
1763 
1764 	@Test
1765 	public void testAutowireBeanByTypeWithTwoMatchesAndPriority() {
1766 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1767 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1768 		RootBeanDefinition bd = new RootBeanDefinition(HighPriorityTestBean.class);
1769 		RootBeanDefinition bd2 = new RootBeanDefinition(LowPriorityTestBean.class);
1770 		lbf.registerBeanDefinition("test", bd);
1771 		lbf.registerBeanDefinition("spouse", bd2);
1772 
1773 		DependenciesBean bean = (DependenciesBean)
1774 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1775 		assertThat(bean.getSpouse(), equalTo(lbf.getBean("test")));
1776 	}
1777 
1778 	@Test
1779 	public void testAutowireBeanByTypeWithIdenticalPriorityCandidates() {
1780 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1781 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1782 		RootBeanDefinition bd = new RootBeanDefinition(HighPriorityTestBean.class);
1783 		RootBeanDefinition bd2 = new RootBeanDefinition(HighPriorityTestBean.class);
1784 		lbf.registerBeanDefinition("test", bd);
1785 		lbf.registerBeanDefinition("spouse", bd2);
1786 
1787 		try {
1788 			lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1789 			fail("Should have thrown UnsatisfiedDependencyException");
1790 		}
1791 		catch (UnsatisfiedDependencyException ex) {
1792 			// expected
1793 			assertNotNull("Exception should have cause", ex.getCause());
1794 			assertEquals("Wrong cause type", NoUniqueBeanDefinitionException.class, ex.getCause().getClass());
1795 			assertTrue(ex.getMessage().contains("5")); // conflicting priority
1796 		}
1797 	}
1798 
1799 	@Test
1800 	public void testAutowireBeanByTypePrimaryTakesPrecedenceOverPriority() {
1801 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1802 		lbf.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
1803 		RootBeanDefinition bd = new RootBeanDefinition(HighPriorityTestBean.class);
1804 		RootBeanDefinition bd2 = new RootBeanDefinition(TestBean.class);
1805 		bd2.setPrimary(true);
1806 		lbf.registerBeanDefinition("test", bd);
1807 		lbf.registerBeanDefinition("spouse", bd2);
1808 
1809 		DependenciesBean bean = (DependenciesBean)
1810 				lbf.autowire(DependenciesBean.class, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1811 		assertThat(bean.getSpouse(), equalTo(lbf.getBean("spouse")));
1812 	}
1813 
1814 	@Test
1815 	public void testAutowireExistingBeanByName() {
1816 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1817 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1818 		lbf.registerBeanDefinition("spouse", bd);
1819 		DependenciesBean existingBean = new DependenciesBean();
1820 		lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, true);
1821 		TestBean spouse = (TestBean) lbf.getBean("spouse");
1822 		assertEquals(existingBean.getSpouse(), spouse);
1823 		assertSame(spouse, BeanFactoryUtils.beanOfType(lbf, TestBean.class));
1824 	}
1825 
1826 	@Test
1827 	public void testAutowireExistingBeanByNameWithDependencyCheck() {
1828 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1829 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1830 		lbf.registerBeanDefinition("spous", bd);
1831 		DependenciesBean existingBean = new DependenciesBean();
1832 		try {
1833 			lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, true);
1834 			fail("Should have thrown UnsatisfiedDependencyException");
1835 		}
1836 		catch (UnsatisfiedDependencyException ex) {
1837 			// expected
1838 		}
1839 	}
1840 
1841 	@Test
1842 	public void testAutowireExistingBeanByNameWithNoDependencyCheck() {
1843 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1844 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1845 		lbf.registerBeanDefinition("spous", bd);
1846 		DependenciesBean existingBean = new DependenciesBean();
1847 		lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, false);
1848 		assertNull(existingBean.getSpouse());
1849 	}
1850 
1851 	@Test
1852 	public void testAutowireExistingBeanByType() {
1853 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1854 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1855 		lbf.registerBeanDefinition("test", bd);
1856 		DependenciesBean existingBean = new DependenciesBean();
1857 		lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1858 		TestBean test = (TestBean) lbf.getBean("test");
1859 		assertEquals(existingBean.getSpouse(), test);
1860 	}
1861 
1862 	@Test
1863 	public void testAutowireExistingBeanByTypeWithDependencyCheck() {
1864 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1865 		DependenciesBean existingBean = new DependenciesBean();
1866 		try {
1867 			lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
1868 			fail("Should have thrown UnsatisfiedDependencyException");
1869 		}
1870 		catch (UnsatisfiedDependencyException expected) {
1871 		}
1872 	}
1873 
1874 	@Test
1875 	public void testAutowireExistingBeanByTypeWithNoDependencyCheck() {
1876 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1877 		DependenciesBean existingBean = new DependenciesBean();
1878 		lbf.autowireBeanProperties(existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, false);
1879 		assertNull(existingBean.getSpouse());
1880 	}
1881 
1882 	@Test
1883 	public void testInvalidAutowireMode() {
1884 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1885 		try {
1886 			lbf.autowireBeanProperties(new TestBean(), AutowireCapableBeanFactory.AUTOWIRE_CONSTRUCTOR, false);
1887 			fail("Should have thrown IllegalArgumentException");
1888 		}
1889 		catch (IllegalArgumentException expected) {
1890 		}
1891 	}
1892 
1893 	@Test
1894 	public void testApplyBeanPropertyValues() {
1895 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1896 		MutablePropertyValues pvs = new MutablePropertyValues();
1897 		pvs.add("age", "99");
1898 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1899 		bd.setPropertyValues(pvs);
1900 		lbf.registerBeanDefinition("test", bd);
1901 		TestBean tb = new TestBean();
1902 		assertEquals(0, tb.getAge());
1903 		lbf.applyBeanPropertyValues(tb, "test");
1904 		assertEquals(99, tb.getAge());
1905 	}
1906 
1907 	@Test
1908 	public void testApplyBeanPropertyValuesWithIncompleteDefinition() {
1909 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1910 		MutablePropertyValues pvs = new MutablePropertyValues();
1911 		pvs.add("age", "99");
1912 		RootBeanDefinition bd = new RootBeanDefinition();
1913 		bd.setPropertyValues(pvs);
1914 		lbf.registerBeanDefinition("test", bd);
1915 		TestBean tb = new TestBean();
1916 		assertEquals(0, tb.getAge());
1917 		lbf.applyBeanPropertyValues(tb, "test");
1918 		assertEquals(99, tb.getAge());
1919 		assertNull(tb.getBeanFactory());
1920 		assertNull(tb.getSpouse());
1921 	}
1922 
1923 	@Test
1924 	public void testCreateBean() {
1925 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1926 		TestBean tb = lbf.createBean(TestBean.class);
1927 		assertSame(lbf, tb.getBeanFactory());
1928 		lbf.destroyBean(tb);
1929 	}
1930 
1931 	@Test
1932 	public void testCreateBeanWithDisposableBean() {
1933 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1934 		DerivedTestBean tb = lbf.createBean(DerivedTestBean.class);
1935 		assertSame(lbf, tb.getBeanFactory());
1936 		lbf.destroyBean(tb);
1937 		assertTrue(tb.wasDestroyed());
1938 	}
1939 
1940 	@Test
1941 	public void testConfigureBean() {
1942 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1943 		MutablePropertyValues pvs = new MutablePropertyValues();
1944 		pvs.add("age", "99");
1945 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1946 		bd.setPropertyValues(pvs);
1947 		lbf.registerBeanDefinition("test", bd);
1948 		TestBean tb = new TestBean();
1949 		assertEquals(0, tb.getAge());
1950 		lbf.configureBean(tb, "test");
1951 		assertEquals(99, tb.getAge());
1952 		assertSame(lbf, tb.getBeanFactory());
1953 		assertNull(tb.getSpouse());
1954 	}
1955 
1956 	@Test
1957 	public void testConfigureBeanWithAutowiring() {
1958 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1959 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1960 		lbf.registerBeanDefinition("spouse", bd);
1961 		MutablePropertyValues pvs = new MutablePropertyValues();
1962 		pvs.add("age", "99");
1963 		RootBeanDefinition tbd = new RootBeanDefinition(TestBean.class);
1964 		tbd.setAutowireMode(RootBeanDefinition.AUTOWIRE_BY_NAME);
1965 		lbf.registerBeanDefinition("test", tbd);
1966 		TestBean tb = new TestBean();
1967 		lbf.configureBean(tb, "test");
1968 		assertSame(lbf, tb.getBeanFactory());
1969 		TestBean spouse = (TestBean) lbf.getBean("spouse");
1970 		assertEquals(spouse, tb.getSpouse());
1971 	}
1972 
1973 	@Test
1974 	public void testExtensiveCircularReference() {
1975 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1976 		for (int i = 0; i < 1000; i++) {
1977 			MutablePropertyValues pvs = new MutablePropertyValues();
1978 			pvs.addPropertyValue(new PropertyValue("spouse", new RuntimeBeanReference("bean" + (i < 99 ? i + 1 : 0))));
1979 			RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
1980 			bd.setPropertyValues(pvs);
1981 			lbf.registerBeanDefinition("bean" + i, bd);
1982 		}
1983 		lbf.preInstantiateSingletons();
1984 		for (int i = 0; i < 1000; i++) {
1985 			TestBean bean = (TestBean) lbf.getBean("bean" + i);
1986 			TestBean otherBean = (TestBean) lbf.getBean("bean" + (i < 99 ? i + 1 : 0));
1987 			assertTrue(bean.getSpouse() == otherBean);
1988 		}
1989 	}
1990 
1991 	@Test
1992 	public void testCircularReferenceThroughAutowiring() {
1993 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
1994 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyBean.class);
1995 		bd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
1996 		lbf.registerBeanDefinition("test", bd);
1997 		try {
1998 			lbf.preInstantiateSingletons();
1999 			fail("Should have thrown UnsatisfiedDependencyException");
2000 		}
2001 		catch (UnsatisfiedDependencyException expected) {
2002 		}
2003 	}
2004 
2005 	@Test
2006 	public void testCircularReferenceThroughFactoryBeanAutowiring() {
2007 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2008 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyFactoryBean.class);
2009 		bd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
2010 		lbf.registerBeanDefinition("test", bd);
2011 		try {
2012 			lbf.preInstantiateSingletons();
2013 			fail("Should have thrown UnsatisfiedDependencyException");
2014 		}
2015 		catch (UnsatisfiedDependencyException expected) {
2016 		}
2017 	}
2018 
2019 	@Test
2020 	public void testCircularReferenceThroughFactoryBeanTypeCheck() {
2021 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2022 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyFactoryBean.class);
2023 		bd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
2024 		lbf.registerBeanDefinition("test", bd);
2025 		try {
2026 			lbf.getBeansOfType(String.class);
2027 			fail("Should have thrown UnsatisfiedDependencyException");
2028 		}
2029 		catch (UnsatisfiedDependencyException expected) {
2030 		}
2031 	}
2032 
2033 	@Test
2034 	public void testAvoidCircularReferenceThroughAutowiring() {
2035 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2036 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyFactoryBean.class);
2037 		bd.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
2038 		lbf.registerBeanDefinition("test", bd);
2039 		RootBeanDefinition bd2 = new RootBeanDefinition(String.class);
2040 		bd2.setAutowireMode(RootBeanDefinition.AUTOWIRE_CONSTRUCTOR);
2041 		lbf.registerBeanDefinition("string", bd2);
2042 		lbf.preInstantiateSingletons();
2043 	}
2044 
2045 	@Test
2046 	public void testConstructorDependencyWithClassResolution() {
2047 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2048 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyWithClassResolution.class);
2049 		bd.getConstructorArgumentValues().addGenericArgumentValue("java.lang.String");
2050 		lbf.registerBeanDefinition("test", bd);
2051 		lbf.preInstantiateSingletons();
2052 	}
2053 
2054 	@Test
2055 	public void testConstructorDependencyWithUnresolvableClass() {
2056 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2057 		RootBeanDefinition bd = new RootBeanDefinition(ConstructorDependencyWithClassResolution.class);
2058 		bd.getConstructorArgumentValues().addGenericArgumentValue("java.lang.Strin");
2059 		lbf.registerBeanDefinition("test", bd);
2060 		try {
2061 			lbf.preInstantiateSingletons();
2062 			fail("Should have thrown UnsatisfiedDependencyException");
2063 		}
2064 		catch (UnsatisfiedDependencyException expected) {
2065 			assertTrue(expected.toString().contains("java.lang.Strin"));
2066 		}
2067 	}
2068 
2069 	@Test
2070 	public void testBeanDefinitionWithInterface() {
2071 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2072 		lbf.registerBeanDefinition("test", new RootBeanDefinition(ITestBean.class));
2073 		try {
2074 			lbf.getBean("test");
2075 			fail("Should have thrown BeanCreationException");
2076 		}
2077 		catch (BeanCreationException ex) {
2078 			assertEquals("test", ex.getBeanName());
2079 			assertTrue(ex.getMessage().toLowerCase().contains("interface"));
2080 		}
2081 	}
2082 
2083 	@Test
2084 	public void testBeanDefinitionWithAbstractClass() {
2085 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2086 		lbf.registerBeanDefinition("test", new RootBeanDefinition(AbstractBeanFactory.class));
2087 		try {
2088 			lbf.getBean("test");
2089 			fail("Should have thrown BeanCreationException");
2090 		}
2091 		catch (BeanCreationException ex) {
2092 			assertEquals("test", ex.getBeanName());
2093 			assertTrue(ex.getMessage().toLowerCase().contains("abstract"));
2094 		}
2095 	}
2096 
2097 	@Test
2098 	public void testPrototypeFactoryBeanNotEagerlyCalled() {
2099 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2100 		lbf.registerBeanDefinition("test", new RootBeanDefinition(FactoryBeanThatShouldntBeCalled.class));
2101 		lbf.preInstantiateSingletons();
2102 	}
2103 
2104 	@Test
2105 	public void testLazyInitFactory() {
2106 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2107 		lbf.registerBeanDefinition("test", new RootBeanDefinition(LazyInitFactory.class));
2108 		lbf.preInstantiateSingletons();
2109 		LazyInitFactory factory = (LazyInitFactory) lbf.getBean("&test");
2110 		assertFalse(factory.initialized);
2111 	}
2112 
2113 	@Test
2114 	public void testSmartInitFactory() {
2115 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2116 		lbf.registerBeanDefinition("test", new RootBeanDefinition(EagerInitFactory.class));
2117 		lbf.preInstantiateSingletons();
2118 		EagerInitFactory factory = (EagerInitFactory) lbf.getBean("&test");
2119 		assertTrue(factory.initialized);
2120 	}
2121 
2122 	@Test
2123 	public void testPrototypeFactoryBeanNotEagerlyCalledInCaseOfBeanClassName() {
2124 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2125 		lbf.registerBeanDefinition("test",
2126 				new RootBeanDefinition(FactoryBeanThatShouldntBeCalled.class.getName(), null, null));
2127 		lbf.preInstantiateSingletons();
2128 	}
2129 
2130 	@Test
2131 	public void testPrototypeStringCreatedRepeatedly() {
2132 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2133 		RootBeanDefinition stringDef = new RootBeanDefinition(String.class);
2134 		stringDef.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2135 		stringDef.getConstructorArgumentValues().addGenericArgumentValue(new TypedStringValue("value"));
2136 		lbf.registerBeanDefinition("string", stringDef);
2137 		String val1 = lbf.getBean("string", String.class);
2138 		String val2 = lbf.getBean("string", String.class);
2139 		assertEquals("value", val1);
2140 		assertEquals("value", val2);
2141 		assertNotSame(val1, val2);
2142 	}
2143 
2144 	@Test
2145 	public void testPrototypeWithArrayConversionForConstructor() {
2146 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2147 		List<String> list = new ManagedList<String>();
2148 		list.add("myName");
2149 		list.add("myBeanName");
2150 		RootBeanDefinition bd = new RootBeanDefinition(DerivedTestBean.class);
2151 		bd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2152 		bd.getConstructorArgumentValues().addGenericArgumentValue(list);
2153 		lbf.registerBeanDefinition("test", bd);
2154 		DerivedTestBean tb = (DerivedTestBean) lbf.getBean("test");
2155 		assertEquals("myName", tb.getName());
2156 		assertEquals("myBeanName", tb.getBeanName());
2157 		DerivedTestBean tb2 = (DerivedTestBean) lbf.getBean("test");
2158 		assertTrue(tb != tb2);
2159 		assertEquals("myName", tb2.getName());
2160 		assertEquals("myBeanName", tb2.getBeanName());
2161 	}
2162 
2163 	@Test
2164 	public void testPrototypeWithArrayConversionForFactoryMethod() {
2165 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2166 		List<String> list = new ManagedList<String>();
2167 		list.add("myName");
2168 		list.add("myBeanName");
2169 		RootBeanDefinition bd = new RootBeanDefinition(DerivedTestBean.class);
2170 		bd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2171 		bd.setFactoryMethodName("create");
2172 		bd.getConstructorArgumentValues().addGenericArgumentValue(list);
2173 		lbf.registerBeanDefinition("test", bd);
2174 		DerivedTestBean tb = (DerivedTestBean) lbf.getBean("test");
2175 		assertEquals("myName", tb.getName());
2176 		assertEquals("myBeanName", tb.getBeanName());
2177 		DerivedTestBean tb2 = (DerivedTestBean) lbf.getBean("test");
2178 		assertTrue(tb != tb2);
2179 		assertEquals("myName", tb2.getName());
2180 		assertEquals("myBeanName", tb2.getBeanName());
2181 	}
2182 
2183 	@Test
2184 	public void testPrototypeCreationIsFastEnough() {
2185 		Assume.group(TestGroup.PERFORMANCE);
2186 		Assume.notLogging(factoryLog);
2187 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2188 		RootBeanDefinition rbd = new RootBeanDefinition(TestBean.class);
2189 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2190 		lbf.registerBeanDefinition("test", rbd);
2191 		StopWatch sw = new StopWatch();
2192 		sw.start("prototype");
2193 		for (int i = 0; i < 100000; i++) {
2194 			lbf.getBean("test");
2195 		}
2196 		sw.stop();
2197 		// System.out.println(sw.getTotalTimeMillis());
2198 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 3000);
2199 	}
2200 
2201 	@Test
2202 	public void testPrototypeCreationWithDependencyCheckIsFastEnough() {
2203 		Assume.group(TestGroup.PERFORMANCE);
2204 		Assume.notLogging(factoryLog);
2205 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2206 		RootBeanDefinition rbd = new RootBeanDefinition(LifecycleBean.class);
2207 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2208 		rbd.setDependencyCheck(RootBeanDefinition.DEPENDENCY_CHECK_OBJECTS);
2209 		lbf.registerBeanDefinition("test", rbd);
2210 		lbf.addBeanPostProcessor(new LifecycleBean.PostProcessor());
2211 		StopWatch sw = new StopWatch();
2212 		sw.start("prototype");
2213 		for (int i = 0; i < 100000; i++) {
2214 			lbf.getBean("test");
2215 		}
2216 		sw.stop();
2217 		// System.out.println(sw.getTotalTimeMillis());
2218 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 3000);
2219 	}
2220 
2221 	/**
2222 	 * @Test
2223 	 * public void testPrototypeCreationIsFastEnough2() throws Exception {
2224 	 * if (factoryLog.isTraceEnabled() || factoryLog.isDebugEnabled()) {
2225 	 * // Skip this test: Trace logging blows the time limit.
2226 	 * return;
2227 	 * }
2228 	 * DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2229 	 * Method setBeanNameMethod = TestBean.class.getMethod("setBeanName", String.class);
2230 	 * Method setBeanFactoryMethod = TestBean.class.getMethod("setBeanFactory", BeanFactory.class);
2231 	 * StopWatch sw = new StopWatch();
2232 	 * sw.start("prototype");
2233 	 * for (int i = 0; i < 100000; i++) {
2234 	 * TestBean tb = TestBean.class.newInstance();
2235 	 * setBeanNameMethod.invoke(tb, "test");
2236 	 * setBeanFactoryMethod.invoke(tb, lbf);
2237 	 * }
2238 	 * sw.stop();
2239 	 * // System.out.println(sw.getTotalTimeMillis());
2240 	 * assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 500);
2241 	 * }
2242 	 */
2243 
2244 	@Test
2245 	@Ignore  // TODO re-enable when ConstructorResolver TODO sorted out
2246 	public void testPrototypeCreationWithConstructorArgumentsIsFastEnough() {
2247 		Assume.group(TestGroup.PERFORMANCE);
2248 		Assume.notLogging(factoryLog);
2249 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2250 		RootBeanDefinition rbd = new RootBeanDefinition(TestBean.class);
2251 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2252 		rbd.getConstructorArgumentValues().addGenericArgumentValue("juergen");
2253 		rbd.getConstructorArgumentValues().addGenericArgumentValue("99");
2254 		lbf.registerBeanDefinition("test", rbd);
2255 		StopWatch sw = new StopWatch();
2256 		sw.start("prototype");
2257 		for (int i = 0; i < 100000; i++) {
2258 			TestBean tb = (TestBean) lbf.getBean("test");
2259 			assertEquals("juergen", tb.getName());
2260 			assertEquals(99, tb.getAge());
2261 		}
2262 		sw.stop();
2263 		// System.out.println(sw.getTotalTimeMillis());
2264 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 3000);
2265 	}
2266 
2267 	/**
2268 	 * @Test
2269 	 * public void testPrototypeCreationWithConstructorArgumentsIsFastEnough2() throws Exception {
2270 	 * if (factoryLog.isTraceEnabled() || factoryLog.isDebugEnabled()) {
2271 	 * // Skip this test: Trace logging blows the time limit.
2272 	 * return;
2273 	 * }
2274 	 * DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2275 	 * Constructor<TestBean> ctor = TestBean.class.getConstructor(String.class, int.class);
2276 	 * Method setBeanNameMethod = TestBean.class.getMethod("setBeanName", String.class);
2277 	 * Method setBeanFactoryMethod = TestBean.class.getMethod("setBeanFactory", BeanFactory.class);
2278 	 * StopWatch sw = new StopWatch();
2279 	 * sw.start("prototype");
2280 	 * for (int i = 0; i < 100000; i++) {
2281 	 * TestBean tb = ctor.newInstance("juergen", 99);
2282 	 * setBeanNameMethod.invoke(tb, "test");
2283 	 * setBeanFactoryMethod.invoke(tb, lbf);
2284 	 * assertEquals("juergen", tb.getName());
2285 	 * assertEquals(99, tb.getAge());
2286 	 * }
2287 	 * sw.stop();
2288 	 * // System.out.println(sw.getTotalTimeMillis());
2289 	 * assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 1500);
2290 	 * }
2291 	 */
2292 
2293 	@Test
2294 	public void testPrototypeCreationWithResolvedConstructorArgumentsIsFastEnough() {
2295 		Assume.group(TestGroup.PERFORMANCE);
2296 		Assume.notLogging(factoryLog);
2297 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2298 		RootBeanDefinition rbd = new RootBeanDefinition(TestBean.class);
2299 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2300 		rbd.getConstructorArgumentValues().addGenericArgumentValue(new RuntimeBeanReference("spouse"));
2301 		lbf.registerBeanDefinition("test", rbd);
2302 		lbf.registerBeanDefinition("spouse", new RootBeanDefinition(TestBean.class));
2303 		TestBean spouse = (TestBean) lbf.getBean("spouse");
2304 		StopWatch sw = new StopWatch();
2305 		sw.start("prototype");
2306 		for (int i = 0; i < 100000; i++) {
2307 			TestBean tb = (TestBean) lbf.getBean("test");
2308 			assertSame(spouse, tb.getSpouse());
2309 		}
2310 		sw.stop();
2311 		// System.out.println(sw.getTotalTimeMillis());
2312 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 4000);
2313 	}
2314 
2315 	@Test
2316 	public void testPrototypeCreationWithPropertiesIsFastEnough() {
2317 		Assume.group(TestGroup.PERFORMANCE);
2318 		Assume.notLogging(factoryLog);
2319 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2320 		RootBeanDefinition rbd = new RootBeanDefinition(TestBean.class);
2321 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2322 		rbd.getPropertyValues().add("name", "juergen");
2323 		rbd.getPropertyValues().add("age", "99");
2324 		lbf.registerBeanDefinition("test", rbd);
2325 		StopWatch sw = new StopWatch();
2326 		sw.start("prototype");
2327 		for (int i = 0; i < 100000; i++) {
2328 			TestBean tb = (TestBean) lbf.getBean("test");
2329 			assertEquals("juergen", tb.getName());
2330 			assertEquals(99, tb.getAge());
2331 		}
2332 		sw.stop();
2333 		// System.out.println(sw.getTotalTimeMillis());
2334 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 3000);
2335 	}
2336 
2337 	/**
2338 	 * public void testPrototypeCreationWithPropertiesIsFastEnough2() throws Exception {
2339 	 * if (factoryLog.isTraceEnabled() || factoryLog.isDebugEnabled()) {
2340 	 * // Skip this test: Trace logging blows the time limit.
2341 	 * return;
2342 	 * }
2343 	 * DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2344 	 * StopWatch sw = new StopWatch();
2345 	 * Method setBeanNameMethod = TestBean.class.getMethod("setBeanName", String.class);
2346 	 * Method setBeanFactoryMethod = TestBean.class.getMethod("setBeanFactory", BeanFactory.class);
2347 	 * Method setNameMethod = TestBean.class.getMethod("setName", String.class);
2348 	 * Method setAgeMethod = TestBean.class.getMethod("setAge", int.class);
2349 	 * sw.start("prototype");
2350 	 * for (int i = 0; i < 100000; i++) {
2351 	 * TestBean tb = TestBean.class.newInstance();
2352 	 * setBeanNameMethod.invoke(tb, "test");
2353 	 * setBeanFactoryMethod.invoke(tb, lbf);
2354 	 * setNameMethod.invoke(tb, "juergen");
2355 	 * setAgeMethod.invoke(tb, 99);
2356 	 * }
2357 	 * sw.stop();
2358 	 * // System.out.println(sw.getTotalTimeMillis());
2359 	 * assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 750);
2360 	 * }
2361 	 */
2362 	@Test
2363 	public void testPrototypeCreationWithResolvedPropertiesIsFastEnough() {
2364 		Assume.group(TestGroup.PERFORMANCE);
2365 		Assume.notLogging(factoryLog);
2366 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2367 		RootBeanDefinition rbd = new RootBeanDefinition(TestBean.class);
2368 		rbd.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2369 		rbd.getPropertyValues().add("spouse", new RuntimeBeanReference("spouse"));
2370 		lbf.registerBeanDefinition("test", rbd);
2371 		lbf.registerBeanDefinition("spouse", new RootBeanDefinition(TestBean.class));
2372 		TestBean spouse = (TestBean) lbf.getBean("spouse");
2373 		StopWatch sw = new StopWatch();
2374 		sw.start("prototype");
2375 		for (int i = 0; i < 100000; i++) {
2376 			TestBean tb = (TestBean) lbf.getBean("test");
2377 			assertSame(spouse, tb.getSpouse());
2378 		}
2379 		sw.stop();
2380 		// System.out.println(sw.getTotalTimeMillis());
2381 		assertTrue("Prototype creation took too long: " + sw.getTotalTimeMillis(), sw.getTotalTimeMillis() < 4000);
2382 	}
2383 
2384 	@Test
2385 	public void testBeanPostProcessorWithWrappedObjectAndDisposableBean() {
2386 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2387 		RootBeanDefinition bd = new RootBeanDefinition(BeanWithDisposableBean.class);
2388 		lbf.registerBeanDefinition("test", bd);
2389 		lbf.addBeanPostProcessor(new BeanPostProcessor() {
2390 			@Override
2391 			public Object postProcessBeforeInitialization(Object bean, String beanName) {
2392 				return new TestBean();
2393 			}
2394 			@Override
2395 			public Object postProcessAfterInitialization(Object bean, String beanName) {
2396 				return bean;
2397 			}
2398 		});
2399 		BeanWithDisposableBean.closed = false;
2400 		lbf.preInstantiateSingletons();
2401 		lbf.destroySingletons();
2402 		assertTrue("Destroy method invoked", BeanWithDisposableBean.closed);
2403 	}
2404 
2405 	@Test
2406 	public void testBeanPostProcessorWithWrappedObjectAndCloseable() {
2407 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2408 		RootBeanDefinition bd = new RootBeanDefinition(BeanWithCloseable.class);
2409 		lbf.registerBeanDefinition("test", bd);
2410 		lbf.addBeanPostProcessor(new BeanPostProcessor() {
2411 			@Override
2412 			public Object postProcessBeforeInitialization(Object bean, String beanName) {
2413 				return new TestBean();
2414 			}
2415 			@Override
2416 			public Object postProcessAfterInitialization(Object bean, String beanName) {
2417 				return bean;
2418 			}
2419 		});
2420 		BeanWithDisposableBean.closed = false;
2421 		lbf.preInstantiateSingletons();
2422 		lbf.destroySingletons();
2423 		assertTrue("Destroy method invoked", BeanWithCloseable.closed);
2424 	}
2425 
2426 	@Test
2427 	public void testBeanPostProcessorWithWrappedObjectAndDestroyMethod() {
2428 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2429 		RootBeanDefinition bd = new RootBeanDefinition(BeanWithDestroyMethod.class);
2430 		bd.setDestroyMethodName("close");
2431 		lbf.registerBeanDefinition("test", bd);
2432 		lbf.addBeanPostProcessor(new BeanPostProcessor() {
2433 			@Override
2434 			public Object postProcessBeforeInitialization(Object bean, String beanName) {
2435 				return new TestBean();
2436 			}
2437 			@Override
2438 			public Object postProcessAfterInitialization(Object bean, String beanName) {
2439 				return bean;
2440 			}
2441 		});
2442 		BeanWithDestroyMethod.closed = false;
2443 		lbf.preInstantiateSingletons();
2444 		lbf.destroySingletons();
2445 		assertTrue("Destroy method invoked", BeanWithDestroyMethod.closed);
2446 	}
2447 
2448 	@Test
2449 	public void testFindTypeOfSingletonFactoryMethodOnBeanInstance() {
2450 		findTypeOfPrototypeFactoryMethodOnBeanInstance(true);
2451 	}
2452 
2453 	@Test
2454 	public void testFindTypeOfPrototypeFactoryMethodOnBeanInstance() {
2455 		findTypeOfPrototypeFactoryMethodOnBeanInstance(false);
2456 	}
2457 
2458 	/**
2459 	 * @param singleton whether the bean created from the factory method on
2460 	 * the bean instance should be a singleton or prototype. This flag is
2461 	 * used to allow checking of the new ability in 1.2.4 to determine the type
2462 	 * of a prototype created from invoking a factory method on a bean instance
2463 	 * in the factory.
2464 	 */
2465 	private void findTypeOfPrototypeFactoryMethodOnBeanInstance(boolean singleton) {
2466 		String expectedNameFromProperties = "tony";
2467 		String expectedNameFromArgs = "gordon";
2468 
2469 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2470 		RootBeanDefinition instanceFactoryDefinition = new RootBeanDefinition(BeanWithFactoryMethod.class);
2471 		MutablePropertyValues pvs = new MutablePropertyValues();
2472 		pvs.add("name", expectedNameFromProperties);
2473 		instanceFactoryDefinition.setPropertyValues(pvs);
2474 		lbf.registerBeanDefinition("factoryBeanInstance", instanceFactoryDefinition);
2475 
2476 		RootBeanDefinition factoryMethodDefinitionWithProperties = new RootBeanDefinition();
2477 		factoryMethodDefinitionWithProperties.setFactoryBeanName("factoryBeanInstance");
2478 		factoryMethodDefinitionWithProperties.setFactoryMethodName("create");
2479 		if (!singleton) {
2480 			factoryMethodDefinitionWithProperties.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2481 		}
2482 		lbf.registerBeanDefinition("fmWithProperties", factoryMethodDefinitionWithProperties);
2483 
2484 		RootBeanDefinition factoryMethodDefinitionGeneric = new RootBeanDefinition();
2485 		factoryMethodDefinitionGeneric.setFactoryBeanName("factoryBeanInstance");
2486 		factoryMethodDefinitionGeneric.setFactoryMethodName("createGeneric");
2487 		if (!singleton) {
2488 			factoryMethodDefinitionGeneric.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2489 		}
2490 		lbf.registerBeanDefinition("fmGeneric", factoryMethodDefinitionGeneric);
2491 
2492 		RootBeanDefinition factoryMethodDefinitionWithArgs = new RootBeanDefinition();
2493 		factoryMethodDefinitionWithArgs.setFactoryBeanName("factoryBeanInstance");
2494 		factoryMethodDefinitionWithArgs.setFactoryMethodName("createWithArgs");
2495 		ConstructorArgumentValues cvals = new ConstructorArgumentValues();
2496 		cvals.addGenericArgumentValue(expectedNameFromArgs);
2497 		factoryMethodDefinitionWithArgs.setConstructorArgumentValues(cvals);
2498 		if (!singleton) {
2499 			factoryMethodDefinitionWithArgs.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2500 		}
2501 		lbf.registerBeanDefinition("fmWithArgs", factoryMethodDefinitionWithArgs);
2502 
2503 		assertEquals(4, lbf.getBeanDefinitionCount());
2504 		List<String> tbNames = Arrays.asList(lbf.getBeanNamesForType(TestBean.class));
2505 		assertTrue(tbNames.contains("fmWithProperties"));
2506 		assertTrue(tbNames.contains("fmWithArgs"));
2507 		assertEquals(2, tbNames.size());
2508 
2509 		TestBean tb = (TestBean) lbf.getBean("fmWithProperties");
2510 		TestBean second = (TestBean) lbf.getBean("fmWithProperties");
2511 		if (singleton) {
2512 			assertSame(tb, second);
2513 		}
2514 		else {
2515 			assertNotSame(tb, second);
2516 		}
2517 		assertEquals(expectedNameFromProperties, tb.getName());
2518 
2519 		tb = (TestBean) lbf.getBean("fmGeneric");
2520 		second = (TestBean) lbf.getBean("fmGeneric");
2521 		if (singleton) {
2522 			assertSame(tb, second);
2523 		}
2524 		else {
2525 			assertNotSame(tb, second);
2526 		}
2527 		assertEquals(expectedNameFromProperties, tb.getName());
2528 
2529 		TestBean tb2 = (TestBean) lbf.getBean("fmWithArgs");
2530 		second = (TestBean) lbf.getBean("fmWithArgs");
2531 		if (singleton) {
2532 			assertSame(tb2, second);
2533 		}
2534 		else {
2535 			assertNotSame(tb2, second);
2536 		}
2537 		assertEquals(expectedNameFromArgs, tb2.getName());
2538 	}
2539 
2540 	@Test(expected = IllegalStateException.class)
2541 	public void testScopingBeanToUnregisteredScopeResultsInAnException() throws Exception {
2542 		BeanDefinitionBuilder builder = BeanDefinitionBuilder.rootBeanDefinition(TestBean.class);
2543 		AbstractBeanDefinition beanDefinition = builder.getBeanDefinition();
2544 		beanDefinition.setScope("he put himself so low could hardly look me in the face");
2545 
2546 		DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
2547 		factory.registerBeanDefinition("testBean", beanDefinition);
2548 		factory.getBean("testBean");
2549 	}
2550 
2551 	@Test
2552 	public void testExplicitScopeInheritanceForChildBeanDefinitions() throws Exception {
2553 		String theChildScope = "bonanza!";
2554 
2555 		RootBeanDefinition parent = new RootBeanDefinition();
2556 		parent.setScope(RootBeanDefinition.SCOPE_PROTOTYPE);
2557 
2558 		AbstractBeanDefinition child = BeanDefinitionBuilder.childBeanDefinition("parent").getBeanDefinition();
2559 		child.setBeanClass(TestBean.class);
2560 		child.setScope(theChildScope);
2561 
2562 		DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
2563 		factory.registerBeanDefinition("parent", parent);
2564 		factory.registerBeanDefinition("child", child);
2565 
2566 		AbstractBeanDefinition def = (AbstractBeanDefinition) factory.getBeanDefinition("child");
2567 		assertEquals("Child 'scope' not overriding parent scope (it must).", theChildScope, def.getScope());
2568 	}
2569 
2570 	@Test
2571 	public void testScopeInheritanceForChildBeanDefinitions() throws Exception {
2572 		RootBeanDefinition parent = new RootBeanDefinition();
2573 		parent.setScope("bonanza!");
2574 
2575 		AbstractBeanDefinition child = new ChildBeanDefinition("parent");
2576 		child.setBeanClass(TestBean.class);
2577 
2578 		DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
2579 		factory.registerBeanDefinition("parent", parent);
2580 		factory.registerBeanDefinition("child", child);
2581 
2582 		BeanDefinition def = factory.getMergedBeanDefinition("child");
2583 		assertEquals("Child 'scope' not inherited", "bonanza!", def.getScope());
2584 	}
2585 
2586 	@Test
2587 	public void testFieldSettingWithInstantiationAwarePostProcessorNoShortCircuit() {
2588 		doTestFieldSettingWithInstantiationAwarePostProcessor(false);
2589 	}
2590 
2591 	@Test
2592 	public void testFieldSettingWithInstantiationAwarePostProcessorWithShortCircuit() {
2593 		doTestFieldSettingWithInstantiationAwarePostProcessor(true);
2594 	}
2595 
2596 	private void doTestFieldSettingWithInstantiationAwarePostProcessor(final boolean skipPropertyPopulation) {
2597 		DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2598 		RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
2599 		int ageSetByPropertyValue = 27;
2600 		bd.getPropertyValues().addPropertyValue(new PropertyValue("age", new Integer(ageSetByPropertyValue)));
2601 		lbf.registerBeanDefinition("test", bd);
2602 		final String nameSetOnField = "nameSetOnField";
2603 		lbf.addBeanPostProcessor(new InstantiationAwareBeanPostProcessorAdapter() {
2604 			@Override
2605 			public boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
2606 				TestBean tb = (TestBean) bean;
2607 				try {
2608 					Field f = TestBean.class.getDeclaredField("name");
2609 					f.setAccessible(true);
2610 					f.set(tb, nameSetOnField);
2611 					return !skipPropertyPopulation;
2612 				}
2613 				catch (Exception ex) {
2614 					fail("Unexpected exception: " + ex);
2615 					// Keep compiler happy about return
2616 					throw new IllegalStateException();
2617 				}
2618 			}
2619 		});
2620 		lbf.preInstantiateSingletons();
2621 		TestBean tb = (TestBean) lbf.getBean("test");
2622 		assertEquals("Name was set on field by IAPP", nameSetOnField, tb.getName());
2623 		if (!skipPropertyPopulation) {
2624 			assertEquals("Property value still set", ageSetByPropertyValue, tb.getAge());
2625 		}
2626 		else {
2627 			assertEquals("Property value was NOT set and still has default value", 0, tb.getAge());
2628 		}
2629 	}
2630 
2631 	@SuppressWarnings("unchecked")
2632 	@Test
2633 	public void testInitSecurityAwarePrototypeBean() {
2634 		final DefaultListableBeanFactory lbf = new DefaultListableBeanFactory();
2635 		RootBeanDefinition bd = new RootBeanDefinition(TestSecuredBean.class);
2636 		bd.setScope(ConfigurableBeanFactory.SCOPE_PROTOTYPE);
2637 		bd.setInitMethodName("init");
2638 		lbf.registerBeanDefinition("test", bd);
2639 		final Subject subject = new Subject();
2640 		subject.getPrincipals().add(new TestPrincipal("user1"));
2641 
2642 		TestSecuredBean bean = (TestSecuredBean) Subject.doAsPrivileged(subject,
2643 				new PrivilegedAction() {
2644 					@Override
2645 					public Object run() {
2646 						return lbf.getBean("test");
2647 					}
2648 				}, null);
2649 		assertNotNull(bean);
2650 		assertEquals("user1", bean.getUserName());
2651 	}
2652 
2653 	@Test
2654 	public void testContainsBeanReturnsTrueEvenForAbstractBeanDefinition() {
2655 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
2656 		bf.registerBeanDefinition("abs", BeanDefinitionBuilder
2657 				.rootBeanDefinition(TestBean.class).setAbstract(true).getBeanDefinition());
2658 		assertThat(bf.containsBean("abs"), equalTo(true));
2659 		assertThat(bf.containsBean("bogus"), equalTo(false));
2660 	}
2661 
2662 	@Test
2663 	public void resolveEmbeddedValue() throws Exception {
2664 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
2665 		StringValueResolver r1 = mock(StringValueResolver.class);
2666 		StringValueResolver r2 = mock(StringValueResolver.class);
2667 		StringValueResolver r3 = mock(StringValueResolver.class);
2668 		bf.addEmbeddedValueResolver(r1);
2669 		bf.addEmbeddedValueResolver(r2);
2670 		bf.addEmbeddedValueResolver(r3);
2671 		given(r1.resolveStringValue("A")).willReturn("B");
2672 		given(r2.resolveStringValue("B")).willReturn(null);
2673 		given(r3.resolveStringValue(isNull(String.class))).willThrow(new IllegalArgumentException());
2674 
2675 		bf.resolveEmbeddedValue("A");
2676 
2677 		verify(r1).resolveStringValue("A");
2678 		verify(r2).resolveStringValue("B");
2679 		verify(r3, never()).resolveStringValue(isNull(String.class));
2680 	}
2681 
2682 
2683 	static class A { }
2684 	static class B { }
2685 
2686 	/**
2687 	 * Test that by-type bean lookup caching is working effectively by searching for a
2688 	 * bean of type B 10K times within a container having 1K additional beans of type A.
2689 	 * Prior to by-type caching, each bean lookup would traverse the entire container
2690 	 * (all 1001 beans), performing expensive assignability checks, etc. Now these
2691 	 * operations are necessary only once, providing a dramatic performance improvement.
2692 	 * On load-free modern hardware (e.g. an 8-core MPB), this method should complete well
2693 	 * under the 1000 ms timeout, usually ~= 300ms. With caching removed and on the same
2694 	 * hardware the method will take ~13000 ms. See SPR-6870.
2695 	 */
2696 	@Test(timeout=1000)
2697 	public void testByTypeLookupIsFastEnough() {
2698 		Assume.group(TestGroup.PERFORMANCE);
2699 		DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
2700 
2701 		for (int i = 0; i < 1000; i++) {
2702 			bf.registerBeanDefinition("a"+i, new RootBeanDefinition(A.class));
2703 		}
2704 		bf.registerBeanDefinition("b", new RootBeanDefinition(B.class));
2705 
2706 		bf.freezeConfiguration();
2707 
2708 		for (int i=0; i<10000; i++) {
2709 			bf.getBean(B.class);
2710 		}
2711 	}
2712 
2713 
2714 	public static class NoDependencies {
2715 
2716 		private NoDependencies() {
2717 		}
2718 	}
2719 
2720 
2721 	public static class ConstructorDependency implements BeanNameAware {
2722 
2723 		public TestBean spouse;
2724 
2725 		public int spouseAge;
2726 
2727 		private String beanName;
2728 
2729 		public ConstructorDependency(TestBean spouse) {
2730 			this.spouse = spouse;
2731 		}
2732 
2733 		public ConstructorDependency(int spouseAge) {
2734 			this.spouseAge = spouseAge;
2735 		}
2736 
2737 		@SuppressWarnings("unused")
2738 		private ConstructorDependency(TestBean spouse, TestBean otherSpouse) {
2739 			throw new IllegalArgumentException("Should never be called");
2740 		}
2741 
2742 		@Override
2743 		public void setBeanName(String name) {
2744 			this.beanName = name;
2745 		}
2746 	}
2747 
2748 
2749 	public static class UnsatisfiedConstructorDependency {
2750 
2751 		public UnsatisfiedConstructorDependency(TestBean t, SideEffectBean b) {
2752 		}
2753 	}
2754 
2755 
2756 	public static class ConstructorDependencyBean {
2757 
2758 		public ConstructorDependencyBean(ConstructorDependencyBean dependency) {
2759 		}
2760 	}
2761 
2762 
2763 	public static class ConstructorDependencyFactoryBean implements FactoryBean<Object> {
2764 
2765 		public ConstructorDependencyFactoryBean(String dependency) {
2766 		}
2767 
2768 		@Override
2769 		public Object getObject() {
2770 			return "test";
2771 		}
2772 
2773 		@Override
2774 		public Class<?> getObjectType() {
2775 			return String.class;
2776 		}
2777 
2778 		@Override
2779 		public boolean isSingleton() {
2780 			return true;
2781 		}
2782 	}
2783 
2784 
2785 	public static class ConstructorDependencyWithClassResolution {
2786 
2787 		public ConstructorDependencyWithClassResolution(Class<?> clazz) {
2788 		}
2789 
2790 		public ConstructorDependencyWithClassResolution() {
2791 		}
2792 	}
2793 
2794 
2795 	public static class BeanWithDisposableBean implements DisposableBean {
2796 
2797 		private static boolean closed;
2798 
2799 		@Override
2800 		public void destroy() {
2801 			closed = true;
2802 		}
2803 	}
2804 
2805 
2806 	public static class BeanWithCloseable implements Closeable {
2807 
2808 		private static boolean closed;
2809 
2810 		@Override
2811 		public void close() {
2812 			closed = true;
2813 		}
2814 	}
2815 
2816 
2817 	public static class BeanWithDestroyMethod {
2818 
2819 		private static boolean closed;
2820 
2821 		public void close() {
2822 			closed = true;
2823 		}
2824 	}
2825 
2826 
2827 	public static class BeanWithFactoryMethod {
2828 
2829 		private String name;
2830 
2831 		public void setName(String name) {
2832 			this.name = name;
2833 		}
2834 
2835 		public TestBean create() {
2836 			TestBean tb = new TestBean();
2837 			tb.setName(this.name);
2838 			return tb;
2839 		}
2840 
2841 		public TestBean createWithArgs(String arg) {
2842 			TestBean tb = new TestBean();
2843 			tb.setName(arg);
2844 			return tb;
2845 		}
2846 
2847 		public Object createGeneric() {
2848 			return create();
2849 		}
2850 	}
2851 
2852 
2853 	public static class FactoryBeanThatShouldntBeCalled implements FactoryBean<Object> {
2854 
2855 		@Override
2856 		public Object getObject() {
2857 			throw new IllegalStateException();
2858 		}
2859 
2860 		@Override
2861 		public Class<?> getObjectType() {
2862 			return null;
2863 		}
2864 
2865 		@Override
2866 		public boolean isSingleton() {
2867 			return false;
2868 		}
2869 	}
2870 
2871 
2872 	public static class LazyInitFactory implements FactoryBean<Object> {
2873 
2874 		public boolean initialized = false;
2875 
2876 		@Override
2877 		public Object getObject() throws Exception {
2878 			this.initialized = true;
2879 			return "";
2880 		}
2881 
2882 		@Override
2883 		public Class<?> getObjectType() {
2884 			return String.class;
2885 		}
2886 
2887 		@Override
2888 		public boolean isSingleton() {
2889 			return true;
2890 		}
2891 	}
2892 
2893 
2894 	public static class EagerInitFactory implements SmartFactoryBean<Object> {
2895 
2896 		public boolean initialized = false;
2897 
2898 		@Override
2899 		public Object getObject() throws Exception {
2900 			this.initialized = true;
2901 			return "";
2902 		}
2903 
2904 		@Override
2905 		public Class<?> getObjectType() {
2906 			return String.class;
2907 		}
2908 
2909 		@Override
2910 		public boolean isSingleton() {
2911 			return true;
2912 		}
2913 
2914 		@Override
2915 		public boolean isPrototype() {
2916 			return false;
2917 		}
2918 
2919 		@Override
2920 		public boolean isEagerInit() {
2921 			return true;
2922 		}
2923 	}
2924 
2925 
2926 	public static class TestBeanFactory {
2927 
2928 		public static boolean initialized = false;
2929 
2930 		public TestBeanFactory() {
2931 			initialized = true;
2932 		}
2933 
2934 		public static TestBean createTestBean() {
2935 			return new TestBean();
2936 		}
2937 
2938 		public TestBean createTestBeanNonStatic() {
2939 			return new TestBean();
2940 		}
2941 	}
2942 
2943 
2944 	public static class ArrayBean {
2945 
2946 		private Integer[] integerArray;
2947 
2948 		private Resource[] resourceArray;
2949 
2950 		public ArrayBean() {
2951 		}
2952 
2953 		public ArrayBean(Integer[] integerArray) {
2954 			this.integerArray = integerArray;
2955 		}
2956 
2957 		public ArrayBean(Integer[] integerArray, Resource[] resourceArray) {
2958 			this.integerArray = integerArray;
2959 			this.resourceArray = resourceArray;
2960 		}
2961 
2962 		public Integer[] getIntegerArray() {
2963 			return this.integerArray;
2964 		}
2965 
2966 		public void setResourceArray(Resource[] resourceArray) {
2967 			this.resourceArray = resourceArray;
2968 		}
2969 
2970 		public Resource[] getResourceArray() {
2971 			return this.resourceArray;
2972 		}
2973 	}
2974 
2975 
2976 	/**
2977 	 * Bean with a dependency on a {@link FactoryBean}.
2978 	 */
2979 	@SuppressWarnings("unused")
2980 	private static class FactoryBeanDependentBean {
2981 
2982 		private FactoryBean<?> factoryBean;
2983 
2984 
2985 		public final FactoryBean<?> getFactoryBean() {
2986 			return this.factoryBean;
2987 		}
2988 
2989 		public final void setFactoryBean(final FactoryBean<?> factoryBean) {
2990 			this.factoryBean = factoryBean;
2991 		}
2992 	}
2993 
2994 
2995 	private static class CustomTypeConverter implements TypeConverter {
2996 
2997 		private final NumberFormat numberFormat;
2998 
2999 		public CustomTypeConverter(NumberFormat numberFormat) {
3000 			this.numberFormat = numberFormat;
3001 		}
3002 
3003 		@Override
3004 		@SuppressWarnings("unchecked")
3005 		public Object convertIfNecessary(Object value, Class requiredType) {
3006 			if (value instanceof String && Float.class.isAssignableFrom(requiredType)) {
3007 				try {
3008 					return new Float(this.numberFormat.parse((String) value).floatValue());
3009 				}
3010 				catch (ParseException ex) {
3011 					throw new TypeMismatchException(value, requiredType, ex);
3012 				}
3013 			}
3014 			else if (value instanceof String && int.class.isAssignableFrom(requiredType)) {
3015 				return new Integer(5);
3016 			}
3017 			else {
3018 				return value;
3019 			}
3020 		}
3021 
3022 		@Override
3023 		@SuppressWarnings("unchecked")
3024 		public Object convertIfNecessary(Object value, Class requiredType, MethodParameter methodParam) {
3025 			return convertIfNecessary(value, requiredType);
3026 		}
3027 
3028 		@Override
3029 		@SuppressWarnings("unchecked")
3030 		public Object convertIfNecessary(Object value, Class requiredType, Field field) {
3031 			return convertIfNecessary(value, requiredType);
3032 		}
3033 	}
3034 
3035 
3036 	private static class TestPrincipal implements Principal {
3037 
3038 		private String name;
3039 
3040 		public TestPrincipal(String name) {
3041 			this.name = name;
3042 		}
3043 
3044 		@Override
3045 		public String getName() {
3046 			return this.name;
3047 		}
3048 
3049 		@Override
3050 		public boolean equals(Object obj) {
3051 			if (obj == this) {
3052 				return true;
3053 			}
3054 			if (!(obj instanceof TestPrincipal)) {
3055 				return false;
3056 			}
3057 			TestPrincipal p = (TestPrincipal) obj;
3058 			return this.name.equals(p.name);
3059 		}
3060 
3061 		@Override
3062 		public int hashCode() {
3063 			return this.name.hashCode();
3064 		}
3065 	}
3066 
3067 
3068 	@SuppressWarnings("unused")
3069 	private static class TestSecuredBean {
3070 
3071 		private String userName;
3072 
3073 		public void init() {
3074 			AccessControlContext acc = AccessController.getContext();
3075 			Subject subject = Subject.getSubject(acc);
3076 			if (subject == null) {
3077 				return;
3078 			}
3079 			setNameFromPrincipal(subject.getPrincipals());
3080 		}
3081 
3082 		private void setNameFromPrincipal(Set<Principal> principals) {
3083 			if (principals == null) {
3084 				return;
3085 			}
3086 			for (Iterator<Principal> it = principals.iterator(); it.hasNext();) {
3087 				Principal p = it.next();
3088 				this.userName = p.getName();
3089 				return;
3090 			}
3091 		}
3092 
3093 		public String getUserName() {
3094 			return this.userName;
3095 		}
3096 	}
3097 
3098 
3099 	@SuppressWarnings("unused")
3100 	private static class KnowsIfInstantiated {
3101 
3102 		private static boolean instantiated;
3103 
3104 		public static void clearInstantiationRecord() {
3105 			instantiated = false;
3106 		}
3107 
3108 		public static boolean wasInstantiated() {
3109 			return instantiated;
3110 		}
3111 
3112 		public KnowsIfInstantiated() {
3113 			instantiated = true;
3114 		}
3115 
3116 	}
3117 
3118 
3119 	@Priority(5)
3120 	private static class HighPriorityTestBean extends TestBean {
3121 	}
3122 
3123 
3124 	@Priority(500)
3125 	private static class LowPriorityTestBean extends TestBean {
3126 	}
3127 
3128 
3129 	private static class NullTestBeanFactoryBean<T> implements FactoryBean<TestBean> {
3130 
3131 		@Override
3132 		public TestBean getObject() throws Exception {
3133 			return null;
3134 		}
3135 
3136 		@Override
3137 		public Class<?> getObjectType() {
3138 			return TestBean.class;
3139 		}
3140 
3141 		@Override
3142 		public boolean isSingleton() {
3143 			return true;
3144 		}
3145 	}
3146 
3147 }