Heizkörperthermostat Heizprogramme per WebFront einstellen

Hallo,

Fehler kommt doch wieder.
" Error HMXML_setTCMode() Device is not of Type HM-CC-TC"

Meine Wandtermometer haben den Typ HM-TC-IT-WM-W-EU.

In der „HMXML.inc.php“ steht zwar Erweitert

  • HMXML_getTempProfile() erweitert um HM-TC-IT-WM-W-EU
    • HMXML_setTempProfile() erweitert um HM-TC-IT-WM-W-EU
    • HMXML_setParamInt() … neu
      aber trotzdem nimmt er die nicht?

Gruß

Oliver

Hi Oliver,

leider kann ich Dir nicht wirklich helfen. Ich habe basierend auf den Heizungs-Scripten meine eigene Implementierung umgesetzt.
Die ist kurz vor Vollendung und wird gerade von mir und @Marc getestet.

Obwohl ich nur HmIP-WTH-2, HmIP-eTRV, HmIP-eTRV und HM-CC-TV+HM-CC-VD besitze, habe ich die Abfrage für HM-TC-IT-WM-W-EU mit aufgenommen :wink: Kann sie aber selber nicht testen.

Schau Dir mal mein Post oben #542 an, wenn es das ist was Du haben möchtest dann kann ich Dir mein Script auch mal zum testen schicken.

ALLES AUF EIGENE GEFAHR!

Gruß Heiko

Die hm tc it wm w eu funktionieren völlig normal und das schon seit Jahren. Ich würde mal die Config checken.

Gesendet von iPhone XS mit Tapatalk

Hallo Heiko,

würde ich gerne testen.

Gruß

Oliver

Hi Oliver,

die Beta ist gerade raus an Marc. Schick mir doch eine PN mit ner Mailadresse - hier gehen keine Anhänge.

Wenn alles funktioniert und die Doku fertig ist poste ich es auch hier ins Forum.

Gruß Heiko

Hallo zusammen,

über Weihnachten hatte ich versucht die vorhandenen Scripte bei mir zu installieren, aber irgendwie wollte das alles nicht so wie ich und überhaupt … :wink:

Habe dann damit rumgespielt und gemerkt das es auch funktioniert mit den neuen WHT-2 und eTRV-2 Geräten und so fing das dann an …
Michael (@Nall-chan) wird sicher mit den Augen rollen, aber es ist wieder ein einzelnes Script geworden, wo die Variablen unterhalb des Scriptes liegen :banghead:

Ich habe versucht soviel wie nötig zu dokumentieren. Danke auch an @Marc der mir auf dem letzten Meter geholfen hat beim Testen und entsprechendes Feedback gegeben hat.

Trotzdem der HINWEIS - NUTZUNG AUF EIGENE GEFAHR!!


<?
################################################################################
# Scriptbezeichnung: HomeMatic.TempSchedule.ips.php
# Version: 1.1.20190222
# Author:  Heiko Wilknitz (@Pitti)
#          Basierend auf Zapp (2011) for the IPS Community
#          Erweitert von Swifty (Heizungs_Scripte v 0.1 - 15.02.2014)
#
# Auslese, Modifizieren und Speichern von Temperatur-Wochenplan
# von HomeMatic(IP)-Themostaten.
#
# !!! KEINE ÜBERNAHME VON GARANTIEN - NUTZUNG AUF EIGENE GEFAHR !!!
#
# ------------------------------ Installation ----------------------------------
#
# Dieses Skript richtet automatisch alle nötigen Objekte bei manueller
# Ausführung ein. Eine weitere manuelle Ausführung setzt alle benötigten Objekte
# wieder auf den Ausgangszustand.
#
# - Neues Skript erstellen
# - Diesen PHP-Code hineinkopieren
# - Abschnitt 'Konfiguration' den eigenen Gegebenheiten anpassen 
# - Skript Abspeichern
# - Skript Ausführen
# - Visualisierung per Link auf entstandene Variablen erstellen
#
# ------------------------------ Visualisierung --------------------------------
#
# Kann natürlich jeder machen wie er möchte, hier ein schematischer Vorschlag
# wie man vorgehen könnte:
#
# Zweischpaltiges Splitpane Layout (Vertikal 50:50)
# 
#   LINKE SEITE                             RECHTE SEITE
# 1. Link auf "Zimmer"                   Dummy Modul "Profil editieren"
# 2. Link auf "Wochenprogramm"            1. Link auf "Tag"
# 3. Link auf "Profil"                    2. Link auf "Zeitabschnitt"
# 4. Link auf "Wochenprofil"              3. Link auf "Zeit"
# 5. Link auf "Tagesprofil"               4. Link auf "Temperatur"
#                                         5. Link auf "Abschnitt"
#                                        Dummy Modul "Tagesprofil kopieren"
#                                         1. Link auf "Tagesauswahl"
#                                         2.Link auf "Kopieren"
#                                        Dummy Modul "Wochenprofil übertragen"
#                                         1. Link auf "Zimmerauswahl"
#                                         2. Link auf "Programmauswahl"
#                                         1. Link auf "Übertragen"
#
# ------------------------------ Changelog -------------------------------------
#
# 02.01.2019 - Initalversion (v1.0)
# 22.02.2019 - Bugfixes, mehr Doku(Hinweise) und Speichern ermöglicht (v1.1)
#
# ------------------------------ Konfiguration ---------------------------------
#
# RPC clients
$client = array();
#
# Service IP (CCUx)
$ip = 'xxx.xxx.xxx.xxx';
#
# Nach dem Übertragen eines Profils an die Geräte wird eine Meldung ausgegeben.
# Soll dafür WFC_SendNotification verwendet werden dann bitte die notwendige
# WebFront-ID hinterlegen, ansonsten erfolgt eine nicht ganz so schöne
# Echo-Ausgabe, welche leider die Überschrift "Fehler" hat :(
$wfc = 0;
#
# BidCos Service Port (true = vorhanden & aktiv) 
$service = array(
	array('ID' => 0, 'TYPE' =>'RF', 'PORT' =>2001, 'ACTIVE' => true), 	// HM
	array('ID' => 1, 'TYPE' =>'IP', 'PORT' =>2010, 'ACTIVE' => true),		// HM IP
	array('ID' => 2, 'TYPE' =>'WD', 'PORT' =>2000, 'ACTIVE' => false) 	// Wired
);
#
# Räume (siehe nachfolgende Elementbelegung) 
#  (0) Logische Id (einfach von 0 durchnummerieren, oder eigene Logik verwenden)
#  (1) Name des Raumes
#  (2) Icon (sollte leer bleiben)
#  (3) Farbe (RGB-Wert, default -1)
#  (4) Wandthermostat-ID (oder auch direkt ein Heizkörperthermostat möglich)
#  (5) 1.Heizkörperthermostat-ID [mit Wandtherostat gekoppelt] - optional
#  (6) 2.Heizkörperthermostat-ID [mit Wandtherostat gekoppelt] - optional
#  (+) x.Heizkörperthermostat-ID [mit Wandtherostat gekoppelt] - optional
#
# HINWEIS IDs:
#  HmIP-WTH-2       - Kanal:1 - HEATING_CLIMATECONTROL_TRANSCEIVER
#  HmIP-eTRV        - Kanal:1 - HEATING_CLIMATECONTROL_TRANSCEIVER
#  HmIP-eTRV-2      - Kanal:1 - HEATING_CLIMATECONTROL_TRANSCEIVER
#  HM-CC-TC         - Kanal:2 - CLIMATECONTROL_REGULATOR
#  HM-TC-IT-WM-W-EU - Kanal 2 - THERMALCONTROL_TRANSMIT (ungetestet!!!)
#
$room = array (  
	array(12, '1 - KG: Hoppyraum', '', -1, 50660 /*[Systeme\Homematic\Thermostat\000A98A9A4E0C6 (HmIP-WTH-2)\000A98A9A4E0C6:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 26857 /*[Systeme\Homematic\Stellantrieb\000A18A994402D (HmIP-eTRV-2)\000A18A994402D:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(21, '2 - EG: Küche', '', -1, 21113 /*[Systeme\Homematic\Thermostat\000A98A9A4E0BE (HmIP-WTH-2)\000A98A9A4E0BE:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 23635 /*[Systeme\Homematic\Stellantrieb\000A18A9943FD9 (HmIP-eTRV-2)\000A18A9943FD9:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 11542 /*[Systeme\Homematic\Stellantrieb\000A18A994405C (HmIP-eTRV-2)\000A18A994405C:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(22, '2 - EG: Wohnen', '', -1, 23498 /*[Systeme\Homematic\Thermostat\000A98A9A4E10D (HmIP-WTH-2)\000A98A9A4E10D:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 58916 /*[Systeme\Homematic\Stellantrieb\000A18A9944035 (HmIP-eTRV-2)\000A18A9944035:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(31, '3 - OG: Bad', '', -1, 56832 /*[Systeme\Homematic\Thermostat\000A98A9A4E0F5 (HmIP-WTH-2)\000A98A9A4E0F5:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 33650 /*[Systeme\Homematic\Stellantrieb\000A18A9944068 (HmIP-eTRV-2)\000A18A9944068:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(32, '3 - OG: Luise', '', -1, 20199 /*[Systeme\Homematic\Thermostat\000A98A9A4E110 (HmIP-WTH-2)\000A98A9A4E110:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 11234 /*[Systeme\Homematic\Stellantrieb\000A18A9944066 (HmIP-eTRV-2)\000A18A9944066:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(33, '3 - OG: Pia', '', -1, 55797 /*[Systeme\Homematic\Thermostat\000A98A9A4E096 (HmIP-WTH-2)\000A98A9A4E096:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 56530 /*[Systeme\Homematic\Stellantrieb\000A18A9943FDB (HmIP-eTRV-2)\000A18A9943FDB:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(34, '3 - OG: Schlafen', '', -1, 30734 /*[Systeme\Homematic\Thermostat\000A98A9A4E0F7 (HmIP-WTH-2)\000A98A9A4E0F7:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 43879 /*[Systeme\Homematic\Stellantrieb\000393C98D1395 (HmIP-eTRV)\000393C98D1395:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 52032 /*[Systeme\Homematic\Stellantrieb\000393C98D1380 (HmIP-eTRV)\000393C98D1380:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(41, '4 - DG: Studio', '', -1, 20652 /*[Systeme\Homematic\Thermostat\000A9709A0D78D (HmIP-WTH-2)\000A9709A0D78D:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/, 52057 /*[Systeme\Homematic\Stellantrieb\000393C98D1313 (HmIP-eTRV)\000393C98D1313:1 - HEATING_CLIMATECONTROL_TRANSCEIVER]*/),
	array(42, '4 - DG: Bad', '', -1, 40693 /*[Systeme\Homematic\Thermostat\JEQ0194704 (HM-CC-TC)\JEQ0194704:2 - CLIMATECONTROL_REGULATOR]*/)
);
#
$program = array (
	array(1, 'Arbeitswoche', '', 255),	// oder Normal
	array(2, 'Zuhause', '', 255),			// oder Frei
	array(3, 'Aus', '', 255)				// oder Abwesend
);
# Auslesen/Speichern Profil
$readwrite = array(
	array(0, 'Auslesen', '', 32768),
	array(1, 'Speichern', '', 16711680)
);
# Kopieren Profil 
$copy = array(
	array(0, ">", "", -1),
	array(1, "Kopieren", "", 0x008000),
);
# Übertragen Profil 
$move = array(
	array(0, ">", "", -1),
	array(1, "Übertragen", "", 0x008000),
);
#
$day = array(
	array(0, 'Mo', '', -1),
	array(1, 'Di', '', -1),
	array(2, 'Mi', '', -1),
	array(3, 'Do', '', -1),
	array(4, 'Fr', '', -1),
	array(5, 'Sa', '', -1),
	array(6, 'So', '', -1)
);
#
$time = array(
	array(1, '-1 h', '', 65280),
	array(2, '-10 min', '', 65280),
	array(3, '+10 min', '', 16744448),
	array(4, '+1 h', '', 16744448)
);
#
$temperature = array(
	array(1, '-1 °C', '', 3368703),
	array(2, '-0,5 °C', '', 3368703),
	array(3, '+0,5 °C', '', 16711680),
	array(4, '+1 °C', '', 16711680)
);
#
$slot = array(
	array(1, 'Löschen', '', 16764057),
	array(2, 'Anfügen', '', 13434828)
);
#
$weekday = array("MONDAY","TUESDAY","WEDNESDAY","THURSDAY","FRIDAY","SATURDAY","SUNDAY");
#
################################################################################
# HINWEIS: Ich arbeite mit einer alten Version der Xml-RPC API Datei,
#          welche ich extra patchen musste damit alles funktioniert.
#          Wer das nicht möchte kann auch die Version 4.3.0 installieren!
#          DANN die nachfolgende Zeile durch ...
#          require "phpxmlrpc-4.3.0/lib/xmlrpc.inc"; oder so ersetzen!!!
require "__xmlrpc.inc.php" ;
################################################################################

//Init XMLRPC clients
Init();
// wichtig, da sonst am Tag der Zeitumstellung WZ/SZ Konflikte auftreten.
date_default_timezone_set('UTC'); 

// INSTALLATION
if ($_IPS['SENDER']=='Execute') {
	$pos = 0;
	// Zimmer
	$vpn = "HM.Heating.Room";
	$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
	CreateProfileInteger($vpn, 'HouseRemote', '', '', 0, 0, 0, 0, $room);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Wochenprogramm
	$vpn = "HM.Heating.Program";
	$vid = CreateVariableByName($_IPS['SELF'], "Wochenprogramm", 1);
	CreateProfileInteger($vpn, 'Temperature', '', '', 0, 0, 0, 0, $program);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 1);
	// Auslese/Speichern Button
	$vpn = "HM.Heating.ReadWrite";
	$vid = CreateVariableByName($_IPS['SELF'], "Profil", 1);
	CreateProfileInteger($vpn, 'Script', '', '', 0, 0, 0, 0, $readwrite);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);
	// Wochen(Temperatur)profil
	$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprofil', 3);
	IPS_SetIcon($vid, "Calendar");
	IPS_SetVariableCustomProfile($vid, '~HTMLBox');
	IPS_SetPosition($vid, $pos++);
	// Tages(Temperatur)profil
	$vid = CreateVariableByName($_IPS['SELF'], 'Tagesprofil', 3);
	IPS_SetIcon($vid, "Clock");
	IPS_SetVariableCustomProfile($vid, '~HTMLBox');
	IPS_SetPosition($vid, $pos++);
	// Tagesauswahl
	$vpn = "HM.Heating.Day";
	$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
	CreateProfileInteger($vpn, 'Calendar', '', '', 0, 0, 0, 0, $day);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Zeitabschnitt auswählen
	$vpn = "HM.Heating.Slot";
	$vid = CreateVariableByName($_IPS['SELF'], "Zeitabschnitt", 1);
	CreateProfileInteger($vpn, 'Database', '', '. Zeitabschnitt', 1, 3, 1, 0);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Zeit editieren
	$vpn = "HM.Heating.Time";
	$vid = CreateVariableByName($_IPS['SELF'], "Zeit", 1);
	CreateProfileInteger($vpn, 'Clock', '', '', 0, 0, 0, 0, $time);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Temperatur editieren
	$vpn = "HM.Heating.Temperature";
	$vid = CreateVariableByName($_IPS['SELF'], "Temperatur", 1);
	CreateProfileInteger($vpn, 'Temperature', '', '', 0, 0, 0, 0, $temperature);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Abschnitt editieren
	$vpn = "HM.Heating.Edit";
	$vid = CreateVariableByName($_IPS['SELF'], "Abschnitt", 1);
	CreateProfileInteger($vpn, 'Edit', '', '', 0, 0, 0, 0, $slot);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Tagesauswahl kopieren
	$vpn = "HM.Heating.Day";
	$vid = CreateVariableByName($_IPS['SELF'], "Tagesauswahl", 1);
	CreateProfileInteger($vpn, 'Calendar', '', '', 0, 0, 0, 0, $day);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Kopieren
	$vpn = "HM.Heating.Copy";
	$vid = CreateVariableByName($_IPS['SELF'], "Kopieren", 1);
	CreateProfileInteger($vpn, 'Script', '', '', 0, 0, 0, 0, $copy);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);
	// Zimmerauswahl
	$vpn = "HM.Heating.Room";
	$vid = CreateVariableByName($_IPS['SELF'], "Zimmerauswahl", 1);
	CreateProfileInteger($vpn, 'HouseRemote', '', '', 0, 0, 0, 0, $room);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	// Programmauswahl
	$vpn = "HM.Heating.Program";
	$vid = CreateVariableByName($_IPS['SELF'], "Programmauswahl", 1);
	CreateProfileInteger($vpn, 'Temperature', '', '', 0, 0, 0, 0, $program);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 1);
	// Übertragen
	$vpn = "HM.Heating.Move";
	$vid = CreateVariableByName($_IPS['SELF'], "Übertragen", 1);
	CreateProfileInteger($vpn, 'Script', '', '', 0, 0, 0, 0, $move);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);
	// Profile Cache
	$vid = CreateVariableByName($_IPS['SELF'], "Profiles", 3);
	IPS_SetHidden($vid, true);
	IPS_SetPosition($vid, -1);
	// Types Cache
	$vid = CreateVariableByName($_IPS['SELF'], "Types", 3);
	IPS_SetHidden($vid, true);
	IPS_SetPosition($vid, -1);
}
// AKTION VIA WEBFRONT
else if($_IPS['SENDER'] == "WebFront") {
	// Aktion
	$name = IPS_GetName($_IPS['VARIABLE']);
	// ZIMMER -------------------------------------------------------------------
	if($name == 'Zimmer') {
		// Welcher Raum?
		$rn = $_IPS['VALUE'];
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Rendern
		RenderProfile($rn, $wp, $wd);
	}
	// WOCHENPROGRANN -----------------------------------------------------------
	if($name == 'Wochenprogramm') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn = GetValue($vid);
		// Welches Wochenprogramm?
		$wp = $_IPS['VALUE'];	
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Rendern
		RenderProfile($rn, $wp, $wd);
	}
	// AUSLESEN/SPEICHERN -------------------------------------------------------
	if( $name == 'Profil') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn  = GetValue($vid);	
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// AUSLESEN
		if($_IPS['VALUE'] == 0) {
			// Temperatur Profil vom Gerät auslesen
			foreach($room as $value) {
				if($value[0] == $rn) {
					$profile = ReadTempProfile($value[4], false);
					SetWeeklyProfile($rn, $profile);
					break;
				}
			}
			// Rendern
			RenderProfile($rn, $wp, $wd);
		}
		// SPEICHERN
		if($_IPS['VALUE'] ==1) {
			// Wochenprofil ermitteln
			$profile = GetWeeklyProfile($rn, $wp);
		   // Teste Integrität der Tagesprofile
			$check = CheckWeeklyProfile($profile);
		   if($check == "OK") {
				foreach($room as $value) {
					if($value[0] == $rn) {
						// Profil zum Gerät übertragen
						$count = count($value);
						for($d = 4; $d < $count; $d++) {
							//echo $value[$d].PHP_EOL;
							$check = WriteTempProfile($value[$d], $profile, $wp);
							// IPS_Sleep(2000); 
						}
					}
				}
				if ($check == true) {
				   $check ="Speichern Erfolgreich";
				}
			}
			// Erolgsmeldung?!
			if($wfc != 0) {
				WFC_SendNotification($wfc, 'HM Heizungsplan', $check, 'Information', 5);
			}
			else {
				echo $check;
			}
		}
		$_IPS['VALUE'] = 0;
	}
	// TAG ----------------------------------------------------------------------
	if( $name == 'Tag') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn  = GetValue($vid);	
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$wd  = $_IPS['VALUE'];
		// Rendern
		RenderProfile($rn, $wp, $wd);
	}
	// ZEITABSCHNITT ------------------------------------------------------------
	if( $name == 'Zeitabschnitt') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn  = GetValue($vid);	
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Profil extrahieren
		$profile = GetWeeklyProfile($rn, $wp);
		$profile = GetDailyProfile($profile, $wd);
		// Welcher Zeitabschnitt? 
		$ts = $_IPS['VALUE'];
		// Render Tagesprofil
		$vid = CreateVariableByName($_IPS['SELF'], 'Tagesprofil', 3);
		SetValue($vid, RenderDailyProfile($profile, $ts));		
	}
	// ZEIT EDITIEREN -----------------------------------------------------------
	if($name == 'Zeit') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn = GetValue($vid);
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Welcher Zeitabschnitt? 
		$vid = CreateVariableByName($_IPS['SELF'], "Zeitabschnitt", 1);
		$ts = GetValue($vid);
		// Wochenprofil ermitteln
		$profile = GetWeeklyProfile($rn, $wp);
		// Tagesprofil ermitteln
		$profile = GetDailyProfile($profile, $wd);
		// Aktion nur für die ersten Zeitabschnitte
		if($ts < count($profile['EndTimes'])) {
			// Verhindert dass die Zeit des letzten Slots geändert wird (immer 24:00)
			if($ts == 1) {
				$start = "00:00";
			}
			else {
				$start = $profile['EndTimes'][$ts-2];
			}
			$end  = $profile['EndTimes'][$ts-1];
			$next = $profile['EndTimes'][$ts];
			// Welche Aktion?		
			switch($_IPS['VALUE']) {
				case 1: // -1h
					if((strtotime($end)-(60*60))> strtotime($start)) {
					   $end = date("H:i", (strtotime($end)-(60*60)));
					}
					$profile['EndTimes'][$ts-1] = $end;
					break;
				case 2: // -10min
					if((strtotime($end)-(10*60))> strtotime($start)) {
						$end = date("H:i", (strtotime($end)-(10*60)));
					}
					$profile['EndTimes'][$ts-1] = $end;
					break;
				case 3: // +10min
					if((strtotime($end)+(10*60))< strtotime($next)) {
						$end = date("H:i", (strtotime($end)+(10*60)));
					}
					$profile['EndTimes'][$ts-1] = $end;
					break;
				case 4: // +1h
					if((strtotime($end)+(60*60))< strtotime($next)) {
					   $end = date("H:i", (strtotime($end)+(60*60)));
					}
					$profile['EndTimes'][$ts-1] = $end;
					break;
			}
			// Schreiben
			SetDailyProfile($rn, $wp, $wd, $profile);
			// Rendern
			RenderProfile($rn, $wp, $wd, $ts);
		}
		// Keine Auswahl
		$_IPS['VALUE'] = 0;		 	   
	}
	// TEMPERATUR EDITIEREN -----------------------------------------------------
	if($name == 'Temperatur') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn = GetValue($vid);
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Welcher Zeitabschnitt? 
		$vid = CreateVariableByName($_IPS['SELF'], "Zeitabschnitt", 1);
		$ts = GetValue($vid);
		// Wochenprofil ermitteln
		$profile = GetWeeklyProfile($rn, $wp);
		// Tagesprofil ermitteln
		$profile = GetDailyProfile($profile, $wd);
		// Welche Temperatur?
		$temperatur = $profile['Values'][$ts-1];
		// Welche Aktion?		
		switch($_IPS['VALUE']) {
		   case 1: // -1°C
				if(($temperatur-1) >= 4.99) {
					$temperatur = $temperatur-1;
					$profile['Values'][$ts-1] = $temperatur;
				}
				break;
			case 2: // -0.5°C
				if(($temperatur-0.5) > 4.9) {
					$temperatur = $temperatur-0.5;
					$profile['Values'][$ts-1] = $temperatur;
				}
				break;
			case 3: // +0.5°C
				if(($temperatur+0.5) < 30.1) {
					$temperatur = $temperatur+0.5;
					$profile['Values'][$ts-1] = $temperatur;
				}
				break;
			case 4: // +1°C
				if(($temperatur+1) <= 30.01) {
					$temperatur = $temperatur+1;
					$profile['Values'][$ts-1] = $temperatur;
				}
				break;
		}
		// Schreiben
		SetDailyProfile($rn, $wp, $wd, $profile);
		// Rendern
		RenderProfile($rn, $wp, $wd, $ts);
		// Keine Auswahl
		$_IPS['VALUE'] = 0;
	}
	// ABSCHNITT EDITIEREN ------------------------------------------------------
	if( $name == 'Abschnitt') {
		// Welches Zimmer?
		$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
		$rn = GetValue($vid);
		// Welches Wochenprogramm?
		$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
		$wp  = GetValue($vid);
		// Welcher Tag?
		$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
		$wd = GetValue($vid);
		// Welcher Zeitabschnitt? 
		$vid = CreateVariableByName($_IPS['SELF'], "Zeitabschnitt", 1);
		$ts = GetValue($vid);
		// Wochenprofil ermitteln
		$profile = GetWeeklyProfile($rn, $wp);
		// Tagesprofil ermitteln
		$profile = GetDailyProfile($profile, $wd);
		// Wieviel Zeitabschnitte?
		$count = count($profile['EndTimes']);
		// Welche Aktion?		
		switch($_IPS['VALUE']) {
			case 1: // Löschen
				// letzter TimeSlot darf nicht gelöscht werden
				if ($count >1) {
					array_splice($profile['EndTimes'], $ts-1, 1);
					array_splice($profile['Values'], $ts-1, 1);
					// letzten TimeSlot Ende immer 24:00
					$profile['EndTimes'][$count-2]="24:00";
				}
				break;
			case 2: // Anfügen
				// max 13 TimeSlots zulässig (manche können auch 24, aber das sollte reichen)
				If ($count <13)  
				{
					array_splice($profile['EndTimes'], $count, 0, "24:00");
					array_splice($profile['Values'], $count, 0, "17");
					// minimaler TimeSlot ist 10 min
					$profile['EndTimes'][$count-1]="23:50";
				}
				break;
		}
		// Wurde was geändert?
		if($count <> count($profile['EndTimes'])) {
			SetDailyProfile($rn, $wp, $wd, $profile);
			// Rendern
			RenderProfile($rn, $wp, $wd);
		}
		// Keine Auswahl
		$_IPS['VALUE'] = 0;
	}
	// TAGESPROFIL KOPIEREN -----------------------------------------------------
	if( $name == 'Kopieren') {
		if($_IPS['VALUE'] ==1) {
			// Welchem Zimmer?
			$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
			$rn = GetValue($vid);
			// Welches Wochenprogramm?
			$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
			$wp  = GetValue($vid);
			// Von welcher Tag?
			$vid = CreateVariableByName($_IPS['SELF'], "Tag", 1);
			$wd = GetValue($vid);
			// Nach Welchen Tag? 
			$vid = CreateVariableByName($_IPS['SELF'], "Tagesauswahl", 1);
			$ta = GetValue($vid);
			if($wd == $ta) {
				echo ('Bitte anderen Tag auswählen!');
			}
			else {
				// Wochenprofil ermitteln
				$profile = GetWeeklyProfile($rn, $wp);
				// Tagesprofil von 
				$profile = GetDailyProfile($profile, $wd);
				// kopieren nach
				SetDailyProfile($rn, $wp, $ta, $profile);
				// Rendern
				RenderProfile($rn, $wp, $wd);
			}
		}
		$_IPS['VALUE'] = 0;
	}
	// WOCHENPROFIL ÜBERTRAGEN --------------------------------------------------
	if( $name == 'Übertragen') {
		if($_IPS['VALUE'] ==1) {
			// Welchem Zimmer?
			$vid = CreateVariableByName($_IPS['SELF'], "Zimmer", 1);
			$rn = GetValue($vid);
			// Welches Wochenprogramm?
			$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprogramm', 1);
			$wp  = GetValue($vid);
			// Nach welchen Zimmer?
			$vid = CreateVariableByName($_IPS['SELF'], "Zimmerauswahl", 1);
			$za = GetValue($vid);
			// Nach welchen Program? 
			$vid = CreateVariableByName($_IPS['SELF'], "Programmauswahl", 1);
			$pa = GetValue($vid);
			if(($rn == $za) and ($wp == $pa)) {
				echo ('Auf sich selber zu übertragen macht keinen Sinn!');
			}	
			else {
				// Wochenprofil holen
				$profile = GetWeeklyProfile($rn, $wp);
				// Übertragen
				SetWeeklyProfile($za, $profile, $pa);
			}
		}
		$_IPS['VALUE'] = 0;
	}
	// DATENÜBERNAHME ------------------------------------------------------
	SetValue($_IPS['VARIABLE'], $_IPS['VALUE']);
}

# ------------------------------ Funktionen ------------------------------------

// Erzeugt pro aktiven Interface ein Client.
function Init() {
global $ip, $service, $client;
	# Return Code 
	$ret = true;
	# Check all Services
	foreach($service as $s) {
		if($s['ACTIVE'] == true) {
			if (!isset($client[$s['TYPE']]) || $client[$s['TYPE']] !== false) {
				$client[$s['TYPE']] = new xmlrpc_client("http://".$ip.":".$s['PORT']);
		   	if ($client[$s['TYPE']] !== false) {
					$ret &= true;
				}
				else {
					$ret = false;
				}
			}
		}
	}
	// client existieren schon
	return false;
}

// Liefert alle Geräte der aktierten Interfaces 
function DevicesList() 
{
global $service, $client;
	//	listDevices
	$request = new xmlrpcmsg('listDevices');
	// merge all together
	$devices = array();
	foreach($service as $s) {
		if($s['ACTIVE'] == true) {
			$ret = Send($request, $s['TYPE']);
			foreach($ret as $device) {
				$device['INTERFACE'] = $s['ID'];
				$devices[] = $device;
			}
			//$devices = array_merge($devices, Send($request, $s['TYPE']));
		}
	}
	return $devices;
}

// Ermittelt den Typ des HM Gerätes (HM terminology)
function DeviceType($device) {
	// Cache auslesen
	$cid = CreateVariableByName($_IPS['SELF'], "Types", 3);
	$types = unserialize(GetValue($cid));
	// HM Adresse vom Device
	$address = explode(":", IPS_GetProperty($device, 'Address'));
	$serial  = $address[0];
	$channel = $address[1];
	// schon mal gelesen
	if(!is_array($types) || array_key_exists($serial, $types) == false) {
		$type = false;
		$list = DevicesList();
		foreach($list as $dev) {
			if (strpos($dev['ADDRESS'], $serial) !== false) {
				$type = $dev['TYPE'].':'.$dev['INTERFACE'];
				$types[$serial] = $type;
				SetValue($cid, serialize($types));
				break;  // We stop at the first one we find
			}
		}
	}
	else
	{
		$type=$types[$serial];
	}
	return $type;
}

// Liest das Temperaturprofil von einem Thermostat für den übergebenen Tag.
// $device: IPS Instance ID
// $day: Name des Tages in English (not case-sensitive) oder false für alle Tage
// $weekprofil: nur für HM-TC-IT-WM-W-EU & HmIP-WTH-2; 
//   gültige Werte 1,2,3; bei -1 werden alle Profile (1-3) zurückgegeben
function ReadTempProfile($device, $day = false, $weekprofil =-1) {
global $service, $weekday;
	// HM Adresse vom Device
	$address = explode(":", IPS_GetProperty($device, 'Address'));
	$serial  = $address[0];
	$channel = $address[1];

	$days = $weekday;
	$temp = array();

	if ($day != false) {
		if(!in_array($day, $weekday)) die("Error: Unknown Day parameter in function ReadTempProfile!");
		$days = array($day);
	}
	// Was für ein HM Gerätetyp & Interface
	$dt 	= explode(":", DeviceType($device));
	$type = $dt[0];
	$if	= $dt[1];
	// Konvert Interface
	foreach($service as $s) {
		if($s['ID'] == $if) {
			$if = $s['TYPE'];
			break;
		}
	}	
	// HM-CC-TC Profil auslesen (hat nur eins)
	if($type == "HM-CC-TC") {
		$params = ReadParamSet($if, $serial, $channel);
		foreach($days as $day) {
			$thisEndTimes 	= array();
			$thisValues		= array();
			$timePrevious 	= "00:00";
			for($index 	= 1; $index <= 24; $index++) {
				$keyTemp 	= "TEMPERATUR_".strtoupper($day)."_".$index;
				$keyTO 		= "TIMEOUT_".strtoupper($day)."_".$index;
				$thisTemp 	= $params[$keyTemp];
				$thisTO 		= $params[$keyTO];
				$thisTime 	= date('H:i', mktime(0, $thisTO)); // $timePassed + TO
				if($thisTO >= 1440) $thisTime = "24:00";
				$timePrevious = $thisTime;
				array_push($thisEndTimes,	$thisTime);
				array_push($thisValues,		$thisTemp);
				if($thisTO >= 1440) break;
			}
			$temp["P1"][$day]['EndTimes'] = $thisEndTimes;
			$temp["P1"][$day]['Values'] 	= $thisValues;
		}
		return $temp;
	}
	// HM-CC-RT-DN Profil auslesen (hat nur eins)	
	if($type == "HM-CC-RT-DN") {
		$params = ReadParamSet($if, $serial, $channel);
		foreach($days as $day) {
			$thisEndTimes 	= array();
			$thisValues		= array();
			$timePrevious  = "00:00";
			for($index = 1; $index <= 13; $index++) {
				$keyTemp 	= "TEMPERATURE_".strtoupper($day)."_".$index;
				$keyTO 		= "ENDTIME_".strtoupper($day)."_".$index;
				$thisTemp 	= $params[$keyTemp];
				$thisTO 		= $params[$keyTO];
				$thisTime = date('H:i', mktime(0, $thisTO)); // $timePassed + TO
				if($thisTO >= 1440) $thisTime = "24:00";
				$timePrevious = $thisTime;
				array_push($thisEndTimes,  $thisTime);
				array_push($thisValues,		$thisTemp);
				if($thisTO >= 1440) break;
			}
			$temp["P1"][$day]['EndTimes'] = $thisEndTimes;
			$temp["P1"][$day]['Values'] 	= $thisValues;
		}
		return $temp;
	}	
	// HM-TC-IT-WM-W-EU Profil auslesen (1-3)	
	if($type == "HM-TC-IT-WM-W-EU") {
		$params = ReadParamSet($if, $serial, $channel);
		// 3 Profile
		for ($p=1; $p<=3; $p++) {
			foreach($days as $day) {
				$thisEndTimes 	= array();
				$thisValues		= array();
				$timePrevious 	= "00:00";
				for($index 	= 1; $index <= 13; $index++) {
					$keyTemp 	= "P". $p ."_TEMPERATURE_".strtoupper($day)."_".$index;
					$keyTO 		= "P". $p ."_ENDTIME_".strtoupper($day)."_".$index;
					//* notwendig da Firmeware beim LAN-Adapter abweicht und beim Profil 1 dort das Präfix "P1_" fehlt.
					if(array_key_exists($keyTemp, $params)) {
						$thisTemp 	= $params[$keyTemp];
						$thisTO 		= $params[$keyTO];
					}
					else {
						$keyTemp 	= "TEMPERATURE_".strtoupper($day)."_".$index;
						$keyTO 		= "ENDTIME_".strtoupper($day)."_".$index;
						$thisTemp 	= $params[$keyTemp];
						$thisTO 		= $params[$keyTO];
					}
					$thisTime = date('H:i', mktime(0, $thisTO)); // $timePassed + TO
					if ($thisTO >= 1440) $thisTime = "24:00";
					$timePrevious = $thisTime;
					array_push($thisEndTimes,	$thisTime);
					array_push($thisValues,		$thisTemp);
					if($thisTO >= 1440) break;
				}
				$temp["P".$p][$day]['EndTimes'] 	= $thisEndTimes;
				$temp["P".$p][$day]['Values'] 	= $thisValues;
			}
		}
		if($weekprofil > 0 and $weekprofil <= 3) {
			return $temp["P".$weekprofil];
		}
		else {
			return $temp;
		}
	}
	// HmIP-WTH-2 || 	HMIP-eTRV || HmIP-eTRV-2 Profil auslesen (1-3 von 6)	
	if($type == "HmIP-WTH-2" or $type =="HmIP-eTRV-2" or $type == "HMIP-eTRV") {
		$params = ReadParamSet($if, $serial, $channel);
		// 3 Profile
		for ($p=1; $p<=3; $p++) {
			foreach($days as $day) {
				$thisEndTimes 	= array();
				$thisValues		= array();
				$timePrevious 	= "00:00";
				for($index 	= 1; $index <= 13; $index++) {
					$keyTemp 	= "P". $p ."_TEMPERATURE_".strtoupper($day)."_".$index;
					$keyTO 		= "P". $p ."_ENDTIME_".strtoupper($day)."_".$index;
					$thisTemp 	= $params[$keyTemp];
					$thisTO 		= $params[$keyTO];
					$thisTime 	= date('H:i', mktime(0, $thisTO)); // $timePassed + TO
					if ($thisTO >= 1440) $thisTime = "24:00";
					$timePrevious = $thisTime;
					array_push($thisEndTimes,	$thisTime);
					array_push($thisValues,		$thisTemp);
					if($thisTO >= 1440) break;
				}
				$temp["P".$p][$day]['EndTimes'] 	= $thisEndTimes;
				$temp["P".$p][$day]['Values'] 	= $thisValues;
			}
		}
		if($weekprofil > 0 and $weekprofil <= 3) {
			return $temp["P".$weekprofil];
		}
		else {
			return $temp;
		}
	}
	echo $type;
	if($type != "HM-CC-RT-DN" and $type != "HM-CC-TC" and $type != "HM-TC-IT-WM-W-EU" and $type != "HmIP-WTH-2" and $type != "HMIP-eTRV" and $type != "HmIP-eTRV-2") {
		die("Error: ReadTempProfile() Device $device is not of Type HM-CC-TC,HM-CC-RT-DN, HM-TC-IT-WM-W-EU, HmIP-WTH-2, HMIP-eTRV or HmIP-eTRV-2!");
	}
}

// Schreibt das Temperaturprofil in ein Thermostat/Stellantrieb.
// $device: IPS Instance ID
// $profile: Temperaturprofil wie von ReadTempProfile() geliefert
// $weekprofil: nur für HM-TC-IT-WM-W-EU & HmIP-WTH-2; 
//   gültige Werte 1,2,3; bei -1 werden alle Profile (1-3) zurückgegeben
function WriteTempProfile(int $device, array $profile, int $weekprofile=0) {
global $service, $weekday;
	// HM Adresse vom Device
	$address = explode(":", IPS_GetProperty($device, 'Address'));
	$serial  = $address[0];
	$channel = $address[1];
	// Was für ein HM Gerätetyp & Interface
	$dt 	= explode(":", DeviceType($device));
	$type = $dt[0];
	$if 	= $dt[1];
	// Konvert Interface
	foreach($service as $s) {if($s['ID'] == $if) {$if = $s['TYPE'];break;}}
	// HM-CC-TC Profil schreiben (hat nur eins)
	if($type == "HM-CC-TC") {
		$params = new xmlrpcval();
		foreach($profile as $day => $values) {
			$timePrevious = "00:00";
			for($index=1; $index <= count($values['EndTimes']); $index++) {
				$key = "TEMPERATUR_".strtoupper($day)."_".$index;
				$temp = array($key => new xmlrpcval($values['Values'][$index-1], "double"));
				$params->addStruct($temp);
				$key = "TIMEOUT_".strtoupper($day)."_".$index;
				if ($values['EndTimes'][$index-1] > $timePrevious) {
					// Convert end time to Timeout
					$thisDayStart = mktime(0, 0);
					$timeEndArray = explode(":", $values['EndTimes'][$index-1]);
					if ($timeEndArray[1] % 10) die("Error: Invalid End Time (must be 10mn increments) for $day at index $index in WriteTempProfile()!");
					$timeEndts = mktime($timeEndArray[0], $timeEndArray[1]);
					$timeout = (($timeEndts - $thisDayStart)/60); // TODO, works  ?
					$paramTime = array($key => new xmlrpcval("$timeout", "int")); // i4
					$params->addStruct($paramTime);
				}
				else {
					die("Error: Invalid End Time for $day at index $index in WriteTempProfile()!");
				}
				$timePrevious = $values['EndTimes'][$index-1];
			}
		}
		$request = new xmlrpcmsg("putParamset",
			array(new xmlrpcval("$serial:2", "string"),
					new xmlrpcval("MASTER", "string"), $params));
		$result = Send($request, $if);
		return true;
	}
	// HM-CC-RT-DN Profil schreiben (hat nur eins)	
	if($type == "HM-CC-RT-DN") {
		$params = new xmlrpcval();
		foreach ($profile as $day => $values) {
			$timePrevious = "00:00";
			for($index=1; $index <= count($values['EndTimes']); $index++) {
				$key = "TEMPERATURE_".strtoupper($day)."_".$index;
				$temp = array($key => new xmlrpcval($values['Values'][$index-1], "double"));
				$params->addStruct($temp);
				$key = "ENDTIME_".strtoupper($day)."_".$index;
				if ($index>13) break; // HM-CC-RT-DN hat nur 13 Tages - Timeslots
				if ($values['EndTimes'][$index-1] > $timePrevious) {
					// Convert end time to Timeout
					$thisDayStart = mktime(0, 0);
					$timeEndArray = explode(":", $values['EndTimes'][$index-1]);
					if ($timeEndArray[1] % 10) die("Error: Invalid End Time (must be 10mn increments) for $day at index $index in WriteTempProfile()!");
					$timeEndts = mktime($timeEndArray[0], $timeEndArray[1]);
					$timeout = (($timeEndts - $thisDayStart)/60); // TODO, works  ?
					$paramTime = array($key => new xmlrpcval("$timeout", "int")); // i4
					$params->addStruct($paramTime);
				}
				else {
					die("Error: Invalid End Time for $day at index $index in WriteTempProfile()!");
				}
				$timePrevious = $values['EndTimes'][$index-1];
			}
		}
		$request = new xmlrpcmsg("putParamset",
			array(new xmlrpcval("$serial", "string"), // no channel NOT TESTED????
					new xmlrpcval("MASTER", "string"), $params));
		$result = Send($request, $if);
		return true;
	}
	// HM-TC-IT-WM-W-EU Profil schreiben (1-3)	
	if ($type == "HM-TC-IT-WM-W-EU") {
		$prefix="P".$weekprofile."_";
		$params = new xmlrpcval();
		foreach ($rofile as $day => $values) {
			$timePrevious = "00:00";
			for ($index=1; $index <= count($values['EndTimes']); $index++) {
				$key = $prefix ."TEMPERATURE_".strtoupper($day)."_".$index;
				$temp = array($key => new xmlrpcval($values['Values'][$index-1], "double"));
				$params->addStruct($temp);
				$key = $prefix ."ENDTIME_".strtoupper($day)."_".$index;
				if ($index>13) break; // HM-TC-IT-WM-W-EU hat nur 13 Tages - Timeslots
				if ($values['EndTimes'][$index-1] > $timePrevious) {
					// Convert end time to Timeout
					$thisDayStart = mktime(0, 0);
					$timeEndArray = explode(":", $values['EndTimes'][$index-1]);
					if ($timeEndArray[1] % 5) die("Error: Invalid End Time (must be 10mn increments) for $day at index $index in WriteTempProfile()!");
					$timeEndts = mktime($timeEndArray[0], $timeEndArray[1]);
					$timeout = (($timeEndts - $thisDayStart)/60); // TODO, works  ?
					$paramTime = array($key => new xmlrpcval("$timeout", "int")); // i4
					$params->addStruct($paramTime);
				}
				else {
					die("Error: Invalid End Time for $day at index $index in WriteTempProfile()!");
				}
				$timePrevious = $values['EndTimes'][$index-1];
			}
		}
		$request = new xmlrpcmsg("putParamset",
			array(new xmlrpcval("$serial", "string"), // no channel NOT TESTED????
					new xmlrpcval("MASTER", "string"), $params));
		$result = Send($request, $if);
		return true;
	}
	// HmIP-WTH-2 || 	HMIP-eTRV || HmIP-eTRV-2 Profil schreiben (1-3 von 6)	
	if($type == "HmIP-WTH-2" or $type =="HmIP-eTRV-2" or $type == "HMIP-eTRV") {
		$prefix="P".$weekprofile."_";
		$params = new xmlrpcval();
		foreach ($profile as $day => $values) {
			$timePrevious = "00:00";
			for ($index=1; $index <= count($values['EndTimes']); $index++) {
				$key = $prefix ."TEMPERATURE_".strtoupper($day)."_".$index;
				$temp = array($key => new xmlrpcval($values['Values'][$index-1], "double"));
				$params->addStruct($temp);
				$key = $prefix ."ENDTIME_".strtoupper($day)."_".$index;
				if ($index>13) break; // nur 13 Tages - Timeslots
				if ($values['EndTimes'][$index-1] > $timePrevious) {
					// Convert end time to Timeout
					$thisDayStart = mktime(0, 0);
					$timeEndArray = explode(":", $values['EndTimes'][$index-1]);
					if ($timeEndArray[1] % 5) die("Error: Invalid End Time (must be 10mn increments) for $day at index $index in HMXML_setTempProfile()<br>
");
					$timeEndts = mktime($timeEndArray[0], $timeEndArray[1]);
					$timeout = (($timeEndts - $thisDayStart)/60); // TODO, works  ?
					$paramTime = array($key => new xmlrpcval("$timeout", "int")); // i4
					$params->addStruct($paramTime);
				}
				else {
					die("Error: Invalid End Time for $day at index $index in WriteTempProfile()!");
				}
				$timePrevious = $values['EndTimes'][$index-1];
			}
		}
		$request = new xmlrpcmsg("putParamset",
			array(new xmlrpcval("$serial:$channel", "string"),
					new xmlrpcval("MASTER", "string"), $params));
		//var_dump($params);
		$result = Send($request, $if);
		return true;
	}
	if($type != "HM-CC-RT-DN" and $type != "HM-CC-TC" and $type != "HM-TC-IT-WM-W-EU" and $type != "HmIP-WTH-2" and $type != "HMIP-eTRV" and $type != "HmIP-eTRV-2") {
		die("Error: WriteTempProfile() Device $device is not of Type HM-CC-TC,HM-CC-RT-DN, HM-TC-IT-WM-W-EU, HmIP-WTH-2, HMIP-eTRV or HmIP-eTRV-2!");
	}
}

// Liest die Parameter von einem Gerät aus.
// $if: HM Inteface
// $adress: HM adress
// $channel: HM device chanvel
// $param: Ein spezifischer Parameter wird ausgelesen (siehe HomeMatic Specficiation),sonst alle
function ReadParamSet($if, $address, $channel, $param = false) {
	// Build request
	$request = new xmlrpcmsg("getParamset",
		array(new xmlrpcval("$address:$channel", "string"), new xmlrpcval("MASTER", "string")));
	$messages = Send($request, $if);
	//var_dump($messages);
	if ($param !== false) return $messages[$param];
	return $messages;
}


// Creates XMLRPC Client Instance and sends request
function Send($request, $type) 
{
global $client;
	// If the client does not exist, initialise it here
	if (isset($client[$type]) &&  $client[$type] !== false) {
		$response = $client[$type]->send($request);
		if ( $response->errno == 0 ) {
   		$messages = php_xmlrpc_decode($response->value());
		}
		else {
			die("Error: Send() Request to $type Service failed -> $response->errstr!
");
		}
	}
	return $messages;
}

// Erzeugt eine Variable unterhalb {id} mit dem Namen {name} vom Typ [type}
// Existiert die Variable schon wird diese zurückgeliefert.
// Types: 0 = Boolean, 1 = Integer, 2 = Float, 3 = String
function CreateVariableByName($id, $name, $type) {
	$vid = @IPS_GetVariableIDByName($name, $id); 
	if($vid===false) {
		$vid = IPS_CreateVariable($type); 
		IPS_SetParent($vid, $id); 
		IPS_SetName($vid, $name); 
	}
	return $vid; 
}

// Erzeugt ein Variablenprofil vom Typ {type} mit Name n{name} 
function CreateProfile($name, $type) {
	if(!IPS_VariableProfileExists($name)) {
		IPS_CreateVariableProfile($name, $type);
	} 
	else {
	  $profile = IPS_GetVariableProfile($name);
	  if($profile['ProfileType'] != $type)
	    throw new Exception("Variable profile type does not match for profile ".$name);
	}
}

// Erzeugt ein Integer-Variablenprofil
function CreateProfileInteger($name, $icon, $prefix, $suffix, $minvalue, $maxvalue, $step, $digits, $asso = NULL) {
	CreateProfile($name, 1);

	IPS_SetVariableProfileIcon($name, $icon);
	IPS_SetVariableProfileText($name, $prefix, $suffix);
	IPS_SetVariableProfileDigits($name, $digits);
	
	if(($asso !== NULL) && (sizeof($asso) !== 0)){
	  $minvalue = 0;
	  $maxvalue = 0;
	} 
	IPS_SetVariableProfileValues($name, $minvalue, $maxvalue, $step);
	
	if(($asso !== NULL) && (sizeof($asso) !== 0)){
	  foreach($asso as $ass) {
	    IPS_SetVariableProfileAssociation($name, $ass[0], $ass[1], $ass[2], $ass[3]);
	  }
	}         
}

// Extrahiert für den übergebenen Raum und Wochenprofil das entsprechende
// Temperaturprofil soweit es schon man ausgelesen und gecached wurde. 
function GetWeeklyProfile(int $rn, int $wp) {
	// Rückgabefeld
	$profil = array();
	// Cache auslesen
	$cid = CreateVariableByName($_IPS['SELF'], "Profiles", 3);
	$profiles = unserialize(GetValue($cid));
	// unseres dabei?
	if(isset($profiles[$rn])) {
		if(isset($profiles[$rn]["P".$wp])) {
			//	"HM-TC-IT-WM-W-EU" oder "HmIP-WTH-2"
			$profil = $profiles[$rn]["P".$wp];
		}
		else {
			//	Quickhack :( "HM-CC-TC" oder "HM-CC-RT-DN"
			$profil = $profiles[$rn]["P1"];
		}
	}
	return $profil;
}

// Speichert für den übergebenen Raum die Wochenprofil(e).
function SetWeeklyProfile(int $rn, array $profile, int $wp =-1) {
	// Cache auslesen
	$cid = CreateVariableByName($_IPS['SELF'], "Profiles", 3);
	$profiles = unserialize(GetValue($cid));
  	if($wp > 0 and $wp <= 3) {
		$profiles[$rn]["P".$wp] = $profile;
	}
	else {
		$profiles[$rn] = $profile;
	}
	// Cache updaten
	SetValue($cid, serialize($profiles));
}

// Extrahiert für den übergebenen Tag das Tagesprofil
function GetDailyProfile(array $week, int $day) {
global $weekday;
	// Rückgabefeld
	$profil = array();
	// unseres dabei?
	if(isset($week[$weekday[$day]])) {
		$profil = $week[$weekday[$day]];
	}
	return $profil;
}

// Speichert für den übergebenen Raum die Wochenprofil(e).
function SetDailyProfile(int $rn, int $wp, int $day, array $dp) {
global $weekday;
	// Cache auslesen
	$cid = CreateVariableByName($_IPS['SELF'], "Profiles", 3);
	$profiles = unserialize(GetValue($cid));
	// Tagesprofil austauschen
	if(isset($profiles[$rn]["P".$wp])) {
		//	"HM-TC-IT-WM-W-EU" oder "HmIP-WTH-2"
		$profiles[$rn]["P".$wp][$weekday[$day]] = $dp;
	}
	else {
		//	"HM-CC-TC" oder "HM-CC-RT-DN"
		$profiles[$rn][$weekday[$day]] = $dp;
	}
	// Cache updaten
	SetValue($cid, serialize($profiles));
}

// Prüfen ob Profil konsistent ist
function CheckWeeklyProfile($profile) {
global $weekday;
	// Ergebniss
	$ret = "OK";
	foreach($weekday as $key => $day) {
		$time1='00:00';
		foreach($profile[$weekday[$key]]['EndTimes'] as $ts => $time2) {
			// Speicherslots des HM WT in min
			if(strtotime($time2) <= strtotime($time1)) {
				$slot = $ts+1;
				$ret="Fehler im Tagesprofil $weekday[$key] (Slot: $slot Start: $time1 - Ende: $time2 )";
				break;
			}
			$time1 = $time2;
		}
	}
	return $ret;
}

// Zeitabschnitt Auswahl im Webfront Anzeige auf Anzahl
// der belegten Slots im HM WT beschränken
function SetTimeSlotProfile($profile, $hl=99) {
	// Profilename
	$vpn = "HM.Heating.Slot";
	// Anzahl Slots
	$count = 0;
	if(!empty($profile)) {
		$count = count($profile['EndTimes']);
	}
	// Auswahl anpassen?!
	$vid = CreateVariableByName($_IPS['SELF'], "Zeitabschnitt", 1);
	if($count > 0) {
		IPS_SetVariableProfileValues ($vpn, 1, $count, 1);
		if($hl <= $count) {
			SetValue($vid, $hl);
			return $hl;
		}
		else {
			SetValue($vid, 1);
			return 1;
		}		
	}
	else {
		IPS_SetVariableProfileValues ($vpn, 1, 1, 1);
		SetValue($vid, 0);
	}
	return 99;
}

// Erzeugt vom übergebenen Wochen-Temperaturprofil das entsprechende HTML
function RenderWeeklyProfile(array $profile, $hl = 99) {
global $day, $weekday;
	// Temeraturen => 15, 16, 17, 18, 19, 20, 21, 22
	if(!empty($profile)) {
		foreach ($weekday as $k => $d)	{
			$time1='00:00';
			foreach ($profile[$weekday[$k]]['EndTimes'] as $time2) {
				// Speicherslots des HM WT in min
				$times[$d][]=(strtotime("01.01.2001 ". $time2)-strtotime("01.01.2001 ". $time1))/60; 
				$time1=$time2;
			}
			foreach ($profile[$weekday[$k]]['Values'] as $v) {
				if($v <= 15) 		$temp[$d][] = 't15';	// sehr kalt
				elseif ($v <= 16)	$temp[$d][] = 't16';	// kalt
				elseif ($v <= 17)	$temp[$d][] = 't17';	// Kühl
				elseif ($v <= 18)	$temp[$d][] = 't18';	// normal
				elseif ($v <= 19)	$temp[$d][] = 't19';	// warm
				elseif ($v <= 20)	$temp[$d][] = 't20';	// sehr warm
				elseif ($v <= 21)	$temp[$d][] = 't21';	// heiß
				else 					$temp[$d][] = 't22';	// sehr heiß
			}
		}
	}
	else {
		// kein Profil kein Highlight!
		$hl = 99;
	}	
	// styles definieren
	$style = '';
	$style = $style.'<style type="text/css">';
	$style = $style.'table.tp {border-collapse: collapse; font-size: 11px; width: 100%; border-right: 1px solid rgba(255, 255, 255, 0.2);}';
	$style = $style.'td.fst {vertical-align: middle; text-align: center; width: 4%; padding: 2px; border-left: 1px solid rgba(255, 255, 255, 0.2); border-right: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.mid {vertical-align: middle; text-align: center; width: 4%; padding: 2px; border-right: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.lst {vertical-align: middle; text-align: center; width: 4%; padding: 2px; border-right: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'tr:last-child {border-bottom: 1px solid rgba(255, 255, 255, 0.2); }';
	$style = $style.'.th { color: rgb(255, 255, 255); background-color: rgba(255, 255, 255,0.25); font-weight:bold; background-image: linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 28%,rgba(0,0,0,0.3) 100%); background-image: -o-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 28%,rgba(0,0,0,0.3) 100%); background-image: -moz-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 28%,rgba(0,0,0,0.3) 100%); background-image: -webkit-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 28%,rgba(0,0,0,0.3) 100%); background-image: -ms-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 28%,rgba(0,0,0,0.3) 100%); }';
	$style = $style.'.hl {background-color: black; opacity: 0.5;}';
	$style = $style.'.t15 {background-color: #6600CC; opacity: 0.9;}'; // lila (sehr kalt) <= 15
	$style = $style.'.t16 {background-color: #0000FF; opacity: 0.9;}'; // dunkelblau (kalt) = 16
	$style = $style.'.t17 {background-color: #0080FF; opacity: 0.9;}'; // hellblau (kühl) = 17
	$style = $style.'.t18 {background-color: #00FFFF; opacity: 0.9;}'; // türkis (normal) 18
	$style = $style.'.t19 {background-color: #00FF00; opacity: 0.9;}'; // grün (warm) =19
	$style = $style.'.t20 {background-color: #FFFF00; opacity: 0.9;}'; // gelb (sehr warm) = 20
	$style = $style.'.t21 {background-color: #FF8000; opacity: 0.9;}'; // orange (heiß) = 21
	$style = $style.'.t22 {background-color: #FF0000; opacity: 0.9;}'; // rot (sehr heiß) >= 22
	$style = $style.'</style>';
	// HTML Table erzeugen
	$html = $style;	
	$html = $html.'<table class="tp">';
	$html = $html.'<tr>';

	for($i=0; $i <= 24; $i++) {
		if($i == 0) {
			$html = $html.'<td class=""></td>';
		}
		elseif ($i == 24) {
			$html = $html.'<td class="lst th" colspan="12">'.sprintf("%02d", $i).'</td>';
		}
		else {
			$html = $html.'<td class="mid th" colspan="12">'.sprintf("%02d", $i).'</td>';
		}
	}
	$html = $html.'</tr>';

	foreach ($weekday as $k => $d)	{
		// wurde Wochentag mit übergeben (0=Mo, 1=Di ... 99=kein Wochentag vorgegeben)
		if($hl <> $k) {
			$html = $html.'<tr><td class="fst th">'. $day[$k][1] .'</td>';
		}
		else {
			$html = $html.'<tr class="hl"><td class="fst th">'. $day[$k][1] .'</td>';
		}
		if(isset($times)) {
			foreach ($times[$d] as $key => $time) {
			   $html = $html.'<td colspan="'.($time/5).'" class="'.$temp[$d][$key].'"> </td>';
			}
		}
		else {
			for($i=0; $i < 24; $i++) {
				$html = $html.'<td colspan="12"> </td>';
			}
		}
		$html = $html.'</tr>';
	}
   $html = $html.'</table>';
   $html = $html.'<div style="height:8px;"><nbsp /></div>';
	// Index Tabelle (Temperatur-Spektrum)
   $html = $html.'<table style="border: 0px; font-size:11px; text-shadow:1px 1px #000000; width:100%; text-align: center">';
	$html = $html.'<tr>';
	$html = $html.'<td class="t15" style="width:12%"><= 15°C</td>';
	$html = $html.'<td class="t16" style="width:13%"><= 16°C</td>';
	$html = $html.'<td class="t17" style="width:12%"><= 17°C</td>';
	$html = $html.'<td class="t18" style="width:13%"><= 18°C</td>';
	$html = $html.'<td class="t19" style="width:12%"><= 19°C</td>';
	$html = $html.'<td class="t20" style="width:13%"><= 20°C</td>';
	$html = $html.'<td class="t21" style="width:12%"><= 21°C</td>';
   $html = $html.'<td class="t22" style="width:13%">>= 22°C</td>';
	$html = $html.'</tr></table>';
	// Rückgabe
	return $html;
}

// Erzeugt vom übergebenen Tages-Temperaturprofil das entsprechende HTML
function RenderDailyProfile(array $profile, int $hl=99) {
	// styles definieren
	$html = "";	
	$html = $html.'<table class="tp">';
	$html = $html.'<tr><td class=""></td><td class="mid th">Startzeit</td><td class="mid th">Endzeit</td><td class="lst th">Temperatur</td></tr>';
	// rendern
	if(!empty($profile)) {
		$start="00:00";
		foreach($profile['EndTimes'] as $key => $end) {
			$temp = number_format($profile['Values'][$key], 1,",",".");
			if($key <> $hl-1) {
				$html = $html.'<tr><td class="fst th">'.($key+1) .'. Zeitabschnitt</td><td class="mid">'.$start.'</td><td class="mid">'.$end.'</td><td class="lst">'.$temp.' °C</td></tr>';
			}
			else {
				$html = $html.'<tr class ="hl"><td class="fst th">'.($key+1). '. Zeitabschnitt</td><td class="mid">'.$start.'</td><td class="mid">'.$end.'</td><td class="lst">'.$temp.' °C</td></tr>';
			}
			$start=$end;
		}
	}
	else {
		// kein Profil vorhanden!
		$html = $html.'<tr><td class="fst th">-<td class="mid">-</td><td class="mid">-</td><td class="lst">-</td></tr>';
	}
	$html = $html.'</table>';
	// Rückgabe
	return $html;
}

// Update HTML
function RenderProfile(int $rn, int $wp, int $wd, int $ts = 99) {
	// Profil extrahieren
	$profile = GetWeeklyProfile($rn, $wp);
	// Rendern Wochenprofil
	$vid = CreateVariableByName($_IPS['SELF'], 'Wochenprofil', 3);
	SetValue($vid, RenderWeeklyProfile($profile, $wd));		
	// Profil extrahieren
	$profile = GetDailyProfile($profile, $wd);
	$ts = SetTimeSlotProfile($profile, $ts);
	// Render Tagesprofil
	$vid = CreateVariableByName($_IPS['SELF'], 'Tagesprofil', 3);
	SetValue($vid, RenderDailyProfile($profile, $ts));		
}

################################################################################
?>

Viel Erfolg
Heiko

2 „Gefällt mir“

Hallo Heiko,

danke für dein Script!!! Es funktioniert auch mit dem HmIP-BWTH. :smiley:

Viele Grüße
Peter

Hi Peter, wunderbar - musstest Du den Typ noch im Script eintragen?

Gruß Pitti

Hi Pitti,

ich hab das Script ja schon lange zur Zufriedenheit laufen…

Eine Sache ist mir gestern beim Aufräumen aufgefallen…
In Deinen Arrays hast Du hinten einen int-Wert… Wozu soll der sein?

bspw.
$time = array(
array(1, ‚-1 h‘, ‚‘, 65280),
array(2, ‚-10 min‘, ‚‘, 65280),
array(3, ‚+10 min‘, ‚‘, 16744448),
array(4, ‚+1 h‘, ‚‘, 16744448)
);

Hab gestern viele alte Variablen gelöscht und da kam dann öfter mal die Warnung dass es noch Referenzen darauf gibt… und das waren dann immer zufällige Treffer aus diesen Arrays…

Das Array dient der Erzeugung von Profilen(Assoziazionen) mit entsprechenden Farbwerten (die INT-Werte!!!)

VG Heiko

Ach so… dann geht symcon jetzt davon aus, dass es Objekt-ID´s sind…

Ok… dann kann man die Warnungen beim löschen ja ignorieren…

Ach, jetzt verstehe ich auch was du mit Warnungen meintest, ja!

In meinen neusten Scripten verwende ich nur noch Hex-Werte für sowas, da passt es dann besser [emoji41]

Gesendet von iPhone mit Tapatalk

@Pitti: Ja, genau. Musste ich nur hinzufügen.

Viele Grüße
Peter

Vielen Dank für die Zusammenfassung der Scripte @Pitti :cool:

Nachdem ich alles gemäß Deiner Anweisungen im Script eingerichtet habe, kann ich leider bei meinen Thermostaten (HM-CC-RT-DN & HM-TC-IT-WM-W-EU) die dort hinterlegten Zeitpläne nicht auslesen. Beim Klick auf die Schaltfläche Auslesen in der Weboberfläche erscheinen wiederholt PHP Notice Meldungen (siehe Screenshot).

Ich habe bereits nach der Ursache gesucht aber komme leider nicht weiter. Vermutlich wird die Variable $params durch ReadParamSet nicht befüllt. In der CCU steht der XML-RPC-API-Zugriff auf Vollzugriff. Auch steht die IP-Adresse des Symcon-Systems auf der Liste der eingeschränkten Adressen.

Die CCU ist bei mir ein RaspberryMatic Version 3.43.15.20190223. IP-Symcon 5.0 läuft unter Ubuntu 18.04.2 LTS. Bei der xmlrpc.inc.php habe ich die erwähnte Version phpxmlrpc-4.3.0 heruntergeladen und im Script eingebunden.

Hat evtl. jemand eine Idee warum das nicht klappt?

Hallo!

Ich habe die HmIP-eTRV-B
Welche ID muß man da eintragen?

oder wird HmIP-eTRV-B nicht unterstüzt?

Mfg
Maxx

Bin gerade nicht am Rechner, aber wenn Du das Script nutzt müsste eine Fehlermeldung kommen das der Typ XYZ (Wahrscheinlich HmIP-eTRV-B) nicht unterstützt wird.

Diese Typbeszeichnung müsstest Du im Script beim Gerätetypcheck (if … then) hinzufügen!

Gruß Heiko

Gesendet von iPad mit Tapatalk

Ich komme leider nicht weiter :frowning:

Hier mal der Inhalt der $request-Variable aus der Funktion ReadParamSet:


xmlrpcmsg Object
(
    [payload] => <?xml version="1.0"?>
<methodCall>
<methodName>getParamset</methodName>
<params>
<param>
<value><string>MEQ0806235:2</string></value>
</param>
<param>
<value><string>MASTER</string></value>
</param>
</params>
</methodCall>
    [methodname] => getParamset
    [params] => Array
        (
            [0] => xmlrpcval Object
                (
                    [me] => Array
                        (
                            [string] => MEQ0806235:2
                        )

                    [mytype] => 1
                    [_php_class] => 
                )

            [1] => xmlrpcval Object
                (
                    [me] => Array
                        (
                            [string] => MASTER
                        )

                    [mytype] => 1
                    [_php_class] => 
                )

        )

    [debug] => 0
    [content_type] => text/xml
    [httpResponse:protected] => Array
        (
            [raw_data] => HTTP/1.0 200 OK
Content-Type: text/xml; charset=iso-8859-1
Content-Length: 149
Content-Security-Policy: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-Content-Security-Policy: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-WebKit-CSP: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-Frame-Options: SAMEORIGIN
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
X-Robots-Tag: none
X-Download-Options: noopen
X-Permitted-Cross-Domain-Policies: none
Referrer-Policy: no-referrer
Connection: close
Date: Thu, 09 May 2019 17:32:12 GMT

<?xml version="1.0" encoding="iso-8859-1"?>
<methodResponse><params><param>
	<value><struct></struct></value>
</param></params></methodResponse>

            [headers] => Array
                (
                    [content-type] => text/xml; charset=iso-8859-1
                    [content-length] => 149
                    [content-security-policy] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
                    [x-content-security-policy] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
                    [x-webkit-csp] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
                    [x-frame-options] => SAMEORIGIN
                    [x-content-type-options] => nosniff
                    [x-xss-protection] => 1; mode=block
                    [x-robots-tag] => none
                    [x-download-options] => noopen
                    [x-permitted-cross-domain-policies] => none
                    [referrer-policy] => no-referrer
                    [connection] => close
                    [date] => Thu, 09 May 2019 17:32:12 GMT
                )

            [cookies] => Array
                (
                )

        )

)

Und hier die Antwort ($response) aus der Funktion send:


PhpXmlRpc\Response Object
(
    [val] => PhpXmlRpc\Value Object
        (
            [me] => Array
                (
                    [struct] => Array
                        (
                        )

                )

            [mytype] => 3
            [_php_class] => 
        )

    [valtyp] => xmlrpcvals
    [errno] => 0
    [errstr] => 
    [payload] => 
    [hdrs] => Array
        (
            [content-type] => text/xml; charset=iso-8859-1
            [content-length] => 149
            [content-security-policy] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
            [x-content-security-policy] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
            [x-webkit-csp] => default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
            [x-frame-options] => SAMEORIGIN
            [x-content-type-options] => nosniff
            [x-xss-protection] => 1; mode=block
            [x-robots-tag] => none
            [x-download-options] => noopen
            [x-permitted-cross-domain-policies] => none
            [referrer-policy] => no-referrer
            [connection] => close
            [date] => Thu, 09 May 2019 17:32:12 GMT
        )

    [_cookies] => Array
        (
        )

    [content_type] => text/xml
    [raw_data] => HTTP/1.0 200 OK
Content-Type: text/xml; charset=iso-8859-1
Content-Length: 149
Content-Security-Policy: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-Content-Security-Policy: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-WebKit-CSP: default-src 'self';frame-ancestors 'self';script-src 'unsafe-inline' 'unsafe-eval' 'self' *.homematic.com https://gitcdn.xyz ;style-src 'unsafe-inline' 'self';img-src 'self' data: ;connect-src 'self' http://*:8088
X-Frame-Options: SAMEORIGIN
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
X-Robots-Tag: none
X-Download-Options: noopen
X-Permitted-Cross-Domain-Policies: none
Referrer-Policy: no-referrer
Connection: close
Date: Thu, 09 May 2019 17:32:12 GMT

<?xml version="1.0" encoding="iso-8859-1"?>
<methodResponse><params><param>
	<value><struct></struct></value>
</param></params></methodResponse>

)

Hallo Heiko,

erstmal vielen Dank für das Skript, ich versuche gerade das bei einem Freund zu installieren.

Wenn jetzt im Webfront auf auslesen geklickt wird, kommt die Fehlermeldung in einem schwarzen Kasten oben rechts.


Error: Send () Request to RF Service Failed
Didn´t Receice 200 OK from Remote Server (http1/1.0 401 unauthorized)

Kannst du mir eventuell sagen was das zu bedeuten hat und wo der Fehler liegt?

Wäre super wenn mir jemand helfen könnte.

Danke und Grüße
Stephan

Hallo Stephan,

sieht nach gesperrten Port aus (Firewall)!?

Führ doch mal folgendes Skript aus und gib mal das Ergebnis preis! (IP eintragen nicht vergessen)


<?php
################################################################################
# Script:   System.Ports.ips.php
# Version:  2.0
# Author:   Heiko Wilknitz
#
# Zum überprüfen ob der entsprechende TCP-Port erreichbar ist oder geblockt wird
# Für einen UDP Check muss ein udp// vor die IP-Adresse gesetzt werden.         
#
################################################################################

// IP CCUx
$ip = "xxx.xxx.x.x";

// Homematic. Für den Lanadapter muss nur Port 2001 und 5544 erreichbar sein
// 2000 - für Wired
// 2001 - für Funk
// 2010 - für IP
// 5544 - für Ereignise 
// 8181 - für Scripte
// 42000 - SSL Wired
// 42001 - SSL Funk
// 42010 - SSL IP
// 48181 - SSL Scripte

$port = array(2000, 2001,2010, 5544, 8181); 

for($i=0; $i<count($port); $i++) {
	// IP Adresse anpassen
    $socket = @fsockopen($ip, $port[$i], $errno, $errstr); 
    if(!$socket) {
        echo "Port: ".$port[$i]." ist NICHT erreichbar!
";
    }
    else {
        echo "Port: ".$port[$i]." ist erreichbar.
";
    }
}
?>

Gruß Heiko

Hallo Heiko,

danke für die schnelle Antwort.

Die IP Adresse ist geändert, bekomme aber folgende Fehlermeldung:

Parse error:  syntax error, unexpected 'for' (T_FOR) in /var/lib/symcon/scripts/43929.ips.php on line 28

Woran liegt das? Danke!