{"id":4503,"date":"2026-09-01T20:27:46","date_gmt":"2026-09-01T18:27:46","guid":{"rendered":"https:\/\/domo.rem81.com\/?p=4503"},"modified":"2026-09-01T20:58:59","modified_gmt":"2026-09-01T18:58:59","slug":"acceder-en-ssh-root-au-cerbo-gx-et-rendre-persistant-le-contexte-node-red","status":"publish","type":"post","link":"https:\/\/domo.rem81.com\/index.php\/2026\/09\/01\/acceder-en-ssh-root-au-cerbo-gx-et-rendre-persistant-le-contexte-node-red\/","title":{"rendered":"Acc\u00e9der en SSH root au Cerbo GX et rendre persistant le contexte Node-RED"},"content":{"rendered":"\n\n\n\n<h1 class=\"wp-block-heading\">Intro<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Deux manipulations utiles quand on pousse Venus OS et Node-RED un peu plus loin que l&rsquo;interface standard : obtenir un acc\u00e8s SSH root sur le Cerbo GX, et faire en sorte que les variables de contexte d&rsquo;un flow Node-RED survivent \u00e0 un red\u00e9marrage.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><\/p>\n\n\n\n<h1 class=\"wp-block-heading\">Activer l&rsquo;acc\u00e8s SSH root sur le Cerbo GX<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Victron cache volontairement cette option pour \u00e9viter les manipulations accidentelles \u2014 elle reste n\u00e9anmoins officiellement support\u00e9e.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">\u00c9tape 1 \u2014 Passer en \u00ab\u00a0User and Installer\u00a0\u00bb<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Sur le Cerbo (\u00e9cran tactile ou Remote Console) : <em>R\u00e9glages \u2192 G\u00e9n\u00e9ral \u2192 Access Level<\/em>, puis choisir <strong>User and Installer<\/strong>. Le mot de passe demand\u00e9 est <code>ZZZ<\/code> (en majuscules).<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">\u00c9tape 2 \u2014 D\u00e9bloquer le niveau Superuser<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Rester positionn\u00e9 sur la ligne <em>Access Level<\/em> (sans la rouvrir) puis :<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Sur \u00e9cran tactile \/ appli mobile : glisser le menu vers le bas et <strong>maintenir l&rsquo;appui 5 secondes<\/strong><\/li>\n\n\n\n<li>Sur PC via le Remote Console classique : maintenir la <strong>fl\u00e8che droite<\/strong> du clavier enfonc\u00e9e (la souris ne fonctionne pas pour ce geste)<\/li>\n<\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">Le niveau bascule alors sur <strong>Superuser<\/strong>.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">\u00c9tape 3 \u2014 D\u00e9finir un mot de passe root<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Un nouveau menu appara\u00eet : <em>R\u00e9glages \u2192 G\u00e9n\u00e9ral \u2192 Set root password<\/em>. Choisir un mot de passe d&rsquo;au moins 6 caract\u00e8res.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><strong>Attention<\/strong> : ce mot de passe est stock\u00e9 sur le rootfs et sera <strong>r\u00e9initialis\u00e9 \u00e0 chaque mise \u00e0 jour de firmware<\/strong> \u2014 c&rsquo;est normal, il faudra le red\u00e9finir apr\u00e8s une mise \u00e0 jour Venus OS si l&rsquo;acc\u00e8s SSH root reste n\u00e9cessaire.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">\u00c9tape 4 \u2014 Activer SSH on LAN<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Toujours dans <em>R\u00e9glages \u2192 G\u00e9n\u00e9ral<\/em>, activer l&rsquo;option <strong>SSH on LAN<\/strong>.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">\u00c9tape 5 \u2014 Se connecter<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>ssh root@&lt;adresse-IP-du-cerbo&gt;<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Si la connexion \u00e9choue avec <code>Too many authentication failures<\/code> avant m\u00eame de demander le mot de passe, c&rsquo;est que votre client SSH tente automatiquement toutes vos cl\u00e9s existantes. Forcez l&rsquo;authentification par mot de passe :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>ssh -o PreferredAuthentications=password -o PubkeyAuthentication=no root@&lt;adresse-IP&gt;<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Rootfs \u00ab\u00a0modifi\u00e9\u00a0\u00bb apr\u00e8s coup<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Une fois le mot de passe root d\u00e9fini, le menu <em>R\u00e9glages \u2192 Firmware<\/em> affichera l&rsquo;\u00e9tat du syst\u00e8me de fichiers racine comme <strong>\u00ab\u00a0Modifi\u00e9\u00a0\u00bb<\/strong>, avec une option <strong>Nettoyer<\/strong>. C&rsquo;est normal : le mot de passe root est stock\u00e9 sur le rootfs, qui doit rester une image en lecture seule identique \u00e0 celle fournie par Victron. Le nettoyage restaure le rootfs d&rsquo;origine (supprimant le mot de passe root et tout paquet tiers \u00e9ventuellement install\u00e9 dessus) sans toucher aux r\u00e9glages ESS, VRM ou r\u00e9seau, qui vivent sur une partition s\u00e9par\u00e9e (<code>\/data<\/code>).<\/p>\n\n\n\n<h1 class=\"wp-block-heading\">Rendre persistant le contexte d&rsquo;un flow Node-RED<\/h1>\n\n\n\n<p class=\"wp-block-paragraph\">Par d\u00e9faut, les variables stock\u00e9es via <code>context.set()<\/code> \/ <code>flow.set()<\/code> \/ <code>global.set()<\/code> dans Node-RED vivent <strong>en m\u00e9moire uniquement<\/strong>. Un red\u00e9marrage du service Node-RED, un redeploy de flow, ou un reboot du Cerbo efface tout. Pour une machine \u00e0 \u00e9tats qui tourne sur plusieurs heures (par exemple un calcul qui suit un cycle de charge\/d\u00e9charge complet), c&rsquo;est un probl\u00e8me : le moindre red\u00e9marrage entre-temps remet le calcul \u00e0 z\u00e9ro sans jamais le laisser aboutir.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Trouver le bon fichier de configuration<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Sur Venus OS, Node-RED est lanc\u00e9 par <code>\/usr\/bin\/node-red-venus.sh<\/code> avec l&rsquo;option <code>--settings \/usr\/lib\/node_modules\/node-red\/venus-settings.js<\/code>. Ce fichier ne doit <strong>jamais \u00eatre \u00e9dit\u00e9 directement<\/strong> (il sera \u00e9cras\u00e9 \u00e0 la prochaine mise \u00e0 jour firmware), mais il inclut en fin de fichier :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>...try_require(\"\/data\/home\/nodered\/.node-red\/settings-venus.js\"),\n...try_require(\"\/data\/home\/nodered\/.node-red\/settings-user.js\"),<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>settings-user.js<\/code> est donc le point d&rsquo;extension officiel pour les r\u00e9glages personnalis\u00e9s \u2014 il survit aux mises \u00e0 jour firmware car il vit sur la partition <code>\/data<\/code>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><strong>Pi\u00e8ge \u00e0 \u00e9viter<\/strong> : ne pas cr\u00e9er un fichier nomm\u00e9 simplement <code>settings.js<\/code> dans <code>~\/.node-red\/<\/code> \u2014 le script de d\u00e9marrage Venus OS le renomme automatiquement en <code>settings.js.old<\/code> au prochain d\u00e9marrage (m\u00e9canisme pr\u00e9vu pour migrer l&rsquo;ancien <code>credentialSecret<\/code>), ce qui neutraliserait silencieusement toute configuration ajout\u00e9e l\u00e0.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Cr\u00e9er settings-user.js<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Le fichier n&rsquo;existe g\u00e9n\u00e9ralement pas encore par d\u00e9faut :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>cat &gt; \/data\/home\/nodered\/.node-red\/settings-user.js &lt;&lt; 'EOF'\nmodule.exports = {\n    contextStorage: {\n        default: \"memoryOnly\",\n        memoryOnly: { module: \"memory\" },\n        file: {\n            module: \"localfilesystem\",\n            config: {\n                dir: \"\/data\/home\/nodered\/.node-red\/context\",\n                flushInterval: 300\n            }\n        }\n    }\n}\nEOF\nchown nodered:nodered \/data\/home\/nodered\/.node-red\/settings-user.js<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"><code>default<\/code> reste sur <code>memoryOnly<\/code> \u2014 seul le store nomm\u00e9 <code>file<\/code> est persistant, \u00e0 utiliser explicitement l\u00e0 o\u00f9 c&rsquo;est n\u00e9cessaire. Le <code>flushInterval<\/code> de 300 secondes limite la fr\u00e9quence d&rsquo;\u00e9criture sur la flash embarqu\u00e9e du Cerbo (\u00e0 m\u00e9nager, ce n&rsquo;est pas un disque classique).<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Utiliser le store persistant dans le code<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">Dans un n\u0153ud <em>function<\/em>, il suffit d&rsquo;ajouter le nom du store en second argument :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\/\/ Lecture\nlet st = context.get('st', 'file') || { phase: \"ARM\" };\n\n\/\/ \u00c9criture\ncontext.set('st', st, 'file');<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Sans ce second argument, Node-RED utilise le store <code>default<\/code> (m\u00e9moire uniquement).<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Red\u00e9marrer Node-RED (pas juste Deploy)<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">C&rsquo;est le point qui pi\u00e8ge le plus souvent : un simple clic sur <strong>Deploy<\/strong> dans l&rsquo;\u00e9diteur ne red\u00e9ploie que le flow, pas le processus Node-RED lui-m\u00eame. Les changements dans <code>settings-user.js<\/code> ne sont lus qu&rsquo;au d\u00e9marrage du service. Il faut donc red\u00e9marrer Node-RED via SSH :<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>ls -la \/service\/ | grep node-red\nsvc -t \/service\/node-red-venus<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">(<code>svc -t<\/code> envoie un signal TERM au service ; le superviseur runit le relance automatiquement.)<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">V\u00e9rifier que \u00e7a fonctionne<\/h2>\n\n\n\n<pre class=\"wp-block-code\"><code>ls -la \/data\/home\/nodered\/.node-red\/context\/<\/code><\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Ce dossier n&rsquo;appara\u00eet qu&rsquo;apr\u00e8s le red\u00e9marrage complet de Node-RED (pas au premier Deploy). Son contenu ne se remplit qu&rsquo;apr\u00e8s le premier <code>flushInterval<\/code> \u00e9coul\u00e9 (5 minutes dans l&rsquo;exemple ci-dessus) suivant une \u00e9criture \u2014 un dossier vide juste apr\u00e8s red\u00e9marrage est normal, pas une erreur.<\/p>\n\n\n\n<h1 class=\"wp-block-heading\">En r\u00e9sum\u00e9<\/h1>\n\n\n\n<ul class=\"wp-block-list\">\n<li>SSH root : Access Level \u2192 User and Installer \u2192 maintien 5s sur la ligne \u2192 Superuser \u2192 Set root password \u2192 SSH on LAN<\/li>\n\n\n\n<li>Contexte persistant : jamais <code>settings.js<\/code>, toujours <code>settings-user.js<\/code> ; d\u00e9clarer un store <code>file<\/code> ; l&rsquo;utiliser explicitement (<code>context.get('x', 'file')<\/code>) ; puis <strong>red\u00e9marrer le service<\/strong>, pas juste red\u00e9ployer.<\/li>\n<\/ul>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<p class=\"wp-block-paragraph\"><em>Article r\u00e9dig\u00e9 avec l&rsquo;assistance de Claude AI (Anthropic) \u00e0 partir de mes donn\u00e9es et retours d&rsquo;exp\u00e9rience.<\/em><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Intro Deux manipulations utiles quand on pousse Venus OS et Node-RED un peu plus loin que l&rsquo;interface standard : obtenir un acc\u00e8s SSH root sur le Cerbo GX, et faire &hellip; <\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[4,98],"tags":[66,63],"class_list":["post-4503","post","type-post","status-publish","format-standard","hentry","category-homeassistant","category-linux","tag-nodered","tag-victron"],"_links":{"self":[{"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/posts\/4503","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/comments?post=4503"}],"version-history":[{"count":2,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/posts\/4503\/revisions"}],"predecessor-version":[{"id":4505,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/posts\/4503\/revisions\/4505"}],"wp:attachment":[{"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/media?parent=4503"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/categories?post=4503"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/domo.rem81.com\/index.php\/wp-json\/wp\/v2\/tags?post=4503"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}