PC SOFT

FORUMS PROFESSIONNELS
WINDEVWEBDEV et WINDEV Mobile

Accueil → WINDEV 25 → N° d'enregistrement du fichier de données changeants
N° d'enregistrement du fichier de données changeants
Débuté par TheMIND, 23 sep. 2020 13:59 - 9 réponses
Membre enregistré
5 messages
Posté le 23 septembre 2020 - 13:59
Bonjour à tous,

Je tourne mon problème dans tous les sens mais ne trouve pas la solution à ce comportement étrange et fini par vous solliciter.

J'ai une fenêtre qui s'ouvre sur clic d'une ligne table, ma fenêtre s'ouvre bien avec mes bonnes valeurs.
Dans cette fenêtre, j'ai un bouton de sauvegarde des données qui fonctionne bien 95 fois sur 100.
Le problème est que les 5 fois sur 100, la sauvegarde m'écrase un autre enregistrement de mon fichier de données avec les valeurs présentent à l'écran.
J'ai mis en place un fichier log via une procédure "PROC_FichierLog" et découvre que le n° d'enregistrement est changé en cours de route !!!

Voici mon code :
PROC_FichierLog("PROC_ToDoModif","Modification - Avant EcranVersFichier")
EcranVersFichier()
PROC_FichierLog("PROC_ToDoModif","Modification - Après EcranVersFichier")
HModifie(Liste_ToDo,hNumEnrEnCours,hBlocageEcriture)
PROC_FichierLog("PROC_ToDoModif","Modification - Après HModifie")


Les 5 fois sur 100 donc, à l'exécution de ce code, PROC_FichierLog("PROC_ToDoModif","Modification - Après EcranVersFichier") et PROC_FichierLog("PROC_ToDoModif","Modification - Avant EcranVersFichier") me renvoient "3366" qui est bien le n° d'enregistrement en cours d'utilisation mais, PROC_FichierLog("PROC_ToDoModif","Modification - Après HModifie") me renvoie "3119", le n° a été changé lors du HModife à priori.
Du coup, les données de l'enregistrement "3119" ont été écrasées par celles du "3366", un doublon est créé avec les conséquences désastreuses que cela comporte.

Quelqu'un aurait-il une idée?

Merci d'avance pour vos retours.
Membre enregistré
1 707 messages
Posté le 23 septembre 2020 - 14:47
Bonjour,
C'est ce que tu demande en spécifiant le N° d'enregistrement.
Il est fort possible que
PROC_FichierLog("PROC_ToDoModif","Modification - Après EcranVersFichier")

modifie l'index de position dans ta table. Il vaut mieux mémoriser l'emplacement avant l'appel de la procédure

--
Il y a peut être plus simple, mais, ça tourne
Membre enregistré
5 messages
Posté le 23 septembre 2020 - 17:07
Bonjour et merci pour le retour :)

Voroltinquo a écrit :
Bonjour,
C'est ce que tu demande en spécifiant le N° d'enregistrement.

Je suppose que tu fais allusion à HModifie(Liste_ToDo,hNumEnrEnCours,hBlocageEcriture) ?
Au départ je ne demandais pas à avoir le N° encours via "hNumEnrEnCours".
J'avais à l'origine, simplement HModifie(), mais le problème était déjà présent.
J'ai donc essayé en forçant le HModifie avec la valeur de l'enregistrement encours même si, en principe, sans mention de n° d'enregistrement dans HModifie(), c'est cette constante qui est prise par défaut.

Voroltinquo a écrit :
Il est fort possible que
PROC_FichierLog("PROC_ToDoModif","Modification - Après EcranVersFichier")
modifie l'index de position dans ta table. Il vaut mieux mémoriser l'emplacement avant l'appel de la procédure

Là aussi, j'ai mis en place cette procédure pour pister le problème déjà présent à l'origine.
La procédure PROC_FichierLog n'est donc pas impliquée dans ce problème.


Peut-être une précision complémentaire, pour ce fichier de données, je suis dans un contexte HFSQL C/S.
Membre enregistré
1 707 messages
Posté le 23 septembre 2020 - 17:55
Si le problème était là avant l'utilisation de hNumEnrEnCours, cela provient du fait que tu ne pointes pas sur le bon tuple.

--
Il y a peut être plus simple, mais, ça tourne
Posté le 23 septembre 2020 - 19:52
problème classique quand on se base sur la notion "d'enregistrement en cours"...

Dés que le programme devient un peu complexe, on peut se retrouver avecun autre process (timer ou autre) qui utilise le même fichier et change donc d'enreg en cours...

La bonne solution est donc de ne JAMAIS compter sur la présence de tel ou tel enreg dans le buffer fichier et de TOUJOURS lire l'enreg quand on en a besoin. Pour ca :
1. passer en paramètre aux fenêtre secondaire l'ID unique de l'enreg à traiter
2. dans le code d'init de la fenêtre lire l'enreg avec cette ID
3. dans le code de modification de l'enreg, commencer par lire l'enreg avant de renseigner les champs modifiés localement et de faire le hmodifie

Le résultat est nettement plus robuste
Membre enregistré
5 messages
Posté le 24 septembre 2020 - 16:38
Bonjour et merci pour vos retours.

Je note donc qu'il ne faut jamais utiliser les n° d'enregistrement mais plutôt les clés uniques que l'on définit dans le fichier de données.
Ne plus utiliser EcranVersFichier() mais relire l'enregistrement, mettre à jour soi-même chaque rubrique de la fenêtre.
Cependant, le plus propre étant de ne mettre à jour que les champs/rubriques qui sont modifiés, je suppose que je vais aussi devoir me taper une procédure qui vérifie si le contenu de chaque champ a été modifié avant de l'enregistrer et l'intercaler dans le code de chaque champ ?
Posté le 24 septembre 2020 - 17:06
> Je note donc qu'il ne faut jamais utiliser les n° d'enregistrement mais plutôt les clés uniques que l'on définit dans le fichier de données.

NON... on PEUT utiliser le numéro d'enreg si on veut pour faire la gestion de fiche... Il ne faut pas compter sur ce numéro pour le long terme, mais ca n'a rien à voir avec le problème exprimé

Ne plus utiliser EcranVersFichier() mais relire l'enregistrement, mettre à jour soi-même chaque rubrique de la fenêtre.

NON PLUS... On peut utiliser fichiervesecran, MAIS IL FAUT AVANT avoir lu l'enreg pour être sur qu'on est dessus. Après utiliser FichierVersEcran ou des affectations par code, c'est un autre débat avec d'autres implications.

> Cependant, le plus propre étant de ne mettre à jour que les champs/rubriques qui sont modifiés, je suppose que je vais aussi devoir me taper une procédure qui vérifie si le contenu de chaque champ a été modifié avant de l'enregistrer et l'intercaler dans le code de chaque champ ?

Perso, SI C'EST IMPORTANT je fais :
1. entrée dans la fenêtre, lecture et sauvegarde de l'enreg en cours en mémoire
2. en modif, lecture de l'enreg en cours, puis comparaison entre les zones saisies et l'enreg sauvegardé (LES MODIFS COURANTES) et affectation uniquement de ces champs...

C'est le système de gestion dit 'le dernier qui parle a raison'...

Ca peut se faire de manière générique avec les indirections, et relativement facilement si on adopte une norme de nommage des champs fenêtres par rapport au fichier.

MAIS : est ce que c'est nécessaire ? Est ce que ton appli est dans un cadre ou tu as bcp de chance d'avoir deux utilisateurs qui travaillent sur le même enreg en même temps ?

Si tu fais de la réplication, alors oui, sinon, c'est beaucoup moins sur... A toi de voir si l'investissement en temps est utilie pour ton cas.
Membre enregistré
5 messages
Posté le 25 septembre 2020 - 09:23
Merci Argus d'avoir pris la peine de revenir avec autant de détails, cela m'aide beaucoup :merci:.
J'y vois plus clair et vais suivre tes conseils en espérant que cela règle mon problème.

J'utilise la journalisation, c'est pourquoi je souhaite éviter les sauvegardes sur des rubriques qui n'ont pas été modifiées par l'utilisateur.

Argus a écrit :
> Est ce que ton appli est dans un cadre ou tu as bcp de chance d'avoir deux utilisateurs qui travaillent sur le même enreg en même temps ?
Oui si je ne fais rien, mais j'ai mis en place le blocage en écriture pour éviter cela.
Membre enregistré
80 messages
Posté le 25 septembre 2020 - 10:21
Avant j'utilisais du code façon rad:
la table est une table fichier.
on est donc placé sur un enreg
on ouvre la fiche correspondante. on fait les modifs
y a juste un hmodifie à la validation

=> trop eu de problemes !

maintenant je passe systématiquement la clef unique en paramètre et avant enregistrement je refais systématiquement la lecture de l'enregistrement puis le ecranversfichier (ou remplissage des zones une à une ça depend du contexte) avant le hmodifie !.

ok je perds du temps mais au moins je suis sûr !
Membre enregistré
5 messages
Posté le 28 septembre 2020 - 09:38
Cdm98 a écrit :
Avant j'utilisais du code façon rad:
la table est une table fichier.
on est donc placé sur un enreg
on ouvre la fiche correspondante. on fait les modifs
y a juste un hmodifie à la validation

=> trop eu de problemes !

Effectivement, j'en fais les frais aussi.

Cdm98 a écrit :
maintenant je passe systématiquement la clef unique en paramètre et avant enregistrement je refais systématiquement la lecture de l'enregistrement puis le ecranversfichier (ou remplissage des zones une à une ça depend du contexte) avant le hmodifie !.

ok je perds du temps mais au moins je suis sûr !

Je teste ce principe actuellement en espérant ne plus avoir de problème.