Stefan: Wie kann ich aus $ENV{QUERY_STRING} nur "feldname=" löschen?

Moin! Moin!

Ich habe ein Formular (methode=POST) mit dem Inhalt name="link" value="/cgi-bin/anderes_script.cgi?zeige=nur_neue_texte"
Beim Submit erhalte ich dann in $ENV{QUERY_STRING} "link=/cgi-bin/anderes_script.cgi?zeige=nur_neue_texte". Ich möchte jetzt den Teil "/cgi-bin/anderes_script.cgi?zeige=nur_neue_texte" in meinem Script an eine URL dranhängen. Bespiel "www.homepage.de/cgi-bin/anderes_script.cgi?zeige=nur_neue_texte".

Dafür habe ich mir dieses Script gebastelt:

----------

#!/usr/bin/perl

read(STDIN, $url, $ENV{'CONTENT_LENGTH'});

print "Location:http://www.homepage.de$url\n";

exit;

----------

Wie kriege ich das hin, das das Script nur den gewünschten Teil, d. h. ohne Angabe des Feldnamens in meine Variable einsetzt.

Falls es da eine Lösung gibt, erklärt mir das ganze bitte mal so, daß ich als Perl-Anfänger das ganze auch verstehe.

Schon mal Danke im Voraus

Gruß

Stefan

  1. 'Nabend,


    #!/usr/bin/perl

    read(STDIN, $url, $ENV{'CONTENT_LENGTH'});

    print "Location:http://www.homepage.de$url\n";

    exit;

    Wenn wirklich nur der eine Parameter übergeben wird, schreib zwischen dem "read" und dem "print" noch

    $url =~ s/^link=//;

    bedeutet folgendes:

    Wende auf die Variable "$url" einen regulären Ausdruck an ("=~"), und zwar eine Ersetzung (Substitution, s/^link=//).

    Die Ersetzung passiert folgendermassen: Suchtext ist das zwischen dem ersten / und dem mittleren /, also in diesem Fall "^link=", ersetzt wird es durch das zwischen dem mittleren / und dem letzten /, also in diesem Fall nix. Das "^" bedeutet "Suche den Text link= nur am Anfang des zu druchsuchenden Textes".

    Weitere Infos zu regulären Ausdrücken siehe "man perlre" wenn du unter Linux/Unix arbeitest.

    Ach ja, du kannst es auch versuchen mit

    substr $url,0,5,"";

    wodurch aus der Variable "$url" von Beginn an ("0") die ersten fünf Zeichen durch "" ersetzt werden (siehe perldoc -f substr). Aber schau mal in einem Monat wieder in den Quelltext, und du weisst nicht mehr unbedingt wofür das gut war...

    Wenn noch mehr Parameter übergeben werden, nimm das Perlmodul "CGI".

    HTH
    Thorsten

    1. Hallo!

      Ach wie schön. Das funktioniert.

      Zunächst mal vielen Dank!!!

      Das war wirklich gut erklärt.

      Da Du Dich ja offensichtlich auskennst, hier gleich die nächste Frage.

      Man sollte bei read ja auch sagen können, ab wo (welchem Byte) gelesen werden soll.

      Ich habe das so versucht:

      read(STDIN, $url, $ENV{"CONTENT_LENGTH"}, 6);
                                                ^
                                                |
                                Diese 6 heißt doch: Lies ab dem 6. Byte, oder?

      Warum hat das Ganze denn so nicht funktioniert? Liege ich da richtig, daß in meinem Fall ein Byte = ein Buchstabe ist?

      Gruß

      Stefan

      1. read(STDIN, $url, $ENV{"CONTENT_LENGTH"}, 6);
                                                  ^
                                                  |
                                  Diese 6 heißt doch: Lies ab dem 6. Byte, oder?

        Mmh, den read-befehl habe ich so noch nie benutzt, aber die Perl-Hilfe dazu sagt folgendes:

        ---snip---
        dralli@hiltrud:~ > perldoc -f read
        =item read FILEHANDLE,SCALAR,LENGTH,OFFSET

        =item read FILEHANDLE,SCALAR,LENGTH

        Attempts to read LENGTH bytes of data into variable SCALAR from the
        specified FILEHANDLE.  Returns the number of bytes actually read,
        C<0> at end of file, or undef if there was an error.  SCALAR will be grown
        or shrunk to the length actually read.  An OFFSET may be specified to
        place the read data at some other place than the beginning of the
        string.  This call is actually implemented in terms of stdio's fread(3)
        call.  To get a true read(2) system call, see C<sysread()>.
        ---snap---

        Was ich so verstehe: die eingelesenen Daten werden ab dem Offset in die Variable geschrieben. Wenn also $url z.B. den Wert "Thunfischpizza" hat und du mit dem Befehl

        read(STDIN, $url, $ENV{"CONTENT_LENGTH"}, 6);

        deinen Link einliest, steht danach in $url

        Thunfilink=/cgi-bin/anderes_script.cgi?zeige=nur_neue_texte

        Falls $url leer ist, stehen halt vor dem "link=..." noch ein paar Null-Bytes.

        Kann mich aber auch irren, hab ich noch nicht ausprobiert...

        Gruß
        Thorsten

        1. ...an diese Möglichkeit hab ich natürlich wieder nicht gedacht. Das könnte sein. Da mein Denkansatz nicht funktioniert hat, wird Deiner wohl richtig sein.

          Vielen Dank nochmal und noch eine schöne Nacht.

          Gruß

          Stefan

    2. Hallo Thorsten!

      Ich muss Stefan recht geben, das war wirklich gut erklärt, denn zum ersten Mal verstehe ich wozu das mir oft augefallene aber von mir nicht näher beachtete "Konstrukt":

      substr $url,0,5,"";

      gut sein soll... Mal sehen, wie ich das für die Browser- oder OS-Auswertung aus den User Agents verwenden kann (oder auch anderen Dingen) ;-)

      Patrick
      <hatehtehpehdoppelpunktslashslashwehwehwehpunktatomicminuseggspunktcomslash>

  2. Sup!

    $ENV{"QUERY_STRING} =~ s/^value=//;

    Entfernt value= am Wortanfang (symbolisiert durch das ^).
    Kauf' ein Perl Buch, vielleicht "Programming Perl" von Larry Wall, O'Reilly, ziemlich teuer.

    Gruesse,

    Bio

    1. Hallo!

      Danke für die schnelle Antwort.

      Ich habe schon ein Perl-Buch, hab es aber leider noch nicht ganz durchgelesen. So weit, daß ich diese Problem hätte lösen können, war ich aber schon lange. Mein Ansatz war aber der, das ich read sage, ab welchem Byte gelesen werden soll. Das hat aber leider nicht funktioniert.

      Aber da Du Dich ja auskennst und ich vielleicht wieder dabei was lernen kann, hier gleich die nächste Frage zu Deiner Möglichkeit:

      Damit ich Deine Möglichkeit nutzen kann, muß ich aber das Formular per method="get" versenden. Oder liege ich da falsch?

      Gruß

      Stefan

      1. Hi,

        ich bin's nochmal. ;-)

        Aber da Du Dich ja auskennst und ich vielleicht wieder dabei was lernen kann, hier gleich die nächste Frage zu Deiner Möglichkeit:

        Scheinbar deine bevorzugte Methode bis das Forum hier dein ganzes Skript zusammengeschustert hat ;-) Tipp: Neues Problem -> neuer Thread.

        Damit ich Deine Möglichkeit nutzen kann, muß ich aber das Formular per method="get" versenden. Oder liege ich da falsch?

        Jepps, das ist richtig. Allgemeiner geht's nur mit dem CGI-Modul (ist IMHO in einer Perl-Standard-Distri drin). Dann sieht dein Skript so aus:

        --snip--
        #!/usr/bin/perl -w

        use CGI qw(:standard);

        $url = param("link");
        print "Location: http://www.homepage.de$url\n\n";
        --snap--

        Ist nicht so schnell (da das CGI-Modul erst geladen werden muss), aber dafür allgemeiner und leicht zu verstehen.

        Und hier der kostenlose Tipp für einen Perl-Neuling: In der ersten Zeile immer das "-w" anhängen, damit Perl ein bißchen redseliger bei typischen Fehlern wird.

        Gruß
        Thorsten

        1. ...Nein, Nein. Das siehst Du falsch.

          Es geht hier um ein und das selbe Problem.
          Ich war mit Deiner Antwort schon vollends bedient.
          Bio hat mir aber einen anderen Ansatz aufgezeigt. Jetzt weiß ich aber vom Üben/Lernen, daß mir QUERY_STRING nur bei method="get" zur Verfügung steht. Das wollte ich nur nochmal bestätigt wissen. Wenn dem aber nicht so sein sollte, hätte ich schon wieder was gelernt.

          perl -w kenne ich, habs vergessen. Ich werde es mir jetzt entgültig zu Herzen nehmen.

          Deine "use CGI-Methode" werde ich natürlich auch noch ausprobieren.

          Gruß

          Stefan

          1. Hi,

            ...Nein, Nein. Das siehst Du falsch.
            Es geht hier um ein und das selbe Problem.

            Don't panic. Ich fand's nur witzig, dass du sowohl auf mein Posting als auch auf das vn Bio mit einem "...avber du du dich ja auszukennen scheinst..." geantwortet hast.

            Ich war mit Deiner Antwort schon vollends bedient.

            Bedient? Das klingt so negativ... ;-) Aber ich verstehe was du meinst.

            Bio hat mir aber einen anderen Ansatz aufgezeigt.

            Eigentlich derselbe Ansatz, nur etwas mehr "perlish" geschrieben.

            perl -w kenne ich, habs vergessen.

            Der erste Fehler in einem Perl-Programm...

            • Thorsten
            1. ...was so eine Formulierung alles ausmachen kann.

              Don't panic. Ich fand's nur witzig, dass du sowohl auf mein Posting als auch auf das vn Bio mit einem "...avber du du dich ja auszukennen scheinst..." geantwortet hast.

              Zumindest ein "Danke Schön gehört sich ja". Ich hatte ja geschrieben, daß ich method="get" nutze, hat mich eben gewundert, daß Bio mit dieser Lösung kam.

              Guts Nächtle

              Stefan

        2. Hallo Thorsten!

          Und hier der kostenlose Tipp für einen Perl-Neuling: In der ersten Zeile immer das "-w" anhängen, damit Perl ein bißchen redseliger bei typischen Fehlern wird.

          Auch gut, und damit gebe ich einen Tipp weiter, den ich selber vor gar nicht so langer Zeit erhalten habe (huhu CK):

          use CGI::Carp qw(fatalsToBrowser);

          Damit werden die Errors direkt im Browser angezeigt (für die, wie ich, die meistens in einer HTTP-Umgebung testen), und man muss ich nicht mühsam die (schlimmsten) Errors in der entsprechenden Error-File zusammen suchen ;-)

          Patrick
          <hatehtehpehdoppelpunktslashslashwehwehwehpunktatomicminuseggspunktcomslash>

      2. Sup!

        Wie wär's mit einem CGI-Buch?

        Bei der POST-Methode steht der ganze Kram nicht in einer ENV-Variablen, sondern wird über STDIN ins Programm geschrieben.
        Das müßte dann ungefähr so in einen Hash reingeschrieben werden können (ich habe das nicht getestet und seit Wochen sowas nicht gemacht!)

        Dann sollte in $hash {form.name} der Wert form.name.value drinstehen, wenn Du verstehst, was ich meine.

        $bla=<STDIN>;
        @array = split "&",$bla;
        foreach $element (@array)
        {
        ($a,$b)=split "=",$element;
        $hash{$a}=$bf;
        }

        Gruesse,

        Bio