Attendre apres la fin dune commande...

Résolu
ELCouz Messages postés 135 Date d'inscription jeudi 22 mars 2007 Statut Membre Dernière intervention 25 juillet 2008 - 2 avril 2007 à 03:15
ELCouz Messages postés 135 Date d'inscription jeudi 22 mars 2007 Statut Membre Dernière intervention 25 juillet 2008 - 3 avril 2007 à 02:36
Bonjour,
jai cree un programme qui list les fichier sur mes dvd et cd afin de les identifier et de faire une recherche du TOC (Contenu du cd-rom) hors ligne sur le reseau ou sur mon ordinateur..

la maniere la plus rapide que jai trouver cest bien sur la methode oldschool c-a-d le bon vieux Dir ... ( precisement dir f: /b /s > montexte.txt) sa prend 10 secondes pour lister 4000-5000 fichiers sur un dvd, et 1 minute pour 20 000 fichiers tandis quavec plusieur methode pure vb  mon programme gelais ou prennais bcp de temps ou de memoire....

bon je mexplique le probleme cest quand jai bcp de fichier sur un disque, le processus DIR est lancer parralelement a mon programme donc vb continue a la ligne suivante qui est ouvre le fichier montexte.txt pour inserer des lignes et le classer dans un bon dossier ... le probleme cest qui est souvent en cours dutilisation (entrain de lister les fichier parallement) jai donc une erreur Access denied ... jai beau assayer la methode sleep mais cest plustot imprecis , puisque si je met sleep 9000 et que la TOC est plus longue a lire que prevus je tombe sur la meme erreur tandis que si je met sleep 60000 (1 minute) je perds du temps quand jai juste 3-4 fichier a lister sur tel dvd ou cd ... mon application est donc inutilisable pendant 60 secondes...surtout que je doit scanner bcp de cd et dvd cest pas pratique...

voici mon code en question:

Call StartProcess("cmd /c" & "dir f: /b /s >" & Valeur & ".idn", True)
    Sleep 4000 'faudrais mettre kekchose autre que sleep pour verifier si la commande plus haut est terminer
    Open idnpath For Input As #1
    Open datapath For Output As #2
    'sauvegarde la date au debut du fichier
    Print #2, "[Date:" & Now & "]"
    Print #2, "[" & disctitle & "]"
    While Not EOF(1)
        Input #1, a$
        Print #2, a$
    Wend
    Close #1
    Close #2
    Sleep 1000 'attend 1 seconde apres la fermeture du fichier...close #1 et #2 cree plus haut juste pour la luck :P
    Kill idnpath 'efface le fichier de DIR temporaire
End Sub

a des fins de comprehension je met le code du module pour faire marcher la fonction StartProcess

Public Type STARTUPINFO
    cb              As Long
    lpReserved      As Long
    lpDesktop       As Long
    lpTitle         As Long
    dwX             As Long
    dwY             As Long
    dwXSize         As Long
    dwYSize         As Long
    dwXCountChars   As Long
    dwYCountChars   As Long
    dwFillAttribute As Long
    dwFlags         As Long
    wShowWindow     As Integer
    cbReserved2     As Integer
    lpReserved2     As Long
    hStdInput       As Long
    hStdOutput      As Long
    hStdError       As Long
End Type

Public Type PROCESS_INFORMATION
    hProcess    As Long
    hThread     As Long
    dwProcessID As Long
    dwThreadID  As Long
End Type

Declare Function CreateProcessA Lib "kernel32" (ByVal lpApplicationName As Long, ByVal lpCommandLine As String, ByVal lpProcessAttributes As Long, ByVal lpThreadAttributes As Long, ByVal bInheritHandles As Long, ByVal dwCreationFlags As Long, ByVal lpEnvironment As Long, ByVal lpCurrentDirectory As Long, lpStartupInfo As STARTUPINFO, lpProcessInformation As PROCESS_INFORMATION) As Long

Public Sub StartProcess(CommandLine As String, Optional Hide As Boolean = False)
    Const STARTF_USESHOWWINDOW As Long = &H1
    Const SW_HIDE As Long = 0
  
    Dim proc As PROCESS_INFORMATION
    Dim Start As STARTUPINFO

    'Initialize the STARTUPINFO structure:
    Start.cb = Len(Start)
    If Hide Then
        Start.dwFlags = STARTF_USESHOWWINDOW
        Start.wShowWindow = SW_HIDE
    End If
    'Start the shelled application:
    CreateProcessA 0&, CommandLine, 0&, 0&, 1&, _
        NORMAL_PRIORITY_CLASS, 0&, 0&, Start, proc

End Sub

ya til une facon de recuprer le processus quon a cree et verifier si il nexiste plus (chercher dans la memoire au pire des cas)?
Tous vos commentaire/optimisation sont la bienvenue...

vous voulez la source? pas de probleme je vous la donne pour mieu comprendre ;) cliquez-ici
http://pages.infinit.net/ironz/lecteurtoc.zip

Merci beaucoup!
Laurent

8 réponses

Renfield Messages postés 17287 Date d'inscription mercredi 2 janvier 2002 Statut Modérateur Dernière intervention 27 septembre 2021 74
2 avril 2007 à 23:27
tu mélange l'exe a appeler et ses parametres...
ajoutes simplement une virgule :

ExecCmd "cmd" , "/c" & " dir f: /b /s >" & Valeur & ".idn"

Renfield
Admin CodeS-SourceS- MVP Visual Basic
3
cs_Exploreur Messages postés 4821 Date d'inscription lundi 11 novembre 2002 Statut Membre Dernière intervention 15 novembre 2016 15
2 avril 2007 à 08:30
Salut,

Il faudrait peut-être utiliser une variable en Boolean , qui t'informe une fois ta procédure terminiée, et de là tu continu la suite de ton programme...Je ne sais pas si c'est la meilleur solution....

A+
Exploreur

 
0
cs_Exploreur Messages postés 4821 Date d'inscription lundi 11 novembre 2002 Statut Membre Dernière intervention 15 novembre 2016 15
2 avril 2007 à 08:31
Salut,


Regarde aussi du côté de l'instruction : DoEvents


A+
Exploreur


 
0
Renfield Messages postés 17287 Date d'inscription mercredi 2 janvier 2002 Statut Modérateur Dernière intervention 27 septembre 2021 74
2 avril 2007 à 08:46
http://www.vbfrance.com/codes/SHELLANDWAIT-EXECUTER-APPLICATION-ATTENDRE-FIN-RENVOYER-SON-CODE_34867.aspx



ne rendra la main qu'apers la fin du process lancé

Renfield
Admin CodeS-SourceS- MVP Visual Basic
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
cs_MPi Messages postés 3877 Date d'inscription mardi 19 mars 2002 Statut Membre Dernière intervention 17 août 2018 23
2 avril 2007 à 11:45
Étant donné que l'erreur Access Denied est "trappable", tu pourrais boucler tant que l'erreur survient, non ?

Du genre

On Error goto Erreur
..................'ton code
Exit Sub
Erreur:
    If Err.Number = 55 then  'mettre le bon numéro d'erreur
        Resume  ' ajouter au besoin un Sleep d'une seconde ou deux
    Else
        ... 'gestion d'autres erreurs
    Endif
End Sub

Pour éviter une boucle infinie, tu pourrais avoir une variable booléenne qui s'active sur la touche "Escape", disons, et qui te permettrait de terminer la boucle si = True

Tu pourrais aussi avoir une Form qui s'affiche tant que le processus n'est pas terminé, avec ou sans ProgressBar

Des idées comme ça... et pas nécessairement les meilleures...
MPi
0
ELCouz Messages postés 135 Date d'inscription jeudi 22 mars 2007 Statut Membre Dernière intervention 25 juillet 2008
2 avril 2007 à 22:08
@ Renfield :

Apparement le code que tu ma rediriger ne support pas le command prompt ... jobtien ceci a lexecution de :

ExecCmd "cmd /c" & " dir f: /b /s >" & Valeur & ".idn"

---------------------------
cmd /c dir f: /b /s >3333.idn
---------------------------
Windows cannot find 'cmd /c dir f: /b /s >3333.idn'. Make sure you typed the name correctly, and then try again. To search for a file, click the Start button, and then click Search.
---------------------------
OK  
---------------------------

@ Mpi :

ton idee est bonne jai assayer le code que tu ma donner avec lerreur numero 70 ,, le probleme cest que meme si ji donne un sleep quand il tombe sur lerreur 70, je ne sais pas pourquoi mais sa ne fonctionne pas :(

jai meme assayer ce code ( a partir de ta base) :

   Call StartProcess("cmd /c" & "dir f: /b /s >" & Valeur & ".idn", True)
    Sleep sleepthatbitch
Resumefichier:
    On Error GoTo Erreur
        Open idnpath For Input As #3 'on peu ouvrir ? .. tombe en erreur si en cours dutilisation
        Close #3
        GoTo Readidn
Exit Sub
Erreur:
    If Err.Number = 70 Then  'si fichier temporaire idn pas fini de se generer, attendre X seconde
        Resume
        Sleep 4000
        GoTo Resumefichier
    If Err.Number = 53 Then  'fichier toc idn pas lah! CMD déteste les chemins reseaux et mapped drives donc a verifier
        Resume
        MsgBox "Impossible de localiser le fichier TOC temporaire, êtes-vous sûre d'avoir le droit d'écriture dans ce dossier (Ex: Disque Réseau) ?"
        Exit Sub
    Else
        MsgBox "General Failure #" & Err.Number
        Exit Sub
    End If
    End If
   
Readidn:
Open idnpath For Input As #1
Open datapath For Output As #2
'sauvegarde la date au debut du fichier
Print #2, "[Date:" & Now & "]"
Print #2, "[" & disctitle & "]"
While Not EOF(1)
    Input #1, a$
    Print #2, a$
Wend
Close #1
Close #2
Sleep 2000
Kill idnpath
MsgBox "operation terminé!"

jai quasiment assayer toute combinaison possible meme au plus stupide fesant le plus de detour possible ... rien ne fonctionne il saute pareil a Readidn: mais parcontre il passe par :

 If Err.Number = 70 Then  'si fichier temporaire idn pas fini de se generer, attendre X seconde
        Resume
        Sleep 4000
        GoTo Resumefichier
sauf que je ne sais pas pkoi il nattend pas 4 seconde...

difficile a expliquer ...

merci de vos reponse cest tres aprecier !! :D
0
cs_MPi Messages postés 3877 Date d'inscription mardi 19 mars 2002 Statut Membre Dernière intervention 17 août 2018 23
2 avril 2007 à 23:40
Le Resume fait en sorte que le code revient à la ligne qui cause l'erreur, donc ne passe pas par le Sleep, si celui-ci est placé après.

Si tu le places avant Resume, le Sleep devrait s'effectuer pour la durée que tu lui donnes, ensuite passera par Resume, donc reviendra à l'appel du fichier et si celui-ci est libre, effectuera sa tâche, sinon il reviendra au Sleep de l'erreur... etc

C'est du moins le principe logique que j'y vois...

MPi
0
ELCouz Messages postés 135 Date d'inscription jeudi 22 mars 2007 Statut Membre Dernière intervention 25 juillet 2008
3 avril 2007 à 02:36
wow sa marche drolement bien Renfield !!! merci beaucoup  ....
merci a toi aussi MPi ,, tu ma apris comment gerer les code derreur tres pratique :D

Passez une bonne journee
Laurent
0
Rejoignez-nous