Button in PowerPI Webinterface einfügen

  • Servus zusammen,
    ich wühle mich Seite Tagen durch Netz und die php Seiten.Ich komme einfach zu keiner Lösung, da die Seiten anscheinend sehr verschachtelt sind.

    Ich habe vorhandene PHP Seiten. Und zwar die von PeterSilies Projekt Haussteuerung.

    Ich würde gerne einen Button einfügen, der genau aussieht wie die anderen, aber ein Python Script ausführt.Das sollte ja mit... exec (python usw.)... funktionieren.
    Deswegen meine Frage:

    Wie bekomme ich einen zusätzlichen Button eingefügt, der aussieht wie die anderen und einen exec Befehl ausführt, ODER noch besser, wie bekomme ich die exec Funktion auf einen bestehenden Button gelegt?

    Zur ergänzung vielleicht noch der Grund:
    Ich möchte mein Rollo Motor steuern.Dazu soll, wenn ich zum Beispiel auf Rollo AN drücke, der GPIO nur 10 Sekunden anbleiben.Dazu habe ich mir ein kleines Python Script gemacht, welches funktioniert.

    Falls ihr noch Infos braucht, sagt mir welche.

    Schonmal vielen Dank!

  • Es sind einige Seiten.Ich weis leider nicht welche alle relevant sind.
    Eine rar Datei mit allen Seiten kann ich nicht anhängen.

    Die home Seite habe ich jetzt mal angehangen, auf der eigentlich die Buttons sein sollten.
    Die andere Seite ist villeicht auch noch interessant.

    Das ganze Paket ist im www ordner http://raspberrypiguide.de/stuff/powerpi-0.1.tar.gz

  • Wieso fragst du nicht den Entwickler? Ich denk das würde einiges vereinfachen :)


    Soweit ich das bisher beurteilen kann wird die Navigation über pages/home.php generiert , aber wie genau ein neuer Eintrag aussehen müsste kann ich nicht sagen - kann ich nur raten: Für jeden AddAction Eintrag scheint es eine dadrunter stehende function zu geben ... aber bei allem andern, wie ein entsprechender Eintrag aussehen müßte usw kann ich nicht nachvollziehen -- wie gesagt, frag einfach den Entwickler der weiß bestimmt auf Anhieb was er sich dabei gedacht hat :D


    PS: Bitte die Überschrift im ersten Beitrag anpassen und "PowerPI" anstatt "in vorhandene Seite" o.ä. ändern

  • Das war auch mein erster Gedanke.Er antwortet mir aber leider nicht :(
    Aber schonmal Danke für deine Hilfe :thumbs1:

    Wenn ich übrigens über einen PHP Editor die Seite vom Server ziehe steht in der index.html zusätzlich untern folgendes:

    lässt sich dort ein Kommando anhängen?

  • Naja ne, die PHP Dateien generieren eine HTML Ausgabe, die dann letzlich als Quellcode angezeigt wird... Aber um diese zu verändern musst du das in der richtigen PHP Datei eintragen damit die dann den entsprechenden HTML Code generiert und ausgibt ;)

    Wie du schon selber festgestellt hast sind die PHP Dateien verschachtelt..

    Spoiler anzeigen


    Die index.php ruft die system.php Datei auf, die wiederum ruft mehrere Dateien auf:
    [code=php]
    <?php
    // Config
    include('./conf/config.php');

    // Modules
    //include('./modules/database.php');
    include('./modules/core.php');
    include('./modules/secure.php');
    include('./modules/template.php');
    include('./modules/navigation.php');
    include('./modules/meta.php');

    $app = new stdClass();
    $app->Conf = new Config();
    //$app->DB = new Database($app);
    $app->Core = new Core($app);
    $app->Secure = new Secure();
    $app->Tpl = new Template($app);
    $app->Nav = new Navigation($app);
    $app->Meta = new Meta($app);
    ?>
    [/php]

    Über www/conf/config.php wird einiges eingestellt bzw geladen:
    [code=php]
    <?php

    class Config
    {
    function Config()
    {
    // General
    $this->LANG = 'EN';
    $this->DOMAIN = '';
    $this->BASEDIR = '.';
    define('_BASEDIR', $this->BASEDIR);

    // Database
    $this->DB_ENABLED = false;
    $this->DB_HOST = 'localhost';
    $this->DB_USER = '';
    $this->DB_PASSWORD = '';
    $this->DB_DATABASE = '';

    // Template-Engine
    $this->TPL_DIR = './pages/';
    $this->TPL_TPLDIR = './pages/tpl/';
    $this->TPL_THEME = 'default';

    // Navigation
    $this->NAV_DEFAULT = _BASEDIR.'/index.php?page=home&action=list';
    $this->NAV_PAGES = array('home');

    // Meta
    $this->META_TITLE = 'PowerPi';
    $this->META_DESCRIPTION = 'Control your home';
    $this->META_KEYWORDS_EN = '';
    $this->META_KEYWORDS_DE = '';
    $this->META_AUTHOR = 'Anton Hammerschmidt';
    }
    }
    ?>
    [/php]

    Und dann gibts halt auch noch template Dateien die die obige Ausgabe beinhaltet www/pages/tpl/home_list.tpl
    [code=php]
    <script>
    $(document).ready(function() {
    $('.socket > .button_on').click(function() {
    var socket = $(this).attr('socket-name');
    if(socket!='' && socket!='undefined') {
    $.get('[BASEDIR]/lib/powerpi.php?action=setsocket&socket='+socket+'&status=1', function() {
    });
    }
    });

    $('.socket > .button_off').click(function() {
    var socket = $(this).attr('socket-name');
    if(socket!='' && socket!='undefined') {
    $.get('[BASEDIR]/lib/powerpi.php?action=setsocket&socket='+socket+'&status=0', function() {
    });
    }
    });

    $('.gpio > .button_on').click(function() {
    var gpio = $(this).attr('gpio-name');
    if(gpio!='' && gpio!='undefined') {
    $.get('[BASEDIR]/lib/powerpi.php?action=setgpio&gpio='+gpio+'&status=1', function() {
    });
    }
    });

    $('.gpio > .button_off').click(function() {
    var gpio = $(this).attr('gpio-name');
    if(gpio!='' && gpio!='undefined') {
    $.get('[BASEDIR]/lib/powerpi.php?action=setgpio&gpio='+gpio+'&status=0', function() {
    });
    }
    });

    $('.schedule').click(function() {
    var schedule = $(this).attr('schedule-name');
    if(schedule!='' && schedule!='undefined') {
    $.get('[BASEDIR]/lib/powerpi.php?action=setschedule&schedule='+schedule, function() {
    window.location.reload();
    });
    }
    });
    });
    </script>


    <div class="container-fluid">
    [SOCKETS]
    [GPIOS]
    [SCHEDULES]
    </div>
    [/php]

    Und wie gesagt, www/pages/home.php sieht so aus:[code=php]
    <?php

    class Home
    {
    var $app;

    function Home(&$app)
    {
    $this->app = $app;

    $this->app->Nav->AddPage('home');
    $this->app->Nav->AddAction('list', 'HomeList');
    $this->app->Nav->AddAction('settings', 'HomeSettings');
    $this->app->Nav->AddAction('help', 'HomeHelp');
    $this->app->Nav->DefaultAction('list');
    }

    function HomeList()
    {
    include('./lib/powerpi.php');

    $data = GetData();

    // ### Sockets ###
    $sockets = ParseSockets($data);
    $sockets_out = '';
    for($i=0;$i<count($sockets);$i++) {
    $sockets_out .= "<li>
    <div class=\"button socket\">
    <div class=\"button_text\">{$sockets[$i]['name']}</div>
    <div class=\"button_off\" socket-name=\"{$sockets[$i]['name']}\">OFF</div>
    <div class=\"button_on\" socket-name=\"{$sockets[$i]['name']}\">ON</div>
    </div>
    </li>";
    }
    $sockets_out = ((count($sockets) > 0) ? "<ul class=\"buttonlist\">{$sockets_out}</ul>" : '');
    $this->app->Tpl->Set('SOCKETS', $sockets_out);


    // ### GPIO'S ###
    $gpios = ParseGpios($data);
    $gpios_out = '';
    for($i=0;$i<count($gpios);$i++) {
    $gpios_out .= "<li>
    <div class=\"button gpio\">
    <div class=\"button_text\">{$gpios[$i]['name']}</div>
    <div class=\"button_off\" gpio-name=\"{$gpios[$i]['name']}\">OFF</div>
    <div class=\"button_on\" gpio-name=\"{$gpios[$i]['name']}\">ON</div>
    </div>
    </li>";
    }
    $gpios_out = ((count($gpios) > 0) ? "<ul class=\"buttonlist\">{$gpios_out}</ul>" : '');
    $this->app->Tpl->Set('GPIOS', $gpios_out);

    // ### Schedules ###
    $schedules = ParseSchedules($data);
    $schedules_out = '';
    for($i=0;$i<count($schedules);$i++) {

    $status_text = (($schedules[$i]['status']=='1') ? 'Active' : 'Inactive');

    $schedules_out .= "<li>
    <div class=\"button schedule\" schedule-name=\"{$schedules[$i]['name']}\">
    <div class=\"button_text\">{$schedules[$i]['name']}</div>
    <div class=\"status\">$status_text</div>
    </div>
    </li>";
    }
    $schedules_out = ((count($schedules) > 0) ? "<ul class=\"buttonlist\">{$schedules_out}</ul>" : '');
    $this->app->Tpl->Set('SCHEDULES', $schedules_out);


    $this->app->Tpl->Set('MENUHOME', 'class="active"');
    $this->app->Tpl->Parse('PAGE', 'home_list.tpl');
    }

    function HomeSettings()
    {
    include('./lib/powerpi.php');

    $data = GetData();

    // ### Sockets ###
    $sockets = ParseSockets($data);
    $socket_table = '';
    for($i=0;$i<count($sockets);$i++) {
    $socket_table .= "<tr><td>{$sockets[$i]['name']}</td>
    <td>{$sockets[$i]['code']}</td>
    <td><a socket-name=\"{$sockets[$i]['name']}\" socket-code=\"{$sockets[$i]['code']}\" href=\"#\" class=\"socket_delete btn btn-large btn-block btn-danger\" style=\"float:none;\"><span class=\"fui-cross-16\"></span></a></td></tr>";
    }
    $this->app->Tpl->Set('SOCKETTABLE', $socket_table);


    // ### GPIO'S ###
    $gpios = ParseGpios($data);
    $gpio_table = '';
    for($i=0;$i<count($gpios);$i++) {
    $gpio_table .= "<tr><td>{$gpios[$i]['name']}</td>
    <td>{$gpios[$i]['gpio']}</td>
    <td><a gpio-name=\"{$gpios[$i]['name']}\" gpio-id=\"{$gpios[$i]['gpio']}\" href=\"#\" class=\"gpio_delete btn btn-large btn-block btn-danger\" style=\"float:none;\"><span class=\"fui-cross-16\"></span></a></td></tr>";
    }
    $this->app->Tpl->Set('GPIOTABLE', $gpio_table);

    // ### Scheduler ###
    $schedules = ParseSchedules($data);
    $schedule_table = '';
    for($i=0;$i<count($schedules);$i++) {
    $onoff_text = (($schedules[$i]['onoff']=='1') ? 'ON' : 'OFF');
    $socket_notfound = (($schedules[$i]['socket']=='' || $this->app->Core->ArraySearch('name', $schedules[$i]['socket'], $sockets))
    ? '' : '<span class="notfound">[Not Found]</span>');
    $gpio_notfound = (($schedules[$i]['gpio']=='' || $this->app->Core->ArraySearch('name', $schedules[$i]['gpio'], $gpios))
    ? '' : '<span class="notfound">[Not Found]</span>');
    $schedule_table .= "<tr>
    <td>{$schedules[$i]['name']}</td>
    <td>{$schedules[$i]['socket']} $socket_notfound</td>
    <td>{$schedules[$i]['gpio']} $gpio_notfound</td>
    <td>".str_pad($schedules[$i]['hour'], 2, 0, STR_PAD_LEFT).":".str_pad($schedules[$i]['minute'], 2, 0, STR_PAD_LEFT)."</td>
    <td>$onoff_text</td>
    <td><a schedule-name=\"{$schedules[$i]['name']}\" schedule-socket=\"{$schedules[$i]['socket']}\" schedule-gpio=\"{$schedules[$i]['gpio']}\" schedule-hour=\"{$schedules[$i]['hour']}\" schedule-minute=\"{$schedules[$i]['minute']}\" schedule-onoff=\"{$schedules[$i]['onoff']}\" href=\"#\" class=\"schedule_delete btn btn-large btn-block btn-danger\" style=\"float:none;\"><span class=\"fui-cross-16\"></span></a></td></tr>";
    }
    $this->app->Tpl->Set('SCHEDULERTABLE', $schedule_table);


    $gpio_select = $this->app->Core->ParseSelect($gpios, 'Choose GPIO');
    $this->app->Tpl->Set('GPIOSELECT', $gpio_select);

    $socket_select = $this->app->Core->ParseSelect($sockets, 'Choose Socket');
    $this->app->Tpl->Set('SOCKETSELECT', $socket_select);

    $hour_select = $this->app->Core->TimeSelect(23);
    $this->app->Tpl->Set('HOURSELECT', $hour_select);

    $minute_select = $this->app->Core->TimeSelect(59);
    $this->app->Tpl->Set('MINUTESELECT', $minute_select);

    $this->app->Tpl->Set('TIME', exec('date +"%T"'));

    $this->app->Tpl->Set('MENUSETTINGS', 'class="active"');
    $this->app->Tpl->Parse('PAGE', 'home_settings.tpl');
    }

    function HomeHelp()
    {

    $this->app->Tpl->Set('MENUHELP', 'class="active"');
    $this->app->Tpl->Parse('PAGE', 'home_help.tpl');
    }

    }
    ?>
    [/php]


    Das einzige was vielleicht in Frage käme wär das ggf manuell in www/themes/default/index.html einzutragen, aber ich weiß nicht ob das funktionieren würde oder alles kaputt macht...

  • +++EDIT+++

    Ich kann manuell in der index.html eine Zeile mit An/Aus Knopf einfügen und natürlich den Text ändern, wenn ich diesen dann aber nicht mit dem exec Befehl Verknüft bekommen bringt das nichts.
    Foto und index hängt an...

    Ich fürchte ich muss auf eine Antwort vom Entwickler hoffen.

    Mal ne andere Idee...

    Wenn ich eine Grafik einfüge von einem Button, ließe sich darüber etwas ausführen? Eine Art Hyperlink zu nem exec Befehl?

  • Einen Hyperlink mußt du ja auch in PHP einfügen und festlegen was dadurch ausgelöst werden muss.... Also kannste auch gleich daher gehen und den PHP Code in die index.html einbauen..


    Zum Beispiel so:
    (KEINE GEWÄHR!)
    [code=php]
    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
    <head>
    <title>[METATITLE]</title>
    <meta name="description" content="[METADESCRIPTION]"/>
    <meta name="keywords" lang="en" content="[METAKEYWORDSEN]"/>[METAKEYWORDSDE]
    <meta name="author" content="[METAAUTHOR]">
    <meta name="date" content="[METADATE]"/>
    <meta name="robots" content="[METAINDEX]">
    <meta http-equiv="content-language" content="en">
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0">

    <link rel="shortcut icon" href="[BASEDIR]/themes/[THEME]/favicon.ico">
    <link rel="stylesheet" type="text/css" href="[BASEDIR]/themes/[THEME]/css/bootstrap.css">
    <link rel="stylesheet" type="text/css" href="[BASEDIR]/themes/[THEME]/css/flat-ui.css">
    <link rel="stylesheet" type="text/css" href="[BASEDIR]/themes/[THEME]/css/no-more-table.css">

    <!-- HTML5 shim, for IE6-8 support of HTML5 elements. All other JS at the end of file. -->
    <!--[if lt IE 9]>
    <script src="[BASEDIR]/js/html5shiv.js"></script>
    <![endif]-->
    <link rel="stylesheet" type="text/css" href="[BASEDIR]/themes/[THEME]/css/main.css" />

    <script src="[BASEDIR]/js/jquery-1.9.1.min.js"></script>
    <script src="[BASEDIR]/js/bootstrap.min.js"></script>

    </head>

    <body>
    <div class="container-fluid">
    <div class="navbar navbar-inverse" style="margin-top:10px;">
    <div class="navbar-inner">
    <div class="container-fluid">
    <button type="button" class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse">
    <span class="icon-bar"></span>
    <span class="icon-bar"></span>
    <span class="icon-bar"></span>
    </button>
    <div class="nav-collapse collapse">
    <ul class="nav">
    <li [MENUHOME]>
    <a href="[BASEDIR]/index.php?page=home&action=list">Home</a>
    </li>
    <li [MENUSETTINGS]>
    <a href="[BASEDIR]/index.php?page=home&action=settings">Settings</a>
    </li>
    <li [MENUHELP]>
    <a href="[BASEDIR]/index.php?page=home&action=help">Help</a>
    </li>
    </ul>
    </div>
    </div>
    </div>
    </div>
    <?php
    $ROLLO = isset($_POST["ROLLO"]) ? $_POST["ROLLO"] : "";
    if (!empty($ROLLO)) {
    if ($ROLLO = 'hoch') { exec("python /path/to/rollohoch.py"); }
    if ($ROLLO = 'runter') { exec("python /path/to/rollorunter.py"); }
    }
    ?>
    <form name='rollo' action='' method='POST'>
    <button type='submit' value='hoch' name='ROLLO'>ROLLO hoch</button>
    <button type='submit' value='runter' name='ROLLO'>ROLLO runter</button>
    </form>
    </div>
    [PAGE]
    </body>
    </html>
    [/php]

  • Ja cool :)
    Damit lässt sich doch vielleicht schon was anstellen.Leider wird das Script nicht ausgeführt.Muss ich mal schauen warum...
    Habe meinen Beitrag von vorhin nochmal editiert und die index.html bearbeitet

    +++EDIT+++

    Ich kann machen was ich will, das Script wird nicht ausgeführt mit deinen Buttons.

    Hab mich an diese Anleitung gehalten: Pythonskript über PHP starten

    Hoffentlich hat noch Jemand eine Idee :(

    Einmal editiert, zuletzt von Bensson (10. Februar 2014 um 18:51)

  • 2014/02/11 16:03:03 [error] 2126#0: *10 FastCGI sent in stderr: "PHP message: PHP Notice: Undefined index: page in /var/www/modules/secure.php on line 13
    PHP message: PHP Notice: Undefined index: action in /var/www/modules/secure.php on line 13" while reading response header from upstream, client: 192.168.178.37, server: localhost, request: "GET / HTTP/1.1", upstream: "fastcgi://unix:/var/run/php5-fpm.sock:", host: "192.168.178.40"


    Auch keine Änderung nach dem Neuaufsetzen des gesamten Systems.
    Habe mal nur die hoch/runter buttons in eine Seite gepackt ohne das Powerpi Webinterface.Ebenfalls ohne Erfolg.Dabei dachte ich das wäre das kleinere Problem :neutral:
    Ich fürchte das gibt keinen

    Einmal editiert, zuletzt von Bensson (11. Februar 2014 um 16:16)

  • Habe folgendes ausgeführt:

    Code
    sudo -u www-data python /var/www/rollohoch.py

    bekomme dann folgendes:

    Traceback (most recent call last):
    File "/var/www/rollohoch.py", line 5, in <module>
    GPIO.setup(22, GPIO.OUT)
    RuntimeError: No access to /dev/mem. Try running as root!

    Meine sudoers sieht so aus:

    Einmal editiert, zuletzt von Bensson (11. Februar 2014 um 23:52)

  • Hab ich bereits gemacht, und grade trotzdem nochmal. Da tut sich nichts.
    Das Script funktioniert über "sudo pyton"
    Habe es auch ausführbar gemacht.
    Einfach nichts.

    Immer noch keine Rechte für dev/mem

    Habe jeden Link der ersten 4 Seiten google bzgl PHP exec durch.Kein Lösungsansatz hat funktioniert.Auch nicht nach neuaufsetzen des Systems.
    ZUr Info vielleicht noch. Ich benutze Nginx.
    Beim anlegen des Benutzers www-data sagte er mir "Eintrag existiert bereits"

    Einmal editiert, zuletzt von Bensson (13. Februar 2014 um 10:27)


  • Habe folgendes ausgeführt:

    Code
    sudo -u www-data python /var/www/rollohoch.py

    bekomme dann folgendes:

    Traceback (most recent call last):
    File "/var/www/rollohoch.py", line 5, in <module>
    GPIO.setup(22, GPIO.OUT)
    RuntimeError: No access to /dev/mem. Try running as root!

    Habe es eben mal bei mir ausprobiert.
    Den Fehler an deinem Testbefehl habe ich gefunden...

    Mit "sudo -u www-data" wechselst du zu dem User www-data.
    Anschließend rufst du aber "python /var/www/rollohoch.py" ohne sudo auf.

    Um Rechtsprobleme auszuschließen kannst du mal folgenden Befehl testen:

    Code
    sudo -u www-data sudo python /var/www/rollohoch.py

    Gruß

    bigdane

  • Das habe ich ebenfalls gemacht und das funktioniert natürlich auch. Ich habe es bewusst ohne sudo gemacht, um zu testen ob ich mit www-data root Rechte habe, da ich über eine PHP Seite ein Script ausführen will. Solange ich diese ja nicht habe wird es auch auf der Seite nicht funktionieren.

    Also wenn:

    sudo -u www-data sudo python /var/www/rollohoch.py

    funktioniert, ist es kein Rechte Problem?

    Einmal editiert, zuletzt von Bensson (13. Februar 2014 um 12:29)

  • Wenn "sudo -u www-data sudo python /var/www/rollohoch.py" funktioniert, sollte auch exec("sudo python /var/www/rollohoch.py") via PHP funktionieren.

    Damit es klappt muss denke ich folgendes in deiner /etc/sudoers stehen:

    Code
    #includedir /etc/sudoers.d
    pi ALL=(ALL) NOPASSWD: ALL
    www-data ALL=(ALL) NOPASSWD: ALL


    Wenn das klappt, kannst du im nächsten Schritt immer noch versuchen, die sudo Rechte für www-data zu reduzieren...

    Einmal editiert, zuletzt von bigdane69 (13. Februar 2014 um 12:53)

  • Aus der PHP gehts nicht.

    sudo -u www-data sudo python /var/www/rollohoch.py läuft ohne Probleme.

    In meiner sudoers steht auch

    Code
    www-data ALL:(ALL) NOPASSWD: ALL

    drin.Genau so wie Du es geschrieben hast, in der gleichen Zeile.

    Einmalie Buttons:


    Und das Python Script:

    Einmal editiert, zuletzt von Bensson (13. Februar 2014 um 17:51)


  • In meiner sudoers steht auch

    Code
    www-data ALL:(ALL) NOPASSWD: ALL

    Genau so wie Du es geschrieben hast, in der gleichen Zeile.

    Vergleich mal deinen Eintrag mit der von bigdane69 -> du nutzt " : " er nutzt aber " = " ... also nicht genau so ...

    .. aber ich nutze eine andere:

    Code
    www-data ALL=NOPASSWD: ALL

    Bitte verwende den Befehl visudo wenn du die sudoers bearbeitest - damit wird die Syntax überprüft und ggf eine Warnung ausgegeben wenn du eine falsche Syntax verwendet haben solltest...



    Einmalie Buttons:

    Debug das halt mal und lass dir das $_POST array ausgeben:

    [code=php]
    <?php
    echo "<pre>";
    var_dump($_POST);
    echo "</pre>";

    $ROLLO = isset($_POST["ROLLO"]) ? $_POST["ROLLO"] : "";
    if (!empty($ROLLO)) {
    if ($ROLLO = 'hoch') { exec("sudo python /var/www/rollohoch.py"); }
    if ($ROLLO = 'runter') { exec("sudo python /var/www/rollorunter.py"); }
    }
    ?>
    [/php]

    Wenn du dann auf einen Knopf drückst sollte dir ein array mit ROLLO -> hoch angezeigt werden

  • Hatte es so wie bigdane drin stehen, aber hier einfach falsch aus dem Kopf reingeschrieben ;)

    Wenn ich den hier mache:



    kommt nur das:

Jetzt mitmachen!

Du hast noch kein Benutzerkonto auf unserer Seite? Registriere dich kostenlos und nimm an unserer Community teil!