Bearer JWT Token

Einklappen
X
 
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge
  • Gast

    #1

    Bearer JWT Token

    Ich versuche, Loxone Virtual Output in die Tedee-Sperr-API zu integrieren (https://api.tedee.com/swagger/index.html und https://tedee-tedee-api-doc.readthed...com/en/latest/).
    Für die Autorisierung ist leider die Verwendung des Bearer JWT-Tokens erforderlich.

    Ich habe 2 Probleme:
    1) Die Integration über virtuelle Ausgabe mit Loxone funktioniert bei mir nicht. Obwohl es gut mit der Kommandozeile funktioniert.
    Arbeitsbefehl:

    curl -X POST "https://api.tedee.com/api/v1.15/my/lock/open" -H "accept: application/json" -H "Authorization: Bearer TOKEN" -H "Content-Type: application/json-patch+json" -d "{"deviceId":1234,"openParameter":0}"

    2) Ich weiß nicht, wie ich dieses Token über Loxone aktualisieren kann. Es muss erfrischt werden. Es läuft alle 4 Stunden ab.


    Ich füge meinen Versuch hinzu, eine virtuelle Ausgabe mit einem Token und einer JWT-Berechtigung zu definieren
    Angehängte Dateien
  • Tico
    Lox Guru
    • 31.08.2016
    • 1035

    #2
    Das Problem, das Sie haben, ist, dass Loxone nicht in der Lage ist, ein großes Token zu verarbeiten.
    Sie müssen ein externes Gerät einsetzen, um den Token in Loxone zu erhalten. Ein Loxberry mit Node-Red kann dies tun.

    Alternativ kann ein Programmblock in Loxone (mit PicoC) möglich sein, aber ich habe noch nie in PicoC programmiert.

    Dieser Link enthält ein Beispiel für die Verwendung einer Token-Autorisierung innerhalb von Loxone.

    https://www.loxforum.com/forum/faqs-...e56#post272202

    Ihre virtuelle Ausgabe sieht nicht korrekt aus. Sie könnten das Token mit den folgenden Befehlen manuell einführen -

    HTTP-Erweiterungen für ON
    Code:
    Authorization: Bearer <v>\r\nContent-Type: application/json
    HTTP-Post-Befehl für On
    Code:
    {"deviceId":"1234","openParameter":"0"}
    HTTP-Verfahren für ON = GET
    (möglicherweise POST für Ihre Anwendung. Mein Befehl ruft Informationen ab)

    Platzieren Sie einen Statusblock vor der virtuellen Ausgabe und fügen Sie das Token manuell durch Kopieren/Einfügen in den Status-Text-Bereich zum Testen ein. Geben Sie TQ an die virtuelle Ausgabe aus.

    Oder ersetzen Sie einfach <v> durch das Token und ändern Sie Use as digital output in checked.
    Zuletzt geändert von Tico; 08.12.2020, 01:19.
    Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

    Kommentar

    • Gast

      #3
      Vielen Dank für Ihre Antwort.
      Ich habe das größte Problem beim Aktualisieren dieses Tokens.
      Ich habe darüber nachgedacht, einen externen Webdienst zu erstellen, um dieses Token zu aktualisieren. Ich bevorzuge jedoch, dass alles auf dem Miniserver ist. Keine zusätzlichen Dienste oder Geräte. Deshalb denke ich an PicoC.
      Es sei denn, jemand anderes hat eine Idee, wie das Token anderweitig aktualisiert werden kann. Für mich persönlich sollte der Service von Authorization 2.0 von Loxone selbst unterstützt werden.

      Kommentar

      • Tico
        Lox Guru
        • 31.08.2016
        • 1035

        #4
        Wie viele Zeichen enthält das Token? Es gibt vielleicht einen anderen Weg, aber das hängt sehr von der Größe des Token ab.

        Hatten Sie Erfolg damit, dass die virtuelle Ausgabe die Sperre aktiviert hat?
        Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

        Kommentar

        • Gast

          #5
          Ja. Ich kontrolliere bereits die virtuelle Ausgabe, indem ich das Token permanent berücksichtige.
          Ich weiß jedoch nicht, wie ich das Token auf der Loxone-Seite aktualisieren soll. Ich möchte keine separate Anwendung - einen Dienst, der das Token aktualisiert und ein neues Token an Loxone sendet.

          Ich möchte die Loxone-Seite auffrischen.
          Mein Token ist 256 Bit.
          Schlüssellänge: 1176 Zeichen

          Kommentar

          • Tico
            Lox Guru
            • 31.08.2016
            • 1035

            #6
            Diese Anzahl von Zeichen schließt die Idee aus, die ich hatte. Es gibt eine Methode zur Texteingabe für den Miniserver. Sie ist nur für kurze Textstrings geeignet -



            Ihre einzige wirkliche Option ist PicoC. Ich habe einen alten PicoC-Programmblock angehängt, der eine Text-Wetter-Synopse liefert. Er kann einen Eindruck davon vermitteln, was erforderlich ist.

            Das Forum hat vielleicht eine spezielle Anleitung, wie man PicoC programmiert, um nur das Token abzurufen.

            Code:
            /*
            Um einen API Key zu erhalten muss man sich auf http://www.wunderground.com/weather/api/ registrieren.
            Als Station gibt man am einfachsten den Namen des Wohnortes an,
            dann wählt Wunderground die passende Wetterstation für einen aus.
            Man kann aber auch eine bestimmte Station angeben.
            Eine Karte der Wetterstationen gibt es hier: http://www.wunderground.com/wundermap/
            Private Wetterstationen haben einen Namen als ID und müssen nach folgende Schema angegeben werden: "pws:NAME123".
            Die offiziellen Stationen haben eine nummerische ID und werden folgendermaßen angegeben: "zmw:00000.0.00000"
            */
            #define API_KEY "aaaabbbbccccdddd" // <-- Hier den API-Key eintragen. // Put your API-Key here.
            #define STATION "pws:IWESTERN999" // <-- Hier ID der Wetterstation eintragen. // Put your Station ID here.
            #define LANG "EN" // <-- Sprache // Language (http://www.wunderground.com/weather/api/d/docs?d=language-support&MR=1)
            #define SERVER "api.wunderground.com"
            #define UDP_ZEIT 75
            #define ZYKLUS 500 // vorher 75 // Programm-Zyklus in Millisekunden.
            #define LOGGING 2
            #define ANZ_WERTE_A 33
            #define ANZ_TAGE_V 8
            #define ANZ_WERTE_V 14
            #define FAKT_XML_DUPL 12 // Multiplikator für XML-Werte die Mehr als einmal vorkommen
            char *v[ANZ_WERTE_V] = {
            "pop",
            "celsius",
            "mm",
            "mm",
            "mm", // mm Kommt als <qpf_allday>, <qpf_day> und <qpf_night> vor.
            "cm",
            "cm", // cm Kommt als <snow_allday>, <snow_day> und <snow_night> vor.
            "cm",
            "cm",
            "dir",
            "degrees",
            "avehumidit",
            "maxhumidity",
            "minhumidity",
            };
            char *a[ANZ_WERTE_A] = {
            "observation_time",
            "magic",
            "wmo",
            "latitude",
            "longitude",
            "elevation",
            "weather",
            "temp_c",
            "relative_humidity",
            "wind_degrees",
            "wind_dir",
            "wind_mph",
            "wind_gust_mph",
            "wind_kph",
            "wind_gust_kph",
            "pressure_mb",
            "pressure_in",
            "pressure_trend",
            "dewpoint_f",
            "dewpoint_c",
            "heat_index_f",
            "heat_index_c",
            "windchill_f",
            "windchill_c",
            "feelslike_f",
            "feelslike_c",
            "visibility_mi",
            "visibility_km",
            "solarradiation",
            "precip_1hr_in",
            "precip_1hr_metric",
            "precip_today_in",
            "precip_today_metric",
            };
            
            // Globale Variabeln erzeugen.
            char cAPIa[100];
            char cAPIv[100];
            int nEvents;
            float fEingangEins;
            float fEingangZwei;
            
            // API-Aufrufe erzeugen.
            strcat(cAPIa,"/api/");
            strcat(cAPIa,API_KEY);
            strcat(cAPIa,"/conditions/lang:");
            strcat(cAPIa,LANG);
            strcat(cAPIa,"/q/");
            strcat(cAPIa,STATION);
            strcat(cAPIa,".xml");
            
            strcat(cAPIv,"/api/");
            strcat(cAPIv,API_KEY);
            strcat(cAPIv,"/forecast/lang:");
            strcat(cAPIv,LANG);
            strcat(cAPIv,"/q/");
            strcat(cAPIv,STATION);
            strcat(cAPIv,".xml");
            
            while(1==1){
            sleep(ZYKLUS); // Warten bis zum nächsten Interval.
            setoutput(1,0); // Ausgang der Uhr auf 0 stellen.
            nEvents = getinputevent(); //Eingänge auslesen.
            
            if (nEvents & 0x18){ // Bitmaske für die Eingang.
            fEingangEins = getinput(0); // Eingänge auf Veränderung prüfen, und ggf. Variabeln aktualisieren.
            fEingangZwei = getinput(1);
            }
            
            // Prüfen ob die Daten aktualisiert werden sollen.
            // Aktuelles Wetter - Anfang.
            if (fEingangEins != 0){
            if(LOGGING == 2){printf("Wunderground-API: Aktualisiere Wetter.");}
            fEingangEins = 0; // 0 setzten, damit der Abruf pro Flanke nur einmal erfolgt.
            char *cDatenA = httpget(SERVER,cAPIa); // Daten abrufen.
            if ((cDatenA != NULL) && (cDatenA != 0)){ //Prüfen ob die Daten Vorhanden sind.
            setoutput(1,1); // Impuls an Uhr
            // Windrichtung Ausgeben.
            char *cWindRichtungXML;
            if((cWindRichtungXML =getxmlvalue(cDatenA,0,"wind_degrees")) != NULL){
            setoutput(0,batof(cWindRichtungXML));
            }
            free(cWindRichtungXML);
            // Drucktendenz ermitteln.
            char* cDruckTendenzXML;
            if((cDruckTendenzXML = getxmlvalue(cDatenA,0,"pressure_trend")) != NULL){
            if(strcmp(cDruckTendenzXML,"+") == 0){ setoutput(2,1); } //steigender Druck.
            else{
            if(strcmp(cDruckTendenzXML,"-") == 0){ setoutput(2,-1); } // fallender Druck
            else{ setoutput(2,0); } // gleichbleibender Druck.
            }
            }
            free(cDruckTendenzXML);
            // UDP Stream erzeugen.
            STREAM* sUDPStreamA = stream_create("/dev/udp/127.0.0.1/2611",0,0);
            if (sUDPStreamA != NULL){
            char cTmpA[255]; // Tmp. für den Text.
            int i = 0;
            while(i < ANZ_WERTE_A){
            sleep(UDP_ZEIT);
            // String erzeugen
            char* cXMLA;
            if((cXMLA = getxmlvalue(cDatenA,0,a[i])) != NULL){ // Wenn der Wert existiert.
            strcat(cTmpA,a[i]);
            strcat(cTmpA,":");
            strcat(cTmpA,cXMLA);
            strcat(cTmpA,"\0"); // Nullterminierung zum Ende des Strings.
            stream_write(sUDPStreamA,cTmpA, strlen(cTmpA)); // Vorbereiten
            stream_flush(sUDPStreamA); //Absenden
            if(LOGGING == 1){
            printf("Wunderground-API_Test: %s",cTmpA); // Logausgabe
            }
            }
            free(cXMLA);
            memset(cTmpA, 0, 255); // Variable leeren.
            i++;
            }
            memset(cTmpA, 0, 255); // Variable leeren.
            //free(cTmpV);
            }
            else if(LOGGING == 1){
            printf("Der UDP-Stream des akt. Wetters konnte nicht erstellt werden.");
            }
            stream_close(sUDPStreamA);
            }
            char *cObservationtimeXML;
            if((cObservationtimeXML = getxmlvalue(cDatenA,0,"observation_time")) != NULL){
            if(LOGGING == 1){
            printf("Wunderground-API_Test: %s", cObservationtimeXML);
            }
            }
            free(cObservationtimeXML);
            // free(cDatenA);
            //Aktuelles Wetter - Ende.
            }
            //Vorherhsage - Anfang.
            if (fEingangZwei != 0){
            if(LOGGING == 2){printf("Wunderground-API: Aktualisiere Wettervorhersage.");}
            fEingangZwei = 0; // 0 setzten, damit der Abruf pro Flanke nur einmal erfolgt.
            char *cDatenV = httpget(SERVER,cAPIv); // Daten abrufen.
            if ((cDatenV != NULL) && (cDatenV != 0)){ //Prüfen ob die Daten Vorhanden sind.
            // Text erzeugen
            char *cWetterHeute = strstrskip(getxmlvalue(cDatenV,0,"fcttext_metric") ,"[CDATA[");
            char *cWetterMorgen = strstrskip(getxmlvalue(cDatenV,2,"fcttext_metric") ,"[CDATA["); // Daten vor dem Text abschneiden
            char *cWetterUeberm = strstrskip(getxmlvalue(cDatenV,4,"fcttext_metric") ,"[CDATA[");
            cWetterHeute[ strlen(cWetterHeute) -3] = '\0'; // Nullterminierung im String setzten damit die nachfolgenden Zeichne ignoriert werden.
            cWetterMorgen[strlen(cWetterMorgen)-3] = '\0';
            cWetterUeberm[strlen(cWetterUeberm)-3] = '\0';
            setoutputtext(0,cWetterHeute);
            setoutputtext(1,cWetterMorgen);
            setoutputtext(2,cWetterUeberm);
            if(LOGGING == 1){
            printf("Wunderground-API: Wetter Heute: %s",cWetterHeute);
            printf("Wunderground-API: Wetter Morgen: %s",cWetterMorgen);
            printf("Wunderground-API: Wetter Uebermorgen: %s",cWetterUeberm);
            }
            // UDP Stream erzeugen.
            STREAM* sUDPStreamV = stream_create("/dev/udp/127.0.0.1/2611",0,0);
            if (sUDPStreamV != NULL){
            char cTmpV[255]; // Tmp. für den Text.
            int j = 0;
            while(j < FAKT_XML_DUPL){ // Die Tage durchsuchen (Multipl. da einige Werte mehrm. pro Tag Vorkommen
            int k = 0;
            while(k < ANZ_WERTE_V){
            sleep(UDP_ZEIT);
            // String erzeugen
            char* cXMLV = getxmlvalue(cDatenV,j,v[k]); // Antwort des XML Parsers
            if(cXMLV != NULL){ // Wenn der Wert existiert.
            sprintf(cTmpV,"%d",j); // Nummer des Tages (0=Heute,1=Morgen, etc.)
            strcat(cTmpV,v[k]);
            strcat(cTmpV,":");
            strcat(cTmpV,cXMLV);
            strcat(cTmpV,"\0"); // Nullterminierung zum Ende des Strings.
            stream_write(sUDPStreamV,cTmpV, strlen(cTmpV)); // Vorbereiten
            stream_flush(sUDPStreamV); //Absenden
            if(LOGGING == 1){
            printf("Wunderground-API_Test: %s",cTmpV); // Logausgabe
            }
            }
            memset(cTmpV, 0, 255); // Variable leeren.
            k++;
            }
            j++; // Nächster Tag
            }
            }
            else if(LOGGING == 1){
            printf("Der UDP-Stream der Vorhersage konnte nicht erstellt werden.");
            }
            stream_close(sUDPStreamV);
            }
            // free(cDatenV);
            }
            //Vorhersage - Ende.
            }
            }
            Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

            Kommentar

            • Gast

              #7
              Methode 1 erfordert eine separate Site, um das Token zu aktualisieren

              Methode 2 scheint derzeit die einzig richtige und stabilste zu sein. Weil es nicht auf zusätzliche Dienstleistungen ankommt.

              Die Frage ist übrigens, wann Loxone standardmäßig tokenbasiertes tokenbasiertes OAuth 2.0 mit aktualisierten digitalen Ein- und Ausgängen einführen wird.

              Kommentar

              • Tico
                Lox Guru
                • 31.08.2016
                • 1035

                #8
                Methode 1 benötigt keine separate Website. Ich habe erfolgreich tokenbasiertes OAuth 2.0 auf dem Miniserver eingesetzt, indem ich nur die Config-Ressourcen verwendet habe. Das Token war in meinem Fall allerdings recht klein und einfach.

                1. Erstellen Sie einen virtuellen Ausgang, um das Token anzufordern.
                2. Stellen Sie sicher, dass Save HTTP Reply mit einem geeigneten Pfad abgeschlossen wird.


                Klicke auf die Grafik für eine vergrößerte Ansicht

Name: Save HTTP reply.png
Ansichten: 2407
Größe: 9,1 KB
ID: 280890


                3. Erstellen Sie einen Virtuellen HTTP-Eingang, um die interne Datei 'token.json' abzufragen

                4. Die URL-Adresse für die interne Datei ist -
                Code:
                http://Username:Password@MiniserverIP:Port/dev/fsget/user/common/token.json
                5. Verwenden Sie dann die Methode https://www.loxwiki.eu/display/LOXEN...+to+Miniserver um den relevanten Text zu extrahieren.

                Die Herausforderung für Sie -

                Beziehen Sie sich auf diesen Link -



                Sie müssen die Token aus verschiedenen 4-Stunden-Perioden vergleichen. Hoffentlich gibt es unveränderlichen Text im Header und Payload. Die Signatur sollte sich ändern. Sie müssen sehen, wie viele Zeichen es sind. Dies könnte mit der Texteingabe in Miniserver machbar sein. Der unveränderliche Text kann mit dem sich ändernden Text mit einem Statusblock verbunden werden.

                Klicke auf die Grafik für eine vergrößerte Ansicht

Name: Rebuild JWT.png
Ansichten: 2116
Größe: 39,8 KB
ID: 280891

                Dann haben Sie den Token neu aufgebaut. Geben Sie den Tokentext an den Virtuellen Ausgang zur Steuerung des Schlosses aus.
                Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

                Kommentar

                • simon_hh
                  Lox Guru
                  • 18.09.2015
                  • 2659

                  #9
                  Tico Eine super Anleitung!

                  Ich habe es geschafft einen 15 stelligen Token meiner Überwachungskamera damit auszulesen.
                  Ich habe den Wert nun, z.B. "a37aeae45a32fae". Das ist der Token

                  Klicke auf die Grafik für eine vergrößerte Ansicht  Name: 15.PNG Ansichten: 0 Größe: 8,5 KB ID: 280906



                  Weißt Du, wie ich diesen an die URL des virtuellen Ausgang bekomme?
                  Der Befehl lautet dann
                  /cgi-bin/api.cgi?cmd=SetMdAlarm&token=a37aeae45a32fae

                  Wie bekomme ich das an den Virtuellen Ausgang Befehl? Den kann man ja nur fest eingeben...


                  Klicke auf die Grafik für eine vergrößerte Ansicht

Name: 16.PNG
Ansichten: 2260
Größe: 28,2 KB
ID: 280908
                  Zuletzt geändert von simon_hh; 21.12.2020, 09:51.
                  Haus: Bj 1959, gekauft 2011, totale Entkernung, Dachausbau, Erweiterung & Vergrößerung: Start: 2014, Ende: 2050
                  Loxone: 1 x Ms Gen.02, 1 x MS Gen.01, 5 x Ext., 4 x Relay Ext., 1 x Dimmer Ext., 2 x 1-wire Ext., 1 x DMX Ext. 1 x TREE Ext. mehr kommt noch
                  Licht: DMX LED Beleuchtung (24V), MW HLG Serie und eldoled Dimmer
                  Heizung: Brötje WBS 22F, OG Heizkörper und FuBoHeizung über RTL, EG FuBoHeizung

                  Kommentar

                  • simon_hh
                    Lox Guru
                    • 18.09.2015
                    • 2659

                    #10
                    Info hier gefunden...
                    Moin, kann man dem virtuellen Ausgang bei 'Befehl bei EIN' auch Text uebergeben oder nimmt die Variable (&lt;v&gt;) nur analoge Werte? Hintergrund ist, dass ich


                    Man kann über Statusbaustein die gesamtze URL generieren und als Wert <v> beim Ausgangs Befehl "Befehl ein EIN" übergeben
                    Haus: Bj 1959, gekauft 2011, totale Entkernung, Dachausbau, Erweiterung & Vergrößerung: Start: 2014, Ende: 2050
                    Loxone: 1 x Ms Gen.02, 1 x MS Gen.01, 5 x Ext., 4 x Relay Ext., 1 x Dimmer Ext., 2 x 1-wire Ext., 1 x DMX Ext. 1 x TREE Ext. mehr kommt noch
                    Licht: DMX LED Beleuchtung (24V), MW HLG Serie und eldoled Dimmer
                    Heizung: Brötje WBS 22F, OG Heizkörper und FuBoHeizung über RTL, EG FuBoHeizung

                    Kommentar


                    • Tico
                      Tico kommentierte
                      Kommentar bearbeiten
                      Eine Alternative ist, <v> dort zu platzieren, wo es in der virtuellen Ausgabe benötigt wird -

                      /cgi-bin/api.cgi?cmd=SetMdAlarm&token=<v>

                      Stellen Sie dann sicher, dass "Als digitalen Ausgang verwenden" nicht angehakt ist.

                      Wenn dies nicht funktioniert, ist die von Ihnen gepostete Version in der Regel erfolgreich.

                    • simon_hh
                      simon_hh kommentierte
                      Kommentar bearbeiten
                      ach das geht auch? Na super... Ich habe es nun über Statusbaustein gelöst. Im Statusbaustein wird /cgi-bin/api.cgi?cmd=SetMdAlarm&token=a37aeae45a32fae erzeugt und am Virtual Output mit <v> übergeben... und ja genau Digital Ausgang muss deaktiviert sein, sonst geht das nicht.
                  • Imperator
                    Extension Master
                    • 10.09.2018
                    • 101

                    #11
                    Verstehe ich dies richtig, dass ihr es erfolgreich geschafft habt die Erneuerung eines Tokens auszulesen? Liesse sich dies auch für einen Virtuellen Eingang verwenden?

                    Kommentar

                    • Tico
                      Lox Guru
                      • 31.08.2016
                      • 1035

                      #12
                      Virtuelle HTTP-Eingänge haben eine feste URL. Sie können kein wechselndes Token in die URL einfügen.

                      Ein virtueller Ausgang kann einen frei definierten Befehl für EIN oder Befehl für AUS haben. Sie können das Änderungs-Token in diese Adresse einfügen.

                      Vielleicht erklären Sie genauer, was Sie tun möchten.
                      Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

                      Kommentar

                      • Imperator
                        Extension Master
                        • 10.09.2018
                        • 101

                        #13
                        Ich suche einen Weg wie ich Abfragen gegenüber 3rd Party Devices und Services machen kann mit zeitlich begrenzten Tokens. Noch schöner wäre natürlich OAuth2, aber das wird in nächster Zeit kaum möglich werden. Die Lösung könnte hier eher über ein Loxberry Plugin führen.

                        Kommentar

                        • Tico
                          Lox Guru
                          • 31.08.2016
                          • 1035

                          #14
                          Haben Sie Beitrag #8 gelesen?

                          Ich versuche, Loxone Virtual Output in die Tedee-Sperr-API zu integrieren (https://api.tedee.com/swagger/index.html und https://tedee-tedee-api-doc.readthedocs-hosted.com/en/latest/). Für die Autorisierung ist leider die Verwendung des Bearer JWT-Tokens erforderlich. Ich habe 2 Probleme: 1) Die Integration über virtuelle
                          Ich spreche kein Deutsch. Gib Google Translate die Schuld, wenn ich unverständlich bin.

                          Kommentar

                          • Imperator
                            Extension Master
                            • 10.09.2018
                            • 101

                            #15
                            Ja, aber noch nicht getestet und ich verstehe die Limitationen dieses Lösungsansatzes noch nicht.

                            Kommentar

                            Lädt...