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

Access Discussion :

Data macro after insert [AC-2010]


Sujet :

Access

  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2005
    Messages
    876
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Novembre 2005
    Messages : 876
    Points : 491
    Points
    491
    Par défaut Data macro after insert
    Bonjour,

    J'ai un problème pour modifier la date de création de l'enregistrement que je viens de créer.

    J'ai une table très simple avec

    testID nombre (et c'est ma clé)
    TestNom texte
    testModif Date/time
    Je voudrais qu'après insertion d'un nouveau ID et nouveau nom, le "trigger" mette la date à jour automatiquement.

    En toute logique, je crée donc une dataMacro AfterInsert.

    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
     
    SetLocalVar
         Name varTestId
         Expression=[TestId]
     
    Look Up A Record In testTbl
         Where Condition =[testTbl].[TestId]=[varTestId]
              Alias AChanger
     
         EditRecord
                   Alias AChanger
     
           SetField
                   Name Achanger.TestModif
                   Value= Now()
         End EditRecord
    Pour le premier que j'insère, il me crée bien la date dans le champ testModif.

    Pour les suivants, il modifie la date de mon PREMIER enregistrement plutot que celle de l'enregistrement que je viens d'ajouter. Pourtant le Lookup et la where condition ont l'ai bien construits non ?

    Merci pour votre aide.

    question subsidiaire: y-a-t'il un moyen d'écrire ce code en VB plutôt que via l'assistant ?

  2. #2
    Expert éminent sénior

    Avatar de Tofalu
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Octobre 2004
    Messages
    9 501
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Associations - ONG

    Informations forums :
    Inscription : Octobre 2004
    Messages : 9 501
    Points : 32 311
    Points
    32 311
    Par défaut
    Bonjour,

    Le plus simple serait d'utiliser la propriété Valeur par Défaut du champ en la fixant à Date(). L'utilisation des DataMacros ne doit pas venir ajouter une couche de traitement superflue. Utilisez le plus simple.

    Deuxième point, l'évènement avant modification peut paraitre plus adapté dans le sens où l'on préfère renseigné le champ avant sa modification :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/04/application"><DataMacro Event="BeforeChange"><Statements><ConditionalBlock><If><Condition>[IsInsert]</Condition><Statements><Action Name="SetField"><Argument Name="Field">TestModif</Argument><Argument Name="Value">Now()</Argument></Action></Statements></If></ConditionalBlock></Statements></DataMacro></DataMacros>
    Enfin, si vraiment vous souhaitez utiliser l'évènement Aprés Insertion :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/04/application"><DataMacro Event="AfterInsert"><Statements><EditRecord><Data/><Statements><Action Name="SetField"><Argument Name="Field">testmodif</Argument><Argument Name="Value">Now()</Argument></Action></Statements></EditRecord></Statements></DataMacro></DataMacros>
    Les codes, sont à copier coller directement dans l'interface d'édition des datamacro, seul moyen de les renseigner (pas de VBA possible)

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2005
    Messages
    876
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Novembre 2005
    Messages : 876
    Points : 491
    Points
    491
    Par défaut
    Merci pour cette réponse.

    Partons du principe que je souhaite absolument utiliser l'événement After pour procéder à la mise à jour de ma date. (la solution de la valeur par défaut ne convient pas si on veut modifier la date de modification "After Update")

    La solution que vous avez envoyée
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/04/application"><DataMacro Event="AfterInsert"><Statements><EditRecord><Data/><Statements><Action Name="SetField"><Argument Name="Field">testmodif</Argument><Argument Name="Value">Now()</Argument></Action></Statements></EditRecord></Statements></DataMacro></DataMacros>
    ne fait aucune mise à jour. Si j'y ajoute au préalable un lookUp, alors celà met à jour mais toujours uniquement le premier enregistrement.

    Pour essayer de comprendre pourquoi il ne modifie que le premier enregistrement, j'ai rajouté un quatrième champ dans ma table testTbl qui devient:

    testID Number
    testNom Text
    testModif Date/Time
    testIdChange Number
    ce champ testIdChange contiendra l'identifiant de la ligne que j'ai mis à jour.

    dans mon exemple, j'ai au départ

    1 toto Null 0
    2 tutu Null 0
    si je change dans le deuxième enregistrement tutu en tututu, je voudrais que la date/heure soit mise à jour et que le testIdChange contienne le testID de l'enregistrement modifié. Donc:
    1 toto Null 0
    2 tututu 7/10/2010 2
    Mais j'obtiens:
    1 toto 7/10/2010 1
    2 tututu Null 0
    Donc deux problèmes, c'est le premier enregistrement qui est modifié, et mon identifiant stocké dans testIdChange est 1 à la place de deux.

    Pour en arriver là, j'ai créé une "Named Macro" qui s'appelle "testModif":

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/11/application"><DataMacro Name="testModif"><Parameters><Parameter Name="parTestID" Description="id test"/></Parameters><Statements><LookUpRecord><Data><Reference>testTbl</Reference><WhereCondition>[testTbl].[testID]=[partestID]</WhereCondition></Data><Statements><EditRecord><Data/><Statements><Action Collapsed="true" Name="SetField"><Argument Name="Field">testTbl.testIdChange</Argument><Argument Name="Value">[partestID]</Argument></Action><Action Collapsed="true" Name="SetField"><Argument Name="Field">testTbl.testModif</Argument><Argument Name="Value">Now()</Argument></Action></Statements></EditRecord></Statements></LookUpRecord></Statements></DataMacro></DataMacros>
    et en plus clair, c'est une macro qui crée un paramètre "parTestID" qui représentera l'identifiant de l'enregistrement sur lequel je suis positionné dans testTbl

    qui fait un look Up dans testTbl ou mon testID est égal à mon paramètre

    Une fois l'enregistrement trouvé,
    met mon paramètre dans le champ testIdChange
    met Now dans testModif

    J'appelle cette Named Macro dans l'événement after Update de ma table test par:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/11/application"><DataMacro Event="AfterUpdate"><Statements><Action Name="RunDataMacro"><Argument Name="MacroName">testTbl.testModif</Argument><Parameters><Parameter Name="partestID" Value="[testID]"/></Parameters></Action></Statements></DataMacro></DataMacros>
    en gros, je lance ma named macro "testModif" avec comme paramètre "testID" qui est l'identifiant de l'enregistrement qui a été mis à jour.

    Je peux comprendre que comme dans un "after update" je lui demande de modifier l'enregistrement en cours, il relance l'after update de manière récursive, il faut modifier l'appel pour qu'il ne lance la named macro que quand je modifie "testNom". J'ajoute donc un:

    If Updated("testNom") Then......end If

    Ce qui donne:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/11/application"><DataMacro Event="AfterUpdate"><Statements><ConditionalBlock><If><Condition>Updated("testNom")</Condition><Statements><Action Name="RunDataMacro"><Argument Name="MacroName">testTbl.testModif</Argument><Parameters><Parameter Name="partestID" Value="[testID]"/></Parameters></Action></Statements></If></ConditionalBlock></Statements></DataMacro></DataMacros>
    Avec l'ajout du if, j'obtiens maintenant:
    1 toto 7/10/2010 2
    2 tututu Null 0
    et 2 dans testIdChange , c'est bien la preuve que mon paramètre correspond bien à mon deuxième enregistrement .

    Pourquoi le lookUp et l'edit se produisent sur le premier ??

  4. #4
    Expert éminent sénior

    Avatar de Tofalu
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Octobre 2004
    Messages
    9 501
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Associations - ONG

    Informations forums :
    Inscription : Octobre 2004
    Messages : 9 501
    Points : 32 311
    Points
    32 311
    Par défaut
    Bonjour,

    Dans la mesure où la question initiale concernait l'afterInsert, je ne vois pas ce que viens faire l'Update ici.

    Essayez plutot :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/11/application"><DataMacro Event="AfterInsert"><Statements><Action Name="SetLocalVar"><Argument Name="Name">varID</Argument><Argument Name="Value">[TestId]</Argument></Action><LookUpRecord><Data Alias="Record1"><Reference>matable</Reference><WhereCondition>[testid]=[varid]</WhereCondition></Data><Statements><EditRecord><Data Alias="Record1"/><Statements><Action Name="SetField"><Argument Name="Field">testmodif</Argument><Argument Name="Value">Date()+1</Argument></Action></Statements></EditRecord></Statements></LookUpRecord></Statements></DataMacro></DataMacros>
    Enfin, si vraiment vous vous interressé à l'update :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-16" standalone="no"?>
    <DataMacros xmlns="http://schemas.microsoft.com/office/accessservices/2009/11/application"><DataMacro Event="AfterUpdate"><Statements><ConditionalBlock><If><Condition>Updated("[TestNom]")</Condition><Statements><Action Name="SetLocalVar"><Argument Name="Name">varID</Argument><Argument Name="Value">[TestId]</Argument></Action><LookUpRecord><Data Alias="Record1"><Reference>matable</Reference><WhereCondition>[testid]=[varid]</WhereCondition></Data><Statements><EditRecord><Data Alias="Record1"/><Statements><Action Name="SetField"><Argument Name="Field">testmodif</Argument><Argument Name="Value">Date()+1</Argument></Action></Statements></EditRecord></Statements></LookUpRecord></Statements></If></ConditionalBlock></Statements></DataMacro></DataMacros>

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2005
    Messages
    876
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Novembre 2005
    Messages : 876
    Points : 491
    Points
    491
    Par défaut
    Merci Tofalu pour cette réponse. Je l'ai testé et ça fonctionne !!!

    En analysant votre code, je me suis rendu compte que j'avais procédé (presque) de la même manière, mais que chez moi ça ne fonctionnait pas !

    J'ai donc cherché ou était la différence:

    La première différence est que vous avez utilisé les Alias. Mais ça, même en le rajoutant, il s'entête à me rajouter la date de modification uniquement sur le premier enregistrement.

    Je me suis alors appercu que dans le:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Look Up A Record In testTbl
    vous aviez pour la Where Condition :
    "[testID]=[varid]"
    alors que moi j'avais:
    [testTbl].[testID]=[varid]
    Et ça, ça fait toute la différence, le premier fonctionne (même sans les alias) et le second pas (ou mal puisqu'il met systématiquement le premier à jour plutôt que l'élément sélectionné)!!!

    C'est d'autant plus surprenant que la syntaxe qui ne fonctionne pas est créée via l'intellisense et que donc en tapant "T" et puis "E", il me propose "testTbl" que je sélectionne puis je tape un point (".") et il me propose testID.

    Il s'agit selon moi d'un BUG qui mériterait d'être corrigé ou pour le moins documenté !

  6. #6
    Expert éminent sénior

    Avatar de Tofalu
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Octobre 2004
    Messages
    9 501
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Ain (Rhône Alpes)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Associations - ONG

    Informations forums :
    Inscription : Octobre 2004
    Messages : 9 501
    Points : 32 311
    Points
    32 311
    Par défaut
    il ne s'agit pas d'un bug dans le sens où le paramètre Clause Where attends une chaine de caractères. Comme le paramètre WhereCondition de la méthode Docmd.Openform par exemple. Mais mieux documenté, c'est certain que ça aurait dû l'être

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2005
    Messages
    876
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Novembre 2005
    Messages : 876
    Points : 491
    Points
    491
    Par défaut
    Merci en tous cas pour votre aide.

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

Discussions similaires

  1. Trigger after insertion pas validée
    Par guigeek dans le forum PostgreSQL
    Réponses: 3
    Dernier message: 20/12/2006, 13h37
  2. Trigger after insertion pas validée
    Par guigeek dans le forum PostgreSQL
    Réponses: 3
    Dernier message: 19/12/2006, 14h23
  3. Un Trigger After INSERT peut-il empêcher l'INSERT ?
    Par cian2006 dans le forum Oracle
    Réponses: 3
    Dernier message: 13/09/2006, 17h27
  4. Trigger after insert, sans each row, possible ??
    Par veenie dans le forum Oracle
    Réponses: 5
    Dernier message: 16/02/2006, 15h18
  5. [Trigger] -recursivité before|after insert
    Par jacquesh dans le forum Oracle
    Réponses: 3
    Dernier message: 24/11/2005, 15h10

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