// ──────────────────────────────────────────────── // DEBUT CONFIGURATION AUTO // ──────────────────────────────────────────────── $parameters = parameters(); // URL complète fournie → extraction automatique du nom de la ville et du code $url = $parameters['url']; // CHANGE ICI le nombre de jours souhaité (1 à 14) $nb_jours_max = $parameters['nbJoursMax']; // à mettre sur false si on ne veut pas des infos détaillées de la journée $detailJour = $parameters['detailJour']; // ──────────────────────────────────────────────── // FIN CONFIGURATION MANUELLE // ──────────────────────────────────────────────── // récupère le nom de la ville et le code meteoblue if (preg_match('#/semaine/([^/_]+)_([^/_]+)_(\d+)#i', $url, $matches)) { $nomVille = urldecode($matches[1]); // saint-avertin $codeVille = $matches[2]; // 2981512 $scenario->setLog("URL analysée → ville : $nomVille | code : $codeVille"); } else { $scenario->setLog("ERREUR : impossible d'extraire ville et code depuis l'URL fournie"); $scenario->setLog("└── Script arrêté (format URL invalide)"); return; } $nomVilleSansAccent = iconv('UTF-8', 'ASCII//TRANSLIT//IGNORE', $nomVille); $nomVilleSansAccent = preg_replace("/[^a-zA-Z0-9 '’\-]+/", '', $nomVilleSansAccent); $scenario->setLog('nom sans accent '. $nomVilleSansAccent); // paramètres pour le plugin virtual $nomVilleAffiche = ucwords(str_replace('-', ' ', $nomVilleSansAccent)); // si tiret remplace par un espace + majuscule, par exemple: saint-avertin → Saint Avertin $nomVilleAffiche = ucwords(str_replace("'", ' ', $nomVilleAffiche)); $nomAffiche = 'météo ' . $nomVilleAffiche; // → détermine le nom du virtuel, par exemple: météo Saint Avertin // Construction du logicalId (format compatible Jeedom : minuscules, underscores) à adapter si vous avez des caractères spéciaux dans le nom de votre ville (au cas où...) $logicalId = 'meteo_' . str_replace('-', '_', strtolower($nomVilleSansAccent)); // → meteo_saint_avertin // et c'est parti if (!is_int($nb_jours_max) || $nb_jours_max < 1 || $nb_jours_max > 14) { $nb_jours_max = 7; // valeur par défaut sécurisée $scenario->setLog("ATTENTION : nb_jours_max invalide → forcé à 7"); } $scenario->setLog("┌── Début script Météo $nomVille ── ($nb_jours_max jours demandés)"); $scenario->setLog("→ URL : " . $url); $scenario->setLog("Récupération page meteoblue..."); // Récupération via cURL $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1); curl_setopt($ch, CURLOPT_TIMEOUT, 15); curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/129.0.0.0 Safari/537.36'); $html = curl_exec($ch); if ($html === false) { $error = curl_error($ch); $scenario->setLog("ERREUR cURL : " . $error); curl_close($ch); $scenario->setLog("└── Script arrêté (erreur réseau)"); return; } $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE); curl_close($ch); $scenario->setLog("Code HTTP : " . $http_code . " | Taille HTML : " . strlen($html) . " octets"); if ($http_code != 200 || strlen($html) < 5000) { $scenario->setLog("ERREUR : page invalide ou trop courte → abandon"); $scenario->setLog("└── Fin script (échec chargement page)"); return; } // Parsing DOM $scenario->setLog("Parsing HTML..."); $dom = new DOMDocument(); libxml_use_internal_errors(true); $dom->loadHTML('' . $html); libxml_clear_errors(); $xpath = new DOMXPath($dom); // Extraction jours et données $jours_nodes = $xpath->query("//time[contains(concat(' ', normalize-space(@class), ' '), ' date ')]"); $jours_data_nodes = $xpath->query("//div[contains(concat(' ', normalize-space(@class), ' '), ' tab-content ')]"); $nb_jours_dispo = $jours_nodes->length; $nb_data_dispo = $jours_data_nodes->length; $nb_jours = min($nb_jours_max, $nb_jours_dispo); $nb_data = min($nb_jours_max, $nb_data_dispo); $scenario->setLog("Jours disponibles sur meteoblue : $nb_jours_dispo"); $scenario->setLog("Jours retenus (limite demandée) : $nb_jours"); $vent = $direction = $tmax = $tmin = $pluie = $soleil = []; for ($i = 0; $i < $nb_data; $i++) { $day = $jours_data_nodes->item($i); // Vent $vent_div_n = $xpath->query(".//div[contains(concat(' ', normalize-space(@class), ' '), ' wind ')]", $day); if ($vent_div_n->length > 0) { $vent_div = $vent_div_n->item(0); $vitesse = trim(str_replace('km/h', '', $vent_div->textContent)); $span_n = $xpath->query(".//span", $vent_div); $dir_val = ($span_n->length > 0) ? end(explode(' ', trim($span_n->item(0)->getAttribute('class')))) : 'N'; } else { $vitesse = '0'; $dir_val = 'N'; } $vent[] = $vitesse; $direction[] = $dir_val; // Autres valeurs $node = $xpath->query(".//div[contains(@class,'tab-temp-max')]", $day)->item(0); $tmax[] = $node ? trim($node->textContent) : ''; $node = $xpath->query(".//div[contains(@class,'tab-temp-min')]", $day)->item(0); $tmin[] = $node ? trim($node->textContent) : ''; $node = $xpath->query(".//div[contains(@class,'tab-precip')]", $day)->item(0); $pluie[] = $node ? trim($node->textContent) : ''; $node = $xpath->query(".//div[contains(@class,'tab-sun')]", $day)->item(0); $soleil[] = $node ? trim($node->textContent) : ''; } $scenario->setLog("Données extraites pour " . count($vent) . " jours"); if (count($vent) > 0) { $scenario->setLog("Exemple jour 0 → Tmax: " . ($tmax[0] ?: '?') . " | Pluie: " . ($pluie[0] ?: '?')); } // ──────────────────────────────────────────────── // Fonctions utilitaires // ──────────────────────────────────────────────── function wind_arrow($dir_val) { $mapping = [ "n" => 0, "nne" => 22.5, "ne" => 45, "ene" => 67.5, "e" => 90, "ese" => 112.5, "se" => 135, "sse" => 157.5, "s" => 180, "sso" => 202.5, "ssw" => 202.5, "so" => 225, "sw" => 225, "oso" => 247.5, "wsw" => 247.5, "o" => 270, "w" => 270, "ono" => 292.5, "wnw" => 292.5, "no" => 315, "nw" => 315, "nno" => 337.5, "nnw" => 337.5 ]; $lower = strtolower(trim($dir_val)); $angle = ($mapping[$lower] ?? 0) + 180; $angle = $angle % 360; return "" . " " . strtoupper($dir_val) . ""; } function temp_color($temp) { preg_match_all('/\d+\.?\d*/', $temp, $m); $nums = array_map('floatval', $m[0]); $s = $nums ? max($nums) : 0; if ($s <= 0) return "#3828c7"; if ($s <= 5) return "#6FA8FF"; if ($s <= 15) return "#b3e146"; if ($s <= 20) return "#3CFF3C"; if ($s <= 28) return "#FFA500"; return "#FF4040"; } function vent_color($speed) { preg_match_all('/\d+\.?\d*/', $speed, $m); $nums = array_map('floatval', $m[0]); $s = $nums ? max($nums) : 0; if ($s < 30) return "#3CFF3C"; if ($s <= 50) return "#FFA500"; return "#FF4040"; } function format_vent($value) { preg_match_all('/\d+\.?\d*/', $value, $m); $nums = $m[0]; if (count($nums) >= 2) { return $nums[0] . " ↯" . end($nums) . ""; } return $value ?: '0'; } function pluie_bg($value) { preg_match_all('/\d+\.?\d*/', $value, $m); $nums = array_map('floatval', $m[0]); $p = $nums ? max($nums) : 0; if ($p == 0) return "#a562a5"; if ($p <= 2) return "#FFD700"; if ($p <= 5) return "#FF8C00"; return "#FF0000"; } function pluie_percent($value) { preg_match_all('/\d+\.?\d*/', $value, $m); $nums = array_map('floatval', $m[0]); $p = $nums ? max($nums) : 0; if ($p == 0) return "#a562a5"; if ($p <= 20) return "#FFD700"; if ($p <= 50) return "#FF8C00"; return "#FF0000"; } function soleil_bar($value, $max_h = 10) { preg_match_all('/\d+/', $value, $m); $h = intval($m[0][0] ?? 0); $ratio = min($h / $max_h, 1); $width = intval($ratio * 100); return "
" . "
" . "
{$h} h
"; } $COLORS = [ "Tmax" => "#FF6B5A", "Tmin" => "#6FA8FF" ]; $ICONS = [ "Vent" => "\u{1F4A8}", "Direction" => "\u{1F9ED}", "Tmax" => "\u{2B06}\u{FE0F}", "Tmin" => "\u{2B07}\u{FE0F}", "Pluie" => "\u{1F327}\u{FE0F}", "Soleil" => "\u{2600}\u{FE0F}" ]; // ──────────────────────────────────────────────── // Construction du tableau HTML // ──────────────────────────────────────────────── $table = ""; // Ligne des jours $table .= ""; $count_jours = 0; foreach ($jours_nodes as $index => $j) { if ($count_jours >= $nb_jours) { break; } $short_node = $xpath->query(".//div[contains(concat(' ', normalize-space(@class), ' '), ' tab-day-short ')]", $j)->item(0); $short_day = $short_node ? trim($short_node->textContent) : ''; $long_node = $xpath->query(".//div[contains(concat(' ', normalize-space(@class), ' '), ' tab-day-long ')]", $j)->item(0); $long_day = $long_node ? trim($long_node->textContent) : ''; $data_meteo[$index] = [ 'jour_court' => $short_day, 'jour_long' => $long_day, 'donnees' => [] ]; $table .= ""; $count_jours++; } $table .= ""; // Lignes des données $rows = [ "Vent" => $vent, "Direction" => $direction, "Tmax" => $tmax, "Tmin" => $tmin, "Pluie" => $pluie, "Soleil" => $soleil ]; $row_index = 0; foreach ($rows as $label => $values) { $bg = ($row_index % 2 == 0) ? "transparent" : "rgba(255,255,255,0.04)"; $icon = $ICONS[$label] ?? ''; $table .= ""; for ($col = 0; $col < $nb_jours; $col++) { $v = $values[$col] ?? ''; // sécurité si tableau plus court $data_meteo[$col]['donnees'][$label] = $v; $cell_bg = $bg; $text_color = "white"; $display = htmlspecialchars($v); $size = in_array($label, ["Tmax", "Tmin"]) ? "1.1em" : "1em"; if ($label == "Vent") { $display = format_vent($v); $text_color = vent_color($v); } elseif ($label == "Direction") { $display = wind_arrow($direction[$col] ?? 'N'); $text_color = vent_color($vent[$col] ?? '0'); } elseif ($label == "Pluie") { $display = preg_replace('/(mm)/', "$1", htmlspecialchars($v)); $cell_bg = pluie_bg($v); $text_color = "black"; } elseif ($label == "Soleil") { $display = soleil_bar($v); } else { $text_color = $COLORS[$label] ?? 'rgb(var(--txt-color))'; } $table .= ""; } $table .= ""; $row_index++; } $json_resultat = json_encode($data_meteo, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT); $table .= "
Jours :" . htmlspecialchars($short_day) . "
" . "" . htmlspecialchars($long_day) . "
{$icon} {$label} :" . $display . "
"; $scenario->setLog("Tableau HTML généré (" . strlen($table) . " caractères)"); // ──────────────────────────────────────────────── // 2. Tableau détaillé aujourd'hui (three-hourly-view) // ──────────────────────────────────────────────── if ($detailJour) { $today_content = "

Tableau horaire introuvable

"; $three_hourly = $xpath->query("//table[contains(@class,'picto') and contains(@class,'three-hourly-view')]"); if ($three_hourly->length > 0) { $tbl = $three_hourly->item(0); $time_cells = $xpath->query(".//tr[contains(@class,'times')]//td", $tbl); $icon_cells = $xpath->query(".//tr[contains(@class,'icons')]//img", $tbl); $temp_cells = $xpath->query(".//tr[contains(@class,'temperatures')]//td//div[contains(@class,'cell')]", $tbl); $feel_cells = $xpath->query(".//tr[contains(@class,'windchills')]//td//div[contains(@class,'cell')]", $tbl); $wind_cells = $xpath->query(".//tr[contains(@class,'windspeeds')]//td//div[contains(@class,'cell')]", $tbl); $dir_cells = $xpath->query(".//tr[contains(@class,'winddirs')]//td//div[contains(@class,'winddir')]", $tbl); $pluie_cells = $xpath->query(".//tr[contains(@class,'precipprobs')]//td//span[contains(@class,'precip-prob')]", $tbl); $pluie_mm = $xpath->query(".//tr[contains(@class,'precips')]//td//div[contains(@class,'cell')]//span", $tbl); $hourly_blocks = $xpath->query(".//div[contains(@class, 'precip-bar-flex')]", $tbl); $rainspot_cells = $xpath->query(".//tr[contains(@class,'rainspots')]//td//div[contains(@class,'rainspot')]", $tbl); $today_content = '
' . '' . '' . '' . (($parameters['detailC2'] ?? false) ? '' : '') . (($parameters['detailC3'] ?? false) ? '' : '') . (($parameters['detailC4'] ?? false) ? '' : '') . (($parameters['detailC5'] ?? false) ? '' : '') . (($parameters['detailC6'] ?? false) ? '' : '') . (($parameters['detailC7'] ?? false) ? '' : '') . (($parameters['detailC8'] ?? false) ? '' : '') . (($parameters['detailC9'] ?? false) ? '' : '') . (($parameters['detailC10'] ?? false) ? '' : '') . (($parameters['detailC11'] ?? false) ? '' : '') . ''; $slots = min(8, $time_cells->length); $data_meteo_detail = []; for ($i = 0; $i < $slots; $i++) { $heure = (int)date('G'); // 2. Calculer l'index de la tranche (0, 1, 2, 3...) pour mette flèche + couleur verte à la tranche horaire actuelle $indexTranche = floor($heure / 3); $h_prefix = ''; // pas de >> par défaut $color_prefix = ''; // pas de couleur par défaut $border_prefix = 'border-bottom:1px solid #444;'; // bordure par défaut $h_node = $xpath->query(".//time", $time_cells->item($i))->item(0); $h = $h_node ? trim($h_node->textContent) : '?'; if ($h === '0300') { $h = '0-3h'; if ($indexTranche == 0) { $h_prefix = '➡ '; } } elseif ($h === '0600') { $h = '3-6h'; if ($indexTranche == 1) { $h_prefix = '➡ '; } } elseif ($h === '0900') { $h = '6-9h'; if ($indexTranche == 2) { $h_prefix = '➡ '; } } elseif ($h === '1200') { $h = '9-12h'; if ($indexTranche == 3) { $h_prefix = '➡ '; } } elseif ($h === '1500') { $h = '12-15h'; if ($indexTranche == 4) { $h_prefix = '➡ '; } } elseif ($h === '1800') { $h = '15-18h'; if ($indexTranche == 5) { $h_prefix = '➡ '; } } elseif ($h === '2100') { $h = '18-21h'; if ($indexTranche == 6) { $h_prefix = '➡ '; } } elseif ($h === '2400') { $h = '21-24h'; if ($indexTranche == 7) { $h_prefix = '➡ '; } } if ($h_prefix) { $color_prefix = 'color:#3CFF3C;font-weight:bold;'; $border_prefix = "border: 6px solid grey; border-style: double; padding: 2px;"; } $current_block = $hourly_blocks->item($i); if ($current_block) { $details = $xpath->query(".//p[@class='precip-help']//strong", $current_block); $probability = ['0%', '0%', '0%']; $precipitation = ['0 mm', '0 mm', '0 mm']; $count = $details->length; for ($j = 0; $j < min(3, $count / 2); $j++) { $prob_node = $details->item($j * 2); $mm_node = $details->item($j * 2 + 1); if ($prob_node) { $probability[$j] = trim($prob_node->textContent); } if ($mm_node) { $precipitation[$j] = trim($mm_node->textContent); } } } $data_meteo_detail[$h] = [ 'temp' => trim($temp_cells->item($i)->textContent ?? '-'), 'ressenti' => trim($feel_cells->item($i)->textContent ?? '-'), 'vent' => trim($wind_cells->item($i)->textContent ?? '-'), 'direction' => ($dir_cells->item($i) ? trim($dir_cells->item($i)->textContent) : '-'), 'pluie_percent' => trim($pluie_cells->item($i)->textContent ?? '0%'), 'pluie_mm' => trim($pluie_mm->item($i)->textContent ?? '0 mm'), 'probability_h1' => $probability[0] ?? '0%', 'precipitation_h1' => $precipitation[0] ?? '0 mm', 'probability_h2' => $probability[1] ?? '0%', 'precipitation_h2' => $precipitation[1] ?? '0 mm', 'probability_h3' => $probability[2] ?? '0%', 'precipitation_h3' => $precipitation[2] ?? '0 mm' ]; $icon = $icon_cells->item($i) ?? null; if ($icon) { $src = htmlspecialchars($icon->getAttribute('src')); $alt = htmlspecialchars($icon->getAttribute('alt') ?? 'Icône météo'); $title = htmlspecialchars($icon->getAttribute('title') ?? $alt); // priorise title si présent, sinon alt $icon_html = ''; // optionnel : améliore le chargement } else { $icon_html = '-'; } // ─── RainSPOT ──────────────────────────────────────── $rainspot_html = '-'; if ($i < $rainspot_cells->length) { $rainspot_div = $rainspot_cells->item($i); // Récupère toutes les lignes .spot-row $rows = $xpath->query(".//div[contains(@class,'spot-row')]", $rainspot_div); if ($rows->length === 7) { // on attend exactement 7 lignes $grid = []; // tableau 7×7 pour stocker les classes rX $valid = true; for ($r = 0; $r < 7; $r++) { $row = $rows->item($r); $cells = $xpath->query(".//div[contains(@class,'spot-col-')]", $row); $col = 0; // position actuelle dans la grille 7 colonnes foreach ($cells as $cell) { $class = $cell->getAttribute('class'); preg_match('/spot-col-(\d+)/', $class, $m_width); preg_match('/r(\d+)/', $class, $m_r); $width = isset($m_width[1]) ? (int)$m_width[1] : 1; $r_val = isset($m_r[1]) ? (int)$m_r[1] : 0; // Remplit les cases fusionnées avec la même valeur for ($w = 0; $w < $width; $w++) { if ($col + $w >= 7) { $valid = false; // débordement → grille invalide break 2; } $grid[$r][$col + $w] = $r_val; } $col += $width; } // Vérifie que la ligne fait bien 7 colonnes if ($col !== 7) { $valid = false; break; } } if ($valid && count($grid) === 7 && count($grid[0]) === 7) { // Palette couleurs (tu peux personnaliser) $color_map = [ 0 => 'transparent', 9 => '#d0e8ff', // très faible / averses légères 1 => '#a0d0ff', 2 => '#6090ff', 3 => '#ff4500', // forte // Ajoute d'autres si meteoblue en utilise plus (rare) ]; $rainspot_html = '
'; for ($row = 0; $row < 7; $row++) { for ($colu = 0; $colu < 7; $colu++) { $rval = $grid[$row][$colu] ?? 0; $bg = $color_map[$rval] ?? '#444'; // Option : mettre en évidence la cellule centrale $extra = ($row === 3 && $colu === 3) ? 'border:1.5px solid #ffeb3b;' : ''; $rainspot_html .= "
"; } } $rainspot_html .= '
'; } } } $temp = trim($temp_cells->item($i)->textContent ?? '-'); $ressenti = trim($feel_cells->item($i)->textContent ?? '-'); $vent = trim($wind_cells->item($i)->textContent ?? '-'); $dir_node = $dir_cells->item($i); $dir = $dir_node ? trim($dir_node->textContent) : '-'; $pluie = trim($pluie_cells->item($i)->textContent ?? '0%'); $pluie_extract_mm = trim($pluie_mm->item($i)->textContent ?? '0 mm'); $vent_display = ($vent !== '-' && $dir !== '-') ? $vent . ' ' . wind_arrow($dir) : ($vent !== '-' ? $vent : $dir); $moyvent = '-'; if (preg_match('/(\d+)\s*-\s*(\d+)/', $vent, $matches)) { $moyVent = ($matches[1] + $matches[2]) / 2; } $vent_color = ($moyVent !== '-') ? vent_color($moyVent) : 'rgb(var(--txt-color))'; $temp_color = ($temp !== '-') ? temp_color($temp) : 'rgb(var(--txt-color))'; $temp_color_ressenti = ($ressenti !== '-') ? temp_color($ressenti) : 'rgb(var(--txt-color))'; $pluie_color = pluie_percent($pluie); $pluie_mm_color = pluie_bg($pluie_extract_mm); $pluie_h1_color = pluie_percent($data_meteo_detail[$h]['probability_h1']); $pluie_h2_color = pluie_percent($data_meteo_detail[$h]['probability_h2']); $pluie_h3_color = pluie_percent($data_meteo_detail[$h]['probability_h3']); if (($i == 0 && $parameters['detailL1']) || ($i == 1 && $parameters['detailL2']) || ($i == 2 && $parameters['detailL3']) || ($i == 3 && $parameters['detailL4']) || ($i == 4 && $parameters['detailL5']) || ($i == 5 && $parameters['detailL6']) || ($i == 6 && $parameters['detailL7']) || ($i == 7 && $parameters['detailL8']) ) { $today_content .= "" . "' . (($parameters['detailC2'] ?? false) ? '' : '') . (($parameters['detailC3'] ?? false) ? '' : '') . (($parameters['detailC4'] ?? false) ? '' : '') . (($parameters['detailC5'] ?? false) ? '' : '') . (($parameters['detailC6'] ?? false) ? '' : '') . (($parameters['detailC7'] ?? false) ? '' : '') . (($parameters['detailC8'] ?? false) ? '' : '') . (($parameters['detailC9'] ?? false) ? '' : '') . (($parameters['detailC10'] ?? false) ? '' : '') . (($parameters['detailC11'] ?? false) ? '' : '') . ''; } } $today_content .= '
HeureIcôneTempRessentiVentPluie(mm/3h)RainSPOT(% mm/h1)(% mm/h2)(% mm/h3)
" . $h_prefix . htmlspecialchars($h) . '' . $icon_html . '' . htmlspecialchars($temp) . '' . htmlspecialchars($ressenti) . '' . $vent_display . '' . htmlspecialchars($pluie) . '' . htmlspecialchars($pluie_extract_mm) . '' . $rainspot_html . '' . htmlspecialchars($probability[0] ?? '0%') . ' ' . htmlspecialchars($precipitation[0] ?? '0 mm') . '' . htmlspecialchars($probability[1] ?? '0%') . ' ' . htmlspecialchars($precipitation[1] ?? '0 mm') . '' . htmlspecialchars($probability[2] ?? '0%') . ' ' . htmlspecialchars($precipitation[2] ?? '0 mm') . '
'; $scenario->setLog("Tableau today complet reconstruit ($slots créneaux)"); } else { $scenario->setLog("Aucun tableau three-hourly-view trouvé"); } } // ──────────────────────────────────────────────── // Gestion équipement virtuel // ──────────────────────────────────────────────── function findVirtual($name) { $name = strtolower(trim($name)); foreach (eqLogic::byType('virtual') as $eq) { if (strtolower(trim($eq->getName())) === $name) { return $eq; } } return null; } // Principal $virtual = findVirtual($nomAffiche); if (!$virtual) { $virtual = new eqLogic(); $virtual->setName($nomAffiche); $virtual->setLogicalId($logicalId); $virtual->setEqType_name('virtual'); $virtual->setIsEnable(1); $virtual->setIsVisible(1); $virtual->save(); $cmd = new cmd(); $cmd->setEqLogic_id($virtual->getId()); $cmd->setLogicalId('tableau_meteo'); $cmd->setName('Tableau Météo'); $cmd->setType('info'); $cmd->setSubType('string'); $cmd->save(); $cmdJson = new cmd(); $cmdJson->setEqLogic_id($virtual->getId()); $cmdJson->setLogicalId('data_meteo_json'); $cmdJson->setName('Données Météo JSON'); $cmdJson->setType('info'); $cmdJson->setSubType('string'); $cmdJson->setIsVisible(0); $cmdJson->save(); } else { $scenario->setLog("Équipement virtuel trouvé : " . $virtual->getName()); $cmdMain = $virtual->getCmd('info', 'tableau_meteo'); $cmdJson = $virtual->getCmd('info', 'data_meteo_json'); if (!$cmdMain) { $scenario->setLog("ATTENTION : commande 'tableau_meteo' manquante → création"); $cmd = new cmd(); $cmd->setEqLogic_id($virtual->getId()); $cmd->setLogicalId('tableau_meteo'); $cmd->setName('Tableau Météo'); $cmd->setType('info'); $cmd->setSubType('string'); $cmd->save(); } if (!$cmdJson) { $scenario->setLog("ATTENTION : commande 'data_meteo_json' manquante → création"); $cmdJson = new cmd(); $cmdJson->setEqLogic_id($virtual->getId()); $cmdJson->setLogicalId('data_meteo_json'); $cmdJson->setName('Données Météo JSON'); $cmdJson->setType('info'); $cmdJson->setSubType('string'); $cmdJson->setIsVisible(0); $cmdJson->save(); } } $cmdMain = $virtual->getCmd('info', 'tableau_meteo'); if ($cmdMain) { $virtual->checkAndUpdateCmd('tableau_meteo', $table); $virtual->refreshWidget(); $scenario->setLog("Principal mis à jour"); } $cmdJson = $virtual->getCmd('info', 'data_meteo_json'); if ($cmdJson) { $virtual->checkAndUpdateCmd('data_meteo_json', $json_resultat); $scenario->setLog("JSON mis à jour"); } // Today if ($detailJour) { $nomToday = $nomAffiche . ' - détaillé'; $logicalToday = $logicalId . '_today'; $virtualToday = findVirtual($nomToday); if (!$virtualToday) { $virtualToday = new eqLogic(); $virtualToday->setName($nomToday); $virtualToday->setLogicalId($logicalToday); $virtualToday->setEqType_name('virtual'); $virtualToday->setIsEnable(1); $virtualToday->setIsVisible(1); $virtualToday->save(); $cmdT = new cmd(); $cmdT->setEqLogic_id($virtualToday->getId()); $cmdT->setLogicalId('tableau_today'); $cmdT->setName('Aujourd\'hui détaillé'); $cmdT->setType('info'); $cmdT->setSubType('string'); $cmdT->save(); $cmdJsonT = new cmd(); $cmdJsonT->setEqLogic_id($virtualToday->getId()); $cmdJsonT->setLogicalId('data_meteo_json_today'); $cmdJsonT->setName('Données Météo JSON Aujourd\'hui'); $cmdJsonT->setType('info'); $cmdJsonT->setSubType('string'); $cmdJsonT->setIsVisible(0); $cmdJsonT->save(); } else { $scenario->setLog("Équipement virtuel pour today trouvé : " . $virtualToday->getName()); $cmdT = $virtualToday->getCmd('info', 'tableau_today'); $cmdJsonT = $virtualToday->getCmd('info', 'data_meteo_json_today'); if (!$cmdT) { $scenario->setLog("ATTENTION : commande 'tableau_today' manquante → création"); $cmdT = new cmd(); $cmdT->setEqLogic_id($virtualToday->getId()); $cmdT->setLogicalId('tableau_today'); $cmdT->setName('Aujourd\'hui détaillé'); $cmdT->setType('info'); $cmdT->setSubType('string'); $cmdT->save(); } if (!$cmdJsonT) { $scenario->setLog("ATTENTION : commande 'data_meteo_json_today' manquante → création"); $cmdJsonT = new cmd(); $cmdJsonT->setEqLogic_id($virtualToday->getId()); $cmdJsonT->setLogicalId('data_meteo_json_today'); $cmdJsonT->setName('Données Météo JSON Aujourd\'hui'); $cmdJsonT->setType('info'); $cmdJsonT->setSubType('string'); $cmdJsonT->setIsVisible(0); $cmdJsonT->save(); } } $cmdToday = $virtualToday->getCmd('info', 'tableau_today'); if ($cmdToday) { $virtualToday->checkAndUpdateCmd('tableau_today', $today_content); $virtualToday->refreshWidget(); $scenario->setLog("Today mis à jour"); } $cmdJsonToday = $virtualToday->getCmd('info', 'data_meteo_json_today'); if ($cmdJsonToday) { $virtualToday->checkAndUpdateCmd('data_meteo_json_today', json_encode($data_meteo_detail, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT)); $scenario->setLog("JSON Today mis à jour"); } } $scenario->setLog("└── Fin script");