Problème plugin IPX800-V5 Jeedom

Bonjour,

J’utilise Jeedom sur un Raspberry. Je n’ai aucun souci pour la communication avec mes 2 IPX800-V4 .

J’ai également maintenant une IPX800-V5 et j’ai installé le plugin qui va bien (GCE IPX800 V5 ) sur Jeedom. Je suis en train de faire la configuration. J’ai donc ajouté mon IPX800-V5 et je l’ai configurée.

Mon problème vient des commandes IPX par défaut. Pas de problème pour les commandes (Relay et Open Collector). Par contre, si je sélectionne n’importe quelle récupération d’information State ou Input, le démon plante et le message “Erreur sur GCE_IPX800V5::pull() : Non-static method GCE_IPX800V5::get() cannot be called statically” apparait. Dès que je désélectionne la commande fautive, le démon reste stable après l’avoir relancé.

Est-ce quelqu’un utilise ce type de configuration et a rencontré ce souci ?

Mon Jeedom est en 4.4.19 et le plugin de l’ IPX800-V5 est en Beta du 2025-02-04.

Merci par avance pour votre aide, bonne journée.

Bonjour,

Je rajoute 3 précisions:

  • La version du plugin GCE IPX800 V5 est 2023-12-28 01:00:56
  • J’ai tenté de réinstaller, sans succès
  • Lorsque le démon est fonctionnel, le log contient une multitude de ces messages :

Attention le plugin GCE IPX800 V5 n’a pas recu de message depuis 1 min Configuration 14
2025-09-11 16:05:32 GCE_IPX800V5

Encore merci par avance pour votre aide.

Bonjour,

quelle version de raspberry pi OS utilisez-vous ? Il semble y avoir un problème avec les dérivés de Debian 12 ( Compatibilité des plugins avec Debian 12 - Bookworm, php 8, python 3.11 - Plugins - Communauté Jeedom )

1 « J'aime »

Bonjour Sylvouille,

Merci de votre intérêt pour mon problème

J’utilise la version 4.4.19 sur un système RPI 3.8+

Le plugin proposé par GCE est toujours en version Beta ? Cela semble faire pas mal de temps qu’il es est ainsi.

Bonne journée.

Bonjour Faurinam,
c’est la version de l’OS dont il est question (Debian 12), pas celle de Jeedom.
Pour ma part je suis resté en Debian 11 à cause des problèmes de compatibilités de plugins.
Bonne journée

Pardon fgtoul, je n’avais pas vu. Merci pour votre aide.

J’ai bien peur que nous soyons en Debian 12. Nous avions changé car certains plugins le nécessitaient. Donc vous confirmez que ce soit possiblement la cause de ce souci ?

Pourquoi le plugin IPX800-V5 est toujours resté en béta ? Pensez-vous qu’une mise à jour va être entreprise ?

Je me demande si beaucoup de monde utilise ce plugin. Il semble abandonné, je ne vois pas de mise à jour depuis 2023.

Si je suis coincé, je vois 2 solutions possibles, mais c’est moins élégant et ça fait un peu usine à gaz :

  1. Envoyer les valeurs et états que j’utilise sur Jeedom par des pushs mais je ne connais pas assez Jeedom pour savoir où les envoyer

  2. J’ai également une IPX800-V4 sur le même réseau qui est interfacée avec ce même Jeedom. Peut-être que je peux modifier des EV ou SV de la V4 en faisant des pushs ? Ensuite le Jeedom va récupérer tout ça sur l’IPX800-V4.

Merci encore pour l’intérêt que vous portez à mon problème.

Bon après-midi.

@GCE
Bonjour Patrick,
est-ce qu’une mise à jour du plugin IPX800 V5 est prévue pour Jeedom ?
Celui-ci apparaît comme incompatible avec Debian 12, qu’en est-il vraiment ?
Bonne journée

Bonjour,

On va migrer sur un Déban 12 pour faire des tests.

Cdt

2 « J'aime »

Ah merci, c’est sympa. Tenez-nous au courant.

Bonne fin de journée.

Le truc c’est que Jeedom pour le moment indique ne pas etre compatible avec debian 12 !!!

Bonjour @GCE

On en avait parlé ici

Et @Alan328 avait proposé une solution

Ca a du passer à la trappe ou alors il y avait un effet de bord ?

Bonjour,

Si si, ils font même des images officielles à base de Debian 12 :

et un sujet du forum recense la compatibilité des différents plugins avec Debian 12 :

@Faurimam

Effectivement si on va sur le post apparemment 2 lignes à modifier, si

$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« io »] = GCE_IPX800V5::get($urlGet, 1);
à modifier en
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« io »] = $GCE_IPX800V5->get($urlGet, 1);

$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = GCE_IPX800V5::get($urlGet, 1);
à modifier en
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = $GCE_IPX800V5->get($urlGet, 1);

Comme c’est indiqué sur le forum Jeedom comme solution @GCE :wink:

A tester !

On va regarder ça aujourd’hui !

2 « J'aime »

Comme je suis plutôt une quiche en PHP :woozy_face:, j’ai demandé a Professeur DeepSeek :rofl::

quelle est la différence entre ces deux lignes et sont elles compatibles avec debian 11 et debian 12 : $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = GCE_IPX800V5::get($urlGet, 1); à modifier en $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = $GCE_IPX800V5->get($urlGet, 1);

Sa réponse

Nous avons deux lignes de code à comparer :

Original :
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = GCE_IPX800V5::get($urlGet, 1);

Modifié :
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = $GCE_IPX800V5->get($urlGet, 1);

La différence est que la première utilise un appel statique à la méthode get de la classe GCE_IPX800V5 (avec :: ), tandis que la seconde utilise un appel de méthode sur l’objet $GCE_IPX800V5 (avec -> ).

Pour que la première ligne fonctionne, la méthode get doit être une méthode statique de la classe GCE_IPX800V5 . Pour la seconde, get doit être une méthode d’instance de l’objet $GCE_IPX800V5 .

Compatibilité avec Debian 11 et 12 :
Ces deux distributions supportent PHP (version 7.4 pour Debian 11 et 8.2 pour Debian 12 par défaut, mais cela peut varier selon les sources). La compatibilité dépend donc de la façon dont la classe GCE_IPX800V5 est définie.

Si la méthode get est définie comme statique, alors la première ligne est correcte. Si c’est une méthode d’instance, alors la seconde est correcte.

Il est important de noter que l’appel statique à une méthode qui n’est pas statique peut provoquer une erreur (dépending du contexte et de la version de PHP). De même, appeler une méthode statique via une instance (avec ->) est possible mais peut générer un warning si les standards stricts sont activés.

Pour la compatibilité avec Debian 11 et 12, il n’y a pas de problème inhérent à ces systèmes d’exploitation, car cela relève du code PHP et non du système.

Cependant, il est important de vérifier la définition de la classe GCE_IPX800V5 pour savoir si la méthode get est statique ou non.

Si la méthode est statique, les deux appels pourraient techniquement fonctionner, mais il est recommandé d’utiliser l’appel statique (::slight_smile: pour les méthodes statiques. Si la méthode n’est pas statique, alors il faut utiliser l’appel d’instance (->).

En résumé, la modification doit être faite en fonction de la nature de la méthode get dans la classe GCE_IPX800V5 .

Note : Les guillemets dans la ligne de code (‹ ip › et « ana » ) sont inhabituels en PHP (on utilise généralement des guillemets simples ou doubles standards). Assurez-vous que ces guillemets sont correctement interprétés par PHP. Si ce sont des guillemets typographiques, cela causera une erreur. Il faudrait les remplacer par des guillemets simples ou doubles ASCII.

Exemple corrigé pour les guillemets :
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = GCE_IPX800V5::get($urlGet, 1);
ou
$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = $GCE_IPX800V5->get($urlGet, 1);

Sans voir la classe, on ne peut pas dire laquelle est correcte, mais la modification demandée consiste à passer d’un appel statique à un appel d’instance.

Si la méthode get est une méthode d’instance, alors la modification est nécessaire pour que le code fonctionne.

La différence entre ces deux lignes réside dans la manière dont la méthode get est appelée :

  1. Première ligne : Utilise un appel statique via GCE_IPX800V5::get(...)
  2. Deuxième ligne : Utilise un appel d’instance via $GCE_IPX800V5->get(...)

Explication détaillée :

  • Appel statique (:: ) : Suppose que la méthode get est une méthode statique de la classe GCE_IPX800V5 . Il n’a pas besoin d’une instance de la classe pour être appelé.
  • Appel d’instance (-> ) : Suppose que $GCE_IPX800V5 est une instance de la classe, et que get est une méthode publique/protected de cette instance.

Compatibilité avec Debian 11 & 12 :

  • La compatibilité dépend de la définition de la classe GCE_IPX800V5 et non de la version de Debian.
  • Si la méthode get est définie comme statique (public static function get(...) ), la première ligne fonctionne.
  • Si la méthode get est une méthode d’instance (sans mot-clé static ), la deuxième ligne est correcte.
  • Les deux versions sont syntaxiquement valides en PHP, donc compatibles avec les versions de PHP fournies par Debian 11 (PHP 7.4) et Debian 12 (PHP 8.2).

Recommandation :

Vérifiez la définition de la méthode get dans la classe GCE_IPX800V5 :

  • Si elle est statique : conservez GCE_IPX800V5::get(...) .
  • Si elle est d’instance : utilisez $GCE_IPX800V5->get(...) .

:warning: Attention : Les guillemets ‹ › et « » dans votre code ne sont pas standards en PHP. Utilisez plutôt ' ou " pour éviter des erreurs de syntaxe. Exemple corrigé :

php

$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = $GCE_IPX800V5->get($urlGet, 1);

Puis je lui ai fourni de code de la classe

D’après le code de la classe fourni, je peux voir que la méthode get est définie comme une méthode d’instance (non statique) dans la classe GCE_IPX800V5 . En effet, on trouve dans la classe :

php

public function get($url, $opt) { // … le code de la méthode }

Cela signifie que la méthode doit être appelée sur une instance de la classe (objet) et non de manière statique.

Par conséquent, la modification à apporter est correcte : il faut remplacer l’appel statique GCE_IPX800V5::get(...) par l’appel d’instance $GCE_IPX800V5->get(...) .

Explication :

  • La première ligne utilise GCE_IPX800V5::get(...) qui est un appel statique. Cela fonctionnerait si la méthode get était déclarée comme public static function get(...) , mais ce n’est pas le cas.
  • La deuxième ligne utilise $GCE_IPX800V5->get(...) qui est un appel sur l’instance de l’objet, ce qui est correct puisque la méthode est une méthode d’instance.

Correction :

Il faut donc modifier la ligne :

php

$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = GCE_IPX800V5::get($urlGet, 1);

en :

php

$cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = $GCE_IPX800V5->get($urlGet, 1);

Remarque sur les guillemets :

Comme mentionné précédemment, les guillemets ‹ › et « » ne sont pas valides en PHP. Utilisez des guillemets simples ' ou doubles " standards.

Compatibilité avec Debian 11 et 12 :

Cette modification est indépendante de la version de Debian. Elle concerne uniquement la logique de programmation PHP. Les versions de PHP sur Debian 11 (PHP 7.4) et Debian 12 (PHP 8.2) supportent parfaitement les deux syntaxes, mais la bonne syntaxe à utiliser dépend de la définition de la méthode. Ici, la méthode étant une méthode d’instance, l’appel via l’instance est nécessaire.

D’après le code de la classe que vous avez fourni, la méthode get() est bien définie comme une méthode d’instance (non statique) :

php

public function get($url, $opt) { $return = array(); if ($opt != 1) $url .= ‹ &option=filter_id ›; $request_http = new com_http($url); try { $return = array_merge($return, is_json($request_http->exec(), array())); } catch (Exception $e) {} return $return; }

La différence entre les deux lignes :

  1. GCE_IPX800V5::get($urlGet, 1) : Appel statique de la méthode - INCORRECT dans ce contexte car la méthode n’est pas statique.
  2. $GCE_IPX800V5->get($urlGet, 1) : Appel via l’instance de l’objet - CORRECT car c’est une méthode d’instance.

Correction nécessaire :

Vous devez donc remplacer l’appel statique par l’appel d’instance :

php

// Ancienne version (incorrecte) : $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = GCE_IPX800V5::get($urlGet, 1); // Nouvelle version (correcte) : $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][‹ ana ›] = $GCE_IPX800V5->get($urlGet, 1);

Compatibilité avec Debian 11 & 12 :

  • Debian 11 (PHP 7.4) : :white_check_mark: Compatible
  • Debian 12 (PHP 8.2) : :white_check_mark: Compatible

Remarques supplémentaires :

  1. Erreur de guillemets : Dans votre code original, vous utilisez ‹ › et « » qui ne sont pas valides en PHP. Utilisez plutôt des guillemets simples ' ou doubles " standards.
  2. Ligne à corriger : La correction doit être appliquée à la ligne où vous récupérez les données analogiques ('ana' ), mais vérifiez aussi les autres appels similaires dans votre code (comme pour 'io' ).
  3. Optimisation : Pour éviter des appels API répétitifs, votre code utilise un système de cache ce qui est une bonne pratique.

Exemple corrigé complet :

php

// Pour ‹ io › if (!isset($cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« io »])) { $urlGet = ‹ http:// › . $GCE_IPX800V5->getConfiguration(‹ ip ›) . ‹ /api/core/io?ApiKey= › . $GCE_IPX800V5->getConfiguration(‹ apikey ›); $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« io »] = $GCE_IPX800V5->get($urlGet, 1); // Appel d’instance } // Pour ‹ ana › if (!isset($cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »])) { $urlGet = ‹ http:// › . $GCE_IPX800V5->getConfiguration(‹ ip ›) . ‹ /api/core/ana?ApiKey= › . $GCE_IPX800V5->getConfiguration(‹ apikey ›); $cache[$GCE_IPX800V5->getConfiguration(‹ ip ›)][« ana »] = $GCE_IPX800V5->get($urlGet, 1); // Appel d’instance }

je lui ai même demandé de reformater le code :

Code de la classe <?php /* * SUMMARY * Includes * Constantes * Preset Tab * Preset Tab IPX * Preset Tab OBJ * Preset Tab EXT * Type Data Tab * Type Data IPX * Type Data OBJ * Pwatch * Thermostat * Counter * Type Data EXT * X4VR * X4FP * X010V * X200 * X24D * X8D * X8R * XDIMMER * XDMX * XPWM * XTHL * X400 * Type Data VAR * FUNCTIONS * Name: event * Name: pull * Name: presetCmd_IPX * Name: presetCmd_EXT * Name: clearCmd * Name: postSave * Name: getIPX * Name: get * Name: put * Command Execute * Refresh * Command Param * IO Command * Ana Command */ require_once dirname(__FILE__) . '/../../../../core/php/core.inc.php'; class GCE_IPX800V5 extends eqLogic { /* Preset Tab IPX */ const PRESET_IPX = ['R_cmd', 'R_state', 'Din_state', 'Ain', 'Oout_cmd', 'Cin_cmd', 'Cin_state']; /* Preset Tab IPX v4 */ const PRESET_IPXV4 = ['V4_R_cmd', 'V4_R_state', 'V4_Din_state', 'V4_Ain_state']; /* Preset Tab OBJ */ const PRESET_OBJ = [ 'Pwatch' => ['Ping Watchdog', 32, 1, 0, ''], 'Thermo' => ['Thermostat', 16, 1, 0, ''], 'Count' => ['Counter', 64, 1, 0, ''] ]; /* Preset Tab EXT */ const PRESET_EXT = [ 'X4VR' => ['X4VR', 8, 4, 0, 'Canal'], 'X4FP' => ['X4FP', 4, 4, 1, 'Canal'], 'X010V' => ['X010V', 4, 4, 1, 'Canal'], 'X200' => ['X200', 2, 1, 0, ''], 'X24D' => ['X24D', 4, 24, 0, 'R'], 'X8D' => ['X8D', 4, 8, 0, 'R'], 'X8R' => ['X8R', 10, 8, 0, 'R'], 'XDIMMER' => ['XDIMMER', 6, 4, 1, 'Canal'], 'XPWM' => ['XPWM', 2, 12, 0, 'Canal'], 'XTHL' => ['XTHL', 16, 1, 0, ''], 'X400' => ['X400', 4, 4, 0, 'Canal'] ]; /* Type Data IPX */ const TYPE_DATA_IPX = [ 'R_cmd' => ['Relays Command', 8, 'action', 'other', 'R', '/api/system/ipx', 'ioRelays', 'ioRelays_id', 'IO'], 'R_state' => ['Relays State', 8, 'info', 'binary', 'R', '/api/system/ipx', 'ioRelayState', 'ioRelayState_id', 'IO'], 'Din_state' => ['Digital input', 8, 'info', 'binary', 'Din', '/api/system/ipx', 'ioDInput', 'ioDInput_id', 'IO'], 'Ain' => ['Analog input', 4, 'info', 'numeric', 'Ain', '/api/system/ipx', 'ana_IPX_Input', 'ana_IPX_Input', 'Ana'], 'Oout_cmd' => ['Sortie Optoisolé State', 4, 'info', 'binary', 'Cout', '/api/system/ipx', 'ioCollInput', 'ioCollInput_id', 'IO'], 'Cin_cmd' => ['Open collecteur Command', 4, 'action', 'other', 'Cin', '/api/system/ipx', 'ioCollOutput', 'ioCollOutput_id', 'IO'], 'Cin_state' => ['Open collecteur State', 4, 'info', 'binary', 'Cin', '/api/system/ipx', 'ioCollOutputState', 'ioCollOutputState_id', 'IO'] ]; /* Type Data IPX800 V4 */ const TYPE_DATA_IPXV4 = [ 'V4_R_cmd' => ['V4 Relay command', 8, 'action', 'other', 'IPX800V4', '/api/plugin/ipx800v4', '', 'ioRelays_id', 'IO'], 'V4_R_state' => ['V4 Relay state', 8, 'info', 'binary', 'IPX800V4', '/api/plugin/ipx800v4', '', 'ioRelays_id', 'IO'], 'V4_Din_state'=> ['V4 Digital input', 8, 'info', 'binary', 'IPX800V4', '/api/plugin/ipx800v4', '', 'ioDInput_id', 'IO'], 'V4_Ain_state'=> ['V4 Analog input', 4, 'info', 'numeric', 'IPX800V4', '/api/plugin/ipx800v4', '', 'anaInput_id', 'Ana'] ]; /* Type Data OBJ */ const TYPE_DATA_OBJ = [ /* Pwatch */ 'Pwatch_cmd' => ['Ping Watchdog command', 32, 'action', 'other', 'Pwatch', '/api/object/pingwd', '', 'ioInput_id', 'IO', 1], 'Pwatch_state' => ['Ping Watchdog state', 32, 'info', 'binary', 'Pwatch', '/api/object/pingwd', '', 'ioFault_id', 'IO', 1], /* Thermostat */ 'Thermo_state' => ['Thermostat state', 16, 'info', 'binary', 'Thermo', '/api/object/thermostat', '', 'ioOutput_id', 'IO', 1], 'Thermo_cmd' => ['Thermostat command', 16, 'action', 'other', 'Thermo', '/api/object/thermostat', '', 'ioOnOff_id', 'IO', 1], 'Thermo_com' => ['Thermostat Comfort', 16, 'action', 'other', 'Thermo', '/api/object/thermostat', '', 'ioComfort_id', 'IO', 1], 'Thermo_eco' => ['Thermostat Eco', 16, 'action', 'other', 'Thermo', '/api/object/thermostat', '', 'ioEco_id', 'IO', 1], 'Thermo_fre' => ['Thermostat Anti Freeze', 16, 'action', 'other', 'Thermo', '/api/object/thermostat', '', 'ioNoFrost_id', 'IO', 1], 'Thermo_set' => ['Thermostat Set command', 16, 'action', 'slider', 'Thermo', '/api/object/thermostat', '', 'anaCurrSetPoint_id', 'Ana', 1], 'Thermo_mea' => ['Thermostat Measure', 16, 'info', 'numeric', 'Thermo', '/api/object/thermostat', '', 'anaMeasure_id', 'Ana', 1], 'Thermo_fau' => ['Thermostat Fault', 16, 'info', 'binary', 'Thermo', '/api/object/thermostat', '', 'ioFault_id', 'IO', 1], /* Counter */ 'Count_add' => ['Counter Plus', 64, 'action', 'other', 'Count', '/api/object/counter', '', 'ioAdd_id', 'IO', 1], 'Count_sub' => ['Counter Minus', 64, 'action', 'other', 'Count', '/api/object/counter', '', 'ioSub_id', 'IO', 1], 'Count_set_cmd' => ['Counter Set', 64, 'action', 'other', 'Count', '/api/object/counter', '', 'ioSet_id', 'IO', 1], 'Count_reset' => ['Counter Reset', 64, 'action', 'other', 'Count', '/api/object/counter', '', 'ioReset_id', 'IO', 1], 'Count_pace' => ['Counter Pace', 64, 'action', 'slider', 'Count', '/api/object/counter', '', 'anaPulseValue_id', 'Ana', 1], 'Count_set_ana' => ['Counter Set Analog', 64, 'action', 'slider', 'Count', '/api/object/counter', '', 'anaSetValue_id', 'Ana', 1], 'Count_ana_state'=> ['Counter Analog State', 64, 'info', 'numeric', 'Count', '/api/object/counter', '', 'anaOut_id', 'Ana', 1] ]; /* Type Data EXT */ const TYPE_DATA_EXT = [ /* X4VR */ 'X4vr_up' => ['X4vr Up command', 8, 'action', 'other', 'X4VR', '/api/ebx/x4vr', '', 'ioCommandUp_id', 'IO', 4], 'X4vr_down' => ['X4vr Down command', 8, 'action', 'other', 'X4VR', '/api/ebx/x4vr', '', 'ioCommandDown_id', 'IO', 4], 'X4vr_stop' => ['X4vr Stop Command', 8, 'action', 'other', 'X4VR', '/api/ebx/x4vr', '', 'ioCommandStop_id', 'IO', 4], 'X4vr_B_up' => ['X4vr BSO_Up command', 8, 'action', 'other', 'X4VR', '/api/ebx/x4vr', '', 'ioCommandBsoUp_id', 'IO', 4], 'X4vr_B_down' => ['X4vr BSO_Down command', 8, 'action', 'other', 'X4VR', '/api/ebx/x4vr', '', 'ioCommandBsoDown_id', 'IO', 4], 'X4vr_a_cmd' => ['X4vr Ana command', 8, 'action', 'slider', 'X4VR', '/api/ebx/x4vr', '', 'anaCommand_id', 'Ana', 4], 'X4vr_a_state' => ['X4vr Ana state', 8, 'info', 'numeric', 'X4VR', '/api/ebx/x4vr', '', 'anaPosition_id', 'Ana', 4], /* X4FP */ 'X4fp_com' => ['X4fp Comfort command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllComfort_id', 'ioComfort_id', 'IO', 4], 'X4fp_eco' => ['X4fp Eco command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllEco_id', 'ioEco_id', 'IO', 4], 'X4fp_fre' => ['X4fp AntiFreeze Command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllAntiFreeze_id', 'ioAntiFreeze_id', 'IO', 4], 'X4fp_com1' => ['X4fp Comfort1 command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllStop_id', 'ioComfort_1_id', 'IO', 4], 'X4fp_com2' => ['X4fp Comfort2 Command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllComfort_1_id', 'ioComfort_2_id', 'IO', 4], 'X4fp_stop' => ['X4fp stop command', 4, 'action', 'other', 'X4FP', '/api/ebx/x4fp', 'ioAllComfort_2_id', 'ioStop_id', 'IO', 4], /* X010V */ 'X010v_on' => ['X010v on', 4, 'action', 'other', 'X010V', '/api/ebx/x010v', 'ioOnAll_id', 'ioOn_id', 'IO', 4], 'X010v_a_cmd' => ['X010v Analog command', 4, 'action', 'slider', 'X010V', '/api/ebx/x010v', '', 'anaCommand_id', 'Ana', 4], 'X010v_a_state' => ['X010v Analog State', 4, 'info', 'numeric', 'X010V', '/api/ebx/x010v', '', 'anaLevel_id', 'Ana', 4], /* X200 */ 'X200_ph' => ['X200 PH State', 2, 'info', 'numeric', 'X200', '/api/ebx/x200', '', 'anaPhVal_id', 'Ana', 1], 'X200_orp' => ['X200 ORP State', 2, 'info', 'numeric', 'X200', '/api/ebx/x200', '', 'anaOrpVal_id', 'Ana', 1], /* X24D */ 'X24D_in' => ['X24D relay State', 4, 'info', 'binary', 'X24D', '/api/ebx/x24d', '', 'ioInput_id', 'IO', 24], /* X8D */ 'X8D_in' => ['X8D relay State', 4, 'info', 'binary', 'X8D', '/api/ebx/x8d', '', 'ioInput_id', 'IO', 8], /* X8R */ 'X8R_out_cmd' => ['X8R relay Command', 10, 'action', 'other', 'X8R', '/api/ebx/x8r', '', 'ioOutput_id', 'IO', 8], 'X8R_out_state' => ['X8R relay State', 10, 'info', 'binary', 'X8R', '/api/ebx/x8r', '', 'ioOutputState_id', 'IO', 8], 'X8R_long_state'=> ['X8R Long push State', 10, 'info', 'binary', 'X8R', '/api/ebx/x8r', '', 'ioLongPush_id', 'IO', 8], /* XDIMMER */ 'XDIMMER_on_cmd' => ['XDIMMER relay Command', 6, 'action', 'other', 'XDIMMER', '/api/ebx/xdimmer', 'ioOnAll_id', 'ioOn_id', 'IO', 4], 'XDIMMER_on_state' => ['XDIMMER relay State', 6, 'info', 'binary', 'XDIMMER', '/api/ebx/xdimmer', 'ioOnAll_id', 'ioOn_id', 'IO', 4], 'XDIMMER_a_cmd' => ['XDIMMER Analog Command', 6, 'action', 'slider', 'XDIMMER', '/api/ebx/xdimmer', '', 'anaCommand_id', 'Ana', 4], 'XDIMMER_a_state' => ['XDIMMER Analog State', 6, 'info', 'numeric', 'XDIMMER', '/api/ebx/xdimmer', '', 'anaPosition_id', 'Ana', 4], 'XDIMMER_speed' => ['XDIMMER Speed Transition', 6, 'action', 'slider', 'XDIMMER', '/api/ebx/xdimmer', '', 'anaSpeedTransition_id', 'Ana', 1], /* XPWM */ 'XPWM_cmd' => ['XPWM Command', 2, 'action', 'slider', 'XPWM', '/api/ebx/xpwm', '', 'anaCommand_id', 'Ana', 12], 'XPWM_speed' => ['XPWM Speed Transition', 2, 'action', 'slider', 'XPWM', '/api/ebx/xpwm', '', 'anaSpeedTransition_id', 'Ana', 1], /* XTHL */ 'XTHL_temp' => ['XTHL Temperature', 16, 'info', 'numeric', 'XTHL', '/api/ebx/xthl', '', 'anaTemp_id', 'Ana', 1], 'XTHL_hum' => ['XTHL Humidity', 16, 'info', 'numeric', 'XTHL', '/api/ebx/xthl', '', 'anaHum_id', 'Ana', 1], 'XTHL_lum' => ['XTHL Luminosite', 16, 'info', 'numeric', 'XTHL', '/api/ebx/xthl', '', 'anaLum_id', 'Ana', 1], /* X400 */ 'X400_state' => ['X400 State', 4, 'info', 'numeric', 'X400', '/api/ebx/x400', '', 'anaOutputVal_id', 'Ana', 4] ]; /* Type Data VAR */ const TYPE_DATA_VAR = [ 'IO_cmd' => ['Analog value Command', 0, 'action', 'other', 'IO', '/api/core/io', '', '', 'IO'], 'IO_state' => ['Analog value State', 0, 'info', 'binary', 'IO', '/api/core/io', '', '', 'IO'], 'Ana_cmd' => ['Analog value Command', 0, 'action', 'other', 'Ana', '/api/core/ana', '', '', 'Ana'], 'Ana_state' => ['Analog value State', 0, 'info', 'numeric', 'Ana', '/api/core/ana', '', '', 'Ana'] ]; const DATA_UNITAIRE_REGEX = '/^([A-Z]+)(\d{1,3})$/'; private static $_eqLogics = null; /* FUNCTIONS */ public static function event() { if (init('onvent') == 1) { $cache = []; foreach (self::searchConfiguration('"ip":"' . init('ip') . '"', 'GCE_IPX800V5') as $GCE_IPX800V5) { if (!isset($cache[$GCE_IPX800V5->getConfiguration('ip')])) { $cache[$GCE_IPX800V5->getConfiguration('ip')] = $GCE_IPX800V5->getIPX(); } self::pull($GCE_IPX800V5->getId(), $cache); } return; } $cmd = self::byId(init('id')); if (!is_object($cmd) || $cmd->getEqType() != 'GCE_IPX800V5') { throw new Exception(__('Commande ID GCE_IPX800V5 inconnue, ou la commande n\'est pas de type GCE_IPX800V5 : ', __FILE__) . init('id') . ', Valeur: ' . init('value')); } $cmd->event(init('value')); } public static function deamon_info() { $return = ['log' => '', 'state' => 'nok', 'launchable' => 'ok']; $cron = cron::byClassAndFunction('GCE_IPX800V5', 'pull'); if (is_object($cron) && $cron->running()) { $return['state'] = 'ok'; } return $return; } public static function deamon_start() { self::deamon_stop(); $deamon_info = self::deamon_info(); if ($deamon_info['launchable'] != 'ok') { throw new Exception(__('Veuillez vérifier la configuration', __FILE__)); } $cron = cron::byClassAndFunction('GCE_IPX800V5', 'pull'); if (!is_object($cron)) { throw new Exception(__('Tâche cron introuvable', __FILE__)); } $cron->setDeamonSleepTime(config::byKey('api::frequency', 'GCE_IPX800V5', 1)); $cron->save(); $cron->run(); } public static function deamon_stop() { $cron = cron::byClassAndFunction('GCE_IPX800V5', 'pull'); if (!is_object($cron)) { throw new Exception(__('Tâche cron introuvable', __FILE__)); } $cron->halt(); } public static function deamon_changeAutoMode($_mode) { $cron = cron::byClassAndFunction('GCE_IPX800V5', 'pull'); if (!is_object($cron)) { throw new Exception(__('Tâche cron introuvable', __FILE__)); } $cron->setEnable($_mode); $cron->save(); } public static function cronDaily() {} public static function pull($_eqLogic_id = null) { if (self::$_eqLogics == null) { self::$_eqLogics = self::byType('GCE_IPX800V5', true); } else { self::$_eqLogics = self::byType('GCE_IPX800V5', true); } $cache = []; foreach (self::$_eqLogics as $GCE_IPX800V5) { foreach ($GCE_IPX800V5->getCmd('info') as $cmd) { $arg = ($cmd->getConfiguration('infoType')) ? $cmd->getConfiguration('infoType') : $cmd->getConfiguration('actionArgument'); $id = $cmd->getConfiguration('infoParameter' . $arg); if ($id == '') { continue; } switch ($arg) { case 'IO': if (!isset($cache[$GCE_IPX800V5->getConfiguration('ip')]["io"])) { $urlGet = 'http://' . $GCE_IPX800V5->getConfiguration('ip') . '/api/core/io?ApiKey=' . $GCE_IPX800V5->getConfiguration('apikey'); $cache[$GCE_IPX800V5->getConfiguration('ip')]["io"] = $GCE_IPX800V5->get($urlGet, 1); } foreach ($cache[$GCE_IPX800V5->getConfiguration('ip')]["io"] as $io) { if ($id == $io["_id"]) { $GCE_IPX800V5->checkAndUpdateCmd($cmd, $io["on"], false); break; } } break; case 'Ana': if (!isset($cache[$GCE_IPX800V5->getConfiguration('ip')]["ana"])) { $urlGet = 'http://' . $GCE_IPX800V5->getConfiguration('ip') . '/api/core/ana?ApiKey=' . $GCE_IPX800V5->getConfiguration('apikey'); $cache[$GCE_IPX800V5->getConfiguration('ip')]["ana"] = $GCE_IPX800V5->get($urlGet, 1); } foreach ($cache[$GCE_IPX800V5->getConfiguration('ip')]["ana"] as $ana) { if ($id == $ana["_id"]) { $GCE_IPX800V5->checkAndUpdateCmd($cmd, $ana["value"], false); break; } } break; } } } } public function presetCmd_IPX($name, $nb, $type, $subType, $action, $api, $key, $key_id, $cmdType) { if ($this->getConfiguration($name) == 1) { $urlGet = 'http://' . $this->getConfiguration('ip') . $api . '?ApiKey=' . $this->getConfiguration('apikey'); $obj = $this->get($urlGet, 0); for ($i = 1; $i <= $nb; $i++) { $id = $obj[$key_id][$i - 1]; if ($id) { if ($cmdType == "IO") { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/io/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } else { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/ana/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } $dispName = $this->get($urlGet, 0)["name"]; $cmd = $this->getCmd(null, $name . '_' . $i); if (!is_object($cmd)) { $cmd = new GCE_IPX800V5Cmd(); } $cmd->setName(__($dispName . '_' . $i, __FILE__)); $cmd->setEqLogic_id($this->getId()); $cmd->setLogicalId($name . '_' . $i); $cmd->setConfiguration('actionArgument', $cmdType); if ($type == "action") { $cmd->setConfiguration('actionParameter' . $cmdType, $id); } else { $cmd->setConfiguration('infoType', $cmdType); $cmd->setConfiguration('infoParameter' . $cmdType, $id); } $cmd->setType($type); $cmd->setSubType($subType); $cmd->save(); } else { $cmd = $this->getCmd(null, $name . '_' . $i); if (is_object($cmd)) { $cmd->remove(); } } } } else { for ($i = 1; $i <= $nb; $i++) { $cmd = $this->getCmd(null, $name . '_' . $i); if (is_object($cmd)) { $cmd->remove(); } } } } public function presetCmd_IPXV4($name, $nb, $type, $subType, $action, $api, $key, $key_id, $cmdType) { for ($i = 0; $i < 4; $i++) { if ($this->getConfiguration("V4" . $i) == 1) { $urlGet = 'http://' . $this->getConfiguration('ip') . $api . '?ApiKey=' . $this->getConfiguration('apikey'); $obj = $this->get($urlGet, 0); if ($this->getConfiguration("V4" . $i . $name) == 1) { for ($j = 1; $j <= $nb; $j++) { $id = $obj[$i][$key_id][$j - 1]; if ($id) { if ($cmdType == "IO") { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/io/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } else { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/ana/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } $dispName = $this->get($urlGet, 0)["name"]; if ($type == "info") { $dispName .= "_state"; } $cmd = $this->getCmd(null, $name . '_' . $i . '_' . $j); if (!is_object($cmd)) { $cmd = new GCE_IPX800V5Cmd(); } $cmd->setName(__($dispName . '_' . $i . '_' . $j, __FILE__)); $cmd->setEqLogic_id($this->getId()); $cmd->setLogicalId($name . '_' . $i . '_' . $j); $cmd->setConfiguration('actionArgument', $cmdType); if ($type == "action") { $cmd->setConfiguration('actionParameter' . $cmdType, $id); } else { $cmd->setConfiguration('infoType', $cmdType); $cmd->setConfiguration('infoParameter' . $cmdType, $id); } $cmd->setType($type); $cmd->setSubType($subType); $cmd->save(); } else { $cmd = $this->getCmd(null, $name . '_' . $i . '_' . $j); if (is_object($cmd)) { $cmd->remove(); } } } } else { for ($j = 1; $j <= $nb; $j++) { $cmd = $this->getCmd(null, $name . '_' . $i . '_' . $j); if (is_object($cmd)) { $cmd->remove(); } } } } else { for ($j = 1; $j <= $nb; $j++) { $cmd = $this->getCmd(null, $name . '_' . $i . '_' . $j); if (is_object($cmd)) { $cmd->remove(); } } } } } public function presetCmd_EXT($name, $nb, $type, $subType, $action, $api, $key_All, $key_id, $cmdType, $canal) { if ($this->getConfiguration($action) == 1) { $urlGet = 'http://' . $this->getConfiguration('ip') . $api . '?ApiKey=' . $this->getConfiguration('apikey'); $obj = $this->get($urlGet, 0); for ($i = 0; $i < $nb; $i++) { if ($this->getConfiguration($action . $i) == 1) { for ($j = 0; $j < $canal; $j++) { if ($this->getConfiguration('Canal' . $action . $i . '_' . $j) == 1 || $canal == 1) { if ($canal > 1) { $id = $obj[$i][$key_id][$j]; } else { $id = $obj[$i][$key_id]; } if ($id) { if ($cmdType == "IO") { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/io/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } else { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/ana/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } $dispName = $this->get($urlGet, 0)["name"]; if ($type == "info") { $dispName .= "_state"; } $cmd = $this->getCmd(null, $name . $i . '_' . $j); if (!is_object($cmd)) { $cmd = new GCE_IPX800V5Cmd(); } $cmd->setName(__($dispName . '_' . $j, __FILE__)); $cmd->setEqLogic_id($this->getId()); $cmd->setLogicalId($name . $i . '_' . $j); $cmd->setType($type); $cmd->setSubType($subType); $cmd->setConfiguration('actionArgument', $cmdType); if ($type == "action") { if ($cmdType == "IO") { $cmd->setConfiguration('actionTypeCmd' . $cmdType, "toggle"); } $cmd->setConfiguration('actionParameter' . $cmdType, $id); } else { $cmd->setConfiguration('infoType', $cmdType); $cmd->setConfiguration('infoParameter' . $cmdType, $id); } $cmd->save(); } else { $this->clearCmd($name, $i, $j); } } else { $this->clearCmd($name, $i, $j); } } if ($this->getConfiguration('Canal' . $action . $i . '_All') == 1 && $key_All != '') { $id = $obj[$i][$key_All]; if ($id) { if ($cmdType == "IO") { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/io/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } else { $urlGet = 'http://' . $this->getConfiguration('ip') . '/api/core/ana/' . $id . '?ApiKey=' . $this->getConfiguration('apikey'); } $dispName = $this->get($urlGet, 0)["name"]; if ($type == "info") { $dispName .= "_state"; } $cmd = $this->getCmd(null, $name . $i . '_All'); if (!is_object($cmd)) { $cmd = new GCE_IPX800V5Cmd(); } $cmd->setName(__($dispName . '_All', __FILE__)); $cmd->setEqLogic_id($this->getId()); $cmd->setLogicalId($name . $i . '_All'); $cmd->setType($type); $cmd->setSubType($subType); $cmd->setConfiguration('actionArgument', $cmdType); if ($type == "action") { if ($cmdType == "IO") { $cmd->setConfiguration('actionTypeCmd' . $cmdType, "toggle"); } $cmd->setConfiguration('actionParameter' . $cmdType, $id); } else { $cmd->setConfiguration('infoType', $cmdType); $cmd->setConfiguration('infoParameter' . $cmdType, $id); } $cmd->save(); } else { $this->clearCmd($name, $i, -2); } } else { $this->clearCmd($name, $i, -2); } } else { for ($j = 0; $j < $canal; $j++) { $this->clearCmd($name, $i, $j); } $this->clearCmd($name, $i, -2); } } } else { for ($i = 0; $i < $nb; $i++) { for ($j = 0; $j < $canal; $j++) { $this->clearCmd($name, $i, $j); } $this->clearCmd($name, $i, -2); } } } public function clearCmd($name, $nb, $canal) { if ($canal >= 0) { $cmd = $this->getCmd(null, $name . $nb . '_' . $canal); } elseif ($canal == -2) { $cmd = $this->getCmd(null, $name . $nb . '_All'); } else { $cmd = $this->getCmd(null, $name . '_' . $nb); } if (is_object($cmd)) { $cmd->remove(); } } public function postSave() { $refresh = $this->getCmd(null, 'refresh'); if (!is_object($refresh)) { $refresh = new GCE_IPX800V5Cmd(); } $refresh->setName(__('Rafraîchir', __FILE__)); $refresh->setEqLogic_id($this->getId()); $refresh->setLogicalId('refresh'); $refresh->setType('action'); $refresh->setSubType('other'); $refresh->save(); foreach (self::TYPE_DATA_IPX as $key => $value) { $this->presetCmd_IPX($key, $value[1], $value[2], $value[3], $value[4], $value[5], $value[6], $value[7], $value[8]); } foreach (self::TYPE_DATA_IPXV4 as $key => $value) { $this->presetCmd_IPXV4($key, $value[1], $value[2], $value[3], $value[4], $value[5], $value[6], $value[7], $value[8]); } foreach (self::TYPE_DATA_EXT as $key => $value) { $this->presetCmd_EXT($key, $value[1], $value[2], $value[3], $value[4], $value[5], $value[6], $value[7], $value[8], $value[9]); } foreach (self::TYPE_DATA_OBJ as $key => $value) { $this->presetCmd_EXT($key, $value[1], $value[2], $value[3], $value[4], $value[5], $value[6], $value[7], $value[8], $value[9]); } } public function getIPX($opt = null) { $return = []; $url = 'http://' . $this->getConfiguration('ip') . '/api/system/ipx?ApiKey=' . $this->getConfiguration('apikey'); if ($opt != 1) { $url .= '&option=filter_id'; } $request_http = new com_http($url); try { $return = array_merge($return, is_json($request_http->exec(), [])); } catch (Exception $e) {} return $return; } public function get($url, $opt) { $return = []; if ($opt != 1) { $url .= '&option=filter_id'; } $request_http = new com_http($url); try { $return = array_merge($return, is_json($request_http->exec(), [])); } catch (Exception $e) {} return $return; } public function put($url, $data) { $curl = curl_init($url); $headers = [ "X-CSRFToken: " . $csrfToken, "Referer: http://" . $this->getConfiguration('ip'), "Content-Type: application/json" ]; curl_setopt($curl, CURLOPT_URL, $url); curl_setopt($curl, CURLOPT_CUSTOMREQUEST, "PUT"); curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); curl_setopt($curl, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1); curl_setopt($curl, CURLOPT_HTTPHEADER, $headers); curl_setopt($curl, CURLOPT_POSTFIELDS, $data); $resp = curl_exec($curl); curl_close($curl); return $resp; } } class GCE_IPX800V5Cmd extends cmd { public function execute($_options = []) { $eqLogic = $this->getEqLogic(); /* Refresh */ if ($this->getLogicalId() == 'refresh') { GCE_IPX800V5::pull($this->getEqLogic_Id()); return; } /* Command Param */ $act = $this->getConfiguration('actionArgument'); $id = $this->getConfiguration('actionParameter' . $act); $subType = $this->getSubType(); /* IO Command */ if ($act == "IO") { $actCmd = $this->getConfiguration('actionTypeCmd' . $act); switch ($actCmd) { case 'toggle': $req = json_encode(['toggle' => true]); break; case 'setOn': $req = json_encode(['on' => true]); break; case 'setOff': $req = json_encode(['on' => false]); break; } $urlPut = 'http://' . $eqLogic->getConfiguration('ip') . '/api/core/io/' . $id . '?ApiKey=' . $eqLogic->getConfiguration('apikey'); $request_http = $eqLogic->put($urlPut, $req); return; } /* Ana Command */ if ($act == "Ana") { $urlPut = 'http://' . $eqLogic->getConfiguration('ip') . '/api/core/ana/' . $id . '?ApiKey=' . $eqLogic->getConfiguration('apikey'); if ($subType == "other") { $body = json_encode(['value' => intval($this->getConfiguration('actionOption' . $act))]); } elseif ($subType == "slider") { $body = json_encode(['value' => intval($_options["slider"])]); } $request_http = $eqLogic->put($urlPut, $body); return; } GCE_IPX800V5::pull($this->getEqLogic_Id()); usleep(10000); } } ?>

Principales améliorations apportées :

Indentation cohérente avec 4 espaces

Organisation des constantes en tableaux plus lisibles

Ajout de commentaires pour séparer les sections

Formatage cohérent des tableaux et structures de contrôle

Suppression des guillemets non standard

Uniformisation de la syntaxe des tableaux ([] au lieu de array())

Amélioration de la lisibilité des longues listes de paramètres

Correction des appels de méthode statique/instance

Cette version reste totalement fonctionnelle et est compatible avec Debian 11 et 12.

A tester …ou détester ! :rofl:

Voila si cela peut aider le scmilililblick !!! :wink:

Bonjour,

Pour les geek voici le fichier corrigé. SI quelqu’un veux bien valider avant que je pousse sur le git ce serait bien :slight_smile: Merci

core.zip (33,3 Ko)

1 « J'aime »

Au final c’est dispo sur le store de Jeedom sur la branche béta.

On attend les retours des utilisateurs pour passer en stable.

Chez nous ça fonctionne; je ne suis pas assez expert Jeedom pour aller plus loin dans le test.

cdt

2 « J'aime »

Bonjour,

J’ai transféré mon jeedom sur Debian 12 pour l’occasion et … Ca fonctionne parfaitement, un grand merci à vous !

1 « J'aime »

Merci pour l’info :slight_smile: c’était pas grand chose au final.

Bonjour,

Pour le coup, est-ce qu’une mise à jour du plugin IPX800-V5 est envisagée ?

Excellente journée à toutes et tous.