Format de date system et portabilité

Soyez le premier à donner votre avis sur cette source.

Vue 11 459 fois - Téléchargée 627 fois

Description

Ce bout de code a été écrit afin gérer les dates (insertion et lecture dans la base de données) quelque soit les paramètres régionnaux du système (en supposant que l'utilisateur saisie une date dans le format de son pays, message d'erreur si ce n'est pas le cas).
J'ai eu à écrire ce code à cause de la non portabilité d'un programme utilisé dans des pays étrangers dû au format des dates.
Une des fonctions disponible dans ce code permet donc de récupérer le format du système afin d'informer l'utilisateur sur comment renseigner les dates en vue d'une insertion. Cette fonction retourne une chaîne type 'dd/mm/yyyy' (d pour jour, m pour mois, y pour année) qui sera affichée dans un label.

Pour tester ce code, modifier les paramètres régionnaux de votre système (sous XP, dans Panneau de configuration > Options régionnales et linguistiques)) et relancer le formulaire à chaque modifications

Ce code n'a été testé que sous XP !

Source / Exemple :


Option Compare Database
Option Explicit

'Déclaration des APIs
Private Declare Function GetLocaleInfo Lib "kernel32.dll" Alias "GetLocaleInfoA" ( _
                    ByVal locale As Long, _
                    ByVal lctype As Long, _
                    ByVal lplcdata As String, _
                    ByVal cchdata As Long _
) As Long
Private Declare Function GetUserDefaultLCID Lib "kernel32" () As Long

'Constante passée à la fonction GetLocaleInfo afin qu'elle renvoie le format de la date courte
' Pour plus d'infos et avoir la liste des constantes http://support.microsoft.com/kb/177146/fr
Const Format_Date_Courte = &H1F

Private Sub Form_Load()
    'On initialise le label avec le format de la date courte renvoyé par le systeme
    format_date.Caption = ReturnFormat(Format_Date_Courte) 'retour du format de la date courte
End Sub

Private Sub Inserer_Click()
    Dim request As String
    'On empêche tout message d'alerte en cas d'insertion dans la base de données
    DoCmd.SetWarnings False
    
    'On test si la date à insérer est bien une date
    If Not IsDate(date_test.Value) Then
        'Message d'erreur si ce n'est pas le cas
        MsgBox "erreur!", vbCritical
    Else
        'Sinon, on insère la date dans la table concernée
        
        'Copnstruction de la requête
        request = "INSERT INTO test (date_test) VALUES (#" & Format$(date_test.Value, "MM\/DD\/YYYY") & "#);"
        'Exécution de la requête
        DoCmd.RunSQL request
    End If
End Sub

Private Sub Chercher_Click()
    'Fonction qui compte le nombre de date recherchée dans la base de donnée
    Dim request As String
    Dim rst As DAO.Recordset
        
    
    'On test si la date à insérer est bien une date
    If Not IsDate(date_recherche.Value) Then
        'Message d'erreur si ce n'est pas le cas
        MsgBox "erreur!", vbCritical
    Else
        'Sinon, on recherche la date dans la table
        
        'Construction de la requête
        request = "SELECT Count(1) AS Nb " & _
                  "FROM test " & _
                  "WHERE test.date_test=#" & Format$(date_recherche.Value, "MM\/DD\/YYYY") & "#;"

        Set rst = CurrentDb.OpenRecordset(request, dbOpenDynaset, dbReadOnly)

        'Affichage du résultat
        MsgBox "Nb de """ & CDate(date_recherche.Value) & """ : " & rst("Nb")
    End If
End Sub

Private Function ReturnFormat(type_retour As String) As String
    'Création du format de la date system
    Dim locale As Long, lctype As Long, lplcdata As String, cchdata As Long, nretval As Long, dwLCID As Long
    
    'Préparation des paramètres de la fonction GetLocaleInfo
    locale = GetUserDefaultLCID()
    lplcdata = Space(255)
    cchdata = Len(lplcdata)
    nretval = 0
    
    'On récupère le format de la date dans le tableau lplcdata
    nretval = GetLocaleInfo(locale, type_retour, lplcdata, cchdata)
    
    'Dans le cas ou la valeur de retour est 0 => on renvoie vide ""
    If nretval = 0 Then
        ReturnFormat = ""
    Else
        'Sinon on renvoie le format de la date
        ReturnFormat = LCase(lplcdata)
    End If
End Function

Codes Sources

A voir également

Ajouter un commentaire

Commentaires

cs_DARKSIDIOUS
Messages postés
15838
Date d'inscription
jeudi 8 août 2002
Statut
Modérateur
Dernière intervention
4 mars 2013
82 -
Y'a un truc qui me choque :
"INSERT INTO test (date_test) VALUES ('" & CDate(date_test.Value) & "');"

Les dates en SQL access doivent être entourées de dièses et être au format américain... à moins que tu ne l'enregistre dans un champ de type texte, mais là c'est pas très optimisé !

DarK Sidious
Renfield
Messages postés
17280
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
21 juillet 2019
57 -
aïe...

tu as fait tout ce qu'il ne faut pas faire, au contraire.
c'est un sujet qui m'est cher, et ton code ne va pas.


les manipulations de dates en SQL se font comme cela :
"INSERT INTO test (date_test) VALUES (#" & Format$(date_test.Value,"MM\/DD\/YYYY") & "#);"

on s'affranchit au plus tôt des parametres regionnaux.


comme nous y invite ton interface, j'ai saisi 02/09/2007
(deux septembre 2007)

mais ton code :
"INSERT INTO test (date_test) VALUES ('" & CDate(date_test.Value) & "');"
execute
... VALUE('02/09/2007')

qui sera interpreté par Access, via les parametres regionnaux...
bonjour le 9 février ^^

on ne force jamais un format de saisie à l'utilisateur, le programme doit s'adapter aux parametres regionnaux.


pour ta recherche, idem...



request = "SELECT Count(1) AS Nb " & _
"FROM test " & _
"WHERE test.date_test=#" & Format$(date_recherche.Value,"MM\/DD\/YYYY") & "#;"


et c'est TOUT....

Access reconnaitra une date, passée en format internationnal, parfaitement compris, quelles que soient les parametres regionnaux
Renfield
Messages postés
17280
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
21 juillet 2019
57 -
en gros, ta seule grosse erreur a été de placer ton label qui invite a saisir les dates en format dd/mm/yyyy. (vu que CDate, que tu as utilisé utilises les parametres regionnaux)


ce qu'indique DarkSidious est vrai, tu fait faire trop de transtypages, qui risque de ralentir la chose... présentement, Access va s'y retrouver, mais bon.
pillsmen
Messages postés
27
Date d'inscription
samedi 27 mai 2006
Statut
Membre
Dernière intervention
3 juillet 2007
-
Merci pour vos conseils,

je modifie la source de suite :).

Par contre Renfield, je crois que tu n'as pas saisi le principe de mon label :).
A l'ouverture du formulaire, la fonction ReturnFormat() permet de construire la chaîne de caractère (masque de saisie) qui indiquera à l'utilisateur sous quel format entrer la date par analyse de la date renvoyée par la fonction Date(). Celui-ci est donc basé sur les paramètres régionnaux (j'ai testé avec tout les formats de dates que j'avais dans Panneau de configuration > Options régionnales et linguistiques). Je n'ai trouver aucune source qui le fasse, c'était donc l'intérêt de celle-ci ;).

En revanche, dans mon programme je devrais gérer l'insertion/lecture de dates quelque soit la région donc si j'ai bien compris en changeant mes requêtes mon code sera portable quelque soit les paramètres régionnaux du système?

Quelle misère cette gestion des dates sous Access ... ;)
pillsmen
Messages postés
27
Date d'inscription
samedi 27 mai 2006
Statut
Membre
Dernière intervention
3 juillet 2007
-
Petite remarque, juste pour essayer de comprendre un peu plus :)

Admettons d'avoir les paramètres régionnaux pour le format date courte : yyyy.mm.dd. (format hongrois, me demander pas pourquoi, c'est le premier format "bizarre" que j'ai trouvé ^^). Si je saisie une date dans un format complètement différent il me sauvegarde n'importe quoi dans la BDD ?!

J'ai tester en entrant un format jj/mm/yyyy (pour exemple : 09/02/2007, en gardant le format system hongrois), quand je consulte la base de donnée, il me met 2007.09.02 !
Autrement dit, si l'utilisateur saisie une date dans un format autre que le format système, si ce format est "proche" du format système, pas de problème (style dd/mm/yyyy et dd.mm.yyyy) mais dans le cas contraire ..... ce qui implique qu'il faudrait une vérification sur le format à l'insertion histoire d'être sûr ?!

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.