Modification d'un champ d'une table Access via VBA

ben en fet C po pr moi mé pour mon maitre de stage, il à un tas de requête a mettre à jour(a lancer) dc il me demande de faire un formulaire pour minimiser les taches a fer surtout les plus chiante!!et en fet il a 4champ a rajouter ds 4 tables différen mais aussi 4champ aussi ds 2autre tables dc assez lourd et perte de tps. Si les champs se place a la fin po tro grave mé il ma di “ca seré mieu si il se place au bon endroit mé sinn po grave”. Mé ya po une méthode pr les déplacer une foi kil soi instaurer ds la table??

Sinon j’ai besoin d’un autre service : en fet je voudrai que si le champ existe déja ds la table alors on le supprime et on le rajoute sinon on le rajoute immédiatement.

merci d’avance

Tu as à nouveau les 2 possibilités:

  • TableDefs (If … then …)
  • SQL

A mon avis si tu exécutes en SQL ALTER TABLE Nom_de_la_table DROP COLUMN Nom_de_la_colonne et que la colonne n’existe pas, ce n’est pas très grave. Du pourrais donc toujours effacer le champ puis le recréer. Mais tu peux aussi tester si le champ existe avec un SELECT, la commande SQL devient un peu plus compliquée.

ok pour les 2 possibilité.
j’ai essayé déja avec le ALTER TABLE…DROP COLUMN… mais si le champ exist pas ben ca me procure un problème!! donc oublions cette possibilité.
D’aprés quel es la possibilité la plus simple entre : “Tabledefs(If…Then…)” et “SELECT…”??
Si "TableDefs(If…Then…) " peut-tu me passer la syntaxe stp cr j’ai beau chercher je ne trouve pas du tout.
Si c’est “SELECT” ben j’ai un pb : quesque je met ds le WHERE?? en gro commen je teste si le champ existe??

MERCI D’AVANCE!!

Non, non, il faut utiliser un test ou faire une boucle dans TableDefs / Fields pour voir si le champs concerné existe déjà.

Le select si si tu voulais tout faire en SQL, mais je ne sais plus par coeur, je vais essayer de te trouver ça.

ok!! ben je veux bien utiliser TableDefs / Fields et sa boucle, mé jvoi po trop comment faire,pourrai-tu m’éclairer stp??!!??

merci d’avance :frowning:

Sinon si l’erreur que tu me dis c’est bêtement à l’exécution de "DoCmd.RunSQL (“ALTER TABLE Table DROP Champ)”, le plus simple est peut-être encore d’ajouter une gestion d’erreur:
try … catch si ça marche dans cette version de VBA, sinon On Error resume next … on error goto 0

voila je vais te mettre mon code ca va peut être t’aider.
Ben je sais pas du tout quoi faire , je suis perdu, ca devien dur, jcompren rien!!lol. si jmet " try…catch ", jle met ou??

Private Sub Table_IPMS_Bpss_Click()
On Error GoTo Err_Table_IPMS_Bpss_Click

DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha  DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz  DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab  DROP COLUMN [DATE_DER_MAJ1];"

DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha  ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz  ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab  ADD COLUMN [DATE_DER_MAJ1] DATE;"

Exit_Table_IPMS_Bpss_Click:
Exit Sub

Err_Table_IPMS_Bpss_Click:
MsgBox err.Description
Resume Exit_Table_IPMS_Bpss_Click
End Sub

:pt1cable: :pfff::grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff: :grrr: :pt1cable: :pfff:

je vien de relancer mon bouton qui fé partir mon code et ce ki se passe C ke si le champ existe alor ca le supprime et le recréée mais si le champ existe pas ben il m’affiche un message d’erreur qui es le suivant : There is no field named ‘DATE_DER_MAJ1’ in table ‘Ipms_icxs_pves_epms_iens_ha_naz’.
Ce qui es normal vu kil ne peu pas supprimer un champ non existant(logike)!!donc jaimeré trouver commen régler ce pb!!(voila je té tt rexpliker pr ke ce soi plu simple et kon parte po de tt les cotés cr sinon dur dur!!lol)
merci pr ton aide jray!!

Pas besoin de boucle, tu as déjà fait ça pour tester l’existence des tables

Il suffit juste d’adapter :
fielsExist = currentDb.TableDefs().Fields().Name

ok gcc, mé jinsére " fielsExist = currentDb.TableDefs().Fields().Name " a kel endroit dans mon code??
Puis pourquoi ma tu remit la fonction IsTableExist?? (cette fonction ma servi pour un otre bouton --> C tt otre chose)

En fait, j’ai voulu écrire FieldExist mais ça ne change rie puisque c’est le nom d’une variable.

La fonction, c’est toi qui l’as trouvée ! elle permet de savoir si une table existe ou non sans être gêné par les messages d’erreur.
De la même manière, ici tu recherches l’existence d’un champ, donc tu crées une fonction FieldsExist que tu déduis de IsTableExist (je t’ai donné la ligne à adapter) et tu l’implémentes dans ton code sur le même modèle.

la fonction je lé effectivement trouvé pour savoir si une table existe.

Pour la fonction FieldExist je la déduis commen dans IsTableexist??
qu’a tu voulu dire par : “(je t’ai donné la ligne à adapter)” ??
merci d’avance

Tu ne la déduis pas DANS IsTableExist , mais DE IsTableExist
C’est à dire que tu recrées une nouvelle fonction que tu nommes FieldExist par exemple.
la seule différence entre les deux fonctions sera la ligne que je t’ai donnée plus haut
FieldExist = currentDb.TableDefs().Fields().Name = <Nom_du_champ_recherché>
à la place de
IsTableExist = CurrentDb.TableDefs().Name =

La solution (pas propre) de gestion d’erreur que je proposait était simplement


On Error Resume Next 'Ignore les erreurs
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz DROP COLUMN [DATE_DER_MAJ1];"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab DROP COLUMN [DATE_DER_MAJ1];"
On Error goto 0 'On n'ignore plus les erreurs

DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_ha ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz ADD COLUMN [DATE_DER_MAJ1] DATE;"
DoCmd.RunSQL "ALTER TABLE Ipms_icxs_pves_epms_iens_fab ADD COLUMN [DATE_DER_MAJ1] DATE;"

Le résultat est le même, mais c’est un peu plus propre si tu testes si le champ existe.

Ce que je trouve dommage dans ton code c’est de mélanger le SQL et le DAO/ADO avec les TablesDefs et autres.
Je pense que ça aurait été bien de tout faire avec la structure Access/DAO/ADO ou alors tout en SQL.
Mais bon, on va pas pinailler, le but c’est que tu arrives au résultat voulu… :wink:

ok, la fonction es réalisé!!
Mais comment je doit faire pour déduire IsFieldExist DE IsTableExist??


C vré, j'avou le but C ke jy arrive, ne soit pas triste jray cr jutilise pas que la structure Access/DAO/ADO ou ke SQL!!LOL. Tkt po jte remerci quand même d'avoir tout fé pr m'aiguillé.... ca m'aide énormément!!!

:clap: MERCI!! :super:

A mon avis la focntion de gcc va retourner une erreur si le champ n’existe pas.

Voici un exemple (c’est plus long, mais bon):


Public Function FieldExists(strTableName As String, strFieldName As String) As Boolean

    'On recherche le champ dans tous les champs de la table
    For i = 0 To CurrentDb.TableDefs(strTableName).Fields.Count - 1
        If LCase(CurrentDb.TableDefs(strTableName).Fields(i).Name) = LCase(strFieldName) Then 'LCase pour éviter les soucis de majuscules
            'On l'a trouvé => il existe
            FieldExists = True
            Exit Function
        End If
    Next
    
    'On ne l'a pas trouvé => n'existe pas
    FieldExists = False

End Function

Remarque: cette fonction ne gère pas l’erreur si le nom de la table est incorrect

“déduire de” c’est équivalent à “prendre modèle sur”. Donc si ta fonction est réalisée c’est bon.
Maintenant, pour l’utiliser, c’est la même méthode que pour le test de la table en début de ton programme :
if FieldExist(<le_nom_du_champ>) then

endif
<mes instructions de création>

Et comme la première fois, pas besoin de else puisque les conditions d’éxécution de la deuxième partie sont identiques quelle que soit la manière dont a été traitée la première partie (à savoir, le champs n’esiste pas).

Et pour comparaison le code avec méthode par gestion d’erreur.
C’est plus court, plus rapide que de faire chaque fois des boucles (surtout pour les grandes BD ou grandes tables), mais c’est moins propre !!


Public Function FieldExists(strTableName As String, strFieldName As String) As Boolean

    'Si le champ n'existe pas, cette fonction retourne une erreur
    On Error GoTo Erreur
    Dim strTest As String
    strTest = CurrentDb.TableDefs(strTableName).Fields(strFieldName).Name
    On Error GoTo 0
    
    'Pas d'erreur => le champ existe
    FieldExists = True
    Exit Function
    
Erreur:
    'Erreur => le champ n'existe pas
    FieldExists = False

End Function

ne vous batté pas voyon!!lol.
gcc j’ai essayé ce que tu ma di mé g tj un pb, lorsque je clike sur mon bouton et ke le champ n’existe pas, il m’affiche cela :

There is no field named ‘DATE_DER_MAJ1’ in table 'Ipms_icxs_pves_epms_iens_ha_naz

mon code es le suivant :

Private Sub Table_IPMS_Bpss_Click()
On Error GoTo Err_Table_IPMS_Bpss_Click

If FieldExist(“DATE_DER_MAJ1”) Then
MsgBox (“le champ DATE_DER_MAJ1 existe”)
DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz DROP COLUMN [DATE_DER_MAJ1];”
MsgBox (“la table est supprimer”)
End If
DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz DROP COLUMN [DATE_DER_MAJ1];”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha DROP COLUMN [DATE_DER_MAJ1];”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz DROP COLUMN [DATE_DER_MAJ1];”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_fab DROP COLUMN [DATE_DER_MAJ1];”
’ MsgBox (“le champ es supprimé”)
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz ADD COLUMN [DATE_DER_MAJ1] DATE;”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha ADD COLUMN [DATE_DER_MAJ1] DATE;”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_fab_naz ADD COLUMN [DATE_DER_MAJ1] DATE;”
’ DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_fab ADD COLUMN [DATE_DER_MAJ1] DATE;”
’ MsgBox (“le champ es créé”)

Exit_Table_IPMS_Bpss_Click:
Exit Sub

Err_Table_IPMS_Bpss_Click:
MsgBox err.Description
Resume Exit_Table_IPMS_Bpss_Click
End Sub

Public Function FieldExist(NomDuChamp As String) As Boolean
On Error Resume Next
FieldExist = (CurrentDb.TableDefs(MaTable).Fields(LeChampCherche).Name = Nom_du_champ_recherché)
CurrentDb.Close
End Function

comment pui-je résoudre mon pb??

dsl, je vien de trouver une erreur( le résultat es tj le meme sauf ke le message me di kil y a une erreur de syntaxe dans la definition du champ)

mon erreur c’est que dans mon code c’est pas le code d’en haut mé :

Private Sub Table_IPMS_Bpss_Click()
On Error GoTo Err_Table_IPMS_Bpss_Click

If FieldExist(“DATE_DER_MAJ1”) Then
MsgBox (“le champ DATE_DER_MAJ1 existe”)
DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz DROP COLUMN [DATE_DER_MAJ1];”
MsgBox (“la table est supprimer”)
End If
DoCmd.RunSQL “ALTER TABLE Ipms_icxs_pves_epms_iens_ha_naz ADD COLUMN [DATE_DER_MAJ1];”

Exit_Table_IPMS_Bpss_Click:
Exit Sub

Err_Table_IPMS_Bpss_Click:
MsgBox err.Description
Resume Exit_Table_IPMS_Bpss_Click
End Sub