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

C# Discussion :

Pb lecture fichier - FileSystemWatcher


Sujet :

C#

  1. #1
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut Pb lecture fichier - FileSystemWatcher
    Bonjour,

    j'ai un ptit soucis de lecture de fichier...

    Alors voilà, je vais essayer de vous expliquer en essayant d'être claire...

    Donc, j'ai une appli qui crée un fichier xml
    Ce fichier xml doit être utilisé par 2 autres applis...
    L'appli qui le crée l'utilise pour le convertir dans un autre format, là ça pose pas de soucis
    Une autre appli l'utilise pour afficher son contenu; celle-ci repose sur un objet FileSystemWatcher qui scrute le répertoire pour savoir dès qu'un fichier est créé... Dès que l'appli reçoit l'évènement qu'un fichier a été créé, je fais une ptite boucle pour tenter de l'ouvrir, une fois que c'est bon, je l'ouvre pour de bon afin d'afficher son contenu

    C'est dans cette appli que j'ai des pb
    En fait, l'évènement qu'un nouveau fichier a été créé est lancé 2 fois pour le même
    et à chaque fois, à la 1ère ouverture il manque des données et ça fait planter mon appli...

    comment cela se fait-il donc?
    auriez-vous des idées pour y remedier ?...

    Merci

  2. #2
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    141
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 141
    Par défaut
    C'est normal,

    il faut interdire l'accès au fichier dans ta première appli jusqu'à la fin de la création du fichier.

    Le problème est :
    CreateFichier() -> cette commence l'écriture du fichier et commence l'écriture des données dans celui-ci.

    Pendant ce temps, ton autre appli détecte la création de ton fichier et le lit avant même que CreateFichier() se soit terminer. (createFichier correspond à la méthode Close() de ton FileStream).

    C'est un problème de multi-threading ou plutôt multi-process dans ton cas

  3. #3
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    J'avais déjà noter ce problème,
    c'est pourquoi, j'ai fait une ptite boucle pour vérifier que le fichier est bien dispo...

    là, c'est autre chose : quand je le lis, il est pas complet...
    et pourquoi, l'évènement 'create' remonte 2 fois?...
    et la 2e fois, c'est bon...

  4. #4
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    141
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 141
    Par défaut
    je ne me suis pas bien expliquer,
    ta boucle doit certainement contenir le code:
    while(!File.Exist(path));

    mais après cette boucle, le close à pu créer le fichier mais pas terminé son écriture. Si tu veux être sur qu'il soit terminé, faut vérifier la taille ou un truc comme ça ou tout simplement bloquer l'accès à ce fichier.

    Pourquoi create se fait deux fois?
    Regarde avec ton debugger la path du fichier créer, il se peut que le fichier soit créer en deux étapes
    1)Faire un fichier temporaire pour sauvegarde les donnée au fur et à mesure
    2)dupliquer le fichier terminer dans le fichier final.

    J'ai eu ce problème avec des fichier .doc

    Sinon, se serait bien que tu mette en ligne le code de ton évènement create et celui de la création de fichier.

  5. #5
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    comment faire pour bloquer l'accès au fichier?...

    je crois que le pb vient du fait que les 2 appli accèdent à ce fichier
    parce que si je fait une autre copie du fichier dans un répertoire à part, que seul le FileSytemWatcher scrute, là ça marche bien...

  6. #6
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    voilà le constructeur de ma classe dans laquelle je créé le FileSystemWatcher

    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
            public NouveauResultat(string strRepertoire)
            {
                try
                {
                    // scrutateur de répertoire
                    fsw = new FileSystemWatcher();
     
                    // Donner le répertoire source
                    fsw.Path = strRepertoire;
                    sRepertoire = strRepertoire;
     
                    // Accepter le multi répertoires
                    fsw.IncludeSubdirectories = true;
     
                    // Filtrer tous les fichiers xml
                    fsw.Filter = "*.xml";
     
                    // Activer le composant
                    fsw.EnableRaisingEvents = true;
     
                    // Création du délégué d'écoute du répertoire source
                    fsw.Created += new FileSystemEventHandler(fsw_Created);
                }
                catch (Exception ex)
                {
                    throw ex;
                }
            }
    et là, la méthode de l'évènement create :
    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
            private void fsw_Created(object sender, FileSystemEventArgs e)
            {
                try
                {
                    #region Vérification d'accessiblité du fichier
                    int cpteur = 0;     // compteur des tentatives d'accès au fichier
                    bool fin = false;   // booléen de sortie de boucle
                    bool ok = true;
                    while (!fin)
                    {
                        try
                        {
                            // Tentative d'ouverture du fichier
                            FileStream f = File.Open(sRepertoire + @"\" + e.Name, FileMode.Open, FileAccess.Read, FileShare.None);
     
                            // Si elle est réussie, on le referme
                            f.Close();
                            fin = true;     // pour sortir de la boucle
                        }
                        catch
                        {
                            Thread.Sleep(200);
                            // Si l'ouverture est impossible, on intercepte l'exception
                            if (++cpteur == 20)
                            {
                                // au bout de 20 tentatives, on signale l'impossibilité d'accéder au fichier
                                ok = false;
                                fin = true;
                            }
                        }
                    }
                    #endregion
                    // le fichier est libre, on peut dire à l'ihm de le charger
                    if (ok)
                    {
                        FichierResultat evt = new FichierResultat(e.Name);
                        InfoResultat(this, evt);     // envoi d'un évènement statuant du transfert de ce fichier
                    }
                }
                catch (Exception ex)
                {
                    throw ex;
                }
            }
    ...

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    141
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 141
    Par défaut
    montre moi ton code d'écriture du fichier que je puisse t'aider un truc du genre

    StreamWriter tmpStream = new StreamWriter("test.txt");
    ecritLesDonnée();
    tmpStream.Close();

  8. #8
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    je t'en mets un bout
    (elle doit faire 500 lignes...):
    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
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
            public ETAT_CALCULS ExporterResultatsXML(string fichierResultats, Hashtable donneesJbus, string typeMesure, bool defMesUS, bool defCapteur, ref string erreur)
            {
                ETAT_CALCULS retour = ETAT_CALCULS.OK;
                erreur = "";
                string stringParam = "";
                long variableBlanche = 0;   // Paramètre disponible non exploité
     
                Traces.Tracer(Traces.CALCULS, "ExporterResultatsXML", "*** DEBUT Traitement ***");
     
                // Création du fichier XML Résultats
                if (File.Exists(fichierResultats))
                    File.Delete(fichierResultats);
                XmlTextWriter xtw = new XmlTextWriter(fichierResultats, System.Text.Encoding.UTF8);
     
                try
                {
                    xtw.Formatting = Formatting.Indented;
                    xtw.Indentation = 3;
                    xtw.WriteStartDocument();
     
                     #region Ecriture des données
     
                    xtw.WriteStartElement("P2US");
                    // xtw.WriteStartElement("RESULTATS");
     
                    xtw.WriteStartElement("DIVERS");
                    // Ecriture de la Date (donnée directement extraite du nom du fichier Resultat)
                    if (retour == ETAT_CALCULS.OK)
                    {
                        string dateFormat = "";
                        if (ExtraireFormatDateHeure(fichierResultats, ref dateFormat, ref erreur))
                        {
                            xtw.WriteComment("Date et heure de la mesure");
                            xtw.WriteStartElement("DATE");
                            xtw.WriteAttributeString("nbVal", "6");
                            xtw.WriteString(dateFormat);
                            xtw.WriteEndElement();
     
                            Traces.Tracer(Traces.CALCULS, "ExporterResultatsXML", "-- Export donnée Date OK");
                        }
                        else
                        {
                            retour = ETAT_CALCULS.ERREUR;
                        }
                    }
     
                    // Ecriture du Nom de la chaîne
                    if (retour == ETAT_CALCULS.OK)
                    {
                        xtw.WriteComment("Nom de la chaîne");
                        xtw.WriteStartElement("CHAINE");
                        xtw.WriteString(Parametrage.LireParametre("CHAINE"));
                        xtw.WriteEndElement();
     
                        Traces.Tracer(Traces.CALCULS, "ExporterResultatsXML", "-- Export donnée Nom de la Chaîne (" + Parametrage.LireParametre("CHAINE") + ") OK");
                    }
     
    				//...
     
                    #endregion
     
                    // Fermeture du fichier XML Résultats
                    // xtw.WriteEndElement();
                    xtw.WriteEndElement();
                    xtw.Flush();
                }
                catch (Exception e)
                {
                    erreur = e.Message;
                    retour = ETAT_CALCULS.ERREUR;
                }
     
                finally
                {
                    xtw.Close();
                    // Indication fin de traitement
                    if (retour.Equals(ETAT_CALCULS.OK))
                    {
                        Traces.Tracer(Traces.CALCULS, "ExporterResultatsXML", "*** FIN Traitement OK ***");
                    }
                }
                return retour;
     
            }

  9. #9
    Expert confirmé
    Avatar de ced600
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Août 2006
    Messages
    3 364
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET

    Informations forums :
    Inscription : Août 2006
    Messages : 3 364
    Par défaut
    Il y a un moyen de faire simple pour ne pas te prendre la tête avec la disponibilité du fichier.

    Tu crées le fichier dans un autre répertoire que celui surveiller par le systemfilewatcher.
    Puis une fois la création et l'écriture fini, tu le copie dans ton répertoire surveiller.

  10. #10
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    141
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 141
    Par défaut
    deuxième solution si cela te turlupine beaucoup, tu lance deux visual avec un point d'arrêt sur le xtw.Close(); dans ton finally et un sur l'instruction suivante; puis dans l'autre visual et un point d'arrêt au début de ton évènement fsw_Created

    tu lance les deux appli avec F5 et tu lance la création de ton fichier Xml. Ainsi, tu vérifie que jusqu'au xtw.Close(), fsw_created ne s'éxecute pas et tu vérifie que l'instruction suivant le close s'éxécute avant l'évènements.

    Si c'est l'inverse, je te conseil de créer un fichier temporaire dans lequel tu met ton Xml, tu le duplique dans ton fichier final et tu supprime ton fichier temporaire. dans ton évènement tu test non pas l'exitence de ton fichier mais la suppression du fichier temporaire comme ca t'es sur que le fichier final est bon

  11. #11
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    oui,
    bah je crois que c'est ce que je vais finir par faire, un fichier temporaire...

    merci...

  12. #12
    Expert confirmé
    Avatar de ced600
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Août 2006
    Messages
    3 364
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET

    Informations forums :
    Inscription : Août 2006
    Messages : 3 364
    Par défaut
    C'est pas pour dire mais ma solution me parait plus simple !!!

  13. #13
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    Citation Envoyé par ced600 Voir le message
    C'est pas pour dire mais ma solution me parait plus simple !!!
    Je suis bien d'accord avec toi,
    surtout que ce répertoire existe déjà, sur un serveur,
    c'est ce que j'avais fait, faire pointer le FileSystemWatcher sur ce répertoire
    mais le client veut qu'il pointe sur le répertoire en local...
    et c'est là que ça pose problème...

    donc, voilà...

    je vais donc faire une copie supplémentaire de ces fichiers...

  14. #14
    Expert confirmé
    Avatar de ced600
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Août 2006
    Messages
    3 364
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET

    Informations forums :
    Inscription : Août 2006
    Messages : 3 364
    Par défaut
    Tu changes pas le pointeur de FileSystemWatcher.
    Mais au lieu de créer le fichier dans le répertoire local, tu le crées ailleurs puis tu déplaces le fichier.
    Tu peux le faire car tu as le droit d'écrire sur le poste sinon tu ne pourrias pas créer le fichier.
    Par exemple tu utilises les spécials folder pour te retrouver dans un truc du genre :
    c:\document and settings\user\local setting\temp\Un rep que je crée avec un nom bizzare qu'aucune application en prendra

  15. #15
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    mwouaich...

    en fait, je pense que je vais le créer avec un nom bidon
    puis je le copierai avec le nom définitif et c'est celui là que le FileSystemWatcher suivra grâce à un filtre sur le nom

    et je me servirai de fichier avec le nom bidon pour le convertir
    puis je le supprimerai quand ça sera fini...

  16. #16
    Expert confirmé
    Avatar de ced600
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Août 2006
    Messages
    3 364
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET

    Informations forums :
    Inscription : Août 2006
    Messages : 3 364
    Par défaut
    Citation Envoyé par melleb Voir le message
    mwouaich...

    en fait, je pense que je vais le créer avec un nom bidon
    puis je le copierai avec le nom définitif et c'est celui là que le FileSystemWatcher suivra grâce à un filtre sur le nom

    et je me servirai de fichier avec le nom bidon pour le convertir
    puis je le supprimerai quand ça sera fini...
    Si tu veux, mais tu double l'espace disque nécessaire.

  17. #17
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    ça reviendra au même...

    de toute façon, je suis persuadée que le pb vient du fait que deux applis accèdent au même fichier...
    avec ma solution, ce ne sera plus le cas...

  18. #18
    Membre éclairé
    Profil pro
    Inscrit en
    Juin 2005
    Messages
    499
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France

    Informations forums :
    Inscription : Juin 2005
    Messages : 499
    Par défaut
    ou bien même, je ne fais pas de copie de fichier
    je pourrais le renommer dans son nom définitif une fois la conversion terminée...
    c'est à ce moment là que la 2e appli pourra s'en servir

    ouais, pas mal, ça

  19. #19
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2006
    Messages
    141
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2006
    Messages : 141
    Par défaut
    En effet, il faudra utilisé l'évènement rename au lieu de create

  20. #20
    Expert confirmé
    Avatar de ced600
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Août 2006
    Messages
    3 364
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France

    Informations professionnelles :
    Activité : Développeur .NET

    Informations forums :
    Inscription : Août 2006
    Messages : 3 364
    Par défaut
    Citation Envoyé par melleb Voir le message
    ou bien même, je ne fais pas de copie de fichier
    je pourrais le renommer dans son nom définitif une fois la conversion terminée...
    c'est à ce moment là que la 2e appli pourra s'en servir

    ouais, pas mal, ça
    oui c'est mieux.

    Et bien sur que c'est lié u problème que le même fichier est utilisé par deux applications.

    On vois cela en programmation temps réél. Le problème d'une même ressource utilisé par 2 applications différentes.
    Normalement faut implémenter des méthodes qui dis aux autres applications :
    1) attention je veux utiliser cette ressource.
    2) Attention j'utilise cette ressource.
    3) attention je n'utilise plus cette ressource.

    A près il y a un problème de priorité à gérer, pour pas qu'une tache prioritaire soit bloqué car elle n'a pas accés à la ressource désiré utilisé par une tache moins prioritaire.

    berf cela peut devenir assez vite compliqué, surtout entre deux applications indépendantes.

+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 2 12 DernièreDernière

Discussions similaires

  1. Lecture fichier Word et remplacement paramètre
    Par Pfeffer dans le forum C++Builder
    Réponses: 4
    Dernier message: 21/02/2005, 17h30
  2. [ifstream] pb lecture fichier non sequentielle
    Par bludo dans le forum SL & STL
    Réponses: 3
    Dernier message: 10/02/2005, 21h30
  3. [LG]probleme lecture fichier
    Par yp036871 dans le forum Langage
    Réponses: 2
    Dernier message: 28/01/2004, 19h22
  4. [LG]Probleme lecture fichier file of ....
    Par John_win dans le forum Langage
    Réponses: 11
    Dernier message: 11/11/2003, 18h53
  5. [langage] prob lecture fichier .txt
    Par martijan dans le forum Langage
    Réponses: 3
    Dernier message: 16/07/2003, 11h08

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