Bonjour, j'ai un petit soucis de requête dans le fichier suivant : sur la partie :
foreach( $controle AS $ruche ) {
$message .= ( $plusieurs ? '<li>' : '' ).$ruche['id_ruche'].' depuis le '.$ruche['date_formatee'].( $plusieurs ? '</li>' : '' );
$messageSMS .= $ruche['id_ruche'].' depuis le '.$ruche['date_formatee'].( $plusieurs ? "\r\n" : '.' );
} //fin de foreach
à partir de $ruche['id_ruche'] il n'y a plus rien...
j'obtiens ceci :
Salut, Ici le raspberry secours.
Il y a un problème de Température intérieure pour la ruche
Je suppose que j'ai mal écrit la requête qui est une adaptation de plusieurs requête que l'on m'a fournie...
La partie // fonction de gestion de la bonne réception des données
quand elle fonctionne très bien!
// ouverture de la base de données ruches
include "/var/www/html/connexion.php"; // insertion code accès à la base
// fonction récupérant valeur associé à l'alias
function getOption( $bdd, $alias ) {
$requete = $bdd->prepare("SELECT valeur FROM options_ruches WHERE alias = ?;" );
$requete->execute( [ $alias ] );
return $requete->fetchColumn();
}
//test si activation envoie mail d'alerte
if( getOption( $bdd, "Mail") ) { // test via la fonction getOption renvoyant true si valeur est vide ou égale à 1
$OKMail = 1;
}
else { $OKMail = 0;
}
echo "Mail = ".$OKMail;
//test si activation envoie SMS
if( getOption( $bdd, "SMS" ) ) {
$OKSMS=1;
}
else { $OKSMS = 0;
}
echo "SMS = ".$OKSMS;
//test si activation surveillance de recpetion de données
if( getOption( $bdd, "Reception_donnees" ) ) {
$OKReception_donnees = 1;
}
else { $OKReception_donnees = 0;
}
echo "Reception_donnees = ".$OKReception_donnees;
//test si activation surveillance capteur Température intérieure
if( getOption( $bdd, "Capteur_T_Int" ) ) {
$OKCapteur_T_Int = 1;
}
else { $OKCapteur_T_Int = 0;
}
echo "Capteur_T_Int = ".$OKCapteur_T_Int;
if ( $OKSMS == 0 && $OKMail == 0){ echo "rien à faire";}
else {
// fonction de gestion du controle du capteur intérieur
if ($OKCapteur_T_Int == 1){
// Liste de toutes les ruches
$requete = $bdd->query('SELECT * FROM Liste_ruches');
$ruches = $requete->fetchAll();
$controle = array();
$requete1 = $bdd->query( '
SELECT
M.id_ruche,
DATE_FORMAT( M.horodatage, "%d/%m/%Y %Hh%i" ) AS date_formatee,
M.tin
FROM
Telemesures_ruches M
INNER JOIN (
-- Date mini de mesure par ruche sur les deux derniers jours
SELECT
id_ruche,
MIN( horodatage ) min_date
FROM Telemesures_ruches
WHERE horodatage >= NOW() - INTERVAL 15 MINUTE
AND tin IS NULL
GROUP BY id_ruche
) D
ON M.id_ruche = D.id_ruche
AND M.horodatage = D.min_date
ORDER BY M.id_ruche ASC;'
);
$controle = $requete1->fetchAll();
// print_r($deltas); //ok
if( count( $controle ) ) {
$plusieurs = count( $controle ) > 1;
$message = '<p>Salut,</p><p>Ici le raspberry secours.</p><p>Il y a un problème de Température intérieure pour '.( $plusieurs ? 'les ruches suivantes :</p>' : 'la ruche ' );
$messageSMS = "Salut, ici ton Raspberry secours!\r\nIl y a un problème de Température intérieure pour".( $plusieurs ? " les ruches suivantes :\r\n" : " la ruche :\r\n" );
$message .= ( $plusieurs ? '<ul>' : '' );
$message .= ( $plusieurs ? '</ul>' : '</p>' );
//on assigne le message constitué à la variable $text
$TEXT=$message;
$TEXTSMS=$messageSMS;
foreach( $controle AS $ruche ) {
$message .= ( $plusieurs ? '<li>' : '' ).$ruche['id_ruche'].' depuis le '.$ruche['date_formatee'].( $plusieurs ? '</li>' : '' );
$messageSMS .= $ruche['id_ruche'].' depuis le '.$ruche['date_formatee'].( $plusieurs ? "\r\n" : '.' );
} //fin de foreach
$message .= ( $plusieurs ? '</ul>' : '</p>' );
if ($OKSMS==1){
$commande = "sudo gammu sendsms TEXT ".$Telephone." -len 400 -text \"".$TEXTSMS."\""; //création de la ligne de commande
$send_line = shell_exec($commande); //envoi du SMS
echo $commande;
echo $send_line;
} // fin du if OKSMS
$hbody.="<body>".$TEXT."<br><br>";
// envoi du mail
if( $OKMail ==1 ){
$r=envoie_mail_secure($SMTPSERVER,$SMTPPORT,$SMTPUSER,$SMTPPASS,$SMTPAUTH,$SMTPSECURE,$DESTLIST,$FROM,$COPYLIST,$SUBJECT ,$hbody,$ATTACHEMENTLIST,$ACUSERECEPTION);
if ($r->CR!="0")
{
echo ($r->MSG);
//@unlink($infile);
}
else
{
echo ("Envoie réussi de ".$SUBJECT." à ".implode(";",$tbto)."\r\n");
}
} // fin du if OKMail
} // fin du if count
else echo "pas de problème de capteur de température Intérieure ou le mail journalier a déjà envoyé";
$hbody=""; // on réinitialise la chaine
} // fin de la fonction capteur intérieur
/***************************************************************/
// fonction de gestion de la bonne réception des données
if ($OKReception_donnees == 1){
// on execute la variable de détection
$reponse = $bdd->query(" SELECT M1.id_ruche, MAX( M1.horodatage) AS derniere_mesure
FROM Telemesures_ruches M1 INNER JOIN Liste_ruches R ON M1.id_ruche = R.id_ruche
WHERE R.date_email IS NULL OR R.date_email < NOW() - INTERVAL 1 DAY
GROUP BY M1.id_ruche HAVING MAX( M1.horodatage ) < NOW() - INTERVAL 10 MINUTE ORDER BY M1.id_ruche ");
$donnees = $reponse->fetchAll();
// si il a des résultats de la requete de détection :
if( count( $donnees ) ) {
$plusieurs = count( $donnees ) > 1;
$message = '<p>Salut,</p><p>Ici le raspberry secours.</p><p>Il y a un problème de réception de données pour '.( $plusieurs ? 'les ruches suivantes :</p>' : 'la ruche ' );
$messageSMS = "Salut, ici ton Raspberry secours!\r\nIl y a un problème de réception de données pour".( $plusieurs ? " les ruches suivantes :\r\n" : " la ruche :\r\n" );
$message .= ( $plusieurs ? '<ul>' : '' );
// préparation requete pour mémoriser dans le champ date_email la date et l'heure actuelle d'envoi de l'email
$requete = $bdd->prepare( " UPDATE Liste_ruches SET date_email = NOW() WHERE id_ruche = ?;" );
foreach( $donnees AS $ruche ) {
$message .= ( $plusieurs ? '<li>' : '' ).$ruche['id_ruche'].' depuis le '.$ruche['derniere_mesure'].( $plusieurs ? '</li>' : '' );
$messageSMS .= $ruche['id_ruche'].' depuis le '.$ruche['derniere_mesure'].( $plusieurs ? "\r\n" : '.' );
//execution requête pour mémorisation dans la table
$requete->execute([$ruche['id_ruche']]);
} //fin de foreach
$message .= ( $plusieurs ? '</ul>' : '</p>' );
//on assigne le message constitué à la variable $text
$TEXT=$message;
$TEXTSMS=$messageSMS;
$hbody.="<body>".$TEXT."<br><br>";
if ($OKSMS==1){
$commande = "sudo gammu sendsms TEXT ".$Telephone." -len 400 -text \"".$TEXTSMS."\""; //création de la ligne de commande
$send_line = shell_exec($commande); //envoi du SMS
echo $commande;
echo $send_line;
} // fin du if OKSMS
// envoi du mail
if( $OKMail ==1 ){
$r=envoie_mail_secure($SMTPSERVER,$SMTPPORT,$SMTPUSER,$SMTPPASS,$SMTPAUTH,$SMTPSECURE,$DESTLIST,$FROM,$COPYLIST,$SUBJECT ,$hbody,$ATTACHEMENTLIST,$ACUSERECEPTION);
if ($r->CR!="0")
{
echo ($r->MSG);
//@unlink($infile);
}
else
{
echo ("Envoie réussi de ".$SUBJECT." à ".implode(";",$tbto)."\r\n");
}
} // fin du if OKMail
} // fin du if count
else echo "pas de problème nouveaux sur les ruches donc pas de mail ou mail journalier déjà envoyé";
$hbody=""; // on réinitialise la chaine
} //fin de la surveillance de données
} // fin else donc Mail ou SMS
?>
Merci pour être plus précis la partie à partir de la ligne 156 fonctionne nickel
Mais j'ai vérifié avec un var_dump et dans le requêteur cela me retourne bien mes données s'il y en a sinon retour vide (logique)
Ce sont les lignes 107 et 108 (même soucis donc même origine) qui me pose soucis je n'arrive pas à récupérer le numéro de ruche qui a un problème de capteur (et surement la date aussi enfin là c'est pas sûr puisque le message s'arrête à la ruche : ).
La première chose à faire est d'activer le reporting des erreurs PHP et de rejouer le script pour voir ce qui se passe dans la boucle.
Je rajouterai aussi un var_dump( $ruche ) entre 106 et 107 pour regarder ce que contient la ligne en question. Il y a bien une colonne id_ruche dans la requête (ligne 69) ...
Je n'ai jamais eu de remontée d'alias dans le nom des index de tableau avec PHP ... d'où ma remarque du var_dump pour voir comment est construit le tableau $ruche ...
Bonsoir l'ajout d'un var_dump($ruches); entre la ligne 106 et 107 donne :
array(3) { ["id_ruche"]=> string(1) "3"
["date_formatee"]=> string(16) "25/09/2022 22h46"
["tin"]=> NULL }
array(3) { ["id_ruche"]=> string(1) "5"
["date_formatee"]=> string(16) "25/09/2022 22h45"
["tin"]=> NULL }
Ce qui me semble bon (puisque j'ai positionné à NULL les ruches 3 &5 pour ce test)
Pour ce qui est l'activation des erreurs c'est déjà fait cela ne se voit plus trop mais sur les conseils Abcabc6 j'ai externalisé les codes de connexion dans un fichier nommé connexion.php (include en ligne 3) et voici ce que contient le fichier includé:
<?php
error_reporting(E_ALL);
ini_set('display_errors', TRUE);
ini_set('display_startup_errors', TRUE);
/* Connexion à une base MySQL avec l'invocation de pilote */
$dsn = 'mysql:dbname=ruches;host=127.0.0.1';
$user = 'abeille';
$password = 'password';
try {
$bdd = new PDO($dsn, $user, $password);
// Activation des erreurs PDO
$bdd->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
// mode de fetch par défaut : FETCH_ASSOC / FETCH_OBJ / FETCH_BOTH
$bdd->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
}
catch (PDOException $e) {
echo 'Connexion échouée : ' . $e->getMessage();
}
?>
Merci
- Edité par GillesMangin-Voirin 25 septembre 2022 à 22:57:27
Bon ne voulant pas surcharger le forum je mets à la suite un autre problème de requête SQL la partie mise à jour avec replace:
// fonction de gestion de la bonne réception des données
if ($OKReception_donnees == 1){
// on execute la variable de détection
$reponse = $bdd->query(" SELECT M1.id_ruche,
MAX( M1.horodatage) AS derniere_mesure
FROM Telemesures_ruches M1
INNER JOIN Liste_ruches R
ON M1.id_ruche = R.id_ruche
LEFT JOIN alerte_ruche AR
ON R.id_ruche = AR.id_ruche
AND AR.id_type_alerte = 6
WHERE
AR.date_email IS NULL
OR AR.date_email < NOW() - INTERVAL 1 DAY
GROUP BY M1.id_ruche
HAVING MAX( M1.horodatage ) < NOW() - INTERVAL 10 MINUTE
ORDER BY M1.id_ruche");
$donnees = $reponse->fetchAll();
// si il a des résultats de la requete de détection :
if( count( $donnees ) ) {
echo "il y a des données suite à la requete de détection";
$plusieurs = count( $donnees ) > 1;
$message = '<p>Salut,</p><p>Ici le raspberry secours.</p><p>Il y a un problème de réception de données pour '.( $plusieurs ? 'les ruches suivantes :</p>' : 'la ruche ' );
$messageSMS = "Salut, ici ton Raspberry secours!\r\nIl y a un problème de réception de données pour".( $plusieurs ? " les ruches suivantes :\r\n" : " la ruche :\r\n" );
$message .= ( $plusieurs ? '<ul>' : '' );
// préparation requete pour mémoriser dans le champ date_email la date et l'heure actuelle d'envoi de l'email
// $requete = $bdd->prepare( " UPDATE Liste_ruches SET date_email = NOW() WHERE id_ruche = ?;" );
$requete = $bdd->prepare( " REPLACE alerte_ruche SET Date_email = NOW() AND ID_Type_Alerte = 4 AND ID_Ruche = ?;" );
foreach( $donnees AS $ruche ) {
$message .= ( $plusieurs ? '<li>' : '' ).$ruche['id_ruche'].' depuis le '.$ruche['derniere_mesure'].( $plusieurs ? '</li>' : '' );
$messageSMS .= $ruche['id_ruche'].' depuis le '.$ruche['derniere_mesure'].( $plusieurs ? "\r\n" : '.' );
//execution requête pour mémorisation dans la table
$requete->execute([$ruche['id_ruche']]);
} //fin de foreach
$message .= ( $plusieurs ? '</ul>' : '</p>' );
//on assigne le message constitué à la variable $text
$TEXT=$message;
$TEXTSMS=$messageSMS;
$hbody.="<body>".$TEXT."<br><br>";
if ($OKSMS==1){
$commande = "sudo gammu sendsms TEXT ".$Telephone." -len 400 -text \"".$TEXTSMS."\""; //création de la ligne de commande
$send_line = shell_exec($commande); //envoi du SMS
echo $commande."<br>";
echo $send_line."<br>";
} // fin du if OKSMS
// envoi du mail
if( $OKMail ==1 ){
$r=envoie_mail_secure($SMTPSERVER,$SMTPPORT,$SMTPUSER,$SMTPPASS,$SMTPAUTH,$SMTPSECURE,$DESTLIST,$FROM,$COPYLIST,$SUBJECT ,$hbody,$ATTACHEMENTLIST,$ACUSERECEPTION);
if ($r->CR!="0")
{
echo ($r->MSG);
//@unlink($infile);
}
else
{
echo ("Envoie réussi de ".$SUBJECT." à ".implode(";",$tbto)."\r\n");
}
} // fin du if OKMail
} // fin du if count
else echo "pas de problème nouveaux sur les ruches donc pas de mail ou mail journalier déjà envoyé<br>";
$hbody=""; // on réinitialise la chaine
} //fin de la surveillance de données
La requête me retourne ceci qui est Ok :
mais la requête de mise à jour est fausse! (replace) car je ne peux écrire dans le champ ID_Ruche (logique c'est une clé primaire étrangère de la table) mais du coup je ne vois pas comment modifier la ligne :
$requete = $bdd->prepare( " REPLACE alerte_ruche SET Date_email = NOW() AND ID_Type_Alerte = 4 AND ID_Ruche = ?;" );
actuellement j'obtiens ceci comme message d'erreur la ligne 371 etant :
$requete->execute([$ruche['id_ruche']]);
Fatal error: Uncaught PDOException: SQLSTATE[HY000]: General error: 1364 Field 'ID_Ruche' doesn't have a default value in /var/www/html/surveillance_donnees_test.php:371 Stack trace: #0 /var/www/html/surveillance_donnees_test.php(371): PDOStatement->execute(Array) #1 {main} thrown in /var/www/html/surveillance_donnees_test.php on line 371
Que dire en plus je l'avais lu dans ton lien que replace fonctionnait comme insert...
Du coup plus d'erreur et en prime cela fonctionne nickel.
Je n'en doutais pas!
Merci
Oups, oui cela fonctionne mais pas l'attente de renvois de l'email durant 24 h à chaque lancement de la requête il y a génération du mail et remise à jour de Date_email dans la table alerte-ruche...
$reponse = $bdd->query(" SELECT M1.id_ruche,
MAX( M1.horodatage) AS derniere_mesure
FROM Telemesures_ruches M1
INNER JOIN Liste_ruches R
ON M1.id_ruche = R.id_ruche
LEFT JOIN alerte_ruche AR
ON R.id_ruche = AR.id_ruche
AND AR.id_type_alerte = 6
WHERE
AR.date_email IS NULL
OR AR.date_email < NOW() - INTERVAL 1 DAY
GROUP BY M1.id_ruche
HAVING MAX( M1.horodatage ) < NOW() - INTERVAL 10 MINUTE
ORDER BY M1.id_ruche");
même si je remplace les 2 AR.date_email par AR.Date_email (qui est le nom du champ de stockage de la date dans la table alerte_ruche)
cela fonctionne aussi avec D majuscule...
Merci
- Edité par GillesMangin-Voirin 27 septembre 2022 à 18:21:58
J'ai trouvé je suis toujours aussi 'null' j'ai supprimé des choses dans les tables, et j'ai renuméroté les types d'alertes du coup le réseau est passé de 6 à 4
ce qui explique le truc j'avais bien modifié dans la requête de replace mais dans dans celle de sélection..
Petite question dans le même fichier je lance souvent des requêtes avec le même nom, cela fonctionne mais est-ce une bonne pratique ou vaut-il mieux changer à chaque fois de nom?
Merci
Je vais revenir.. je suis en train de regarder si j'arrive à modifier (avec les nouvelles tables) les requêtes que j'avais fais pour les pannes capteurs.
Que disais je?
Cette requête ne plante pas c'est déjà pas mal pour moi!
Mais elle ne retourne pas ce que je souhaitais :
à savoir les ruches dont le capteur extérieur (2) a des valeurs tex ou hyg is 'null' dans les 15 dernières minutes
elle me sort dans le requêteur un seul point en date du 31/07/22 sur la ruche 5 alors que j'ai des ruches...
Bien sur j'ai enlevé les conditions avec variables pour le test...
$reponse = $bdd->query(' SELECT M1.id_ruche,
MAX( M1.horodatage) AS derniere_mesure,
M1.tex,
M1.hyg
FROM Telemesures_ruches M1
INNER JOIN Liste_ruches R
ON M1.id_ruche = R.id_ruche
LEFT JOIN alerte_ruche AR
ON R.id_ruche = AR.id_ruche
AND AR.id_type_alerte = 2
WHERE (M1.tex IS NULL OR M1.hyg IS NULL or M1.tex >= "$TMax_Capteur_T_Ext" OR M1.tex <= "$TMin_Capteur_T_Ext")
AND (AR.Date_email IS NULL OR AR.Date_email < NOW() - INTERVAL 1 DAY )
GROUP BY M1.id_ruche
HAVING MAX( M1.horodatage ) < NOW() - INTERVAL 16 MINUTE
ORDER BY M1.id_ruche');
Merci
- Edité par GillesMangin-Voirin 27 septembre 2022 à 20:19:31
dans le même fichier je lance souvent des requêtes avec le même nom, cela fonctionne mais est-ce une bonne pratique ou vaut-il mieux changer à chaque fois de nom?
Je ne sais pas si il existe une bonne pratique sur le sujet. Personnellement j'aime bien recycler les variables qui n'ont servie que ponctuellement, ce qui est le cas pour les PDOStatement ... Cela économise de la ressource en évitant la multiplication en mémoire des objets PDOStatement.
GillesMangin-Voirin a écrit:
les ruches dont le capteur extérieur (2) a des valeurs tex ou hyg is 'null' dans les 15 dernières minutes
Vu que sur 15 minutes tu peux avoir plusieurs mesures pour une même ruche, je te propose le code suivant :
$requete = $bdd->prepare('
SELECT DISTINCT M1.id_ruche
FROM
Telemesures_ruches M1
INNER JOIN Liste_ruches R
ON M1.id_ruche = R.id_ruche
LEFT JOIN alerte_ruche AR
ON R.id_ruche = AR.id_ruche
AND AR.id_type_alerte = 2
WHERE
M1.horodatage >= NOW() - INTERVAL 15 MINUTE
AND (
M1.tex IS NULL
OR M1.tex >= ?
OR M1.tex <= ?
OR M1.hyg IS NULL
)
AND (
AR.Date_email IS NULL
OR AR.Date_email < NOW() - INTERVAL 1 DAY
)
ORDER BY M1.id_ruche;'
);
$requete->execute([
getOption( $bdd, 'TMax_Capteur_T_Ext' ),
getOption( $bdd, 'TMin_Capteur_T_Ext' )
]);
$donnees = $requete->fetchAll();
Ok merci pour l'info de "recyclage" des variables.
Super merci je dois encore faire quelques tests ce soir pour voir différents cas mais cela à l'air de bien fonctionner!
Sinon
dans la requête suivante :
$reponse = $bdd->query(" SELECT M1.id_ruche,
MAX( M1.horodatage) AS derniere_mesure
FROM Telemesures_ruches M1
INNER JOIN Liste_ruches R
ON M1.id_ruche = R.id_ruche
LEFT JOIN alerte_ruche AR
ON R.id_ruche = AR.id_ruche
AND AR.id_type_alerte = 4
WHERE
AR.Date_email IS NULL
OR AR.Date_email < NOW() - INTERVAL 1 DAY
GROUP BY M1.id_ruche
HAVING MAX( M1.horodatage ) < NOW() - INTERVAL 10 MINUTE
ORDER BY M1.id_ruche");
Peut-on remettre derniere_mesure en format français?
× Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
× Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
Activer les erreurs PDO / (julp) htmlspecialchars / FAQ PHP / Pas d'aide par MP
Activer les erreurs PDO / (julp) htmlspecialchars / FAQ PHP / Pas d'aide par MP
Activer les erreurs PDO / (julp) htmlspecialchars / FAQ PHP / Pas d'aide par MP