Blue Ribbon Campaign for Free Speech Bijlagen voor "CGI Is Heel Makkelijk"

Terug naar Hoofd Pagina Ga naar andere tutorials

  1. Voorbeelden van CGI programma's
  2. CGI Mailer Script
  3. CGI Scripts en veiligheid
  4. Het plaatsen van je script op de server
  5. Een eerder gemaakt bestand terugzenden als antwoord
  6. Andere bruikbare CGI Environment Variabelen
  7. Een plaatje of ander Niet-HTML antwoord terugsturen na een CGI script
  8. Wat is het verschil tussen GET en POST?
  9. Krijg meer controle met "non-parsed header scripts"

Voorbeelden van CGI Programma's

Omdat mij vaak gevraagd werd om wat programma's bij de tutorial te doen, zijn hier een aantal "hello, world" CGI programma's om mee te beginnen. De simpele versie laat alleen de CGI uitvoer zien, en de langere versie zal ook een aantal invoervelden met antwoord teruggeven. Perl en C-versies, met broncode. Terug naar de top


CGI Mailer Script

Een van de meest gangbare toepassing van een CGI script is om de formulier-data naar een e-mailadres te mailen. Hier is een simpel script, geschreven in Perl, wat dat doet, het heet mailer.pl.

Maak deze veranderingen in het script voordat je het ergens neerzet:

Formulier Data Mailen Zonder CGI

Er is een andere (maar die vinden wij, CGI-ers, wel een zwakkere) manier om formulierdata te mailen, die manier gebruikt alleen HTML: in de <form> tag maak je van de action een "mailto:" URL, en de enctype wordt "text/plain". De meeste browsers verwerken dat goed, ze zenden namelijk de formulierdata in een mail-bericht. Bijvoorbeeld:
<form action="mailto:ik@mijnserver.nl" enctype="text/plain">
Er zijn nadelen: je kan het formaat van de gemailde tekst niet controleren, en je kunt geen antwoord terugzenden aan de gebruiker. Verder "begrijpen" niet alle browsers het gebruik van de <form> tag op deze manier.

Terug naar de top


CGI Scripts en veiligheid

Denk aan het volgende -- een CGI script is een programma dat iedereen in de wereld kan uitvoeren op jouw machine. Kijk daarom uit voor veiligheidsgaten als je het script schrijft.

Vertrouw over het algemeen de gebruikersinvoer niet. Als eerste moet je geen gebruikersdata in een shell-commando zetten zonder de data goed hebt geverifieerd, zodat niet plotseling een hacker een virtuele grasmaaier door je veiligheidsgat kan maaien.

Laten we zeggen dat je een CGI-programma hebt dat de gebruikers "finger" laat uitvoeren op jouw host. Zo'n Perl script zal een regel hebben als

system "finger $username" ;
Maar als een hacker typt: "james; rm -rf /" als de gebruikersnaam, dan voert je programma uit:
system "finger james; rm -rf /" ;
wat zoveel mogelijk bestanden als mogelijk verwijdert, mogelijk niet precies wat je bedoeling was! Dus verifieer dat de gebruikersnaam normaal is, met iets als
$username!~ /[^\w.-]/   || die "Haha! Leuk geprobeerd, hackertje." ;
of gebruik een andere vorm van het system commando:
system("finger", $username) ;
of bedenk zelf een manier om het probleem op te lossen.

Het is makkelijk voor een hacker om wie weet wat voor formuliervariabelen naar jouw script te verzenden, met alle mogelijke waarden (ook karakters die niet weergegeven kunnen worden). Je veiligheid moet niet over de kop gaan op velden met constante waarden, of ze bestaan of niet.

Terug naar de top


Het plaatsen van je script op de server

Verschillende Webservers zijn verschillend geconfigureerd. Sommigen laten je CGI-scripts in dezelfde directory als je Web-pagina's plaatsen, met bestandsnamen die eindigen op ".cgi". Andere servers laten je alle CGI-scripts in een specifieke directory zetten, die meestal "cgi-bin" heet. Je webmaster heeft de eindantwoorden.

Je moet de goede permissies instellen op het programmabestand. Bij Unix draait de Web server (net als ieder ander proces) onder een bepaalde gebruikersnaam. Je CGI programma moet uitvoerbaar zijn voor die gebruikersnaam, en ook leesbaar als het een Perl of shell script is. Je stelt de goede permissies in met  "chmod 750 *.cgi" (of "chmod 755 *.cgi", als je server geen groepstoegang heeft tot je bestanden -- probeer allebei, of vraag aan je webmaster).

Als je script niet werkt:

Terug naar de top


Een Eerder Gemaakt Bestand Terugsturen als Respons

Als je HTML respons altijd hetzelfde is, of als je wilt antwoorden met een aantal bestaande pagina's, vind je de "Location:" respons header misschien bruikbaar. Gebruik het om de browser naar een andere URL door te sturen.

Bijvoorbeeld, als je CGI script de volgende regel heeft staan onder STDOUT:

Location: response.html
gevolgd door een lege regel, dan zal de browser response.html laten zien als respons op het CGI script. Je kunt de browser doorsturen naar een relatieve of absolute URL.

In deze situatie moet je niet de "Content-type:" response header toevoegen.

Terug naar de top


Andere Bruikbare CGI Environment Variabelen

CGI scripts hebben toegang to ongeveer 20 environment variabelen, zoals QUERY_STRING en CONTENT_LENGTH al besproken werden op de hoofdpagina.

Een paar andere die je misschien handig vind:

REQUEST_METHOD
De HTTP methode waarmee dit script was aangeroepen. Meestal "GET", "POST", of "HEAD".
HTTP_REFERER
De URL van het formulier dat was verstuurd. Dit is niet altijd ingesteld, dus reken er niet op. En ga verder ook niet de privacy van mensen mee verbreken.
PATH_INFO
Extra "pad" informatie. Het is mogelijk om extra info aan je script te geven in de URL, na de bestandsnaam van het CGI script. Bijvoorbeeld, de URL aanroepen door
http://www.myhost.com/mypath/myscript.cgi/path/info/here
zal PATH_INFO zetten op "/path/info/here". Meestal gebruikt voor data die te maken heeft met het pad, maar je kunt het voor alles gebruiken.
SERVER_NAME
Je Web server's hostnaam of IP adres (tenminste, voor dit verzoek).
SERVER_PORT
Je Web server's poort (at least for this request).
SCRIPT_NAME
De lokale URL van het script dat wordt uitgevoerd. De CGI standaard is onduidelijk of de eerste slash inbegrepen wordt, maar vandaag de dag voegen de meeste servers het toe. Je kunt allebei de gevallen met deze lijn Perlscript ondersteunen:

$ENV{'SCRIPT_NAME'}=~ s#^/?#/# ;
Dus de URL van het script dat wordt uitgevoerd is, in Perl,
"http://$ENV{'SERVER_NAME'}:$ENV{'SERVER_PORT'}$ENV{'SCRIPT_NAME'}"
Hier is de complete lijst bij de NCSA.

Terug naar de top


Een Figuur of Ander Niet-HTML Respons Terugsturen na een CGI Script

De meeste CGI scripts geven HTML data terug, maar je kunt alles wat je wilt includeren. Je moet alleen maar het juiste MIME type in de "Content-type:" regel geven, gevolgd door de nodige lege regel, en daarna gevolgd door de ruwe data van de bron die je terugstuurd. In het geval van HTML bestanden, is de ruwe data HTML tekst. In het geval van figuren, audio of video, is het ruwe binaire data. Bijvoorbeeld, om met een GIF bestand te antwoorden, gebruik:
Content-type: image/gif

GIF89a&%*$@#--- binaire code van het plaatje ---$(*&%(*@#......

Je HTML bestand kan een script-gegenereerde figuur oproepen met:
<img src="gifmaker.cgi?param1=value1&param2=value2">
Een van mijn favoriete voorbeelden was de Interactive Graphics Renderer, die 3-D iconen maakt volgens de kleuren, vorm, lichtval, enz. die jij definieert. Je kunt de resulterende ikonen op je Webpagina's gebruiken, voor knopjes en horizontale lijnen. Noot: Deze site is tijdelijk offline; de auteur zegt dat dit eventueel de nieuwe locatie zal wijzen.

MIME Types

MIME types zijn standaard tekstjes die een data type identificeren, over het hele internet gebruikt voor vele doelen. Ze beginnen met het algemene type data (bijv.  text, image, of audio), gevolgd door een slash, en eindigen met een specifiek type data (bijv. html, gif, of jpeg). HTML bestanden worden geidentificeerd met text/html, en GIFs en JPEGs met image/gif en image/jpeg.

Terug naar de top


Wat is het verschil tussen GET en POST?

GET en POST zijn twee verschillende methodes, gedefinieerd in HTTP die heel erg verschillende dingen doen, maar allebei de mogelijkheid hebben om formulierverzendingen naar de server te zenden.

Normaliter wordt GET gebruikt om een bestand of andere bron te krijgen, mogelijk met parameters die beter specifieren wat precies nodig is. In het geval van formulierinvoer, voegt GET de invoer geheel in de URL toe, als

GET is hoe je browser de meeste bestanden download, als HTML bestanden en figuren. Het kan ook worden gebruikt voor de meeste formulieren, als er tenminste niet te veel data is (het limiet verschilt per browser)

De GET methode is idempotent, wat betekent dat de effecten van verschillende gelijke GET verzoeken hetzelfde zijn als van 1 GET verzoek. Browsers en proxies kunnen GET antwoorden in hun cache opslaan, dus twee gelijke inzendingen kunnen mogelijk niet beiden in je CGI script terecht komen. Dus gebruik GET niet als je ieder verzoek wilt loggen, of op een andere manier data van ieder verzoek wilt opslaan.

Normaal gesproken wordt POST gebruikt om een heleboel data naar de server te sturen om te worden verwerkt, wat dat verwerken ook inhoudt. (De naam POST komt waarschijnlijk van het idee van een notitie toevoegen aan een discussie- of nieuwsgroep.) Je kunt hele bestanden versturen met POST. Verder is de grootte van de data ongelimiteerd, anders dan bij GET.

Dit alles is echter achter de schermen. Voor de CGI programmeur, werken GET en POST bijna hetzelfde, en kun je ze gelijkwaardig gebruiken. Een paar voordelen van POST zijn dat je ongelimiteerd bent in de data die je verstuurt, en dat je erop kunt rekenen dat je script iedere keer als het formulier is verstuurd wordt aangeroepen. Een voordeel van GET is dat je gehele formulierinvoer kan worden samengevoegd tot 1 URL, als een hyperlink of bladwijzer (zie AutoPOST om dit te doen met POST).

Terug naar de top


Krijg Meer Controle met Non-Parsed Header Scripts

Normaal gesproken, als je CGI script de "Content-type:", "Location:", of andere headers in zich heeft, herkent de server deze headers en genereert een juist HTTP respons voor de gebruiker. Misschien wil je een handigere controle over de HTTP respons. De meeste Web servers ondersteunen non-parsed header (of "NPH") scripts, die een complete HTTP respons genereren en niet de normale herkenning door de server doorstaan.

Om dit te gebruiken, moet je wat HTTP kunnen -- specifiek de formaten van de status lijn en header lijn.

In je non-parsed header script moet je gewoon de hele HTTP status en header regels neerzetten waar in een normaal script de "Content-Type:" regel zou staan. Ook de lege regel is nodig. Wat in je script staat wordt woord voor woord aan de gebruiker verzonden, zonder wijzigingen door de server.

Geef je NPH scripts een naam die begin met "nph-", als "nph-mijnscript.cgi"; ieder script waarvan de naam start met "nph-" zal worden behandeld als een NPH script. Dit werkt op de meeste servers, ook Apache and NCSA. Andere servers hebben mogelijk andere schema's om NPH scripts te identificeren; lees de documentatie of vraag het aan je webmaster.

Voor een voorbeeld van een NPH script, zie CGIProxy.

Als dit verwarrend overkomt, maak je geen zorgen. Als je al ooit een NPH script nodig zal hebben, zal je dit alles beter begrijpen.

Terug naar de top


Terug naar Hoofd Pagina


© 1996-1998 James Marshall
© 1999-2000 Nederlandse vertaling by Simon Amstel
(commentaar is hartelijk welkom; voor vragen, lees alstublieft eerst de FAQ)
Opmerking: Commentaar op de inhoud graag (in het Engels) naar J. Marshall, commentaar op de vertaling (in Nederlands of Engels) naar S. Amstel
Laatst Gewijzigd (originele tekst): 18 april 1998 http://www.jmarshall.com/easy/cgi/cgi_footnotes.html
Laatst Gewijzigd (vertaling): 4 januari 2000 http://www.jmarshall.com/easy/cgi/dutch/cgi_footnotes.html