IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Spring Java Discussion :

Spring bean conflit


Sujet :

Spring Java

  1. #1
    Membre du Club
    Inscrit en
    Août 2002
    Messages
    67
    Détails du profil
    Informations forums :
    Inscription : Août 2002
    Messages : 67
    Points : 48
    Points
    48
    Par défaut Spring bean conflit
    bonjour,

    je developpe une API (jar) qui a besoin d'un bean spring (LocalValidatorFactoryBean).
    Donc le ApplicationContext.xml doit contenir une declaration de ce bean.

    Le probleme est que , dans un context spécifique comme Spring MVC, ce dernier instancie aussi ce meme bean.

    Il y a donc un conflit.

    Comment resoudre ce conflit sachant que mon api a besoin de ce bean ?


    Merci

  2. #2
    Membre confirmé
    Avatar de Khaled.Noordin
    Homme Profil pro
    Inscrit en
    Janvier 2005
    Messages
    354
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2005
    Messages : 354
    Points : 497
    Points
    497
    Billets dans le blog
    1
    Par défaut
    Je ne comprends pas bien ta question enfin si il est question de choix d'injection entre deux implémentations et/ou deux instances d'une même interface,tu peux résoudre le choix d’injection en procédant avec un qualifier, la doc springsource est ton ami

  3. #3
    Membre à l'essai
    Profil pro
    Inscrit en
    Septembre 2007
    Messages
    21
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2007
    Messages : 21
    Points : 20
    Points
    20
    Par défaut
    Je profite de la thématique soulevée par la question de l'auteur du post pour rebondir (et par la même éviter des doublons) car je suis confronté à un problème du même ordre.

    J'ai un projet dans lequel j'ai certaines classes qui portent le même nom, bien que se trouvant dans différents packages.
    Lorsque je teste unitairement mes classes, j'instancie et manipule les classes d'un même package dans une seule classe de test, avec un seul application context contenant les beans correspondant à chacune de ces classes. Pour résumer : Un package, une classe de test, un seul application context pour toutes les classes du package.

    Mon problème survient lorsque deux packages différents viennent à avoir des classes portant le même nom. Quand je lance le test, j'ai droit à chaque fois à un conflictingbeandefinitionexception. Les quelques recherches que j'ai mené ont mené à la conclusion qu'il suffisait de changer le nom des classes.

    Arborescence des classes :

    org.pack1-|
    -Foo
    -Bar
    org.pack2- |
    -Foo
    -Bar

    Extrait de l'application context de org.pack2 :

    Code xml : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
     
    <context:component-scan base-package="spring" />
     
    	<context:annotation-config />
     
    	<bean id="foo" class="org.pack2.Foo">
    		<property name="name" value="Apurav"></property>
    	</bean>
    	<bean id="anotherFoo" class="org.pack2.Foo">
    		<property name="name" value="Chauhan"></property>
    		<qualifier value="secondaryFoo"></qualifier>
    	</bean>
     
    	<bean id="bar" class="org.pack2.Bar">
    		<property name="foo" ref="foo" />
    		<property name="foo2" ref="anotherFoo" />
    	</bean>


    Classe Bar du pack2 :

    Code java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
     
    package org.pack2;
     
    import javax.annotation.Resource;
     
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.beans.factory.annotation.Qualifier;
    import org.springframework.stereotype.Component;
     
    @Component
    public class Bar {
     
    	//Je teste ici deux manières d'injecter les valeurs de l'app context dans les deux attributs de type Foo
    	@Autowired
    	@Qualifier(value="foo")
    	private Foo foo;
     
    	@Resource(name="secondaryFoo")
    	private Foo foo2;
     
    	public Foo getFoo() {
    		return this.foo;
    	}
     
    	public Foo getFoo2() {
    		return this.foo2;
    	}
     
    	public void setFoo(Foo foo) {
    		this.foo = foo;
    	}
     
    	public void setFoo2(Foo foo) {
                    this.foo2 = foo;
            }
     
    	public void printFooNames() {
    		System.out.println("foo name : " + foo.getName());
    		System.out.println("foo2 name : " + foo2.getName());
    	}
    }

    Classe Foo du pack 2 :

    Code java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
     
    package spring.annot;
     
    import org.springframework.stereotype.Component;
     
    @Component
    public class Foo {
    	private String name;
     
    	/**
             * @return the name
             */
    	public String getName() {
    		return name;
    	}
     
    	/**
             * @param name the name to set
             */
    	public void setName(String name) {
    		this.name = name;
    	}
     
    }


    Ma classe de test (dans le package pack2) :

    Code java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
     
    public class testInjectFooBar {
     
    	@Autowired
    	@Qualifier(value="bar")
    	private Bar barLamane;
     
    	@Test
    	public void test() {		
    		ClassPathXmlApplicationContext appCtx = new ClassPathXmlApplicationContext("ApplicationContext.xml");
    		Foo temp = barLamane.getFoo();
    		Assert.assertEquals(temp.getName(),"Apurav");
    		Assert.assertEquals(barLamane.getFoo2().getName(),"Chauhan");
    		appCtx.close();
    	}
     
    }

    Quand je la lance, ça me met cette exception :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
     
    org.springframework.beans.factory.BeanDefinitionStoreException: Unexpected exception parsing XML document from class path resource [ApplicationContext.xml]; nested exception is org.springframework.context.annotation.ConflictingBeanDefinitionException: Annotation-specified bean name 'bar' for bean class [org.pack1.Bar] conflicts with existing, non-compatible bean definition of same name and class [org.pack2.Bar]
    	at org.springframework.beans.factory.xml.XmlBeanDefinitionReader.doLoadBeanDefinitions(XmlBeanDefinitionReader.java:414)
    	at org.springframework.beans.factory.xml.XmlBeanDefinitionReader.loadBeanDefinitions(XmlBeanDefinitionReader.java:336)
    	at org.springframework.beans.factory.xml.XmlBeanDefinitionReader.loadBeanDefinitions(XmlBeanDefinitionReader.java:304)
    	at org.springframework.beans.factory.support.AbstractBeanDefinitionReader.loadBeanDefinitions(AbstractBeanDefinitionReader.java:181)
    	at org.springframework.beans.factory.support.AbstractBeanDefinitionReader.loadBeanDefinitions(AbstractBeanDefinitionReader.java:217)
    	at org.springframework.beans.factory.support.AbstractBeanDefinitionReader.loadBeanDefinitions(AbstractBeanDefinitionReader.java:188)
    	at org.springframework.beans.factory.support.AbstractBeanDefinitionReader.loadBeanDefinitions(AbstractBeanDefinitionReader.java:252)
    	at org.springframework.context.support.AbstractXmlApplicationContext.loadBeanDefinitions(AbstractXmlApplicationContext.java:127)
    	at org.springframework.context.support.AbstractXmlApplicationContext.loadBeanDefinitions(AbstractXmlApplicationContext.java:93)
    	at org.springframework.context.support.AbstractRefreshableApplicationContext.refreshBeanFactory(AbstractRefreshableApplicationContext.java:129)
    	at org.springframework.context.support.AbstractApplicationContext.obtainFreshBeanFactory(AbstractApplicationContext.java:537)
    	at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:452)
    	at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:139)
    	at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:83)
    	at spring.annot.testInjectFooBar.test(testInjectFooBar.java:24)
    	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    	at java.lang.reflect.Method.invoke(Method.java:597)
    	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    	at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
    	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
    	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    	at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    	at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    	at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)
    	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:675)
    	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)
    	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)
    Caused by: org.springframework.context.annotation.ConflictingBeanDefinitionException: Annotation-specified bean name 'bar' for bean class [org.pack1.Bar] conflicts with existing, non-compatible bean definition of same name and class [org.pack2.Bar]
    	at org.springframework.context.annotation.ClassPathBeanDefinitionScanner.checkCandidate(ClassPathBeanDefinitionScanner.java:320)
    	at org.springframework.context.annotation.ClassPathBeanDefinitionScanner.doScan(ClassPathBeanDefinitionScanner.java:259)
    	at org.springframework.context.annotation.ComponentScanBeanDefinitionParser.parse(ComponentScanBeanDefinitionParser.java:87)
    	at org.springframework.beans.factory.xml.NamespaceHandlerSupport.parse(NamespaceHandlerSupport.java:74)
    	at org.springframework.beans.factory.xml.BeanDefinitionParserDelegate.parseCustomElement(BeanDefinitionParserDelegate.java:1427)
    	at org.springframework.beans.factory.xml.BeanDefinitionParserDelegate.parseCustomElement(BeanDefinitionParserDelegate.java:1417)
    	at org.springframework.beans.factory.xml.DefaultBeanDefinitionDocumentReader.parseBeanDefinitions(DefaultBeanDefinitionDocumentReader.java:174)
    	at org.springframework.beans.factory.xml.DefaultBeanDefinitionDocumentReader.doRegisterBeanDefinitions(DefaultBeanDefinitionDocumentReader.java:144)
    	at org.springframework.beans.factory.xml.DefaultBeanDefinitionDocumentReader.registerBeanDefinitions(DefaultBeanDefinitionDocumentReader.java:100)
    	at org.springframework.beans.factory.xml.XmlBeanDefinitionReader.registerBeanDefinitions(XmlBeanDefinitionReader.java:510)
    	at org.springframework.beans.factory.xml.XmlBeanDefinitionReader.doLoadBeanDefinitions(XmlBeanDefinitionReader.java:392)
    	... 37 more

    Du coup, je dois me résigner à changer les noms, ou existe-t-il une manière de pouvoir identifier les beans à leur nom complet (c'est à dire avec package) ?

Discussions similaires

  1. Réponses: 15
    Dernier message: 29/01/2014, 18h42
  2. Réponses: 3
    Dernier message: 26/11/2008, 17h19
  3. Créer son bean de config avec Spring
    Par progamer54 dans le forum Spring
    Réponses: 1
    Dernier message: 10/04/2007, 17h02
  4. Réponses: 4
    Dernier message: 10/09/2006, 10h49
  5. Réponses: 12
    Dernier message: 24/05/2006, 15h37

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo