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 :

Surveiller Création de fichier


Sujet :

C#

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    18
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2007
    Messages : 18
    Points : 12
    Points
    12
    Par défaut Surveiller Création de fichier
    Bonjour,

    Voila je cherche à surveiller la fin de création de fichier dans un répertoire. J'ai regarder autour du FileSystemWatcher, mais il semblerait que le paramètrage possible ne corresponde pas à ce que j'attend.

    Je vous explique mon cas :
    Dans un répertoire je peux placer des fichier plus ou moins volumineur (de 1Ko à 300 Mo)
    Une fois le fichier fini d'etre créer (cad qu'il n'y a plus d'ecriture), je veux effecteur un traitement sur ce fichier.

    Avec le SystemFileWatcher, je ne peut que savoir quand est créé mon fichier. Laconfiguration qui retourne lastAccess me produit 3 evenement lorsque le fichier fait plus de 0ko et 2 seulement quand le fichier est vide. (Mais quand savoir si le 3 eme evenement sera généré car dans le cas d'un gros fichier, tant que l'ecriture n'est pas fini on peut pas accéder à ces infos)
    Pour le LastWrite, qui est censé intervenir lors de la dernière ecriture eh bien ca ne fonctionne pas.

    Je ne veux pas faire de distinction, je prends tous les fichiers du répertoire dans mon traitement.

    Actuellement, j'ai une boucle qui essaye de lire le fichier et au bout de 10 essai abondonne la lecture (avec une pause entre chaque lecture). C'est pas terrible comme solution.

    je cherche donc un truc qui me permettrait de savoir quand un fichier a fini d'être copié.

  2. #2
    Inactif  
    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Janvier 2007
    Messages
    6 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 63
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet NTIC

    Informations forums :
    Inscription : Janvier 2007
    Messages : 6 604
    Points : 13 314
    Points
    13 314
    Par défaut
    Bonjour

    A première vue, je ne vois pas de solution simple à ton problème, si les fonctionnalités du FileSystemWatcher ne te conviennent pas.

    Il est possible (je crois, mais je ne l'ai jamais fait) de faire un hook fichier, mais qui doit travailler en mode driver (encore une fois : il me semble, car jamais fait); bref rien de simple. (de plus, C# n'est pas forcément le langage de choix dans ce cas - C ou C++ serait plus adapté).

    Peut on savoir quel est l'objectif fonctionnel ici ?

  3. #3
    Expert éminent sénior Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 175
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 175
    Points : 25 116
    Points
    25 116
    Par défaut
    quoi ou qui déclenche la copie du fichier ?

  4. #4
    Membre à l'essai
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    18
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2007
    Messages : 18
    Points : 12
    Points
    12
    Par défaut
    La copie de fichier est faite par un utilisateur, mais il n'est pas impossible que part la suite la création soit exécuté, en plus, par un programme tiers.

    Ce que je veux en faite, c'est que dés que le fichier est fini d'être créer, mon programme C# lise son contenu et le traite. Pour cela je doit savoir quand le fichier est libéré, car sinon je ne peux pas le lire.


    Merci...

  5. #5
    Expert éminent sénior Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 175
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 175
    Points : 25 116
    Points
    25 116
    Par défaut
    soit tu modifies ce que fait l'utilisateur

    soit quand tu recois l'info que le fichier a été créé, tu le donnes à un thread qui s'occupe de vérifier si le fichier grandit (si pendant une minute il n'a pas grandit, on doit pouvoir considérer qu'il est fini)

  6. #6
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Juillet 2007
    Messages
    1 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations forums :
    Inscription : Juillet 2007
    Messages : 1 277
    Points : 1 521
    Points
    1 521
    Par défaut
    http://www.ivanlef0u.tuxfamily.org/?p=13

    Comme on l'avait dit, ça risque de ne pas être simple .

  7. #7
    Inactif  
    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Janvier 2007
    Messages
    6 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 63
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet NTIC

    Informations forums :
    Inscription : Janvier 2007
    Messages : 6 604
    Points : 13 314
    Points
    13 314
    Par défaut
    Une solution intermédaire consiste peut être à utiliser le FileSystemWatcher pour détecter la création du fichier et, à ce moment, "poller" le fichier à interval régulier (toutes les 1/2 secondes par exemple) pour détecter sa fermeture.

    Certes, c'est pas le top de l'élégance programmatique, mais ça évite de te lancer dans un développement de type "hook fichier" qui, en dehors de son indéniable complexité, peut, en cas de bug, altérer la stabilité du système (ce qui est très très génant sur un serveur par exemple).

  8. #8
    Membre à l'essai
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    18
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2007
    Messages : 18
    Points : 12
    Points
    12
    Par défaut
    Citation Envoyé par Bluedeep Voir le message
    Une solution intermédaire consiste peut être à utiliser le FileSystemWatcher pour détecter la création du fichier et, à ce moment, "poller" le fichier à interval régulier (toutes les 1/2 secondes par exemple) pour détecter sa fermeture.

    Certes, c'est pas le top de l'élégance programmatique, mais ça évite de te lancer dans un développement de type "hook fichier" qui, en dehors de son indéniable complexité, peut, en cas de bug, altérer la stabilité du système (ce qui est très très génant sur un serveur par exemple).
    En effet, c'est ce que j'ai effecuté, un second thread qui se charge de traiter les fichiers détecter par le FileSystemWatcher.

    Concernant l'API Windows, ca me parait bien compliquer, et le truc c'est surtout que j'ai pas de processus à espionner.


    Merci à tous

  9. #9
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Juillet 2007
    Messages
    1 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations forums :
    Inscription : Juillet 2007
    Messages : 1 277
    Points : 1 521
    Points
    1 521
    Par défaut
    L'API Windows te retoune tous les handles. L'intérêt de connaître le PID du processus, c'est justement de pouvoir filtrer ... mais tu peux parcourir la liste des handles et voir si le fichier qui t'intéresse est utilisé ou pas. Mais question performance, je ne suis pas convaincu que ce soit plus pertinent que la tentative d'ouverture. Et ça ne résoud pas le problème de devoir faire du polling de toute façon...

    Le mieux effectivement, c'est de tenter l'ouverture du fichier à intervalle régulier. En couplant en plus avec la taille du fichier invariable, on doit pouvoir obtenir un code qui ne dégrade pas trop les performances.

  10. #10
    Inactif  
    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Janvier 2007
    Messages
    6 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 63
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet NTIC

    Informations forums :
    Inscription : Janvier 2007
    Messages : 6 604
    Points : 13 314
    Points
    13 314
    Par défaut
    Citation Envoyé par Kaidan Voir le message
    L'API Windows te retoune tous les handles. L'intérêt de connaître le PID du processus, c'est justement de pouvoir filtrer ... mais tu peux parcourir la liste des handles et voir si le fichier qui t'intéresse est utilisé ou pas. Mais question performance, je ne suis pas convaincu que ce soit plus pertinent que la tentative d'ouverture.
    Je serais même presque convaincu du contraire à cause des possibilités d'impact sur des processus tiers.

    Le mieux effectivement, c'est de tenter l'ouverture du fichier à intervalle régulier. En couplant en plus avec la taille du fichier invariable, on doit pouvoir obtenir un code qui ne dégrade pas trop les performances.
    D'autant qu'il peut chuter sans dommage la prio du thread en question.

  11. #11
    Membre habitué Avatar de Johann7751
    Profil pro
    Analyste Programmeur Junior
    Inscrit en
    Février 2009
    Messages
    234
    Détails du profil
    Informations personnelles :
    Âge : 38
    Localisation : France

    Informations professionnelles :
    Activité : Analyste Programmeur Junior

    Informations forums :
    Inscription : Février 2009
    Messages : 234
    Points : 142
    Points
    142
    Par défaut
    Salut,

    J'avais le même genre de problématique à résoudre dans mon projet.
    C'est un service Windows qui doit regarder à intervalle régulier une liste de répertoire d'intérêts, voir les fichiers qu'il y a dans chaque répertoire et ne récupérer que les fichiers 'prêts pour traitement'.

    Le service considère un fichier 'prêt pour traitement',
    c'est à dire qu'il n'est pas en cours de copie ou d'écriture,
    lorsque l'intervalle de temps entre la date courante et la date de dernier accès en écriture au fichier est supérieure à 5 min par exemple.

    5, 10, 30, 60 min, c'est toi après qui peut le définir..

    On peut récupérer la date de dernier accès en écriture d'un fichier grâce à l'objet 'FileInfo' de 'System.IO'.





    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
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.IO;
     
    namespace ConsoleApplication1
    {
        class Program
        {
            static void Main(string[] args)
            {
     
                // Ton répertoire à scruter
                string directory = @"C:\Users\Johann\Desktop\toto";
     
                // L'intervalle (en minutes) entre la date courante et la date de dernier accès en écriture au fichier
                // que tu juges suffisant pour considérer qu'un fichier est "prêt" pour ton traitement.
                int intervalleRequis = 5;
     
                // Création d'un objet 'DirectoryInfo' sur ton répertoire
                DirectoryInfo di = new DirectoryInfo(directory);
     
                // Récupération de la liste des fichiers contenus dans ton répertoire
                // dans un tableau d'objets 'FileInfo'
                FileInfo [] fileList = di.GetFiles();
     
                // S'il y a au moins un fichier dans la liste récupérée..
                if (fileList.Length > 0)
                {
                    // Pour chaque objet 'FileInfo' dans ton tableau "fileList"..
                    foreach (FileInfo f in fileList)
                    {
     
                        DateTime now = DateTime.Now;
                        DateTime lastWrite = f.LastWriteTime;
     
                        TimeSpan diff = now - lastWrite;
                        int interval = (int)diff.TotalMinutes;
     
                        if (interval >= intervalleRequis)
                        {
                            // OK, le fichier peut être traité
                        }
                        else
                        {
                            // KO : l'intervalle entre la date courante et la date de dernier accès en écriture
                            // n'est pas suffisant (inférieur à 5 min) : le fichier ne peut pas être traité
                        }
     
     
     
                    }
                }
     
            }
        }
    }
    J'espère que ça pourra t'aider.

  12. #12
    Membre à l'essai
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    18
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2007
    Messages : 18
    Points : 12
    Points
    12
    Par défaut
    Citation Envoyé par Johann7751 Voir le message
    Salut,

    J'avais le même genre de problématique à résoudre dans mon projet.
    C'est un service Windows qui doit regarder à intervalle régulier une liste de répertoire d'intérêts, voir les fichiers qu'il y a dans chaque répertoire et ne récupérer que les fichiers 'prêts pour traitement'.

    Le service considère un fichier 'prêt pour traitement',
    c'est à dire qu'il n'est pas en cours de copie ou d'écriture,
    lorsque l'intervalle de temps entre la date courante et la date de dernier accès en écriture au fichier est supérieure à 5 min par exemple.

    5, 10, 30, 60 min, c'est toi après qui peut le définir..

    On peut récupérer la date de dernier accès en écriture d'un fichier grâce à l'objet 'FileInfo' de 'System.IO'.





    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
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.IO;
     
    namespace ConsoleApplication1
    {
        class Program
        {
            static void Main(string[] args)
            {
     
                // Ton répertoire à scruter
                string directory = @"C:\Users\Johann\Desktop\toto";
     
                // L'intervalle (en minutes) entre la date courante et la date de dernier accès en écriture au fichier
                // que tu juges suffisant pour considérer qu'un fichier est "prêt" pour ton traitement.
                int intervalleRequis = 5;
     
                // Création d'un objet 'DirectoryInfo' sur ton répertoire
                DirectoryInfo di = new DirectoryInfo(directory);
     
                // Récupération de la liste des fichiers contenus dans ton répertoire
                // dans un tableau d'objets 'FileInfo'
                FileInfo [] fileList = di.GetFiles();
     
                // S'il y a au moins un fichier dans la liste récupérée..
                if (fileList.Length > 0)
                {
                    // Pour chaque objet 'FileInfo' dans ton tableau "fileList"..
                    foreach (FileInfo f in fileList)
                    {
     
                        DateTime now = DateTime.Now;
                        DateTime lastWrite = f.LastWriteTime;
     
                        TimeSpan diff = now - lastWrite;
                        int interval = (int)diff.TotalMinutes;
     
                        if (interval >= intervalleRequis)
                        {
                            // OK, le fichier peut être traité
                        }
                        else
                        {
                            // KO : l'intervalle entre la date courante et la date de dernier accès en écriture
                            // n'est pas suffisant (inférieur à 5 min) : le fichier ne peut pas être traité
                        }
     
     
     
                    }
                }
     
            }
        }
    }
    J'espère que ça pourra t'aider.

    Merci beaucoup, c'est une solution qui l'air propre !!

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

Discussions similaires

  1. Surveiller et lister la création de fichiers dans un répertoire
    Par remyclem dans le forum Développement de jobs
    Réponses: 4
    Dernier message: 07/06/2012, 14h24
  2. Surveillance création de fichier
    Par Blokator dans le forum Windows Serveur
    Réponses: 7
    Dernier message: 02/04/2007, 00h18
  3. surveillance répertoire pour création de fichier
    Par gerald2545 dans le forum Entrée/Sortie
    Réponses: 4
    Dernier message: 03/08/2006, 08h21
  4. création de fichiers .x
    Par Pazz dans le forum DirectX
    Réponses: 1
    Dernier message: 03/12/2002, 00h33

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