Search code examples
phphtmlbashshlamp

Execute sh file with html button click


I'm new to programming in html/php/javascript so I don't know how to start.

I'm trying to execute a .sh file (on linux) with a button on a webpage (so html I guess).

I read that I'd have to make a button on html but put the execute code in php but I can't seem to make a code out of it.

Help would be greatly appreciated

This isn't a duplicate, I said I'm new and I don't know how to do this with a button, thats where it's a diffrent question.


Solution

  • Most simple way is using GET Method and send a request to the script. This works even without fancy php coding.

    Simple Link

    http://example.com/script.sh?name=value&name2=value2&name3=value3&
    

    CGI-Scripts can process the Request via QUERY_STRING variable.


    In combination with SSL and POST u can send Data after the url, so your requests will be secured a bit.

    Html-form

    <form action="script.sh" method="POST">
    <input type="hidden" name="name3" value="value3">
    <input type="hidden" name="name2" value="value2">
    <button name="name" value="value">Click me</button>
    </form>
    

    The Script should react on POST Request and read stdin for the data deliverd. For the beginning the most important variables are REQUEST_METHOD and QUERY_STRING.

    hope this helps a bit.


    Here is a simple JavaScript variation to request data from cgi...

    var query_string = "name=value&name2=value2&name3=value3&";
    var request = new XMLHttpRequest();
    request.open("POST", "script.sh");
    request.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
    request.addEventListener('load', function(event) {
        if (request.status >= 200 && request.status < 300) {
            console.log(request.responseText);
        } else {
            console.warn(request.statusText);
        }
    });
    request.send(query_string);
    

    This code as an event like .addEventListener("click", functionname);


    I can also imagine u want to create a Bash-Script by ur own. If so u have to consider many things. I walk u though as simple as possible ...

    To react on a request u need to send back the content-type as first, followed by an empty line.

    echo "Content-Type: text/html"
    echo ""
    

    There are many many more options for CORS, but content-type is the most important.

    Next step would be checking the request.

    case "$REQUEST_METHOD" in
    POST)
        if [ "$CONTENT_TYPE" = "application/x-www-form-urlencoded" ]; then
            read -n "$CONTENT_LENGTH" QUERY_STRING_POST
                QUERY_STRING_ENC=$(echo -e $(echo "$QUERY_STRING_POST" | sed 's/+/ /g;s/%\(..\)/\\x\1/g;'))
        else    
            echo -e "Error\t777\ņReceived header has a bad CONTENT_TYPE.\nThe value has to be application/x-www-form-urlencoded."
        fi
    ;;
    *)
        echo -e "Error:\t555\nReceived header has wrong REQUEST_METHOD.\nThe value has to be POST only."
    ;;
    esac
    

    This code part checks for a valide REQUEST_METHOD and reads the stdin. Then it html-decode the query_string via sed.

    some security questions...

    DOMAIN="example.com"
    if [ "$HTTP_CONNECTION" != "keep-alive" ] || [ "$HTTP_HOST" != "$DOMAIN" ] || [ "$SERVER_NAME" != "$DOMAIN" ] || [ "$SERVER_PORT" -ne 443 ]; then
        echo -e "Error:\t666\nCorrupted connection refused."
    fi
    

    This checks for a valide connection. All envirement variables are listed in the manual of the http-server.

    Note that the environment variables like REQUEST_METHOD and QUERY_STRING can be processed by the shell directly. One must filter the input to avoid cross site scripting. Filter out "<>&*?./" to avoid trouble from hackers!

    After these steps u can put what ever u want in stdout. But keep in mind that every envirement-variable and stdin can be a threat and u need to filter all out before processing these things.

    cat << EOF
    <!DOCTYPE html>
    
    <html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
        <title>CGI Test</title>
    </head>
    <body>
        <h1>Hello World</h1>
    </body>
    </html>
    EOF
    

    Addition:

    To test all step by step I created me envtest.sh and inputtest.sh. U can copy inputtest.sh into /usr/lib/cgi-bin/ and make them executable.

    Terminal

    cd /usr/lib/cgi-bin
    chmod +x inputtest.sh 
    

    Now u can learn the html side first. Or the JavaScript variation. Or php and phyhon ...

    inputtest.sh

    #!/bin/bash
    
    exec 2>&1       # every error gets redirected into the html too
    
    
    echo "Content-type: text/html"
    echo ""
    echo "<html>"
    echo "<head>"
    echo "<title>Test</title>"
    echo "<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">"
    echo "</head>"
    echo "<body>"
    
    case "$REQUEST_METHOD" in
    GET)
        echo "<p>QUERY_STRING: ${QUERY_STRING}</p>"
    ;;
    POST)
        if [ "$CONTENT_TYPE" != "" ]; then
            read -n "$CONTENT_LENGTH" QUERY_STRING_POST
            echo "<p>$QUERY_STRING_POST</p>"
        else
            echo "<p>Error while REQUEST_METHOD=POST and CONTENT_TYPE=${CONTENT_TYPE}</p>"
        fi
    ;;
    *)
        echo "<p>Error wrong REQUEST_METHOD: \"${REQUEST_METHOD}\"</p>"
    esac
    
    echo "</body></html>"
    
    exit 0
    

    The link will look like ...

    http://example.com/cgi-bin/script.sh