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 2.5] Problème de création d'un service Générique IService<T>


Sujet :

Spring Java

  1. #1
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Janvier 2007
    Messages : 51
    Points : 30
    Points
    30
    Par défaut [Spring 2.5] Problème de création d'un service Générique IService<T>
    bonjour,

    Je me suis inspiré de cet article http://www.ibm.com/developerworks/ja...enericdao.html pour créer un DAO générique.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    public interface IDAO<T> {
     
    	public T get(Long id);
     
    	public T getReference(Long id);
     
    	public void save(T t);
     
    	public void update(T t);
     
    	public void remove(T t);
    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
    54
    55
     
    @Repository
    public abstract class AbstractDAOBean<T extends AbstractEntity> implements IDAO<T> {
     
    	private static final Logger	log	= Logger.getLogger(AbstractDAOBean.class);
     
    	@PersistenceContext(type = PersistenceContextType.EXTENDED)
    	protected EntityManager		em;
     
    	private final Class<T>		entityClass;
     
    	/**
             * Default constructor.
             */
    	@SuppressWarnings("unchecked")
    	public AbstractDAOBean() {
    		this.entityClass = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
    	}
     
    	/**
             * Returns the underlying Hibernate Session of the current EntityManager.
             * 
             * @return the Hibernate Session.
             */
    	protected Session getSession() {
    		return (Session) em.getDelegate();
    	}
     
    	protected Class<T> getEntityClass() {
    		return entityClass;
    	}
     
    	public T get(Long id) {
    		return em.find(entityClass, id);
    	}
     
    	public T getReference(Long id) {
    		return em.getReference(entityClass, id);
    	}
     
    	public void save(T t) {
    			if (t.getId() == null) {
    				// new
    				em.persist(t);
    			}
    			else {
    				// update
    				em.merge(t);
    			}
    		log.debug(entityClass.getSimpleName() + "Saves");
    	}
     
    	public void update(T t) {
    		em.merge(t);
    	}
    Lorsque j'appelle toutes les classes fils de mon DAO générique depuis une seule classe service. Pas de problème tout marche parfaitement.

    En revanche pour éviter de dupliquer les même fonctions de la couche services dans toutes les classes qui en hérite. J'ai voulu créer une classe Service Générique.

    Cette interface << IService<T> >> liste toutes les fonctions CRUD dans mon IDAO.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    public interface IService<T> {
     
    	public T get(Long id);
     
    	public T getReference(Long id);
     
    	public void save(T t);
     
    	public void update(T t);
     
    	public void remove(T t);
    }
    Une classe AbstractService générique implémente l"interface IService<T>
    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
     
    @Service
    @Transactional
    public abstract class AbstractServiceBean<T extends AbstractEntity> implements IService<T> {
     
    	// couche [dao]
    	public IDAO<T>	dao;
     
    	public IDAO<T> getDao() {
    		return dao;
    	}
     
    	@Autowired
    	public void setDao(IDAO<T> dao) {
    		this.dao = dao;
    	}
     
    	private final Class<T>	entityClass;
     
    	/**
             * Default constructor.
             */
    	@SuppressWarnings("unchecked")
    	public AbstractServiceBean() {
    		this.entityClass = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
    	}
     
    	protected Class<T> getEntityClass() {
    		return entityClass;
    	}
     
    	public T get(Long id) {
    		return dao.get(id);
    	}
     
    	public T getReference(Long id) {
    		return dao.getReference(id);
    	}
     
    	public void save(T t) {
    		dao.save(t);
    	}
     
    	public void update(T t) {
    		dao.update(t);
    	}
     
    	public void remove(T t) {
    		dao.remove(t);
    	}
    Je me fait également injecter les différents DAO dans les différents services comme suit
    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
     
    @Service("RequestService")
    @Transactional
    public class RequestServiceBean extends AbstractServiceBean<Request> implements RequestService {
    	private static final Logger	log	= Logger.getLogger(RequestServiceBean.class);
     
    	// Inject couche [dao]
    	private RequestDao			dao;
     
    	public RequestDao getDao() {
    		return dao;
    	}
     
    	@Autowired
    	public void setDao(RequestDao dao) {
    		this.dao = dao;
    	}
       ....
    Lorsque je veut me faire injecter tous mes services lors de l'initialisation de l'application :

    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
     
     
    	ApplicationContext ctx = new ClassPathXmlApplicationContext("spring-config.xml");
     
           @Autowired
    	private PDVService		pdvService;
     
    	@Autowired
    	private InfosService	infosService;
     
    	@Autowired
    	private RequestService	requestService;
     
    	@Autowired
    	private PageService		pageService;
     
    	@Autowired
    	private XmlFileService	xmlFileService;
     
    	@Autowired
    	private TestService		testService;
    Spring me génère cette erreur :

    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
     
    Exception in thread "main" org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'InfosService': Autowiring of methods failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void fr.stime.service.AbstractServiceBean.setDao(fr.stime.dao.IDAO); nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [fr.stime.dao.IDAO] is defined: expected single matching bean but found 6: [infosDaoBean, pageDaoBean, PDVDaoBean, requestDaoBean, testDaoBean, xmlFileDaoBean]
    	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:256)
    	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:998)
    	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:472)
    	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory$1.run(AbstractAutowireCapableBeanFactory.java:409)
    	at java.security.AccessController.doPrivileged(Native Method)
    	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:380)
    	at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:264)
    	at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
    	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:261)
    	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:185)
    	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:164)
    	at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:429)
    	at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:728)
    	at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:380)
    	at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:139)
    	at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:93)
    	at fr.stime.manager.Injector.init(Injector.java:10)
    	at fr.stime.test.InitDB.main(InitDB.java:49)
    Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void fr.stime.service.AbstractServiceBean.setDao(fr.stime.dao.IDAO); nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [fr.stime.dao.IDAO] is defined: expected single matching bean but found 6: [infosDaoBean, pageDaoBean, PDVDaoBean, requestDaoBean, testDaoBean, xmlFileDaoBean]
    	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:543)
    	at org.springframework.beans.factory.annotation.InjectionMetadata.injectMethods(InjectionMetadata.java:117)
    	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:253)
    	... 17 more
    Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [fr.stime.dao.IDAO] is defined: expected single matching bean but found 6: [infosDaoBean, pageDaoBean, PDVDaoBean, requestDaoBean, testDaoBean, xmlFileDaoBean]
    	at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:621)
    	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:499)
    	... 19 more
    Il me dit que IDAO n'est pas un Bean unique ! je dois avoir une @Autowired en plus ou en moins dans un mauvais endroit !

    Avez-vous une idée de quoi ce peut prevenir et comment résoudre ce problème ?

    Merci par avance de votre aide.

  2. #2
    Membre habitué Avatar de sewatech
    Inscrit en
    Février 2007
    Messages
    141
    Détails du profil
    Informations personnelles :
    Âge : 54

    Informations forums :
    Inscription : Février 2007
    Messages : 141
    Points : 166
    Points
    166
    Par défaut
    Effectivement, tu as trop de @Autowired. Tu ne peux pas injecter automatiquement tes dao dans ta classe de service. Il faut donc que tu supprimes cette annotation de AbstractServiceBean et que tu injectes explicitement tes dao dans les sous-classes : @Qualifier ou @Resource si tu as le JDK6.

  3. #3
    Membre chevronné

    Homme Profil pro
    Architecte logiciel
    Inscrit en
    Novembre 2006
    Messages
    1 252
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 48
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Architecte logiciel
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Novembre 2006
    Messages : 1 252
    Points : 1 954
    Points
    1 954
    Par défaut
    Tu dois mettre l'annotation @Autowired dans le setter de la classe RequestServiceBean (et pour toutes les filles) et non dans la classe abstraite.

  4. #4
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Janvier 2007
    Messages : 51
    Points : 30
    Points
    30
    Par défaut Erreur Service Générique
    Bonjour,

    J'ai déjà testé ça. Lorsque j'enlève @Autowired de la classe abstraite AbstractServiceBean et j'essaye d'appeler la fonction save(T t) depuis un service de la classe fille :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    @Autowired
    private PDVService		pdvService;
    ....
    PDV t = new PDV();
    t.setNAme("toto");
    pdvService.save(t);
    j'ai cette erreur :

    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
     
    Exception in thread "main" java.lang.NullPointerException
    	at fr.stime.service.AbstractServiceBean.save(AbstractServiceBean.java:64)
    	at fr.stime.service.AbstractServiceBean.save(AbstractServiceBean.java:1)
    	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    	at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    	at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    	at java.lang.reflect.Method.invoke(Unknown Source)
    	at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:307)
    	at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:182)
    	at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:149)
    	at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:106)
    	at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:171)
    	at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:204)
    	at $Proxy40.save(Unknown Source)
    	at fr.stime.test.InitDB.main(InitDB.java:58)
    Comme il n'arrive pas à injecter le IDAO<T> dans le service abstrait, j'ai java.lang.NullPointerException sur la fonction save ==> la variable dao est à null

    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
     
    @Service
    @Transactional
    public abstract class AbstractServiceBean<T extends AbstractEntity>
    		implements
    			IService<T> {
     
    	// couche [dao]
    	public IDAO<T> dao;
     
    	public IDAO<T> getDao() {
    		return dao;
    	}
     
    	// @Autowired
    	public void setDao(IDAO<T> dao) {
    		this.dao = dao;
    	}
     
    	private final Class<T> entityClass;
     
    	/**
             * Default constructor.
             */
    	@SuppressWarnings("unchecked")
    	public AbstractServiceBean() {
    		this.entityClass = (Class<T>) ((ParameterizedType) getClass()
    				.getGenericSuperclass()).getActualTypeArguments()[0];
    	}
     
    	protected Class<T> getEntityClass() {
    		return entityClass;
    	}
     
    	public T get(Long id) {
    		return dao.get(id);
    	}
     
    	public T getReference(Long id) {
    		return dao.getReference(id);
    	}
     
    	public void save(T t) {
    		dao.save(t);
    	}

  5. #5
    Membre habitué Avatar de sewatech
    Inscrit en
    Février 2007
    Messages
    141
    Détails du profil
    Informations personnelles :
    Âge : 54

    Informations forums :
    Inscription : Février 2007
    Messages : 141
    Points : 166
    Points
    166
    Par défaut
    En enlevant tout les @Autowired, tu n'injectes plus du tout de dao. Il faut que tu fasses une injection explicite dans la sous-classe. Les façons de faire avec annotations sont :
    • Redéfinir setDao, et l'annoter
    • Faire de l'injection par constructeur

  6. #6
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Janvier 2007
    Messages : 51
    Points : 30
    Points
    30
    Par défaut
    Je n'ai pas compris ta réponse

    Peux-tu me donne plus d'explication STP ?

    Je n'ai pas enlevé toutes les @Autowired de toutes les classes filles ! Je l'ai enlevé juste de la classe abstraite et je l'ai gardé dans toutes les classes filles

    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
     
    public abstract class AbstractServiceBean<T extends AbstractEntity>
    		implements
    			IService<T> {
     
    	// couche [dao]
    	public IDAO<T> dao;
     
    	public IDAO<T> getDao() {
    		return dao;
    	}
     
    	// @Autowired
    	public void setDao(IDAO<T> dao) {
    		this.dao = dao;
    	}

    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
     
    @Service("PDVService")
    @Transactional
    public class PDVServiceBean extends AbstractServiceBean<PDV> implements PDVService {
    	private static final Logger	log	= Logger.getLogger(PDVServiceBean.class);
     
    	// Inject couche [dao]
    	private PDVDao				dao;
     
    	public PDVDao getDao() {
    		return dao;
    	}
     
    	@Autowired
    	public void setDao(PDVDao dao) {
    		this.dao = dao;
    	}
    Merci

  7. #7
    Membre habitué Avatar de sewatech
    Inscrit en
    Février 2007
    Messages
    141
    Détails du profil
    Informations personnelles :
    Âge : 54

    Informations forums :
    Inscription : Février 2007
    Messages : 141
    Points : 166
    Points
    166
    Par défaut
    Désolé, j'avais mal regardé.

    Ce qui ne va pas dans ton code, c'est que tu redéfinis ton champs dao. Laisse-le dans la classe abstraite uniquement. Ensuite, dans la sous-classe, injecte explicitement, en précisant son nom, le bon DAO. C'est ici que mon message précédent redevient pertinent : par setter ou par constructeur.

    Tu peux jeter un coup d'oeil ici pour la configuration du @Qualifier ou du @Resource.

    Moyennant quelques améliorations de généricité, cela devrait ressembler à ceci :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    @Service("PDVService")
    @Transactional
    public class PDVServiceBean extends AbstractServiceBean<PDV> implements PDVService {
    	private static final Logger	log	= Logger.getLogger(PDVServiceBean.class);
     
    	@Autowired @Qualifier(PDVDao)
    	public void setDao(PDVDao dao) {
    		super.setDao(dao);
    	}
     }
    Si cela ne marche pas, essaie par constructeur.

  8. #8
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Janvier 2007
    Messages : 51
    Points : 30
    Points
    30
    Par défaut Génial !
    Merci beaucoup sewatech !
    Ca marche parfaitement. Je n'ai pas pensé à injecter le Dao dans la classe abstraite en passant par le super

    Pour ceux qui sont intéressé par la solution, voici le code :
    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
     
    @Service("TestService")
    @Transactional
    public class TestServiceBean extends AbstractServiceBean<Test>
    		implements
    			TestService {
     
    	private static final Logger log = Logger.getLogger(TestServiceBean.class);
     
    	// Inject couche [dao]
    	private TestDao testdao;
     
    	public TestDao getTestdao() {
    		return testdao;
    	}
     
    	@Autowired
    	public void setDao(TestDao dao) {
    		super.setDao(dao);
    		this.dao = dao;
    	}

  9. #9
    Membre habitué Avatar de sewatech
    Inscrit en
    Février 2007
    Messages
    141
    Détails du profil
    Informations personnelles :
    Âge : 54

    Informations forums :
    Inscription : Février 2007
    Messages : 141
    Points : 166
    Points
    166
    Par défaut
    A quoi sert le champ testdao, dans ton exemple ?

  10. #10
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    51
    Détails du profil
    Informations personnelles :
    Localisation : France, Paris (Île de France)

    Informations forums :
    Inscription : Janvier 2007
    Messages : 51
    Points : 30
    Points
    30
    Par défaut
    La classe TestDao définit une autre fonction non déclarée dans l'interface générique IDAO<T>

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    public interface TestDao extends IDAO<Test> {
     
    	public Test getTestByStep(ProjectStepType step);
    }
    Donc, pour pouvoir invoquer cette fonction qui n'est pas visible au niveau de la classe service abstraite, je suis obligé de définir le champ testdao.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
     
            // Inject du [Testdao]
    	private TestDao testdao;
     
    	@Autowired
    	public void setDao(TestDao dao) {
    		super.setDao(dao);
    	}
     
    	public Test getTestByStep(ProjectStepType step) {
    		log.debug(TestServiceBean.class.getSimpleName() + " Call service");
    		return testdao.getTestByStep(step);
    	}
    D'ailleurs, tj dans la même problématique, aurais-tu une solution à me proposer concernant mon problème de Rollback ?
    http://www.developpez.net/forums/d66...k/#post3897509
    Merci !

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. probléme de création des bean Spring
    Par lionel84 dans le forum Spring Web
    Réponses: 1
    Dernier message: 20/08/2008, 20h38
  2. Réponses: 5
    Dernier message: 04/07/2006, 00h11
  3. Problème de création de table sous MySql
    Par ducamba dans le forum Requêtes
    Réponses: 2
    Dernier message: 21/06/2003, 09h59
  4. Problème de création de fenêtre
    Par tomateauketchup dans le forum DirectX
    Réponses: 1
    Dernier message: 08/06/2003, 19h42
  5. [Rave Report] problème de création dynamique
    Par Nivux dans le forum Rave
    Réponses: 2
    Dernier message: 24/05/2003, 00h07

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