Enphase - Envoy - Script - Json Node-Red

Merci.
J’ai trouvé. Je ne comprenais pas comment le scénario mettait à jour les données dans le virtuel.
C’est la donnée « Commande » de l’action du scénario qui précise où doit aller le résultat.
Cela marche maintenant. Il me reste à personnaliser le code.

@matth1 Je vois dans ton post un tableau avec toutes les variables créées. Peux tu me précisé si c’est un affichage Jeedom et si oui où puis je le trouver.

Je suis vraiment désolé de vous déranger avec mes questions basiques, mais il y a tellement d’informations sur Jeedom qu’il est difficile de trouver une réponse à une question aussi simple.

SAlut à tous,
Quelqu’un a réussi à récupérer les trames http://IP_envoy/stream/meter ?

Sous Node red, j’arrive à faire l’authentification avec http://IP_envoy/installer/setup/home

Par contre, je ne sais pas récupérer le flux, je n’ai rien en résultat.

Voilà, je sèche :joy:

bonjour, @Manumdk

Intéressant a y réfléchir si c’est un flux c’est peut-être pas une connexion avec une méthode get …
(j’en sais pas plus)
mais dit moi je voir que tu utilise un username installer le mot de passe qui va avec correspond a quelque cohse en rapport avec l’ID de la passerelle ?

bonne journée

1 « J'aime »

Salut @olive,
Je suis parti de ce post : https://thecomputerperson.wordpress.com/2016/08/03/enphase-envoy-s-data-scraping/#comment-5838, déjà évoqué ici, pour pouvoir récupérer les trames le flux /stream/meter.

Dans le post, tu as un utilitaire android qui te permet qui te génère un mot de passe pour le compte installer en fonction du N° série de ta Envoy.

Manu

Merci je vais aller voir ça.

il faudrait essayer ce module, avec ce fix, mais je n’y arrive pas :slight_smile:
EDIT: en fait ca marche pour le premier paquet puis fail

1 « J'aime »

Salut à tous,
J’ai bien avancé dans ma recherche de récupération des données via le stream.
Sous node-red, j’ai trouvé un exemple qui marche, je n’ai rien inventé :wink:
Envoy-Stream

[{"id":"990e535c.6c9aa","type":"tab","label":"Envoy-Stream","disabled":false,"info":""},{"id":"830c8b80.f89718","type":"inject","z":"990e535c.6c9aa","name":"Start / Restart / Unpause stream","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"3600","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":250,"y":180,"wires":[["aab7d19.38676b"]]},{"id":"de79afb2.f459b","type":"inject","z":"990e535c.6c9aa","name":"Pause stream","repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":190,"y":300,"wires":[["31c2c1a4.b6aabe"]]},{"id":"3e4f28c7.35f5c8","type":"debug","z":"990e535c.6c9aa","name":"Display event","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","x":870,"y":280,"wires":[]},{"id":"31c2c1a4.b6aabe","type":"change","z":"990e535c.6c9aa","name":"","rules":[{"t":"set","p":"pause","pt":"msg","to":"true","tot":"bool"}],"action":"","property":"","from":"","to":"","reg":false,"x":400,"y":300,"wires":[["50364aa0.f4b3d4"]]},{"id":"fc7709e7.f95788","type":"inject","z":"990e535c.6c9aa","name":"Stop stream","props":[{"p":"payload","v":"","vt":"date"},{"p":"topic","v":"","vt":"string"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":190,"y":260,"wires":[["fc633663.b0ce48"]]},{"id":"fc633663.b0ce48","type":"change","z":"990e535c.6c9aa","name":"","rules":[{"t":"set","p":"stop","pt":"msg","to":"true","tot":"bool"}],"action":"","property":"","from":"","to":"","reg":false,"x":390,"y":260,"wires":[["50364aa0.f4b3d4"]]},{"id":"5e0c1620.061b18","type":"function","z":"990e535c.6c9aa","name":"Set Cookie","func":"msg.headers = {'Cookie': 'sessionId=' + msg.responseCookies.sessionId.value};\nreturn msg;\n","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":690,"y":180,"wires":[["50364aa0.f4b3d4"]]},{"id":"50364aa0.f4b3d4","type":"sse-client","z":"990e535c.6c9aa","name":"","url":"http://192.168.1.179/stream/meter","events":["message"],"headers":{},"proxy":"","restart":true,"rejectUnauthorized":false,"withCredentials":true,"timeout":"10","x":680,"y":280,"wires":[["3e4f28c7.35f5c8"]]},{"id":"aab7d19.38676b","type":"http request","z":"990e535c.6c9aa","name":"","method":"GET","ret":"txt","paytoqs":"ignore","url":"http://192.168.1.179/installer/setup/home","tls":"","persist":false,"proxy":"","authType":"digest","x":490,"y":180,"wires":[["5e0c1620.061b18"]]}]

Il vous suffit de renseigner votre IP sur http request avec votre user installer et son password ainsi que dans le SSE-Client.

Je ferais une flow avec l’export en mqtt par la suite.

A+

bonsoir @Manumdk
peut tu detailler un peu plus ou faire des captures d 'ecran voir ce que cela donne
cdt

Voilà le flow :

Le json reçu toutes les secondes

{
	"production": {
		"ph-a": {
			"p": 1362.265,
			"q": 154.081,
			"s": 1367.864,
			"v": 235.775,
			"i": 5.803,
			"pf": 0.99,
			"f": 50.0
		},
		"ph-b": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		},
		"ph-c": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		}
	},
	"net-consumption": {
		"ph-a": {
			"p": 2358.498,
			"q": -390.764,
			"s": 2445.46,
			"v": 235.822,
			"i": 10.358,
			"pf": 0.96,
			"f": 50.0
		},
		"ph-b": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		},
		"ph-c": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		}
	},
	"total-consumption": {
		"ph-a": {
			"p": 3720.762,
			"q": -544.845,
			"s": 3810.641,
			"v": 235.798,
			"i": 16.161,
			"pf": 0.98,
			"f": 50.0
		},
		"ph-b": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		},
		"ph-c": {
			"p": 0.0,
			"q": 0.0,
			"s": 0.0,
			"v": 0.0,
			"i": 0.0,
			"pf": 0.0,
			"f": 0.0
		}
	}
}
2 « J'aime »

Si quelqu’un sait extraire d’un Json les clés suivantes :

"production": {
		"ph-a": {
			"p"

"net-consumption": {
		"ph-a": {
			"p":

"total-consumption": {
		"ph-a": {
			"p":

Je suis preneur :wink:

Mon but est d’envoyer ces valeurs toutes les secondes en mqtt à mon routeurPV qui gérera l’ECS.

bonsoir,

en php tu a la fonction json_decode

https://www.php.net/manual/fr/function.json-decode.php

et en node red tu a des exemples dans le sujet aussi

bonne soirée

Voilà,
Mon flow est fonctionnel

[{"id":"990e535c.6c9aa","type":"tab","label":"Envoy-Stream","disabled":false,"info":""},{"id":"830c8b80.f89718","type":"inject","z":"990e535c.6c9aa","name":"Start / Restart / Unpause stream","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"3600","crontab":"","once":true,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":250,"y":180,"wires":[["aab7d19.38676b"]]},{"id":"de79afb2.f459b","type":"inject","z":"990e535c.6c9aa","name":"Pause stream","repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":190,"y":300,"wires":[["31c2c1a4.b6aabe"]]},{"id":"31c2c1a4.b6aabe","type":"change","z":"990e535c.6c9aa","name":"","rules":[{"t":"set","p":"pause","pt":"msg","to":"true","tot":"bool"}],"action":"","property":"","from":"","to":"","reg":false,"x":400,"y":300,"wires":[["50364aa0.f4b3d4"]]},{"id":"fc7709e7.f95788","type":"inject","z":"990e535c.6c9aa","name":"Stop stream","props":[{"p":"payload","v":"","vt":"date"},{"p":"topic","v":"","vt":"string"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":190,"y":260,"wires":[["fc633663.b0ce48"]]},{"id":"fc633663.b0ce48","type":"change","z":"990e535c.6c9aa","name":"","rules":[{"t":"set","p":"stop","pt":"msg","to":"true","tot":"bool"}],"action":"","property":"","from":"","to":"","reg":false,"x":410,"y":260,"wires":[["50364aa0.f4b3d4"]]},{"id":"5e0c1620.061b18","type":"function","z":"990e535c.6c9aa","name":"Set Cookie","func":"msg.headers = {'Cookie': 'sessionId=' + msg.responseCookies.sessionId.value};\nreturn msg;\n","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":670,"y":180,"wires":[["50364aa0.f4b3d4"]]},{"id":"50364aa0.f4b3d4","type":"sse-client","z":"990e535c.6c9aa","name":"","url":"http://192.168.1.179/stream/meter","events":["message"],"headers":{},"proxy":"","restart":true,"rejectUnauthorized":false,"withCredentials":true,"timeout":"10","x":700,"y":280,"wires":[["2f0684e0.5f6d54"]]},{"id":"aab7d19.38676b","type":"http request","z":"990e535c.6c9aa","name":"","method":"GET","ret":"txt","paytoqs":"ignore","url":"http://192.168.1.179/installer/setup/home","tls":"","persist":false,"proxy":"","authType":"digest","x":490,"y":180,"wires":[["5e0c1620.061b18"]]},{"id":"2f0684e0.5f6d54","type":"json","z":"990e535c.6c9aa","name":"","property":"payload","action":"","pretty":false,"x":170,"y":460,"wires":[["2ab03576.40b95a","f43980a0.3f7be","6c81fa17.83fd3c"]]},{"id":"2ab03576.40b95a","type":"function","z":"990e535c.6c9aa","name":"production[\"ph-a\"].p","func":"//msg.payload = msg.payload.production.ph-a.p;\nmsg.topic = \"Envoy/Stream/Prod\"\nmsg.payload = msg.payload.production[\"ph-a\"].p;\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":410,"y":420,"wires":[["6d349e5f.f4c798"]]},{"id":"f43980a0.3f7be","type":"function","z":"990e535c.6c9aa","name":"[\"net-consumption\"][\"ph-a\"].p","func":"msg.payload = msg.payload[\"net-consumption\"][\"ph-a\"].p;\nmsg.topic = \"Envoy/Stream/NetConso\"\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":420,"y":460,"wires":[["6d349e5f.f4c798"]]},{"id":"6c81fa17.83fd3c","type":"function","z":"990e535c.6c9aa","name":"[\"total-consumption\"][\"ph-a\"].p","func":"//msg.payload = msg.payload.production.ph-a.p;\nmsg.payload = msg.payload[\"total-consumption\"][\"ph-a\"].p;\nmsg.topic = \"Envoy/Stream/TotConso\"\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":420,"y":500,"wires":[["6d349e5f.f4c798"]]},{"id":"3620e13f.635166","type":"mqtt out","z":"990e535c.6c9aa","name":"","topic":"","qos":"","retain":"","respTopic":"","contentType":"","userProps":"","correl":"","expiry":"","broker":"c5910688.657cf8","x":810,"y":460,"wires":[]},{"id":"6d349e5f.f4c798","type":"rbe","z":"990e535c.6c9aa","name":"Filtre","func":"deadbandEq","gap":"5%","start":"","inout":"out","septopics":true,"property":"payload","x":650,"y":460,"wires":[["3620e13f.635166"]]},{"id":"c5910688.657cf8","type":"mqtt-broker","name":"192.168.1.217","broker":"192.168.1.217","port":"1883","clientid":"","usetls":false,"protocolVersion":"4","keepalive":"60","cleansession":true,"birthTopic":"","birthQos":"0","birthPayload":"","birthMsg":{},"closeTopic":"","closeQos":"0","closePayload":"","closeMsg":{},"willTopic":"","willQos":"0","willPayload":"","willMsg":{},"sessionExpiry":""}]
4 « J'aime »

:+1: Bravo merci pour le partage !

Bonjour @Manumdk
Ça te permet de récupérer koi comme info ?
Tous les panneaux , les compteurs ?
Cordialement

Salut,
Non, c’est du temps réel, toutes les secondes, j’ai mis une sortie au message #388.
Perso, ça va me permettre d’alimenter mon routeur PV sans y devoir intégrer les mesures.

Pour le différer et les compteurs, il vaut mieux récupérer les datas via le script proposé par Olive.
Mais si tu mixes les deux, tu peux ne faire les requêtes json que toutes les 5 ou 10 minutes par exemple.
A+

1 « J'aime »

Bonjour Olive , je me permet de te contacter concernant ton installation enphase couplée à des batteries pylontech.
Je suis sur le point de commander un kit enphase 3,4kwc (pour commencer) avec s metered pour le zéro injection. Vu le prix exorbitant des batteries enphase. Je me penche sur un kit wks opti c 3kw avec 4,8kw pylontech. Ma question est si j’installe les deux kits, est ce que le s metered va considérer le wks comme une conso. Et est ce le wks va fonctionner correctement ayant tous les deux les pinces de conso et production au même endroit.
Le zéro injection de l’enphase étant primordial si les batteries sont pleines. J’espère que tu pourras me renseigner car aucun revendeur n’est capable de me répondre .
Autre question , en théorie 2 batteries enphase 1,2kw AC ont elle la même autonomie que 1 pylontech 2,4kw DC. La différence de prix est incroyable .
En te remerciant par avance . Salutations

Bonjour, @Lolo55

le Zéro injection est une connerie sans nom …

ça c’est une bonne option

si ta pince qui mesure l’injection est bien en fin de ligne juste avant compteur
ce que puise le wks sera comme de la consommation et donc la pince enphase verra passer 0 .

bonne journée

Bonjour à tous,

J’utilise le plugin script avec une box enphase s-metered.

En utilisant, l’adresse http://envoy:XXXXXX@192.168.1.84/api/v1/production/inverters/ avec XXXXXX numero de série du S-metered Enphase, j’obtiens le Json contenant les infos des micro-onduleurs.

Je bute sur l’interrogation de ce Json dans le plugin script. Je fais pourtant 0>serialNumber et cela ne remonte rien. Je doute sur la syntaxe, auriez vous une idée ?

Merci et bon we !
Seb

Précision, le fichier Json est de structure

[
  {
    "serialNumber": "121945029692",
    "lastReportDate": 1630243127,
    "devType": 1,
    "lastReportWatts": 246,
    "maxReportWatts": 255
  },
  {
    "serialNumber": "121945029709",
    "lastReportDate": 1630243132,
    "devType": 1,
    "lastReportWatts": 242,
    "maxReportWatts": 254
  }
]

Bonsoir @Seb38

Je suis pas certain que tu puisse passer l’authentification par un script

Utilise plutôt un scenario ce qui t’évitera d’appeler autant de fois que tu a de données a récupérer.

le décodage se fait à l’aide de la fonction json_decode

$login='envoy';$passwd='011770';$ip = '192.168.0.248';
$tags = $scenario->getTags();
$request_http = new com_http('http://'.$ip.'/api/v1/production/inverters',"$login","$passwd");
$request_http->setCURLOPT_HTTPAUTH(CURLAUTH_DIGEST);
$json=json_decode(trim($request_http->exec()), true);

$tableau = "<table><tr><td>Paneau</td><td>N° de Série</td><td>Moment</td><td>Type</td><td>Puissance</td><td>Maxi</td></tr>";
$x=0;
$total=0;
foreach ($json as &$value) {
  $y = $x + 1;
  $tableau .= '<tr>';
  $tableau .= '<td>'.$y.'</td>';
  $tableau .= '<td>'.$json[$x]['serialNumber'].'</td>';
  $tableau .= '<td>'.date('H:i:s d-m-Y',$json[$x]['lastReportDate']).'</td>';
  $tableau .= '<td>'.$json[$x]['devType'].'</td>';  
  $tableau .= '<td>'.$json[$x]['lastReportWatts'].' W</td>';
  $total += (int)$json[$x]['lastReportWatts'];
  $tableau .= '<td>'.$json[$x]['maxReportWatts'].' W</td>';
  $tableau .= "</tr>";
  $x+=1;
}

$tableau .= "</table>";
$tableau = str_replace("<td>","<td style ='border: 1px solid red;height: 30px;padding-right: 2px;padding-left: 2px;'>",$tableau);
$scenario->setLog($total);
$scenario->setLog($tableau);

//unset($value);
$tableau = 'Total '.$total.' Watts'.$tableau;
$tags['#tableau#'] = $tableau;
$scenario->setTags($tags);

La sortie est ici dans un virtuel avec une commande info.

Amuse toi bien