NEWS
[Gelöst] Speicherort eigene Dateien/Files ?
-
Hi,
Bis zu meinem heutigen Javascript Adapter update konnte ich eigene Dateien ja z.B. hier Speichern:
/opt/iobroker/iobroker-data/files/_temp/eingangstuer/
Jetzt ist der Zugriff ja verboten wenn ich z.B. aus einem Script dahin schreiben will.
Was ist denn der empfohlene Ordner / Pfad ?
EDIT: Und ist es richtig das ich hier auch keine Ordner mehr per Datei Manager erstellen kann?
Thx.
-
/opt/iobroker/iobroker-data/files/0_userdata.0 /* falls man vis instaliert hat */ /opt/iobroker/iobroker-data/files/vis.0
-
@mcu sagte in Speicherort eigene Dateien/Files ?:
/opt/iobroker/iobroker-data/files/0_userdata.0
An den Ordner hatte ich gedacht, gibt es bei mir aber aus irgendeinem Grund nicht. Wann sollte der angelegt werden oder muss ich den selber anlegen?
-
@wendy2702 js-controller-Version?
node: v18.20.2, js-controller: 5.0.19 -
@mcu Diese Ordner im Dateisystem sollte man aber manuell nie schreiben und einfach komplett in Ruhe lassen. Zumal diese gar nicht existieren wenn man zB Redis verwendet.
Wenn man etwas speichern will, immer mit den ioBroker Funktionen arbeiten (CLI, Dateien-Tab im Admin, JavaScript-Adapter, usw).
-
@mcu Sorry, nicht drüber nachgedacht.
JS Controller: 5.0.19
NodeJS: v18.20.2 -
@wendy2702 Was willst du denn mit den Dateien machen?
Du schreibst sie mitwriteFile
in das entsprechende Verzeichnis? -
@haus-automatisierung sagte in Speicherort eigene Dateien/Files ?:
Wenn man etwas speichern will, immer mit den ioBroker Funktionen arbeiten (CLI, Dateien-Tab im Admin, JavaScript-Adapter, usw).
Sorry verstehe ich als Script legasteniker nicht.
Mal hier das Script welches nach Update z.B. jetzt nicht mehr funktioniert weil Permission denied:
// ------------------------------------------------------------------------- // Dieses Script überwaht den Zustand eines Bewegungsmelders und speichert bei // Aktivierung ein Bild einer Überwachnungskamera in einem Vereichnis und sendet // dieses via Telegram.0-Adapter. Nach 10 Sek wird ein weiteres Bild erstellt und // gesendet. // Die Speicherung der Bilder erfolgt als "Stack", d.h. das aktuellste Bild bekommt // immer den Suffix "0" und es werden n Bilder mit den Suffixen 1..n-1 vorgehalten // Uhula 2017.11 // ------------------------------------------------------------------------- // ------------------------------------------------------------------------- // Konfiguration // ------------------------------------------------------------------------- // Objekt-ID des Bewegungsmelders const oidLichtBewmelderTuer = "hm-rpc.0.PEQ0390697.1.MOTION"; // URL zur Kamera umn ein Image (jpg) zu erhalten const cam_url = "http://192.168.178.54:8765/picture/4/current/"; // Pfadangabe für die Speicherung der Bilder, der Pfad muss existieren const dest_path = '/opt/iobroker/iobroker-data/files/_temp/eingangstuer/'; // Anzahl der Bilder, die vorgehalten werden sollen const imageCountMax = 8; // Prefix für die Bildnamen const imageNamePre = "Haustuer_Einfahrt_"; // ------------------------------------------------------------------------- // Scriptteil // ------------------------------------------------------------------------- var request = require('request'); var fs = require('fs'); // Bild an telegram schicken function sendImage (path) { try { var stats = fs.statSync(path); var msg = formatDate(stats.birthtime,"DD.MM.YYYY hh:mm:ss") + " " + path.substring(path.lastIndexOf('/')+1); sendTo('telegram.0', { text: path, caption: msg, disable_notification: true, user: 'Mirko', }); } catch(err) { if (err.code != "ENOENT") log(err); } } // löscht eine Datei synchron (wartet auf das Ergebnis) function fsUnlinkSync(path) { try { var stats = fs.statSync(path); try { fs.unlinkSync(path); } catch(err) { if (err.code != "ENOENT") log(err); } } catch(err) { if (err.code != "ENOENT") log(err); } } // benennt eine Datei synchron um (wartet auf das Ergebnis) function fsRenameSync(oldPath, newPath) { try { var stats = fs.statSync(oldPath); try { fs.renameSync(oldPath, newPath); } catch(err) { if (err.code != "ENOENT") log(err); } } catch(err) { if (err.code != "ENOENT") log(err); } } // Bild speichern und senden function saveImage() { // Bild imageCountMax-1 löschen fsUnlinkSync( dest_path + imageNamePre + (imageCountMax-1) + ".jpg" ); // Bilder 0..imageCountMax-2 umbenennen for (var i=imageCountMax-4; i >= 0; i-- ) { fsRenameSync(dest_path + imageNamePre + i + ".jpg", dest_path + imageNamePre + (i+1) + ".jpg"); } // Bild 0 löschen var fname = imageNamePre + "0.jpg"; fsUnlinkSync( fname ); // Bild holen und speichern request.get({url: cam_url, encoding: 'binary'}, function (err, response, body) { fs.writeFile(dest_path + fname, body, 'binary', function(err) { if (err) { log('Fehler beim Bild speichern: ' + err, 'warn'); } else { // dem Filesystem 2 Sek Zeit zum Speichern lassen setTimeout(function() { sendImage(dest_path + fname); }, 2000); } }); }); } // sofort ein Bild senden und nach 3 Sek erneut //function onEvent() { // saveImage(); // setTimeout(function() { saveImage(); }, 10 * 300); //} // sofort ein Bild senden und nach 3 Sek erneut function onEvent() { saveImage(); setTimeout(function() { saveImage(); }, 3 * 1000); setTimeout(function() { saveImage(); }, 6 * 1000); setTimeout(function() { saveImage(); }, 9 * 1000); } // Ereignisroutine //on({id: oidLichtBewmelderTuer, val: true}, function (obj) { // onEvent( obj ); on({id: 'hm-rpc.0.PEQ0390697.1.MOTION', change: "ne"}, function (obj) { var value = obj.state.val; var oldValue = obj.oldState.val; if (getState("hm-rpc.0.PEQ0390697.1.MOTION").val === true && getState("hm-rpc.0.NEQ1110202.1.STATE").val === false) onEvent( obj ); }); // manuelle Ausführung (Test) onEvent();
Das lief so seit 2017 bis eben heute.
Was müsste denn geändert werden?
EDIT: das request depreceated ist weiss ich und baue das auch gerade um.
-
@wendy2702 Du musst es mit writeFile speichern nicht mit fs.writeFile
Versuch es mal hiermit/* directory ist das Verzeichnis ab 0_userdata.0 */ /* z.B. let directory = '/telegram/' */ /* so ungefähr ? Nur mit writeFile werden entsprechende Berechtigungen gesetzt, nicht bei fs.writeFile */ writeFile('0_userdata.0', directory + dateiname, Buffer.from(body, 'binary'), function (error) { if(error){ log('fehler beim Bild speichern: ' +error ,'warn'); } }
-
@mcu Danke für deine Hilfe.
Ich habe es einmal so probiert:
// Bild holen und speichern request.get({url: cam_url, encoding: 'binary'}, function (err, response, body) { writeFile(dest_path + fname, body, 'binary', function(err) { if (err) { log('Fehler beim Bild speichern: ' + err, 'warn'); } else { // dem Filesystem 2 Sek Zeit zum Speichern lassen setTimeout(function() { sendImage(dest_path + fname); }, 2000); } }); });
Und erhalte dann das im log:
17:54:08.204 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: Error: Parameter "filename" needs to be of type "string" but type "undefined" has been passed 17:54:08.205 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:80:9) 17:54:08.206 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: Error: Parameter "filename" needs to be of type "string" but type "undefined" has been passed 17:54:08.206 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:80:9) 17:54:14.218 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: Error: Parameter "filename" needs to be of type "string" but type "undefined" has been passed 17:54:14.218 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:80:9) 17:54:14.220 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: Error: Parameter "filename" needs to be of type "string" but type "undefined" has been passed 17:54:14.220 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:80:9)
Und einmal so:
// Bild holen und speichern request.get({url: cam_url, encoding: 'binary'}, function (err, response, body) { writeFile('0_userdata.0', directory + dateiname, Buffer.from(body, 'binary'), function (error) { if(error){ log('fehler beim Bild speichern: ' +error ,'warn'); } else { // dem Filesystem 2 Sek Zeit zum Speichern lassen setTimeout(function() { sendImage(dest_path + fname); }, 2000); } }); });
Zusätzlich mal die Const für Dateiname und Directory angelegt, keine Ahnung ob das richtig ist:
const directory = "test" const dateiname = "test_bild"
Aber dann erhalte ich das im log:
18:13:26.122 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: TypeError [ERR_INVALID_ARG_TYPE]: The first argument must be of type string or an instance of Buffer, ArrayBuffer, or Array or an Array-like Object. Received undefined 18:13:26.122 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:84:66) 18:13:26.124 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: TypeError [ERR_INVALID_ARG_TYPE]: The first argument must be of type string or an instance of Buffer, ArrayBuffer, or Array or an Array-like Object. Received undefined 18:13:26.124 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:84:66) 18:13:32.106 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: TypeError [ERR_INVALID_ARG_TYPE]: The first argument must be of type string or an instance of Buffer, ArrayBuffer, or Array or an Array-like Object. Received undefined 18:13:32.106 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:84:66) 18:13:32.108 error javascript.0 (97118) script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt: TypeError [ERR_INVALID_ARG_TYPE]: The first argument must be of type string or an instance of Buffer, ArrayBuffer, or Array or an Array-like Object. Received undefined 18:13:32.108 error javascript.0 (97118) at Request._callback (script.js.common.Cameras.Telegramm_Screenshot_Haustuer_Einfahrt:84:66)
Keine Ahnung was da jetzt noch falsch ist. Für mich aktuell zu hoch.
-
@wendy2702 sagte in Speicherort eigene Dateien/Files ?:
const directory = "test" const dateiname = "test_bild"
const directory = "/test/" const dateiname = "test_bild.jpg" .... writeFile('0_userdata.0', directory + dateiname, body, function (error) {
-
@mcu Wie oben geschrieben habe ich das directory nicht:
@mcu sagte in Speicherort eigene Dateien/Files ?:
0_userdata.0
Keine Ahnung warum nicht und auch nicht wann es erzeugt wird.
Unter Objekten gibt es den Ordner ja:
-
@wendy2702 Nein unter Files schauen
-
@mcu Da kommt bei mir dieser Fehler wenn ich den Ordner öffnen will:
EDIT: wenn ich den nur markieren und versuche einen weiteren Ordner darin zu erstellen kann ich im Eingabefeld keinen Namen eingeben und es blinkt nur der Cursor
-
@wendy2702 Schau mal auf der console unter
cd /opt/iobroker/iobroker-data/files/0_userdata.0 ls -l
Hast du eigentlich den vis.0-Ordner?
-
-
@wendy2702 sagte in Speicherort eigene Dateien/Files ?:
Keine Ahnung warum nicht und auch nicht wann es erzeugt wird.
Unter Objekten gibt es den Ordner ja:
Objekte vom Typ
folder
"enthalten" nur andere Objekte (bzw. bilden eine Objekt-Hierarchie ab). Das hat nichts mit Dateien zu tun. Du hast nur das Meta-Objekt. Alles weitere passiert im Dateien-Tab. Bitte nicht Objekte mit Dateien verwechseln.Ansonsten sind in der Dokumentation Beispiele. Du kannst mit
node:fs
natürlich aus anderen Quellen im Dateisystem Daten lesen und diese dann im ioBroker speichern. Aber eben mitwriteFile
unter Angabe des Meta-Objektes (wirdnull
übergeben, gibt es einen Fallback auf0_userdata.0
).https://github.com/ioBroker/ioBroker.javascript/blob/master/docs/en/javascript.md#writefile
Ich habe das im ioBroker Master Kurs ausführlich rauf und runter erklärt wo wann welche Dateien liegen und warum man nicht direkt in
/opt/iobroker/iobroker-data/files/
schreiben sollte. Macht man das, wird die Datei trotzdem nicht im Dateien-Tab auftauchen (weil die Metadaten fehlen, welche zu der Datei normalerweise geschrieben werden).Und mach mal den Expertenmodus aus. Den braucht man in 99% der Fälle nicht.
-
@wendy2702 bevor es zu kompliziert wird: Wenn ich das richtig sehe, speicherst du ein Bild der Kamera um es per Telegram zu senden?
Dann nimm doch als Pfad einfach
/tmp/NamedesBildes
Der
/tmp
ordner ist dafür da, ich mache das auch mit den Bilder per Telegram und speichere dort.
Nach einem reboot ist der Ordner halt leer, das Bild muss aber ja auch keinen reboot überleben.Anders wäre es wenn du das Bild auch noch in der VIS verwenden wolltest.
-
@bananajoe Hi,
Danke für die einfache Lösung.
Mittlerweile hat mein Sohn sich der Sache angenommen und das Script direkt von "request" befreit.
@haus-automatisierung sagte in Speicherort eigene Dateien/Files ?:
Ich habe das im ioBroker Master Kurs ausführlich rauf und runter erklärt wo wann welche Dateien liegen und warum man nicht direkt in /opt/iobroker/iobroker-data/files/ schreiben sollte. Macht man das, wird die Datei trotzdem nicht im Dateien-Tab auftauchen (weil die Metadaten fehlen, welche zu der Datei normalerweise geschrieben werden).
Ja, das mag sein aber wenn ein Script so seit 2017 lief und es jetzt erst die restriktionen gibt ist das für nicht Javascript affine wie mich ein Problem.
Jetzt werden die Bilder in userdata ordner bzw. weiteren unterordnern gespeichert.
Allerdings erschließt sich mir hier noch nicht die logik warum die nur solange sichtbar sind wie da eine Datei drin liegt.
Aber das ist ein anderes Thema.
-
@wendy2702 Dann stell bitte das fertige Script rein, damit andere die auf den Post stoßen den richtigen Ansatz haben. Danke.