Précédent   Forum des professionnels en informatique > PHP > Langage > Fonctions
Fonctions Forum d'entraide sur les fonctions PHP. Avant de poster -> FAQ fonctions et Sources diverses
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 29/09/2011, 09h31   #1
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
Par défaut Fonction system() ; Exécution trop longue -> timeout

Bonjour,
je bosse sur une application chargée de gérer des fichiers sur un serveur.
Pour cela, l'application en PHP propose une interface utilisateur qui lance des scripts shells sur le serveur avec la commande system :
Code :
 system("ma commande unix");
Ces opérations peuvent durer longtemps et provoquent un timeout (la page arrête de charger) et les instructions suivantes ne sont pas traitées.

Comment est ce que je peux faire pour palier ce problème ?

merci d'avance.
ben
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h01   #2
Membre chevronné
 
Avatar de Marc3001
 
Homme
Ingénieur développement logiciels
Inscription : février 2008
Messages : 430
Détails du profil
Informations personnelles :
Sexe : Homme
Âge : 28
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Ingénieur développement logiciels

Informations forums :
Inscription : février 2008
Messages : 430
Points : 682
Points : 682
Modifie la valeur max_execution_time définie dans le php.ini.
__________________
Le logiciel, c'est comme le sexe, c'est meilleur quand c'est libre.

Linus Torvalds
Marc3001 est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h10   #3
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
Je suis pas root et je voulais éviter de toucher aux valeur de la conf ?
Est ce la seule solution ?

J'ai également essayé :
mais sans effet.

merci
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h11   #4
Membre régulier
 
Guillaume M.
Inscription : décembre 2010
Messages : 59
Détails du profil
Informations personnelles :
Nom : Guillaume M.

Informations forums :
Inscription : décembre 2010
Messages : 59
Points : 82
Points : 82
Si l’exécution du script ne retourne rien de particulier il est aussi possible de lancer la commande en arrière plan (avec "nohup"). Dans l'idéal on crée un fichier vide au lancement de la commande, et on le détruit à la fin de l’exécution, comme ça le script php peut savoir où il en est.
gmarsay est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h19   #5
Membre chevronné
 
Avatar de Marc3001
 
Homme
Ingénieur développement logiciels
Inscription : février 2008
Messages : 430
Détails du profil
Informations personnelles :
Sexe : Homme
Âge : 28
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Ingénieur développement logiciels

Informations forums :
Inscription : février 2008
Messages : 430
Points : 682
Points : 682
Lu dans la doc PHP.

Citation:
Notez que set_time_limit() n'a pas d'effet lorsque PHP fonctionne en mode safe mode. Il n'y a pas d'autre solution que de changer de mode, ou de modifier la durée maximale d'exécution dans le php.ini.
Récupères-tu la sortie de ton script?

Il faudra peut-être revoir la manière dont tu lances ta commande pour ne pas attendre la fin de celle-ci pour finir le traitement php.
Après en Ajax tu pourrais récupérer le statut et éventuellement la sortie voire les logs de ta commande.
__________________
Le logiciel, c'est comme le sexe, c'est meilleur quand c'est libre.

Linus Torvalds
Marc3001 est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h25   #6
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
oui le serveur tourne en mode safe, donc effectivement set_time_limit ne sert à rien et en plus ça n'aurait pas fonctionné car j'utilise un appel externe avec system().

Actuellement, le script shell, qui est executé via system(), produit un fichier de log, en fonction des valeurs contenues dans ce fichier de log, l'appli va effectuer des opérations en bas de données.

J'aurais besoin d'attendre la fin de l’exécution du script.
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h31   #7
Membre chevronné
 
Avatar de Marc3001
 
Homme
Ingénieur développement logiciels
Inscription : février 2008
Messages : 430
Détails du profil
Informations personnelles :
Sexe : Homme
Âge : 28
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Ingénieur développement logiciels

Informations forums :
Inscription : février 2008
Messages : 430
Points : 682
Points : 682
Citation:
Envoyé par ben.IT Voir le message
en plus ça n'aurait pas fonctionné car j'utilise un appel externe avec system().
Si tu avais pu utiliser set_time_limit, cela aurait fonctionné.

Là tu es bloqué si tu ne veux pas modifier le php.ini, tu ne peux pas augmenter le timeout des scripts php.

Il ne te reste plus qu'à faire comme je te l'ai expliqué dans mon post précédent.
__________________
Le logiciel, c'est comme le sexe, c'est meilleur quand c'est libre.

Linus Torvalds
Marc3001 est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h38   #8
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
Citation:
Envoyé par Marc3001 Voir le message
Si tu avais pu utiliser set_time_limit, cela aurait fonctionné.
Citation:
La fonction set_time_limit et la directive de configuration max_execution_time n'affectent que le temps d'exécution du script lui-même. Tout temps passé en dehors du script, comme un appel système utilisant system , des opérations sur les flux, les requêtes sur base de données, etc. n'est pas pris en compte lors du calcul de la durée maximale d'exécution du script.
Il semble bien que je sois bloqué ...
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h39   #9
Membre chevronné
 
Avatar de nathieb
 
Homme olivier Thiébaut
Chef de projet/Architecte
Inscription : mai 2004
Messages : 626
Détails du profil
Informations personnelles :
Nom : Homme olivier Thiébaut
Âge : 45
Localisation : France

Informations professionnelles :
Activité : Chef de projet/Architecte
Secteur : Service public

Informations forums :
Inscription : mai 2004
Messages : 626
Points : 704
Points : 704
Par défaut Ajax

Bonjour,

D'accord avec le dernier post Ajax est la solution.
Je l'utilise abondamment sur le lancement de procédures stockés en base.
Le process se détache. Pour le contrôle, après fichier de log
ou table

Olivier
__________________
Architecte déstructurant,
be cool, be free

J2EE - PHP - Free OS
nathieb est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h42   #10
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
ok super merci pour vos réponses, le hic est que je ne connais vraiment pas bien ajax ... mais je ne vois pas d'autres solutions...
Si vous avez des conseils ou des exemples, je suis preneur...
merci d'avance,
ben
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 11h44   #11
Membre chevronné
 
Avatar de nathieb
 
Homme olivier Thiébaut
Chef de projet/Architecte
Inscription : mai 2004
Messages : 626
Détails du profil
Informations personnelles :
Nom : Homme olivier Thiébaut
Âge : 45
Localisation : France

Informations professionnelles :
Activité : Chef de projet/Architecte
Secteur : Service public

Informations forums :
Inscription : mai 2004
Messages : 626
Points : 704
Points : 704
Par défaut bibliothèque

Bonjour,

Regarde du côté de prototype ou Jquery

simple efficace, pas la peine de réinventer la roue.

Olivier
__________________
Architecte déstructurant,
be cool, be free

J2EE - PHP - Free OS
nathieb est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 15h13   #12
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
ok, je regarde du coté AJAX et JQUERY pour lancer mon script de façon asynchrone. Est ce que tu peux m'orienter vers une méthode pour executer mon script de façon asynchrone ? Je suis en train de chercher mais je ne suis vraiment pas familier avec ces technos ...

merci d'avance,
ben
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 17h02   #13
Membre chevronné
 
Avatar de nathieb
 
Homme olivier Thiébaut
Chef de projet/Architecte
Inscription : mai 2004
Messages : 626
Détails du profil
Informations personnelles :
Nom : Homme olivier Thiébaut
Âge : 45
Localisation : France

Informations professionnelles :
Activité : Chef de projet/Architecte
Secteur : Service public

Informations forums :
Inscription : mai 2004
Messages : 626
Points : 704
Points : 704
Par défaut Ajax et process

Bonjour,

Tu peux détacher un process de son père, cela dépend de ta plateforme.
Comme tu es sur une plateforme digne, unix ou linux
il suffit d'utiliser, un script de cette forme
Code :
1
2
3
4
 
function lanceProcess($filename, $options=''){
         exec(PHP_PATH_BIN . " -f  {$filename} {$options} >> /dev/null & ");
}
C'est le >> /dev/null & qui detache le process
Après tu peux améliorer, car dans mon cas je redirige la sortie
standard vers rien
0 : STDIN
1: STDOUT
2: STDERR
ces notions sont des notions bash.
ce qui fait que tu peux faire un log des erreurs

Code :
1
2
exec(PHP_PATH_BIN . " -f  {$filename} {$options} &> execution.log & ");
Ce cas fonctionne sans Ajax.
Il suffit que tu appelles la commande

Code :
1
2
3
4
5
6
7
 
<?php
require_once 'malibquitueduprocessdelamort.php';
 
....
lanceProcess('commande','mesoptions');
...
Olivier
__________________
Architecte déstructurant,
be cool, be free

J2EE - PHP - Free OS
nathieb est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 17h22   #14
Membre régulier
 
Guillaume M.
Inscription : décembre 2010
Messages : 59
Détails du profil
Informations personnelles :
Nom : Guillaume M.

Informations forums :
Inscription : décembre 2010
Messages : 59
Points : 82
Points : 82
Attention cependant avec le "&" en bash, la commande s’exécute bien en arrière plan mais n'est pas détachée. Par exemple si la console est fermée avant la fin de l’exécution alors elle sera interrompu. Il est possible que le problème se pose à la fin de l’exécution du script PHP ?

Le préfixe "nohup" permet lui de détacher réellement le process.
gmarsay est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 29/09/2011, 21h31   #15
Membre chevronné
 
Avatar de nathieb
 
Homme olivier Thiébaut
Chef de projet/Architecte
Inscription : mai 2004
Messages : 626
Détails du profil
Informations personnelles :
Nom : Homme olivier Thiébaut
Âge : 45
Localisation : France

Informations professionnelles :
Activité : Chef de projet/Architecte
Secteur : Service public

Informations forums :
Inscription : mai 2004
Messages : 626
Points : 704
Points : 704
Par défaut exact

Bonjour,

Effectivement, oublié le détail, nohup est le meilleur

Olivier
__________________
Architecte déstructurant,
be cool, be free

J2EE - PHP - Free OS
nathieb est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 03/10/2011, 14h28   #16
Membre éprouvé
 
Avatar de ben.IT
 
Homme Benoît
Inscription : janvier 2009
Messages : 392
Détails du profil
Informations personnelles :
Nom : Homme Benoît
Âge : 24
Localisation : France, Puy de Dôme (Auvergne)

Informations forums :
Inscription : janvier 2009
Messages : 392
Points : 439
Points : 439
merci pour vos réponses,

nohup permet bien, en shell, de détacher un process du terminal ... mais dans cas ça ne résout pas mon problème : à savoir que l'instruction doit être traitée avant de pouvoir continuer à traiter les autres instructions PHP.

Dans mon cas,

soit le fichier script.sh :
Code :
1
2
3
4
5
6
7
8
#!/bin/bash
echo 'start'
for i in {1..1000}
do
  echo $i
  sleep 1
done
echo 'end'

et le fichier index.php :

Code :
1
2
3
4
5
<?php
echo 'begining of script..' ;
exec("nohup /tmp/script.sh &") ;
echo 'end  of script..' ;
?>

Je dois attendre 1000 secondes avant de pouvoir afficher la page et c'est là que je rencontre le timeout.

Dans mon cas, le script ne fait pas un "sleep 1000" mais un traitement qui peut effectivement durer très longtemps.

J'ai pu voir un problème similaire ici



Any idea ?
merci d'avance,
ben
__________________
Meet the free software gang
ben.IT est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 04/10/2011, 13h16   #17
Membre chevronné
 
Avatar de nathieb
 
Homme olivier Thiébaut
Chef de projet/Architecte
Inscription : mai 2004
Messages : 626
Détails du profil
Informations personnelles :
Nom : Homme olivier Thiébaut
Âge : 45
Localisation : France

Informations professionnelles :
Activité : Chef de projet/Architecte
Secteur : Service public

Informations forums :
Inscription : mai 2004
Messages : 626
Points : 704
Points : 704
Par défaut The solution

Bonjour,

En fait je crois avoir trouvé la piste de la solution

int pcntl_fork ( void )

Voir la documentation PHP

http://php.net/manual/fr/function.pcntl-fork.php
Il faut comprendre par contre, la notion de processus père et fils, ainsi que la notion de contexte d'un programme.


Olivier
__________________
Architecte déstructurant,
be cool, be free

J2EE - PHP - Free OS
nathieb est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 12/10/2011, 16h31   #18
Membre régulier
 
Guillaume M.
Inscription : décembre 2010
Messages : 59
Détails du profil
Informations personnelles :
Nom : Guillaume M.

Informations forums :
Inscription : décembre 2010
Messages : 59
Points : 82
Points : 82
Dans le script bash :
Code :
1
2
3
4
5
6
#!/bin/bash
touch /tmp/toto
...
# script
...
rm /tmp/toto
Et dans le script PHP :
Code :
1
2
3
4
5
6
<?php
if (file_exists('/tmp/toto')) {
    exit('Waiting...');
}
.....
?>
Tant que le fichier /tmp/toto existe tu bloques les actions sur ton interface web. Plus de problème de timeout.
gmarsay est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 20h45.


 
 
 
 
Partenaires

Hébergement Web