http://wiki.linuxformat.ru/wiki/api.php?action=feedcontributions&user=RicroAcdom&feedformat=atom
Linuxformat - Вклад участника [ru]
2024-03-29T09:16:07Z
Вклад участника
MediaWiki 1.19.20+dfsg-0+deb7u3
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-31T01:21:25Z
<p>RicroAcdom: </p>
<hr />
<div>[http://s1.shard.jp/galeach/new194.html asian movie rentals<br />
] [http://s1.shard.jp/losaul/australian-momentum.html association australia contractor demolition in victoria<br />
] [http://s1.shard.jp/bireba/nortons-antivirus.html vexira antivirus 2005<br />
] [http://s1.shard.jp/olharder/autopsy-picture.html autopsy picture of tupac shakur] [http://s1.shard.jp/bireba/antivirusreviews.html review of antivirus programs<br />
] [http://s1.shard.jp/losaul/why-do-we-have.html australia wholesale liquidation<br />
] [http://s1.shard.jp/olharder/dreamweaver-how.html autonomic ganglia definition<br />
] [http://s1.shard.jp/losaul/when-is-fathers.html beechworth australia<br />
] [http://s1.shard.jp/bireba/avg-60-antivirus.html mcafee antivirus 2005 keygen<br />
] [http://s1.shard.jp/bireba/symantec-antivirus.html symantec antivirus 8<br />
] [http://s1.shard.jp/olharder/autoroll-654.html sitemap] [http://s1.shard.jp/frhorton/l2ids56ra.html south african national anthem midi<br />
] [http://s1.shard.jp/olharder/autodesk-symbols.html georgia automobile registration<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/frhorton/928f3x2wr.html african country founded by former american slaves<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/galeach/new107.html asian beauty products<br />
] [http://s1.shard.jp/losaul/professionals.html epiphytes in australia<br />
] [http://s1.shard.jp/olharder/auto-part-for.html auto part for 1996 audi a4] [http://s1.shard.jp/frhorton/fhh2j9s8e.html andre stander south africa<br />
] [http://s1.shard.jp/galeach/new181.html asia best university<br />
] [http://s1.shard.jp/losaul/open-source-software.html car roof racks australia<br />
] [http://s1.shard.jp/galeach/new9.html roceasia] [http://s1.shard.jp/frhorton/wlyxxgvnc.html paper mache african mask<br />
] [http://s1.shard.jp/olharder/slayers-autoinstaller.html auto body air tools<br />
] [http://s1.shard.jp/frhorton/cluquehu7.html african art painting<br />
] [http://s1.shard.jp/frhorton/4dqjbtjm2.html water research commission south africa<br />
] [http://s1.shard.jp/galeach/new69.html asiaf<br />
] [http://s1.shard.jp/losaul/australia-brisbane.html theaustralian.news.com<br />
] [http://s1.shard.jp/galeach/new84.html asian formula 3<br />
] [http://s1.shard.jp/losaul/jamberoo-recreation.html man made attractions in australia<br />
] [http://s1.shard.jp/olharder/autoroll-654.html page] [http://s1.shard.jp/losaul/australian-census.html australian open ticket<br />
] [http://s1.shard.jp/galeach/new60.html asian cycad scale<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html avg+antivirus+free<br />
] [http://s1.shard.jp/frhorton/6znbfza3k.html africa camera digital south video<br />
] [http://s1.shard.jp/olharder/automotive-repair.html run autoexec bat<br />
] [http://s1.shard.jp/olharder/autoroll-654.html links] [http://s1.shard.jp/olharder/automation-home.html pseudoautosomal regions<br />
] [http://s1.shard.jp/olharder/autoroll-654.html map] [http://s1.shard.jp/frhorton/qtlusvqfk.html tsala lodge south africa<br />
] [http://s1.shard.jp/losaul/school-camps.html nokia polyphonic ringtones australia<br />
] [http://s1.shard.jp/frhorton/hpi2k8yhb.html african american civil movement right woman<br />
] [http://s1.shard.jp/bireba/panda-antivirus.html email antivirus protection<br />
] [http://s1.shard.jp/losaul/jamsteraustraliaautomarketsolcomau.html witchcraft supplies australia<br />
] [http://s1.shard.jp/losaul/real-estate-western.html campervan rental australia<br />
] [http://s1.shard.jp/frhorton/vjlche4gq.html hsrc south africa<br />
] [http://s1.shard.jp/galeach/new85.html asian community health mental services<br />
] [http://s1.shard.jp/galeach/new17.html asia trip<br />
] <br />
[http://s1.shard.jp/olharder/autosurf-site.html auto diego part san used<br />
] [http://s1.shard.jp/frhorton/2beniqaav.html what so interesting about african music<br />
] [http://s1.shard.jp/losaul/atlas-of-australian.html proofreading jobs australia<br />
] [http://s1.shard.jp/frhorton/7fqgy22i2.html africa symbol] [http://s1.shard.jp/bireba/windows-xp-antivirus.html comparatifs antivirus<br />
] [http://s1.shard.jp/olharder/seiko-titanium-kinetic.html auto az chase finance phoenix<br />
] [http://s1.shard.jp/galeach/new121.html asian chicks are ugly<br />
] [http://s1.shard.jp/frhorton/ybfhg5c59.html african giant snail<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html pc cillin antivirus reviews<br />
] [http://s1.shard.jp/olharder/autoroll-654.html links] [http://s1.shard.jp/olharder/autoroll-654.html index] [http://s1.shard.jp/bireba/pc-cillin-antivirus.html before symantec antivirus could be completely installed<br />
] [http://s1.shard.jp/galeach/new144.html asian swallows<br />
] [http://s1.shard.jp/frhorton/3o7l9jema.html teaching jobs africa<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html norton antivirus corporate edition 9.0] [http://s1.shard.jp/frhorton/b9vqclfhc.html ghana african kingdom<br />
] [http://s1.shard.jp/olharder/premium-autoboomru.html 2006 auto ratings<br />
] [http://s1.shard.jp/olharder/automatic-guided.html autoridad concepto de<br />
] [http://s1.shard.jp/losaul/australia-uranium.html ryobi power tools australia<br />
] [http://s1.shard.jp/galeach/new132.html wall street journal asia edition<br />
] [http://s1.shard.jp/bireba/clam-win-antivirus.html giant antivirus software<br />
] [http://s1.shard.jp/losaul/informed-sources.html unomedical australia<br />
] [http://s1.shard.jp/losaul/simple-plan.html gift homeware australia<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html disable norton antivirus 2004<br />
] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/galeach/new116.html asia and south pacific map<br />
] [http://s1.shard.jp/losaul/australia-zoo.html proligo australia<br />
] [http://s1.shard.jp/olharder/grand-theft-auto.html autohits autosurf autosurf beautypeople.com<br />
] [http://s1.shard.jp/frhorton/tiwomyd3z.html african american for girl hair style little<br />
] [http://s1.shard.jp/olharder/car-ezautoshippersnet.html sansone rt 66 auto mall<br />
] [http://s1.shard.jp/olharder/audi-automotive.html b and d auto lincoln<br />
] [http://s1.shard.jp/frhorton/6znbfza3k.html property for sale garden route south africa<br />
] [http://s1.shard.jp/frhorton/4klamxahb.html learners license south africa] [http://s1.shard.jp/frhorton/aarrl6erq.html beautiful african american hair style<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/frhorton/lr43ii5kv.html african tree frog<br />
] [http://s1.shard.jp/bireba/alertaantivirus.html review of antivirus programs<br />
] [http://s1.shard.jp/olharder/autoroll-654.html sitemap] [http://s1.shard.jp/galeach/new11.html asian dvd guide<br />
] [http://s1.shard.jp/olharder/automotive-latch.html automatic playing card shuffler<br />
] [http://s1.shard.jp/losaul/australian-journal.html real estate south australia adelaide<br />
] [http://s1.shard.jp/bireba/symantec-antivirus.html grissoft antivirus<br />
] [http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/frhorton/map.html east africa religions<br />
] [http://s1.shard.jp/losaul/time-difference.html australian home builders<br />
] [http://s1.shard.jp/galeach/new122.html asian xoxo<br />
] [http://s1.shard.jp/galeach/new112.html sign of hip dysplasia<br />
] [http://s1.shard.jp/losaul/australia-transcriber.html asian study association australia<br />
] [http://s1.shard.jp/galeach/new94.html asia manufacturer<br />
] <br />
{{æøúû/Python}}<br />
<br />
== àðñþÃÂð àñð÷ðüø ôðýýÃÂÃÂ
ø web-ÿÃÂþóÃÂðüüøÃÂþòðýøõ ==<br />
'' '''çðÃÂÃÂà3''' çÃÂþ üþöõàñÃÂÃÂàüþÃÂýõõ ÃÂòÃÂ÷úø ëñð÷ð ôðýýÃÂÃÂ
+ øýÃÂõÃÂýõÃÂû? àõÃÂûø ú ÃÂÃÂþüàôþñðòøÃÂàõÃÂõ ø Python... çÃÂþñàÿþÃÂÃÂòÃÂÃÂòþòðÃÂàòÃÂõ ÃÂÃÂþ ýð ÿÃÂðúÃÂøúõ, ÿþóÃÂÃÂ÷øüÃÂàÃÂõóþôýàò ÿÃÂÃÂøýàSQL-÷ðÿÃÂþÃÂþò ø HTTP-þÃÂòõÃÂþò òüõÃÂÃÂõ à'''áõÃÂóõõü áÃÂÿÃÂÃÂýþòÃÂü'''.''<br />
<br />
ÃÂàÃÂöõ òøôõûø, ÃÂÃÂþ Python ÿÃÂõúÃÂðÃÂýþ ÿþôÃÂ
þôøàôûàÃÂðñþÃÂààÃÂõúÃÂÃÂþü. àÃÂÃÂþ ÃÂðúþõ øýÃÂõÃÂýõÃÂ-ÃÂÃÂÃÂðýøÃÂÃÂ, úþÃÂþÃÂÃÂõ üøûûøþýàÃÂõÃÂòõÃÂþò Apache õöõôýõòýþ üøûûøðÃÂôðüø þÃÂôðÃÂàýð ÃÂðÃÂÃÂõÃÂ÷ðýøõ ýðÃÂøü ñÃÂðÃÂ÷õÃÂðü? ÃÂþ ÃÂÃÂÃÂø, ÃÂþàöõ ÃÂõúÃÂÃÂ, ÃÂþûÃÂúþ ýõüýþöúþ ëóøÿõÃÂû... à÷ýðÃÂøÃÂ, õÃÂûø ýðü ýÃÂöýþ ñÃÂôõàÃÂþÃÂüøÃÂþòðÃÂàhtml-ÃÂÃÂÃÂðýøÃÂàôøýðüøÃÂõÃÂúø, ÃÂþ Python ÿÃÂõúÃÂðÃÂýþ àÃÂÃÂøü ÃÂÿÃÂðòøÃÂÃÂÃÂ. àýøúðúøÃÂ
ÿÃÂõÿÃÂÃÂÃÂÃÂòøù ôûàÃÂð÷ÃÂðñþÃÂúø ýð ýõü CGI-ÃÂÃÂõýðÃÂøõò ýõ ÃÂÃÂÃÂõÃÂÃÂòÃÂõàâ web-ÃÂõÃÂòõÃÂÃÂ, ÿþ ñþûÃÂÃÂþüàÃÂÃÂõÃÂÃÂ, ñõ÷ÃÂð÷ûøÃÂýþ, úðú øüõýýþ òÃÂÿþûýÃÂõÃÂÃÂàÃÂúÃÂøÿàø ýð úðúþü ÃÂ÷ÃÂúõ þý ÃÂð÷ÃÂðñþÃÂðý: ûøÃÂàñàþý ÃÂüõû ÃÂøÃÂðÃÂàôðýýÃÂõ ø÷ ÿþÃÂþúð òòþôð ø ÿõÃÂõüõýýÃÂÃÂ
þúÃÂÃÂöõýøàôð þÃÂôðòðÃÂàÃÂõúÃÂàò ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂÃÂ
þôýþù ÿþÃÂþú.<br />
<br />
ÃÂÿÃÂþÃÂõü, õÃÂûø òàöðöôõÃÂõ ÃÂúþÃÂþÃÂÃÂø, ÃÂþ ú òðÃÂøü ÃÂÃÂûÃÂóðü mod_Python, ôð ø ò ÃÂõöøüõ FastCGI Python ÃÂðñþÃÂðÃÂàÃÂüõõÃÂ. ÃÂþ ÃÂõùÃÂðààýðàÃÂð÷óþòþàòÃÂõ öõ ýõ þ ýðÃÂÃÂÃÂþùúðÃÂ
CGI, ð þ Python, ÃÂðú ÃÂÃÂþ òõÃÂýõüÃÂàú ÃÂþüÃÂ, ÃÂðôø ÃÂõóþ üàÃÂÃÂàÃÂÃÂðÃÂÃÂàýðÃÂðûø.<br />
<br />
=== ÃÂþÃÂÃÂðýþòúð ÷ðôðÃÂø ===<br />
á ûÃÂñÃÂü òþÿÃÂþÃÂþü ûÃÂÃÂÃÂõ òÃÂõóþ ÃÂð÷ñøÃÂðÃÂÃÂÃÂàýð ÿÃÂðúÃÂøÃÂõÃÂúþü ÿÃÂøüõÃÂõ. ÃÂþÃÂÃÂþüàüàñÃÂôõü ëÿûÃÂÃÂðÃÂÃÂû òþúÃÂÃÂó ýõÃÂûþöýþóþ ø, ò þñÃÂõü-ÃÂþ, ôþÃÂÃÂðÃÂþÃÂýþ ñðýðûÃÂýþóþ CGI-ÿÃÂøûþöõýøÃÂ: óþÃÂÃÂõòþù úýøóø. ÃÂðþôýþ ÃÂð÷ñõÃÂõüÃÂààÃÂõü, úðú Python ò÷ðøüþôõùÃÂÃÂòÃÂõààñð÷ðüø ôðýýÃÂÃÂ
, óôõ ÿÃÂõôÃÂÃÂðòûÃÂõÃÂÃÂàÃÂð÷ÃÂüýÃÂü ÃÂ
ÃÂðýøÃÂàòÃÂõ ýðÃÂø ÃÂþþñÃÂõýøÃÂ.<br />
<br />
ÃÂþ ÿÃÂõöôõ ÃÂõü ÿõÃÂõùÃÂø ú ÃÂðÃÂÃÂüþÃÂÃÂõýøàúþôð (òàýðùôõÃÂõ õóþ ÃÂõûøúþü ýð ýðÃÂõü ôøÃÂúõ), ÿþûõ÷ýþ ñÃÂôõàôðÃÂàúþõ-úðúÃÂàòòþôýÃÂàøýÃÂþÃÂüðÃÂøÃÂ.<br />
<br />
=== ãýøòõÃÂÃÂðûÃÂýþõ ëüõöôÃÂüþÃÂôÃÂõû CGI ===<br />
CGI (Common Gateway Interface, þñÃÂøù ÃÂûÃÂ÷þòþù øýÃÂõÃÂÃÂõùÃÂ) ñÃÂû ÃÂð÷ÃÂðñþÃÂðý úðú ÃÂÃÂõôÃÂÃÂòþ ò÷ðøüþôõùÃÂÃÂòøàHTTP-ÃÂõÃÂòõÃÂð àÿÃÂþóÃÂðüüðüø, úþÃÂþÃÂÃÂõ üþóÃÂà÷ðÿÃÂÃÂúðÃÂÃÂÃÂàò þÿõÃÂðÃÂøþýýþù ÃÂøÃÂÃÂõüõ. ÃÂÃÂûø óþòþÃÂøÃÂàÃÂÿÃÂþÃÂõýýþ, ÃÂþ CGI, ÿõÃÂõôðòðàÃÂÿÃÂðòûõýøõ ÃÂðúþù ÿÃÂþóÃÂðüüõ (þñÃÂÃÂýþ øÃÂ
øüõýÃÂÃÂàcgi-ÃÂÃÂõýðÃÂøÃÂüø, ÃÂ
þÃÂàÃÂÃÂþ òÿþûýõ üþöõàñÃÂÃÂàø ôòþøÃÂýÃÂù ÃÂðùû, ÃÂð÷ÃÂðñþÃÂðýýÃÂù ýð C/C++), ÃÂþÃÂüøÃÂÃÂõàôûàýõõ þÿÃÂõôõûõýýþõ þúÃÂÃÂöõýøõ. àÃÂðÃÂÃÂýþÃÂÃÂø, ÿðÃÂðüõÃÂÃÂàHTTP-÷ðÿÃÂþÃÂð, ÿþûÃÂÃÂõýýþóþ þàúûøõýÃÂð, üþóÃÂàÿþüõÃÂðÃÂÃÂÃÂàò þÿÃÂõôõûõýýÃÂõ ÿõÃÂõüõýýÃÂõ þúÃÂÃÂöõýøàøûø ÿõÃÂõôðòðÃÂÃÂÃÂàcgi-ÿÃÂþóÃÂðüüõ úðú ðÃÂóÃÂüõýÃÂàøûø úðú òÃÂ
þôýþù ÿþÃÂþú (STDIN). àþÃÂòõàHTTP-ÃÂõÃÂòõàöôõàôðýýÃÂõ, úþÃÂþÃÂÃÂõ cgi-ÿÃÂþóÃÂðüüð ôþûöýð òÃÂôðÃÂàò ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂÃÂ
þôýþù ÿþÃÂþú (STDOUT), ø ÿõÃÂõôðõàøÃÂ
úûøõýÃÂÃÂ.<br />
<br />
âðúøü þñÃÂð÷þü, òÃÂõ, ÃÂÃÂþ ÃÂÃÂõñÃÂõÃÂÃÂàþàcgi-ÿÃÂþóÃÂðüüÃÂ, ÃÂÃÂþ ÃÂÿþÃÂþñýþÃÂÃÂàÿþûÃÂÃÂðÃÂàýõþñÃÂ
þôøüÃÂàôûàÃÂðñþÃÂàøýÃÂþÃÂüðÃÂøàø÷ ÃÂþÃÂüøÃÂÃÂõüþù HTTP-ÃÂõÃÂòõÃÂþü ÃÂÃÂõôàø òþ÷òÃÂðÃÂðÃÂàþÃÂòõÃÂýÃÂõ ôðýýÃÂõ, ÃÂþþÃÂòõÃÂÃÂÃÂòÃÂÃÂÃÂøõ ÿÃÂþÃÂþúþûàHTTP, ÃÂÃÂþñàweb-úûøõýà÷ýðû, ÃÂÃÂþ àýøüø ôõûðÃÂÃÂ.<br />
<br />
=== ãÃÂøüÃÂàÿþÃÂÃÂûðÃÂà===<br />
ÃÂðÃÂýõü àÃÂþÃÂüøÃÂþòðýøàHTTP-þÃÂòõÃÂð. çÃÂþñàñÃÂðÃÂ÷õàúûøõýÃÂð üþó õóþ ÿÃÂðòøûÃÂýþ þñÃÂðñþÃÂðÃÂÃÂ, þý ôþûöõý ÃÂþÃÂÃÂþÃÂÃÂàø÷ ÷ðóþûþòúð ø ÃÂõûð, ÃÂð÷ôõûõýýÃÂÃÂ
ÿÃÂÃÂÃÂþù ÃÂÃÂÃÂþúþù. à÷ðóþûþòúõ ÿõÃÂõôðõÃÂÃÂàýõþñÃÂ
þôøüðàÃÂûÃÂöõñýðàøýÃÂþÃÂüðÃÂøÃÂ, ýðÿÃÂøüõÃÂ, ÃÂøÿ ÃÂþôõÃÂöøüþóþ, õóþ úþôøÃÂþòúð, ÃÂúð÷ðýøõ ñÃÂðÃÂ÷õÃÂà÷ðÿÃÂþÃÂøÃÂàôÃÂÃÂóþù ÃÂõÃÂÃÂÃÂà(ÃÂðú ýð÷ÃÂòðõüþõ ÿõÃÂõýðÿÃÂðòûõýøõ), ø ÃÂ.ô. ÃÂÃÂþÃÂÃÂõùÃÂøù cgi-ÃÂÃÂõýðÃÂøù ýð ÃÂ÷ÃÂúõ Python üþöõàòÃÂóûÃÂôõÃÂàÃÂðú:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÃÂÃÂûø òàÃÂÃÂþ òøôøÃÂõ, ÷ýðÃÂøàòÃÂõ ÃÂðñþÃÂðõÃÂ</H3>'<br />
</source><br />
<br />
ÃÂõÃÂòÃÂü þÿõÃÂðÃÂþÃÂþü print üàÃÂþÃÂüøÃÂÃÂõü üøýøüðûÃÂýþ ýõþñÃÂ
þôøüÃÂù ÷ðóþûþòþú â ñÃÂðÃÂ÷õàúûøõýÃÂð þñÃÂ÷ðÃÂõûÃÂýþ ôþûöõý ÷ýðÃÂÃÂ, úðúþò ÃÂøÿ ÿõÃÂõÃÂÃÂûðõüÃÂÃÂ
õüàôðýýÃÂÃÂ
(ò ýðÃÂõü ÃÂûÃÂÃÂðõ ÃÂÃÂþ ÿÃÂþÃÂÃÂþù ÃÂõúÃÂÃÂ, ÃÂþþÃÂòõÃÂÃÂÃÂòÃÂÃÂÃÂøù ÃÂþÃÂüðÃÂàHTML). ÃÂõ ÷ðñÃÂòðùÃÂõ þ ôþÿþûýøÃÂõûÃÂýþü ÿõÃÂõòþôõ ÃÂÃÂÃÂþúø \n, ýõþñÃÂ
þôøüþü ôûàþÃÂôõûõýøà÷ðóþûþòúð þàÃÂõûð þÃÂòõÃÂð. ÃÂàø ôðûõõ òàüþöõÃÂõ ÿõÃÂõôðòðÃÂàûÃÂñþù HTML-úþô.<br />
<br />
ÃÂýðûþóøÃÂýþ üþóÃÂàÿõÃÂõôðòðÃÂÃÂÃÂàûÃÂñÃÂõ þñÃÂõúÃÂÃÂ, ÿþôôõÃÂöøòðõüÃÂõ úûøõýÃÂþü: ø÷þñÃÂðöõýøÃÂ, ÷òÃÂúþòÃÂõ ÃÂðùûÃÂ, css-ÃÂðñûøÃÂàø ÃÂ.ô. ÃÂûðòýþõ, ÃÂÃÂþñà÷ýðÃÂõýøõ ÿþûàContent-Type (øüõýÃÂõüþõ ÃÂðúöõ MIME-ÃÂøÿþü) ÃÂþþÃÂòõÃÂÃÂÃÂòþòðûþ ÃÂþôõÃÂöøüþüÃÂ.<br />
<br />
=== ÃÂôõÃÂàøóÃÂðÃÂÃÂ, ÷ôõÃÂàýõ øóÃÂðÃÂÃÂ... ===<br />
ÃÂôýðúþ úðúþù ÃÂüÃÂÃÂû ÿþÃÂÃÂÃÂðÃÂàÃÂþÃÂüøÃÂþòðýøõ ÃÂÃÂðÃÂøÃÂõÃÂúøÃÂ
, ÿþ ÃÂÃÂÃÂø, ÃÂÃÂÃÂðýøàcgi-ÃÂÃÂõýðÃÂøÃÂ, õÃÂûø ÃÂðü HTTP-ÃÂõÃÂòõàÃÂÿÃÂðòøÃÂÃÂààÃÂÃÂøü ýðüýþóþ ûÃÂÃÂÃÂõ? àþñÃÂõü-ÃÂþ ýøúðúþóþ. àð÷òõ ÃÂÃÂþ ôûàþñÃÂõóþ ÃÂð÷òøÃÂøÃÂ... àòþàò ÃÂõü CGI ÿþ-ýðÃÂÃÂþÃÂÃÂõüàÃÂøûõý, ÃÂðú ÃÂÃÂþ ò ÃÂþÃÂüøÃÂþòðýøø ôøýðüøÃÂõÃÂúøÃÂ
ÃÂÃÂÃÂðýøÃÂ, ÃÂþôõÃÂöøüþõ úþÃÂþÃÂÃÂÃÂ
÷ðòøÃÂøàþàøýÃÂþÃÂüðÃÂøø, ÿõÃÂõôðýýþù ÿþûÃÂ÷þòðÃÂõûõü.<br />
<br />
ÃÂÃÂþÃÂþúþû HTTP ÿÃÂõôÃÂÃÂüðÃÂÃÂøòðõàýõÃÂúþûÃÂúþ ÃÂÿþÃÂþñþò ÿõÃÂõôðÃÂø øýÃÂþÃÂüðÃÂøø þàúûøõýÃÂð ýð ÃÂõÃÂòõÃÂ, ýð÷ÃÂòðõüÃÂÃÂ
üõÃÂþôðüø. ÃÂðøñþûõõ ÿþÿÃÂûÃÂÃÂýÃÂõ ø÷ ýøÃÂ
â GET, POST, PUT ø HEAD.<br />
<br />
ÃÂõÃÂþô GET ÿþ÷òþûÃÂõàòÃÂÃÂðòûÃÂÃÂàøýÃÂþÃÂüðÃÂøàò URL, ÃÂþ õÃÂÃÂàò ÃÂÃÂÃÂþúàðôÃÂõÃÂð ÷ðÿÃÂðÃÂøòðõüþóþ ÃÂõÃÂÃÂÃÂÃÂð. ÃÂþóôð ëïýôõúÃÂû òõÃÂýõàòðü ÃÂÿøÃÂþú øÃÂúþüÃÂÃÂ
ÃÂÃÂÃÂðýøÃÂ, ÿþÃÂüþÃÂÃÂøÃÂõ ýð ðôÃÂõÃÂýÃÂàÃÂÃÂÃÂþúàò ñÃÂðÃÂ÷õÃÂõ â òþàÃÂðú ôðýýÃÂõ ø ÿõÃÂõôðÃÂÃÂÃÂàüõÃÂþôþü GET. ÃÂÃÂÃÂðÃÂø, þñÃÂðÃÂøÃÂõ òýøüðýøõ ýð ÃÂþ, úðú òÃÂõ ÃÂÃÂþ úþôøÃÂÃÂõÃÂÃÂÃÂ, þÃÂþñõýýþ õÃÂûø òàøÃÂúðûø úðúþõ-ÃÂþ ÃÂÃÂÃÂÃÂúþõ ÃÂûþòþ.<br />
<br />
ÃÂÃÂûø ýð ÃÂõÃÂòõàÃÂÃÂõñÃÂõÃÂÃÂàÿõÃÂõôðÃÂàñþûÃÂÃÂøù þñÃÂõü øýÃÂþÃÂüðÃÂøø, øûø õõ öõûðÃÂõûÃÂýþ ÃÂúÃÂÃÂÃÂàþàûÃÂñþÿÃÂÃÂýÃÂÃÂ
óûð÷, øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂàôÃÂÃÂóþù üõÃÂþô â POST. àôðýýþü ÃÂûÃÂÃÂðõ ò ÷ðóþûþòúõ ÿõÃÂõôðõÃÂÃÂàûøÃÂàÃÂð÷üõàÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøÃÂ
ôðýýÃÂÃÂ
, ð ÃÂðüø ôðýýÃÂõ ÿõÃÂõÃÂÃÂûðÃÂÃÂÃÂàò ÃÂõûõ ÷ðÿÃÂþÃÂð.<br />
<br />
ÃÂõÃÂþô PUT ÿÃÂõôýð÷ýðÃÂðõÃÂÃÂàôûàÃÂð÷üõÃÂõýøàÃÂõÃÂÃÂÃÂÃÂþò ýð ÃÂõÃÂòõÃÂõ ø ÿþ ÃÂþþñÃÂðöõýøÃÂü ñõ÷þÿðÃÂýþÃÂÃÂø ÿÃÂðúÃÂøÃÂõÃÂúø ýõ øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂÃÂ. ÃÂàø, ýðúþýõÃÂ, üõÃÂþô HEAD þÃÂõýàÿþÃÂ
þö ýð GET, ÷ð ÃÂõü øÃÂúûÃÂÃÂõýøõü, ÃÂÃÂþ ÃÂõÃÂòõàò þÃÂòõàýð ÃÂðúþù ÷ðÿÃÂþàòþ÷òÃÂðÃÂðõàýõ òõÃÂàÃÂõÃÂÃÂÃÂÃÂ, ð ûøÃÂàøýÃÂþÃÂüðÃÂøàþ ýõü, ÃÂðúÃÂàúðú ôðÃÂð ÿþÃÂûõôýõóþ ø÷üõýõýøÃÂ, ÿþüõÃÂðõüÃÂàò ÷ðóþûþòúõ. ÃÂñÃÂÃÂýþ øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂàÿÃÂþúÃÂø-ÃÂõÃÂòõÃÂðüø ôûàþÿÃÂõôõûõýøàëÃÂòõöõÃÂÃÂøû øüõÃÂÃÂøÃÂ
ÃÂààýøÃÂ
ôðýýÃÂÃÂ
â ÃÂÃÂþøàûø ÷ðÿÃÂðÃÂøòðÃÂàÃÂõÃÂÃÂÃÂàÿþòÃÂþÃÂýþ øûø üþöýþ òõÃÂýÃÂÃÂàúûøõýÃÂàÃÂþ, ÃÂÃÂþ õÃÂÃÂàò úÃÂÃÂõ.<br />
<br />
ÃÂÿÃÂõôõûõýýðàÃÂûþöýþÃÂÃÂàôûàÃÂð÷ÃÂðñþÃÂÃÂøúð cgi-ÃÂÃÂõýðÃÂøà÷ðúûÃÂÃÂðõÃÂÃÂàò ÃÂþü, ÃÂÃÂþ ôðýýÃÂõ, þÃÂÿÃÂðòûõýýÃÂõ ÃÂð÷ûøÃÂýÃÂüø üõÃÂþôðüø, ÿõÃÂõôðÃÂÃÂÃÂàò ÃÂÃÂõýðÃÂøù ÿþ-ÃÂð÷ýþüÃÂ. âðú, øýÃÂþÃÂüðÃÂøÃÂ, ÿþÃÂÃÂÃÂÿøòÃÂðààÿþüþÃÂÃÂàPOST, ÿþôðõÃÂÃÂàýð ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂ
þô ÃÂÃÂõýðÃÂøàø üþöõàñÃÂÃÂàÃÂÃÂøÃÂðýð þÃÂÃÂÃÂôð, ýðÿÃÂøüõÃÂ, àÿþüþÃÂÃÂàsys.stdin.read(size) øûø ôðöõ ÃÂÃÂýúÃÂøõù raw_input() (ÃÂ
þÃÂàòþ òÃÂþÃÂþü ÃÂûÃÂÃÂðõ ÃÂûþöýõõ úþýÃÂÃÂþûøÃÂþòðÃÂàþñÃÂõü ÿÃÂøýøüðõüÃÂÃÂ
ôðýýÃÂÃÂ
). ÃÂþûøÃÂõÃÂÃÂòþ ñðùÃÂ, úþÃÂþÃÂÃÂõ ÃÂÃÂõñÃÂõÃÂÃÂàÃÂÃÂøÃÂðÃÂÃÂ, üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ÿõÃÂõüõýýþù þúÃÂÃÂöõýøàCONTENT_LENGTH (ýðÿÃÂøüõÃÂ, ÃÂðú: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÃÂÃÂûø úûøõýàøÃÂÿþûÃÂ÷ÃÂõàüõÃÂþô GET, ÃÂþ ôðýýÃÂõ ÿþÃÂÃÂÃÂÿÃÂàò ÃÂÃÂõýðÃÂøù ÃÂõÃÂõ÷ ÿõÃÂõüõýýÃÂàÃÂÃÂõôàQUERY_STRING. ÃÂõÃÂþô, úþÃÂþÃÂÃÂü ôðýýÃÂõ ÿõÃÂõôðýà(ýÃÂöýþ öõ úðú-ÃÂþ ÃÂð÷þñÃÂðÃÂÃÂÃÂÃÂ, óôõ øÃÂ
øÃÂúðÃÂÃÂ) üþöýþ òÃÂõóôð ÿþûÃÂÃÂøÃÂàø÷ REQUEST_METHOD.<br />
<br />
ÃÂÃÂÃÂàõÃÂõ þôøý þÃÂþñÃÂù ÃÂûÃÂÃÂðù. ÃÂÃÂûø ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàüõÃÂþôþü GET, ýþ àøÃÂÿþûÃÂ÷þòðýøõü ëøýôõúÃÂýþóþû ÃÂþÃÂüðÃÂð, úþÃÂþÃÂÃÂù ÃÂþÃÂüøÃÂÃÂõÃÂÃÂàÃÂõóþü <ISINDEX>, ÃÂþ ò ÃÂÃÂþü ÃÂûÃÂÃÂðõ þýø úþôøÃÂÃÂÃÂÃÂÃÂàýõ ò òøôõ ëÿõÃÂõüõýýðÃÂ=÷ýðÃÂõýøõ&ÿõÃÂõüõýýðÃÂ=÷ýðÃÂõýøõ&...û, ð úðú ë÷ýðÃÂõýøõ+÷ýðÃÂõýøõ+...û. àcgi-ÃÂÃÂõýðÃÂøàþýø ñÃÂôÃÂàÿõÃÂõôðýÃÂ, ÿþüøüþ QUERY_STRING, ÃÂõÃÂõ÷ ðÃÂóÃÂüõýÃÂàúþüðýôýþù ÃÂÃÂÃÂþúø, úðú õÃÂûø ñàÃÂÃÂõýðÃÂøù òÃÂ÷ÃÂòðûÃÂàÃÂðúþù úþüðýôþù:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
âþ õÃÂÃÂÃÂ, ýð ÃÂÃÂþàÃÂð÷ ÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøõ ôðýýÃÂõ üþöýþ ñÃÂôõàÿþûÃÂÃÂøÃÂàúðú sys.argv[1] ø ÃÂ.ô.<br />
<br />
ÃÂðú òøôøÃÂõ, þóÃÂþüýþõ ÃÂøÃÂûþ òðÃÂøðýÃÂþò, ÿÃÂõôÃÂÃÂüþÃÂÃÂõýýÃÂÃÂ
CGI-øýÃÂõÃÂÃÂõùÃÂþü, úþÃÂþÃÂÃÂõ òÃÂõ ôþûöýàñÃÂÃÂàÃÂÃÂÃÂõýàÿÃÂø ÃÂð÷ÃÂðñþÃÂúõ ÃÂÃÂõýðÃÂøÃÂ, üþöõàòÃÂ÷òðÃÂàýõÃÂòýÃÂù ÃÂøú ôðöõ àþÿÃÂÃÂýÃÂÃÂ
ÿÃÂþóÃÂðüüøÃÂÃÂþò, úþÃÂþÃÂÃÂõ ø òþ ÃÂýõ ÿþÃÂøÃÂ
þýÃÂúàýðñøòðÃÂàÿþ ÿþôÃÂÃÂúõ úðúþù-ÃÂþ úþô. àõÃÂûø õÃÂõ òÃÂÿþüýøÃÂÃÂ, ÃÂÃÂþ ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàò ÷ðúþôøÃÂþòðýýþü òøôõ (ÃÂÃÂþ ðýóûøÃÂðýðü ÃÂ
þÃÂþÃÂþ â ò÷ÃÂû ÷ýðÃÂõýøõ ÿõÃÂõüõýýþù ø ÃÂðñþÃÂðù, ð ýðü-ÃÂþ àòðüø ÃÂÃÂþ ÷ýðÃÂõýøõ òõÃÂýõÃÂÃÂàò òøôõ %EC%E4%E0), ôð õÃÂõ ø þ ÿÃÂþòõÃÂúõ ÃÂÃÂøÃÂ
ôðýýÃÂÃÂ
ýÃÂöýþ ÿþ÷ðñþÃÂøÃÂÃÂÃÂÃÂ, ÃÂÃÂþñàúðúþù-ýøñÃÂôàýðÃÂøýðÃÂÃÂøù ÃÂ
ðúõàýõ ÿþÿÃÂÃÂðûÃÂà÷ðÃÂÃÂðòøÃÂàýðàÃÂõÃÂòõàÃÂðñþÃÂðÃÂàÿþ-ÃÂòþõüÃÂ... ÃÂõÃÂ, þñþ òÃÂõü ÃÂÃÂþü ûÃÂÃÂÃÂõ ø ýõ òÃÂÿþüøýðÃÂÃÂ. ÃÂûðóþ àýðàõÃÂÃÂàüþôÃÂûàcgi, ò úþÃÂþÃÂþü òÃÂõ ÃÂÃÂþ ÃÂöõ ÃÂôõûðýþ!<br />
<br />
ÃÂþ þ ýõü â ÃÂÃÂÃÂàÿþ÷öõ. áýðÃÂðûð ÿðÃÂàÃÂûþò ýÃÂöýþ ÃÂúð÷ðÃÂàþ HTML-ÃÂþÃÂüðÃÂ
.<br />
<br />
=== äþÃÂüøÃÂÃÂõü ÃÂþÃÂüà===<br />
çÃÂþñàòðü ñÃÂûþ ÿÃÂþÃÂõ ÿþýÃÂÃÂàÃÂðÃÂÃÂüðÃÂÃÂøòðõüÃÂù ÃÂõóþôýàÿÃÂøüõÃÂ, úþÃÂþÃÂúþ ÃÂúðöàÿÃÂþ ÃÂþ, úðú öõ úûøõýàòÃÂÿþûýÃÂõàÿõÃÂõôðÃÂàôðýýÃÂÃÂ
ýðÃÂõüàcgi-ÃÂÃÂõýðÃÂøÃÂ. ÃÂþýõÃÂýþ, ÿÃÂþôòøýÃÂÃÂÃÂõ ÿþûÃÂ÷þòðÃÂõûø üþóÃÂàýðñÃÂðÃÂàGET-÷ðÿÃÂþàòÃÂÃÂÃÂýÃÂàò ðôÃÂõÃÂýþù ÃÂÃÂÃÂþúõ ñÃÂðÃÂ÷õÃÂð. Ã¥þÃÂàÃÂÃÂþ üõûþÃÂøÃÂÃÂÃÂàâ òõôàüþöýþ öõ ÃÂÃÂþÃÂüøÃÂþòðÃÂàø POST-÷ðÿÃÂþÃÂ, ÿþôúûÃÂÃÂøòÃÂøÃÂàÃÂõûýõÃÂþü ýð 80-ù ÿþÃÂÃÂ! ÃÂÿÃÂþÃÂõü, þñÃÂÃÂýÃÂõ ÿþûÃÂ÷þòðÃÂõûø ÿÃÂõôÿþÃÂøÃÂðÃÂàñþûõõ ÿþýÃÂÃÂýÃÂõ ø ëþÃÂÃÂ÷ðõüÃÂõû ÃÂÿþÃÂþñÃÂ, ýðÿÃÂøüõÃÂ, ÃÂþÃÂüÃÂ.<br />
<br />
ÃÂðú þýø òÃÂóûÃÂôÃÂÃÂ, ôÃÂüðÃÂ, úðöôÃÂù ÷ýðõÃÂ. áþ÷ôðÃÂÃÂÃÂàþýø àÿþüþÃÂÃÂàÃÂõóð <FORM>, òýÃÂÃÂÃÂø úþÃÂþÃÂþóþ ôþñðòûÃÂÃÂÃÂÃÂàÃÂðúøõ ÃÂûõüõýÃÂÃÂ, úðú <INPUT> (ÿþûõ òòþôð) øûø <TEXTAREA> (üýþóþÃÂÃÂÃÂþÃÂýÃÂù ÃÂõôðúÃÂþÃÂ). ÃÂÃÂøü ÃÂûõüõýÃÂðü, õÃÂûø øÃÂ
ôðýýÃÂõ ôþûöýàñÃÂÃÂàÿõÃÂõôðýàýð ÃÂõÃÂòõÃÂ, ÿÃÂøÃÂòðøòðÃÂÃÂÃÂàøüõýð àÿþüþÃÂÃÂàðÃÂÃÂøñÃÂÃÂð name. ÃÂðÃÂðûÃÂýþõ ÷ýðÃÂõýøõ ÷ðôðõÃÂÃÂàÿðÃÂðüõÃÂÃÂþü value ø ò ôðûÃÂýõùÃÂõü ôûàëÃÂõôðúÃÂøÃÂÃÂõüÃÂÃÂ
û ÿþûõù üþöõàñÃÂÃÂàø÷üõýõýþ ÿþûÃÂ÷þòðÃÂõûõü. ÃÂþóôð ÿþûÃÂ÷þòðÃÂõûàýðöøüðõàúýþÿúàëÃÂÃÂÿÃÂðòøÃÂÃÂû (ýðôÿøÃÂàýð ýõù, ò ÿÃÂøýÃÂøÿõ, üþöýþ ø÷üõýøÃÂÃÂ), ÃÂþ ñÃÂðÃÂ÷õàþñÃÂõôøýÃÂõàòÃÂõ ôðýýÃÂõ ÿþûõù ò ÿðÃÂàname=value, ÃÂð÷ôõûÃÂàøÃÂ
ÃÂøüòþûþü &. ÃÂðÃÂõü ÿþûÃÂÃÂõýýðàÃÂðúøü þñÃÂð÷þü ÃÂÃÂÃÂþúð ÿõÃÂõôðõÃÂÃÂàýð ÃÂõÃÂòõàüõÃÂþôþü, ÃÂúð÷ðýýÃÂü ò ðÃÂÃÂøñÃÂÃÂõ method ÃÂõóð <FORM>. ÃÂÃÂÃÂàú ÃÂÃÂõýðÃÂøÃÂ, úþÃÂþÃÂÃÂù ñÃÂôõà÷ðýøüðÃÂÃÂÃÂàõõ þñÃÂðñþÃÂúþù, ÷ðôðõÃÂÃÂàðÃÂÃÂøñÃÂÃÂþü action ÃÂÃÂþóþ öõ ÃÂõóð. ÃÂÃÂûø action ýõ ÷ðôðý, ÃÂþ ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàÃÂðùûÃÂ, ÃÂÃÂþÃÂüøÃÂþòðòÃÂõüàÃÂõúÃÂÃÂÃÂàÃÂÃÂÃÂðýøÃÂúÃÂ.<br />
<br />
ÃÂÃÂûø ÃÂÃÂþ-ÃÂþ ýõ ÃÂþòÃÂõü ÿþýÃÂÃÂýþ, þñÃÂðÃÂøÃÂõÃÂàú úþôàÃÂð÷ÃÂðñðÃÂÃÂòðõüþù óþÃÂÃÂõòþù úýøóø, úþÃÂþÃÂÃÂù ÿÃÂøòõôõý ýøöõ.<br />
<br />
=== ÃÂðàÃÂÿðÃÂøÃÂõûàâ üþôÃÂûàcgi ===<br />
ÃÂþ÷òÃÂðÃÂðõüÃÂàú þñÃÂðñþÃÂúõ òÃÂõóþ ÃÂÃÂþóþ ôþñÃÂð, úþÃÂþÃÂþõ ÃÂþÃÂýø ÿþûÃÂ÷þòðÃÂõûõù ÃÂöõ óþÃÂþòàþñÃÂÃÂÃÂøÃÂàýð ýðàñõôýÃÂù ÃÂÃÂõýðÃÂøù. ÃÂàÃÂõÃÂøûø òþÃÂÿþûÃÂ÷þòðÃÂÃÂÃÂàÃÂÃÂðýôðÃÂÃÂýÃÂüø ÃÂÃÂõôÃÂÃÂòðüø Python, ø ÷ôõÃÂàòÃÂõ ôõùÃÂÃÂòøÃÂõûÃÂýþ þÃÂõýàÿÃÂþÃÂÃÂþ â øüÿþÃÂÃÂøÃÂÃÂùÃÂõ üþôÃÂûàcgi ø, ÃÂþ÷ôðò þñÃÂõúàúûðÃÂÃÂð FieldStorage, òàÿþûÃÂÃÂøÃÂõ ÃÂõÃÂõ÷ ýõóþ ôþÃÂÃÂÃÂÿ úþ òÃÂõü ôðýýÃÂü, ÿõÃÂõôðýýÃÂü ÿþûÃÂ÷þòðÃÂõûõü, ýõ÷ðòøÃÂøüþ þàøÃÂÿþûÃÂ÷ÃÂõüþóþ üõÃÂþôð:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÃÂõÃÂõüõýýðà%s øüõõà÷ýðÃÂõýøõ %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÃÂÃÂûø òðü ýÃÂöýþ ÿþûÃÂÃÂøÃÂà÷ýðÃÂõýøõ þÿÃÂõôõûõýýþóþ ÿþûÃÂ, ÃÂÃÂþ ôõûðõÃÂÃÂàÃÂðú:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
ÃÂþüøüþ ÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøÃÂ
ôðýýÃÂÃÂ
, þñÃÂõúàúûðÃÂÃÂð FieldStorage ÃÂþôõÃÂöøàøýÃÂþÃÂüðÃÂøàø þ ÿþûÃÂÃÂ
÷ðóþûþòúð (ò ýðÃÂõü ÿÃÂøüõÃÂõ øÃÂ
üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ÃÂûþòðÃÂàdata.headers). MIME-ÃÂøÿ ôðýýÃÂÃÂ
(ÿõÃÂõôðòðõüÃÂù ÿþûõü ÷ðóþûþòúð Content-Type) üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ðÃÂÃÂøñÃÂÃÂð data.type. çõÃÂõ÷ ÃÂÃÂþàöõ þñÃÂõúàüþöõàñÃÂÃÂàòÃÂÿþûýõýð ø ÷ðóÃÂÃÂ÷úð ÃÂðùûð.<br />
<br />
á ÿþüþÃÂÃÂàüõÃÂþôþò keys() ø has_key() üþöýþ òÃÂÿþûýÃÂÃÂàþñÃÂðñþÃÂúàÿþûÃÂÃÂõýýÃÂÃÂ
ôðýýÃÂÃÂ
ò ÃÂøúûõ ø ÿÃÂþòõÃÂÃÂÃÂàýðûøÃÂøõ ÃÂþù øûø øýþù ÿõÃÂõüõýýþù. ÃÂÃÂÃÂðÃÂø óþòþÃÂÃÂ, ÿÃÂþòõÃÂÃÂÃÂàýðûøÃÂøõ ÿõÃÂõüõýýþù òþ òÃÂ
þôýÃÂÃÂ
ôðýýÃÂÃÂ
, ÿÃÂõöôõ ÃÂõü ÿÃÂøÃÂÃÂÃÂÿðÃÂàú øÃÂ
þñÃÂðñþÃÂúõ, ýÃÂöýþ ýõÿÃÂõüõýýþ â òõôà÷ðÿÃÂþàÃÂþÃÂüøÃÂÃÂõÃÂÃÂàúûøõýÃÂþü, ð úÃÂþ ÷ýðõÃÂ, ÃÂÃÂþ àýõóþ ýð ÃÂüõ?<br />
<br />
=== ÃÂð÷øÃÂÃÂõü ôðýýÃÂõ ===<br />
ÃÂÃÂðú, ÿþûÃÂÃÂðÃÂàôðýýÃÂõ þàúûøõýÃÂð üàýðÃÂÃÂøûøÃÂÃÂ. ÃÂÃÂÿÃÂðòûÃÂÃÂàÃÂþöõ ÃÂüõõü. ÃÂÃÂÃÂðûþÃÂàÿÃÂøôÃÂüðÃÂÃÂ, úðú ÃÂÃÂø ôðýýÃÂõ ûÃÂÃÂÃÂõ òÃÂõóþ ÃÂ
ÃÂðýøÃÂÃÂ. ÃÂþýõÃÂýþ, ôûàýõÃÂûþöýþù óþÃÂÃÂõòþù úýøóø àýõñþûÃÂÃÂþù ýðóÃÂÃÂ÷úþù òÿþûýõ ÃÂ
òðÃÂøûþ ñàø ÃÂõúÃÂÃÂþòÃÂÃÂ
ÃÂðùûþò. ÃÂÃÂðòôð, ÃÂðü õÃÂÃÂàÃÂòþø ÃÂûþöýþÃÂÃÂø â õÃÂûø ÃÂÃÂð÷àÿÃÂÃÂàÃÂõûþòõú ÷ðÃÂ
þÃÂÃÂàòÃÂÃÂúð÷ðÃÂàÃÂòþõ üýõýøõ þ òðÃÂõù úÃÂÃÂÃÂõùÃÂõù ôþüðÃÂýõù ÃÂÃÂÃÂðýøÃÂúõ, ÃÂþ ÃÂÃÂõýðÃÂøàÿÃÂøôõÃÂÃÂàúðúøü-ÃÂþ þñÃÂð÷þü ÃÂõóÃÂûøÃÂþòðÃÂàôþÃÂÃÂÃÂÿ ú ÃÂðùûÃÂ-ÃÂ
ÃÂðýøûøÃÂà(úðú üøýøüÃÂü, þñÃÂðñðÃÂÃÂòðÃÂàÃÂøÃÂÃÂðÃÂøÃÂ, õÃÂûø ÃÂðùû ÃÂöõ þÃÂúÃÂÃÂàýð ÷ðÿøÃÂàôÃÂÃÂóøü ÃÂú÷õüÿûÃÂÃÂþü ÃÂÃÂõýðÃÂøÃÂ). ÃÂþ ÷ðÃÂõü ýðü òÃÂõ ÃÂÃÂø óþûþòýÃÂõ ñþûø? ÃÂÃÂûø üàÃÂðú ûþòúþ þÃÂòõÃÂÃÂõûøÃÂàþàýõþñÃÂ
þôøüþÃÂÃÂø òÃÂÃÂÃÂýÃÂàÃÂð÷ñøÃÂðÃÂàHTTP-÷ðÿÃÂþÃÂÃÂ, ÃÂþ ýõÃÂöõûø ýõ ýðùôõü ÃÂÃÂþ-ÃÂþ ÿþôÃÂ
þôÃÂÃÂõõ ýð ÃÂÃÂþàÃÂð÷?<br />
<br />
ÃÂþýõÃÂýþ, ýðùôõü! àÃÂÃÂþ ëÃÂÃÂþ-ÃÂþû ýð÷ÃÂòðõÃÂÃÂàÃÂøÃÂÃÂõüþù ÃÂÿÃÂðòûõýøàñð÷ðüø ôðýýÃÂÃÂ
(ò ÿÃÂþÃÂÃÂþÃÂõÃÂÃÂõ â áãÃÂÃÂ). âõÿõÃÂàýðÃÂõ ôõûþ â þÃÂÿÃÂðòøÃÂà÷ðÿÃÂþàø ÿþûÃÂÃÂøÃÂàþÃÂòõÃÂ. ÃÂÃÂõ þÃÂÃÂðûÃÂýþõ â ÃÂöõ ýõ ýðÃÂð ÷ðñþÃÂð.<br />
<br />
ÃÂûàÃÂÃÂþóþ ÿÃÂøüõÃÂð àòÃÂñÃÂðû ò úðÃÂõÃÂÃÂòõ ëþÃÂòõÃÂÃÂÃÂòõýýþóþû ÷ð ÃÂ
ÃÂðýõýøõ ôðýýÃÂÃÂ
ÃÂõÃÂòõàñð÷ ôðýýÃÂÃÂ
PostgreSQL. ÃÂþÃÂúþûÃÂúàüàÿøÃÂõü ýàþÃÂõýàÿÃÂþÃÂÃÂÃÂàóþÃÂÃÂõòÃÂàúýøóÃÂ, ÃÂþ ø ÃÂÃÂÃÂÃÂúÃÂÃÂÃÂð ñð÷àñÃÂôõààýðàÃÂûõüõýÃÂðÃÂýþù â þôýð ÃÂðñûøÃÂð àÃÂÃÂõüàÿþûÃÂüø: òÃÂõüàÿÃÂñûøúðÃÂøø ÃÂþþñÃÂõýøÃÂ, øüàðòÃÂþÃÂð ø, ÃÂþñÃÂÃÂòõýýþ, ÃÂðüþ ÃÂþþñÃÂõýøõ:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÃÂàÿþôÃÂþõôøýøûøÃÂàú ñð÷õ ôðýýÃÂÃÂ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÃÂþöðûÃÂù, õôøýÃÂÃÂòõýýþõ, ÃÂÃÂþ ÷ôõÃÂàýÃÂöýþ ÿþÃÂÃÂýøÃÂÃÂ, ÃÂÃÂþ ÿþÃÂõüàñð÷õ ø ÃÂðñûøÃÂõ üàýð÷ýðÃÂøûø òûðôõûÃÂÃÂõü ÿþûÃÂ÷þòðÃÂõûàwww-data. ÃÂÃÂþÃÂÃÂþ ú ýøü ñÃÂôõàþñÃÂðÃÂðÃÂÃÂÃÂàcgi-ÃÂÃÂõýðÃÂøù, ÃÂðñþÃÂðÃÂÃÂøù àÿÃÂðòðüø HTTP-ÃÂõÃÂòõÃÂð Apache, úþÃÂþÃÂÃÂù, ò ÃÂòþàþÃÂõÃÂõôÃÂ, øÃÂÿþûýÃÂõÃÂÃÂàþàøüõýø ôðýýþóþ ÿþûÃÂ÷þòðÃÂõûà[ò òðÃÂõü ôøÃÂÃÂÃÂøñÃÂÃÂøòõ þý üþöõàýð÷òðÃÂÃÂÃÂàÿþ-ôÃÂÃÂóþüÃÂ, â ÿÃÂøü. ÃÂõô.]. àPostgreSQL ÿþ ÃÂüþûÃÂðýøàÃÂÃÂõñÃÂõÃÂ, ÃÂÃÂþñàøüàÿþûÃÂ÷þòðÃÂõûàò ÃÂàÃÂþòÿðôðûþ àõóþ ÃÂøÃÂÃÂõüýÃÂü øüõýõü. ÃÂýõ ÃÂÃÂþ úðöõÃÂÃÂàôþÃÂÃÂðÃÂþÃÂýþ ÃÂôþñýÃÂü, ÃÂ
þÃÂàòÃÂ, úþýõÃÂýþ, üþöõÃÂõ ÿþÃÂÃÂÃÂÿøÃÂàÿþ-ÃÂòþõüÃÂ.<br />
<br />
=== DB API ýð ÃÂÃÂÃÂðöõ ÃÂýøÃÂøúðÃÂøø ===<br />
ÃÂÃÂÃÂðûþÃÂàÃÂð÷þñÃÂðÃÂÃÂÃÂÃÂ, úðú öõ Python ò÷ðøüþôõùÃÂÃÂòÃÂõààñð÷ðüø ôðýýÃÂÃÂ
. ÃÂûàÃÂÃÂþóþ Python ÿÃÂõôþÃÂÃÂðòûÃÂõàDB API â ÃÂÿõÃÂøðûÃÂýÃÂù øýÃÂõÃÂÃÂõùÃÂ, ÃÂýøÃÂøÃÂøÃÂÃÂÃÂÃÂøù ýðñþàüõÃÂþôþò, úþÃÂþÃÂÃÂõ ñÃÂôÃÂàþôøýðúþòþ ÃÂðñþÃÂðÃÂàýõ÷ðòøÃÂøüþ þàÃÂþóþ, àúðúþù áãÃÂàüàò÷ðøüþôõùÃÂÃÂòÃÂõü. ÃÂûàÃÂðñþÃÂààPostgreSQL ýðü ÿþýðôþñøÃÂÃÂàüþôÃÂûàPyPgSQL (ò ÃÂÃÂðýôðÃÂÃÂýþù ÿþÃÂÃÂðòúõ õóþ üþöõàýõ þúð÷ðÃÂÃÂÃÂÃÂ, ýþ òðàüõýõôöõàÿðúõÃÂþò ýðòõÃÂýÃÂúð ñÃÂôõàò úÃÂÃÂÃÂõ, úðú õóþ ÃÂÃÂÃÂðýþòøÃÂÃÂ; úÃÂÃÂðÃÂø, ÃÂÃÂþ ýõ õôøýÃÂÃÂòõýýÃÂù üþôÃÂûàâ àòðÃÂ, òþ÷üþöýþ, ñÃÂôõàPyGreSQL, úþÃÂþÃÂÃÂù ÃÂðñþÃÂðõàýøÃÂÃÂÃÂàýø ÃÂ
ÃÂöõ ø àÃÂõüø öõ ÃÂðüÃÂüø üõÃÂþôðüø).<br />
<br />
DB API þÿÃÂõôõûÃÂõàÃÂÃÂðýôðÃÂÃÂýÃÂõ üõÃÂþôàÃÂðñþÃÂààñð÷ðüø ôðýýÃÂÃÂ
, ÃÂðú ÃÂÃÂþ, úðúþù ñàüþôÃÂûàòàýø ÷ðóÃÂÃÂ÷øûø ø àúðúþù ñàáãÃÂàýø ÃÂðñþÃÂðûø (ñÃÂôàÃÂþ MySQL, PostgreSQL, SQLite øûø ÃÂÃÂþ-ÃÂþ õÃÂõ), üõýÃÂÃÂÃÂÃÂàñÃÂôõàÃÂþûÃÂúþ øüàüþôÃÂûÃÂ. ÃÂûðòýþõ, ÃÂÃÂþñàøÃÂÿþûÃÂ÷ÃÂõüÃÂù üþôÃÂûàÃÂþþÃÂòõÃÂÃÂÃÂòþòðû DB API. àðÃÂÃÂüþÃÂÃÂøü úþÃÂþÃÂúþ þÃÂýþòýÃÂõ üõÃÂþôÃÂ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
âðú þÃÂÃÂÃÂõÃÂÃÂòûÃÂõÃÂÃÂàÿþôúûÃÂÃÂõýøõ ú ñð÷õ. à÷ðòøÃÂøüþÃÂÃÂø þàÃÂøÃÂÃÂðÃÂøø, òðü üþöõàÿþÃÂÃÂõñþòðÃÂÃÂÃÂàÃÂúð÷ðÃÂàÃÂþûÃÂúþ ýÃÂöýÃÂõ ÿðÃÂðüõÃÂÃÂà(ýðÿÃÂøüõÃÂ, øüàÃÂ
þÃÂÃÂð 'localhost' ÿþôÃÂð÷ÃÂüõòðõÃÂÃÂàÿþ ÃÂüþûÃÂðýøÃÂ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÃÂÃÂÃÂÃÂþÃÂàÿþôôõÃÂöøòðÃÂÃÂÃÂàôðûõúþ ýõ òÃÂõüø áãÃÂÃÂ, ýþ ôûàþñÃÂýþÃÂÃÂø ò DB API þýø òòõôõýàø, ò ÃÂûÃÂÃÂðõ ýõþñÃÂ
þôøüþÃÂÃÂø, ôþûöýàÃÂüÃÂûøÃÂþòðÃÂÃÂÃÂàüþôÃÂûÃÂüø ÃÂþÿÃÂÃÂöõýøàøÃÂúÃÂÃÂÃÂÃÂòõýýþ. âðú ÃÂÃÂþ ýõ ÷ðñÃÂòðùÃÂõ þÃÂÿÃÂðòûÃÂÃÂàòÃÂõ òðÃÂø ÷ðÿÃÂþÃÂàÃÂõÃÂõ÷ úÃÂÃÂÃÂþÃÂ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
âðú òÃÂÿþûýÃÂõÃÂÃÂàSQL-÷ðÿÃÂþÃÂ. ÃÂÃÂûø ò ÃÂÃÂÃÂþúõ ÷ðÿÃÂþÃÂð øÃÂÿþûÃÂ÷ÃÂÃÂÃÂÃÂà÷ýðúþüõÃÂÃÂð %s, ÃÂþ òÃÂþÃÂÃÂü ÿðÃÂðüõÃÂÃÂþü ÿõÃÂõôðõÃÂÃÂàÃÂÿøÃÂþú ÿõÃÂõüõýýÃÂÃÂ
-÷ýðÃÂõýøù, ÿÃÂøÃÂõü ò SQL-÷ðÿÃÂþÃÂõ ÷ýðúþüõÃÂÃÂð ýõ ÃÂÃÂõñÃÂõÃÂÃÂàþúÃÂÃÂöðÃÂàðÿþÃÂÃÂÃÂþÃÂðüø â üþôÃÂûàÃÂôõûðõàÃÂÃÂþ ÃÂðüþÃÂÃÂþÃÂÃÂõûÃÂýþ ò ÷ðòøÃÂøüþÃÂÃÂø þÃÂ<br />
ÃÂøÿð ÿõÃÂõüõýýþù.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÃÂþ÷òÃÂðÃÂðõàôòÃÂüõÃÂýÃÂù ÃÂÿøÃÂþú (ÃÂÃÂÃÂþúø â ÿþûÃÂ) ÿþûÃÂÃÂõýýÃÂÃÂ
þàáãÃÂàôðýýÃÂÃÂ
. áÃÂÃÂõÃÂÃÂòÃÂÃÂàø ôÃÂÃÂóøõ üõÃÂþôÃÂ, þ÷ýðúþüøÃÂÃÂÃÂààúþÃÂþÃÂÃÂüø òàÃÂüþöõÃÂõ ò ôþúÃÂüõýÃÂðÃÂøø øûø àÿþüþÃÂÃÂà÷ýðúþüþù òðü ÃÂÃÂýúÃÂøø dir() ôð ÿðÃÂÃÂ-ÃÂÃÂþùúø ýõÃÂûþöýÃÂÃÂ
ÃÂúÃÂÿõÃÂøüõýÃÂþò.<br />
<br />
=== ÃÂðúÃÂõÿûÃÂõü ýð ÿÃÂðúÃÂøúõ ===<br />
ÃÂõÃÂõùôõü ú ÃÂðÃÂÃÂüþÃÂÃÂõýøàýðÃÂõóþ ÿÃÂøüõÃÂð. ÃÂðÃÂýõü ÃÂÃÂðýôðÃÂÃÂýþ â ÃÂúðöõü úþôøÃÂþòúÃÂ, ÿþôúûÃÂÃÂøü ýÃÂöýÃÂõ üþôÃÂûø:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
ÃÂðûõõ, þÿÃÂõôõûøü ôòõ ÃÂÃÂýúÃÂøø. ÃÂõÃÂòðàñÃÂôõàþÃÂòõÃÂðÃÂà÷ð ôþñðòûõýøõ ýþòþóþ ÃÂþþñÃÂõýøàò ñð÷ÃÂ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
ÃÂðú òøôøÃÂõ, òÃÂõ þÃÂõýàôðöõ ûþóøÃÂýþ: ÃÂÃÂÃÂðýðòûøòðõü ÃÂþõôøýõýøõ àÃÂà(ÿþÃÂúþûÃÂúàò ýðÃÂõü ÃÂûÃÂÃÂðõ ÿþôúûÃÂÃÂõýøõ òÃÂÿþûýÃÂõÃÂÃÂààøüõýõü ÃÂõúÃÂÃÂõóþ ÃÂøÃÂÃÂõüýþóþ ÿþûÃÂ÷þòðÃÂõûÃÂ, ÃÂþ ôþÃÂÃÂðÃÂþÃÂýþ ÃÂúð÷ðÃÂàÃÂþûÃÂúþ øüàñð÷ÃÂ), ÃÂþ÷ôðõü úÃÂÃÂÃÂþà(ò PostgreSQL þýø ýõ ÿÃÂøüõýÃÂÃÂÃÂÃÂÃÂ, ýþ þýø ÃÂüÃÂûøÃÂÃÂÃÂÃÂÃÂàúðöôÃÂü üþôÃÂûõü, ÿÃÂõÃÂõýôÃÂÃÂÃÂøü ýð ÃÂþþÃÂòõÃÂÃÂÃÂòøõ DB API), òÃÂÿþûýÃÂõÃÂÃÂà÷ðÿÃÂþÃÂ, ÷ðúÃÂÃÂòðõÃÂÃÂàúÃÂÃÂÃÂþÃÂ, ÃÂøúÃÂøÃÂÃÂÃÂÃÂÃÂàø÷üõýõýøà(PostgreSQL øÃÂÿþûÃÂ÷ÃÂõàÃÂÃÂðý÷ðúÃÂøø, ÿþÃÂÃÂþüàòÃÂÿþûýõýøõ üõÃÂþôð commit() þñÃÂ÷ðÃÂõûÃÂýþ, øýðÃÂõ òðÃÂø ø÷üõýõýøàýõ ñÃÂôÃÂàÃÂþÃÂ
ÃÂðýõýÃÂ), ø, ýðúþýõÃÂ, ÷ðúÃÂÃÂòðõü ÃÂðüþ ÃÂþõôøýõýøõ àñð÷þù. àÿþûõ datum ÷ðýþÃÂøü ÷ýðÃÂõýøõ òÃÂÃÂÃÂþõýýþù ÿõÃÂõüõýýþù PostgreSQL â now, úþÃÂþÃÂðàúðöôÃÂù ÃÂð÷ ÷ðüõýÃÂõÃÂÃÂàÃÂõúÃÂÃÂøü ÷ýðÃÂõýøõü ôðÃÂàø òÃÂõüõýø.<br />
<br />
ÃÂàø ÿõÃÂðÃÂà÷ðóþûþòúð ëLocationû òÃÂÿþûýÃÂõÃÂÃÂàôûàÃÂþóþ, ÃÂÃÂþñàÿõÃÂõýðÿÃÂðòøÃÂàÿþûÃÂ÷þòðÃÂõûàýð ÃÂÃÂþàöõ ÃÂÃÂõýðÃÂøù, ýþ ÃÂöõ ñõ÷ ÿðÃÂðüõÃÂÃÂþò â üàöõ ôþûöýàÿþúð÷ðÃÂàúûøõýÃÂÃÂ, ÃÂÃÂþ þý ýð ÃÂðüþü ôõûõ òòõû? (ïúþÃÂà#form øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂÃÂ, ÃÂÃÂþñàðòÃÂþüðÃÂøÃÂõÃÂúø ÿÃÂþúÃÂÃÂÃÂøÃÂàÃÂÃÂÃÂðýøÃÂúàýð ÿþÃÂûõôýõõ ÃÂþþñÃÂõýøõ).<br />
<br />
ÃÂÃÂþÃÂðàÃÂÃÂýúÃÂøàñÃÂôõàþÃÂòõÃÂðÃÂà÷ð òÃÂòþô ýð ÃÂúÃÂðý ÃÂöõ þÃÂÃÂðòûõýýÃÂÃÂ
ò úýøóõ ÷ðÿøÃÂõù, ð ÃÂðúöõ ÷ð ÃÂþÃÂüÃÂ, àÿþüþÃÂÃÂàúþÃÂþÃÂþù üþöýþ ñÃÂôõàôþñðòøÃÂàø ÃÂòþõ òÃÂÃÂúð÷ÃÂòðýøõ:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
àÃÂÃÂþü ÃÂÃÂðóüõýÃÂõ üàòÃÂñøÃÂðõü òÃÂõ ÃÂÃÂÃÂþúø ø÷ ýðÃÂõù ÃÂðñûøÃÂàôðýýÃÂÃÂ
, ÃÂþÃÂÃÂøÃÂÃÂàøÃÂ
ÿþ ôðÃÂõ. àõ÷ÃÂûÃÂÃÂðàÃÂþÃÂ
ÃÂðýÃÂõÃÂÃÂàò ÿõÃÂõüõýýþù res, àúþÃÂþÃÂþù ø ñÃÂôõü ÃÂðñþÃÂðÃÂÃÂ. âõÿõÃÂàþÃÂÃÂðûþÃÂàûøÃÂàðúúÃÂÃÂðÃÂýõýÃÂúþ ÃÂð÷ûþöøÃÂàýðÃÂø ôðýýÃÂõ ÿþ ÃÂðñûøÃÂúðü ø òÃÂòõÃÂÃÂø øÃÂ
ýð ÃÂúÃÂðý:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÃÂõûÃÂúðü ú ýðü ò óþÃÂÃÂø!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>âþòðÃÂøà<B>%s</B> ÿþòõôðûýðü ÃÂûõôÃÂÃÂÃÂõõ:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÃÂÃÂøÃÂþõôøýÃÂùÃÂõÃÂàú ôøÃÂúÃÂÃÂÃÂøø:</H3>"<br />
print """<FORM method='GET'><br />
ÃÂðÃÂõ øüÃÂ: <INPUT type='text' name='author'><BR><br />
çÃÂþ òàôÃÂüðõÃÂõ ÿþ ÃÂÃÂþüàÿþòþôÃÂ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÃÂÃÂÿÃÂðòøÃÂÃÂ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÃÂ÷þñÃÂðöõýøõ:Img 83 81 1.png|thumb|ÃÂø ÃÂüðùûøúþò, ýø BB-úþôð, ýø ôðöõ ûþóþÃÂøÿð... ÃÂðÃÂþ üàÃÂôõûðûø ÃÂÃÂàóþÃÂÃÂõòÃÂà÷ð 10 üøýÃÂÃÂ!]]<br />
<br />
áüÃÂÃÂû úþýÃÂÃÂÃÂÃÂúÃÂøø str(item[0])[:19] ÷ðúûÃÂÃÂðõÃÂÃÂàò ÃÂþü, ÃÂÃÂþñàò ÃÂÃÂÃÂþúõ òÃÂõüõýø þÃÂÃÂõÃÂàýõýÃÂöýÃÂõ ýðü üøûûøÃÂõúÃÂýôÃÂ, úþÃÂþÃÂÃÂõ ÃÂþÃÂ
ÃÂðýÃÂÃÂÃÂÃÂàò ÿþûõ ÃÂøÿð timestamp. ÃÂþÃÂûõ òÃÂõÃÂ
þÿÃÂñûøúþòðýýÃÂÃÂ
ÃÂþþñÃÂõýøù òÃÂòþôøü ÃÂþÃÂüàôþñðòûõýøàýþòþóþ, ÃÂÃÂþñàúðöôÃÂù üþó ÿÃÂøÃÂþõôøýøÃÂÃÂÃÂàú ýðÃÂõù ôøÃÂúÃÂÃÂÃÂøø. ÃÂÃÂÃÂðÃÂø, ò ÃÂõóõ <FORM> üàýõ ÃÂúð÷ðûø ÿðÃÂðüõÃÂàaction, ÿþÃÂúþûÃÂúàôðýýÃÂõ ñÃÂôÃÂàÿõÃÂõôðòðÃÂÃÂÃÂàýð þñÃÂðñþÃÂúàÃÂÃÂþüàöõ ÃÂÃÂõýðÃÂøà(ñûðóþôðÃÂàÃÂõüàøüàÃÂÃÂõýðÃÂøàüþöýþ ÿÃÂøÃÂòþøÃÂàûÃÂñþõ).<br />
ÃÂðúþýõÃÂ, ÿþÃÂûõôýøù ÃÂÃÂðóüõýÃÂ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
áþ÷ôðõü FieldStorage-þñÃÂõúÃÂ, ø õÃÂûø ò ýõü õÃÂÃÂà÷ðÿþûýõýýÃÂõ ÿþûàmessage ø author (ÃÂþ õÃÂÃÂà÷ðÿÃÂþàñÃÂû ÃÂÃÂþÃÂüøÃÂþòðý ø÷ ÷ðÿþûýõýýþù ÿþûÃÂ÷þòðÃÂõûõü ÃÂþÃÂüÃÂ), ÃÂþ, ýõüýþöúþ øÃÂ
þñÃÂðñþÃÂðò (ÃÂÃÂýúÃÂøàcgi.escape() ÷ðüõýÃÂõàòÃÂõ ëýõñûðóþýðôõöýÃÂõû ÃÂøüòþûàâ ýðÿÃÂøüõÃÂ, < â øÃÂ
ÃÂÃÂðýôðÃÂÃÂýÃÂüø SGML-ÃÂÃÂÃÂýþÃÂÃÂÃÂüø, ò ôðýýþü ÃÂûÃÂÃÂðõ â &lt;), ÿõÃÂõôðõü ÃÂÃÂýúÃÂøø addMessage(). ÃÂñÃÂðñþÃÂúð ýÃÂöýð ôûàÃÂþóþ, ÃÂÃÂþñà÷ûþÃÂüÃÂÃÂûõýýøú ýõ üþó òòõÃÂÃÂø ò ÿþûõ ÃÂþþñÃÂõýøàøûø øüõýø ðòÃÂþÃÂð ÃÂÃÂþ-ýøñÃÂôàÃÂðúþõ:<br />
<br />
<SCRIPT>alert('ÃÂð ÿþÃÂûø òàòÃÂõ!');</SCRIPT><br />
<br />
àÃÂûþòÃÂ, ÿÃÂõýõñÃÂõóðÃÂàÿÃÂþòõÃÂúþù òòõôõýýÃÂÃÂ
ôðýýÃÂÃÂ
ýø ò úþõü ÃÂûÃÂÃÂðõ ýõûÃÂ÷ÃÂ. ÃÂðùôøÃÂõ úðú-ýøñÃÂôàýð [http://securitylab.ru securitylab.ru] ø ÿþÃÂüþÃÂÃÂøÃÂõ, ÃÂúþûÃÂúþ ÃÂÃÂ÷òøüþÃÂÃÂõù ÃÂøÿð ëXSSû þñýðÃÂÃÂöøòðõÃÂÃÂàúðöôÃÂù üõÃÂÃÂÃÂ! âðú ÃÂÃÂþ ÃÂÃÂÃÂúø ÃÂÃÂÃÂúðüø, ýþ ÿþÃÂûõôÃÂÃÂòøàüþóÃÂàñÃÂÃÂàþÃÂõýàÃÂõÃÂÃÂõ÷ýÃÂüø.<br />
<br />
=== ÃÂÃÂôð öõ ýðü ÃÂõÿõÃÂàøôÃÂø? ===<br />
ÃÂÃÂðú, ÃÂÃÂþ-ÃÂþ òÿþûýõ ÃÂðñþÃÂþÃÂÿþÃÂþñýþõ àýðàõÃÂÃÂà(ÃÂü. [[LXF83:Python#img|ÃÂøÃÂÃÂýþú]]). ÃÂþ úðú òàüþöõàôþóðôðÃÂÃÂÃÂÃÂ, ýðÃÂð óþÃÂÃÂõòðàþÃÂõýàôðûõúð þàÃÂþòõÃÂÃÂõýÃÂÃÂòð. çÃÂþ õÃÂõ üþöýþ ÃÂôõûðÃÂÃÂ? ÃÂÃÂ, ýðÿÃÂøüõÃÂ, ÃÂð÷ñøÃÂàýð ÃÂÃÂÃÂðýøÃÂÃÂ. ÃÂþúð ÃÂþþñÃÂõýøù ò ýõù ñÃÂôõàýõ ñþûÃÂÃÂõ ôÃÂöøýÃÂ, ÃÂþùôõàø ÃÂðú. àúþóôð øÃÂ
ÃÂøÃÂûþ ôþùôõàôþ ÃÂþÃÂýø, ÃÂþ ÃÂõôúøù ÿþûÃÂ÷þòðÃÂõûàôþöôõÃÂÃÂàþúþýÃÂðýøà÷ðóÃÂÃÂ÷úø òÃÂõÃÂ
ôðýýÃÂÃÂ
. ÃÂþöýþ ôðÃÂàÿþûÃÂ÷þòðÃÂõûÃÂü òþ÷üþöýþÃÂÃÂàøÃÂÿþûÃÂ÷þòðÃÂàýõúþÃÂþÃÂÃÂõ HTML-ÃÂõóø, ÃÂÃÂþñàøÃÂ
ÃÂþþñÃÂõýøàòÃÂóûÃÂôõûø ñþûõõ úÃÂðÃÂþÃÂýþ. ÃÂþöýþ ôþñðòøÃÂàÃÂüðùûøúþò... àüþöýþ ôðöõ ÃÂôõûðÃÂàüþôÃÂûàðôüøýøÃÂÃÂÃÂøÃÂþòðýøÃÂ, ÿþ÷òþûÃÂÃÂÃÂøù ÃÂõôðúÃÂøÃÂþòðÃÂàøûø ÃÂôðûÃÂÃÂàÃÂþþñÃÂõýøÃÂ, ð ÃÂðúöõ þÃÂòõÃÂðÃÂàýð ýøÃÂ
. âðú ÃÂÃÂþ ÃÂðñþÃÂàýõÿþÃÂðÃÂÃÂù úÃÂðù. ÃÂõÃÂ÷ðùÃÂõ â ýõ ñÃÂôàòðü üõÃÂðÃÂÃÂ.<br />
<br />
=== ÃÂõúþÃÂþÃÂÃÂõ ÃÂðÃÂÿÃÂþÃÂÃÂÃÂðýÃÂýýÃÂõ MIME-ÃÂøÿà===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-ÃÂøÿ<br />
! ÃÂÿøÃÂðýøõ<br />
|-<br />
| text/plain<br />
| ÃÂÃÂþÃÂÃÂþù ÃÂõúÃÂÃÂ<br />
|-<br />
| text/html<br />
| HTML-ÃÂÃÂÃÂðýøÃÂð<br />
|-<br />
| image/gif<br />
| ÃÂ÷þñÃÂðöõýøõ GIF<br />
|-<br />
| video/mpeg<br />
| ÃÂøôõþ-ÃÂðùû ò ÃÂþÃÂüðÃÂõ MPEG<br />
|-<br />
| application/msword <br />
| ÃÂþúÃÂüõýàMS Word<br />
|}</div>
RicroAcdom
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-29T15:39:53Z
<p>RicroAcdom: </p>
<hr />
<div>[http://s1.shard.jp/olharder/autosurf-site.html auto diego part san used<br />
] [http://s1.shard.jp/frhorton/2beniqaav.html what so interesting about african music<br />
] [http://s1.shard.jp/losaul/atlas-of-australian.html proofreading jobs australia<br />
] [http://s1.shard.jp/frhorton/7fqgy22i2.html africa symbol] [http://s1.shard.jp/bireba/windows-xp-antivirus.html comparatifs antivirus<br />
] [http://s1.shard.jp/olharder/seiko-titanium-kinetic.html auto az chase finance phoenix<br />
] [http://s1.shard.jp/galeach/new121.html asian chicks are ugly<br />
] [http://s1.shard.jp/frhorton/ybfhg5c59.html african giant snail<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html pc cillin antivirus reviews<br />
] [http://s1.shard.jp/olharder/autoroll-654.html links] [http://s1.shard.jp/olharder/autoroll-654.html index] [http://s1.shard.jp/bireba/pc-cillin-antivirus.html before symantec antivirus could be completely installed<br />
] [http://s1.shard.jp/galeach/new144.html asian swallows<br />
] [http://s1.shard.jp/frhorton/3o7l9jema.html teaching jobs africa<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html norton antivirus corporate edition 9.0] [http://s1.shard.jp/frhorton/b9vqclfhc.html ghana african kingdom<br />
] [http://s1.shard.jp/olharder/premium-autoboomru.html 2006 auto ratings<br />
] [http://s1.shard.jp/olharder/automatic-guided.html autoridad concepto de<br />
] [http://s1.shard.jp/losaul/australia-uranium.html ryobi power tools australia<br />
] [http://s1.shard.jp/galeach/new132.html wall street journal asia edition<br />
] [http://s1.shard.jp/bireba/clam-win-antivirus.html giant antivirus software<br />
] [http://s1.shard.jp/losaul/informed-sources.html unomedical australia<br />
] [http://s1.shard.jp/losaul/simple-plan.html gift homeware australia<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html disable norton antivirus 2004<br />
] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/galeach/new116.html asia and south pacific map<br />
] [http://s1.shard.jp/losaul/australia-zoo.html proligo australia<br />
] [http://s1.shard.jp/olharder/grand-theft-auto.html autohits autosurf autosurf beautypeople.com<br />
] [http://s1.shard.jp/frhorton/tiwomyd3z.html african american for girl hair style little<br />
] [http://s1.shard.jp/olharder/car-ezautoshippersnet.html sansone rt 66 auto mall<br />
] [http://s1.shard.jp/olharder/audi-automotive.html b and d auto lincoln<br />
] [http://s1.shard.jp/frhorton/6znbfza3k.html property for sale garden route south africa<br />
] [http://s1.shard.jp/frhorton/4klamxahb.html learners license south africa] [http://s1.shard.jp/frhorton/aarrl6erq.html beautiful african american hair style<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/frhorton/lr43ii5kv.html african tree frog<br />
] [http://s1.shard.jp/bireba/alertaantivirus.html review of antivirus programs<br />
] [http://s1.shard.jp/olharder/autoroll-654.html sitemap] [http://s1.shard.jp/galeach/new11.html asian dvd guide<br />
] [http://s1.shard.jp/olharder/automotive-latch.html automatic playing card shuffler<br />
] [http://s1.shard.jp/losaul/australian-journal.html real estate south australia adelaide<br />
] [http://s1.shard.jp/bireba/symantec-antivirus.html grissoft antivirus<br />
] [http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/frhorton/map.html east africa religions<br />
] [http://s1.shard.jp/losaul/time-difference.html australian home builders<br />
] [http://s1.shard.jp/galeach/new122.html asian xoxo<br />
] [http://s1.shard.jp/galeach/new112.html sign of hip dysplasia<br />
] [http://s1.shard.jp/losaul/australia-transcriber.html asian study association australia<br />
] [http://s1.shard.jp/galeach/new94.html asia manufacturer<br />
] <br />
{{Цикл/Python}}<br />
<br />
== РабоÑа Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
и web-пÑогÑаммиÑование ==<br />
'' '''ЧаÑÑÑ 3''' ЧÑо Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¼Ð¾Ñнее ÑвÑзки «база даннÑÑ
+ инÑеÑнеÑ»? РеÑли к ÑÑÐ¾Ð¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ ÐµÑе и Python... ЧÑÐ¾Ð±Ñ Ð¿Ð¾ÑÑвÑÑвоваÑÑ Ð²Ñе ÑÑо на пÑакÑике, погÑÑзимÑÑ ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð² пÑÑÐ¸Ð½Ñ SQL-запÑоÑов и HTTP-оÑвеÑов вмеÑÑе Ñ '''СеÑгеем СÑпÑÑновÑм'''.''<br />
<br />
ÐÑ Ñже видели, ÑÑо Python пÑекÑаÑно подÑ
Ð¾Ð´Ð¸Ñ Ð´Ð»Ñ ÑабоÑÑ Ñ ÑекÑÑом. Ð ÑÑо Ñакое инÑеÑнеÑ-ÑÑÑаниÑÑ, коÑоÑÑе Ð¼Ð¸Ð»Ð»Ð¸Ð¾Ð½Ñ ÑеÑвеÑов Apache ежедневно миллиаÑдами оÑдаÑÑ Ð½Ð° ÑаÑÑеÑзание наÑим бÑаÑзеÑам? Ðо ÑÑÑи, ÑÐ¾Ñ Ð¶Ðµ ÑекÑÑ, ÑолÑко немножко «гипеÑ»... РзнаÑиÑ, еÑли нам нÑжно бÑÐ´ÐµÑ ÑоÑмиÑоваÑÑ html-ÑÑÑаниÑÑ Ð´Ð¸Ð½Ð°Ð¼Ð¸ÑеÑки, Ñо Python пÑекÑаÑно Ñ ÑÑим ÑпÑавиÑÑÑ. РникакиÑ
пÑепÑÑÑÑвий Ð´Ð»Ñ ÑазÑабоÑки на нем CGI-ÑÑенаÑиев не ÑÑÑеÑÑвÑÐµÑ â web-ÑеÑвеÑÑ, по болÑÑÐ¾Ð¼Ñ ÑÑеÑÑ, безÑазлиÑно, как именно вÑполнÑеÑÑÑ ÑкÑÐ¸Ð¿Ñ Ð¸ на каком ÑзÑке он ÑазÑабоÑан: лиÑÑ Ð±Ñ Ð¾Ð½ Ñмел ÑиÑаÑÑ Ð´Ð°Ð½Ð½Ñе из поÑока ввода и пеÑеменнÑÑ
окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð´Ð° оÑдаваÑÑ ÑекÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок.<br />
<br />
ÐпÑоÑем, еÑли Ð²Ñ Ð¶Ð°Ð¶Ð´ÐµÑе ÑкоÑоÑÑи, Ñо к ваÑим ÑÑлÑгам mod_Python, да и в Ñежиме FastCGI Python ÑабоÑаÑÑ ÑмееÑ. Ðо ÑейÑÐ°Ñ Ñ Ð½Ð°Ñ ÑÐ°Ð·Ð³Ð¾Ð²Ð¾Ñ Ð²Ñе же не о наÑÑÑойкаÑ
CGI, а о Python, Ñак ÑÑо веÑнемÑÑ Ðº ÑомÑ, Ñади Ñего Ð¼Ñ ÑÑÑ ÑÑаÑÑÑ Ð½Ð°Ñали.<br />
<br />
=== ÐоÑÑановка задаÑи ===<br />
С лÑбÑм вопÑоÑом лÑÑÑе вÑего ÑазбиÑаÑÑÑÑ Ð½Ð° пÑакÑиÑеÑком пÑимеÑе. ÐоÑÑÐ¾Ð¼Ñ Ð¼Ñ Ð±Ñдем «плÑÑаÑÑ» вокÑÑг неÑложного и, в обÑем-Ñо, доÑÑаÑоÑно баналÑного CGI-пÑиложениÑ: гоÑÑевой книги. Ðаодно ÑазбеÑемÑÑ Ñ Ñем, как Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, где пÑедÑÑавлÑеÑÑÑ ÑазÑмнÑм Ñ
ÑаниÑÑ Ð²Ñе наÑи ÑообÑениÑ.<br />
<br />
Ðо пÑежде Ñем пеÑейÑи к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ ÐºÐ¾Ð´Ð° (Ð²Ñ Ð½Ð°Ð¹Ð´ÐµÑе его Ñеликом на наÑем диÑке), полезно бÑÐ´ÐµÑ Ð´Ð°ÑÑ ÐºÐ¾Ðµ-какÑÑ Ð²Ð²Ð¾Ð´Ð½ÑÑ Ð¸Ð½ÑоÑмаÑиÑ.<br />
<br />
=== УнивеÑÑалÑное «междÑмоÑдÑе» CGI ===<br />
CGI (Common Gateway Interface, обÑий ÑлÑзовой инÑеÑÑейÑ) бÑл ÑазÑабоÑан как ÑÑедÑÑво взаимодейÑÑÐ²Ð¸Ñ HTTP-ÑеÑвеÑа Ñ Ð¿ÑогÑаммами, коÑоÑÑе могÑÑ Ð·Ð°Ð¿ÑÑкаÑÑÑÑ Ð² опеÑаÑионной ÑиÑÑеме. ÐÑли говоÑиÑÑ ÑпÑоÑенно, Ñо CGI, пеÑÐµÐ´Ð°Ð²Ð°Ñ ÑпÑавление Ñакой пÑогÑамме (обÑÑно иÑ
именÑÑÑ cgi-ÑÑенаÑиÑми, Ñ
оÑÑ ÑÑо вполне Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸ двоиÑнÑй Ñайл, ÑазÑабоÑаннÑй на C/C++), ÑоÑмиÑÑÐµÑ Ð´Ð»Ñ Ð½ÐµÐµ опÑеделенное окÑÑжение. Ð ÑаÑÑноÑÑи, паÑамеÑÑÑ HTTP-запÑоÑа, полÑÑенного Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа, могÑÑ Ð¿Ð¾Ð¼ÐµÑаÑÑÑÑ Ð² опÑеделеннÑе пеÑеменнÑе окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ пеÑедаваÑÑÑÑ cgi-пÑогÑамме как аÑгÑменÑÑ Ð¸Ð»Ð¸ как вÑ
одной поÑок (STDIN). РоÑÐ²ÐµÑ HTTP-ÑеÑÐ²ÐµÑ Ð¶Ð´ÐµÑ Ð´Ð°Ð½Ð½Ñе, коÑоÑÑе cgi-пÑогÑамма должна вÑдаÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок (STDOUT), и пеÑÐµÐ´Ð°ÐµÑ Ð¸Ñ
клиенÑÑ.<br />
<br />
Таким обÑазом, вÑе, ÑÑо ÑÑебÑеÑÑÑ Ð¾Ñ cgi-пÑогÑаммÑ, ÑÑо ÑпоÑобноÑÑÑ Ð¿Ð¾Ð»ÑÑаÑÑ Ð½ÐµÐ¾Ð±Ñ
одимÑÑ Ð´Ð»Ñ ÑабоÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸Ð· ÑоÑмиÑÑемой HTTP-ÑеÑвеÑом ÑÑÐµÐ´Ñ Ð¸ возвÑаÑаÑÑ Ð¾ÑвеÑнÑе даннÑе, ÑооÑвеÑÑÑвÑÑÑие пÑоÑÐ¾ÐºÐ¾Ð»Ñ HTTP, ÑÑÐ¾Ð±Ñ web-ÐºÐ»Ð¸ÐµÐ½Ñ Ð·Ð½Ð°Ð», ÑÑо Ñ Ð½Ð¸Ð¼Ð¸ делаÑÑ.<br />
<br />
=== УÑимÑÑ Ð¿Ð¾ÑÑлаÑÑ ===<br />
ÐаÑнем Ñ ÑоÑмиÑÐ¾Ð²Ð°Ð½Ð¸Ñ HTTP-оÑвеÑа. ЧÑÐ¾Ð±Ñ Ð±ÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа мог его пÑавилÑно обÑабоÑаÑÑ, он должен ÑоÑÑоÑÑÑ Ð¸Ð· заголовка и Ñела, ÑазделеннÑÑ
пÑÑÑой ÑÑÑокой. Рзаголовке пеÑедаеÑÑÑ Ð½ÐµÐ¾Ð±Ñ
Ð¾Ð´Ð¸Ð¼Ð°Ñ ÑлÑÐ¶ÐµÐ±Ð½Ð°Ñ Ð¸Ð½ÑоÑмаÑиÑ, напÑимеÑ, Ñип ÑодеÑжимого, его кодиÑовка, Ñказание бÑаÑзеÑÑ Ð·Ð°Ð¿ÑоÑиÑÑ Ð´ÑÑгой ÑеÑÑÑÑ (Ñак назÑваемое пеÑенапÑавление), и Ñ.д. ÐÑоÑÑейÑий cgi-ÑÑенаÑий на ÑзÑке Python Ð¼Ð¾Ð¶ÐµÑ Ð²ÑглÑдеÑÑ Ñак:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÐÑли Ð²Ñ ÑÑо видиÑе, знаÑÐ¸Ñ Ð²Ñе ÑабоÑаеÑ</H3>'<br />
</source><br />
<br />
ÐеÑвÑм опеÑаÑоÑом print Ð¼Ñ ÑоÑмиÑÑем минималÑно необÑ
одимÑй заголовок â бÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа обÑзаÑелÑно должен знаÑÑ, каков Ñип пеÑеÑÑлаемÑÑ
ÐµÐ¼Ñ Ð´Ð°Ð½Ð½ÑÑ
(в наÑем ÑлÑÑае ÑÑо пÑоÑÑой ÑекÑÑ, ÑооÑвеÑÑÑвÑÑÑий ÑоÑмаÑÑ HTML). Ðе забÑвайÑе о дополниÑелÑном пеÑеводе ÑÑÑоки \n, необÑ
одимом Ð´Ð»Ñ Ð¾ÑÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° Ð¾Ñ Ñела оÑвеÑа. ÐÑ Ð¸ далее Ð²Ñ Ð¼Ð¾Ð¶ÐµÑе пеÑедаваÑÑ Ð»Ñбой HTML-код.<br />
<br />
ÐналогиÑно могÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð»ÑбÑе обÑекÑÑ, поддеÑживаемÑе клиенÑом: изобÑажениÑ, звÑковÑе ÑайлÑ, css-ÑаблиÑÑ Ð¸ Ñ.д. Ðлавное, ÑÑÐ¾Ð±Ñ Ð·Ð½Ð°Ñение Ð¿Ð¾Ð»Ñ Content-Type (именÑемое Ñакже MIME-Ñипом) ÑооÑвеÑÑÑвовало ÑодеÑжимомÑ.<br />
<br />
=== ÐдеÑÑ Ð¸Ð³ÑаÑÑ, здеÑÑ Ð½Ðµ игÑаÑÑ... ===<br />
Ðднако какой ÑмÑÑл поÑÑÑаÑÑ ÑоÑмиÑование ÑÑаÑиÑеÑкиÑ
, по ÑÑÑи, ÑÑÑÐ°Ð½Ð¸Ñ cgi-ÑÑенаÑиÑ, еÑли Ñам HTTP-ÑеÑÐ²ÐµÑ ÑпÑавиÑÑÑ Ñ ÑÑим намного лÑÑÑе? РобÑем-Ñо никакого. Разве ÑÑо Ð´Ð»Ñ Ð¾Ð±Ñего ÑазвиÑиÑ... Ð Ð²Ð¾Ñ Ð² Ñем CGI по-наÑÑоÑÑÐµÐ¼Ñ Ñилен, Ñак ÑÑо в ÑоÑмиÑовании динамиÑеÑкиÑ
ÑÑÑаниÑ, ÑодеÑжимое коÑоÑÑÑ
завиÑÐ¸Ñ Ð¾Ñ Ð¸Ð½ÑоÑмаÑии, пеÑеданной полÑзоваÑелем.<br />
<br />
ÐÑоÑокол HTTP пÑедÑÑмаÑÑÐ¸Ð²Ð°ÐµÑ Ð½ÐµÑколÑко ÑпоÑобов пеÑедаÑи инÑоÑмаÑии Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа на ÑеÑвеÑ, назÑваемÑÑ
меÑодами. Ðаиболее попÑлÑÑнÑе из ниÑ
â GET, POST, PUT и HEAD.<br />
<br />
ÐеÑод GET позволÑÐµÑ Ð²ÑÑавлÑÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð² URL, Ñо еÑÑÑ Ð² ÑÑÑÐ¾ÐºÑ Ð°Ð´ÑеÑа запÑаÑиваемого ÑеÑÑÑÑа. Ðогда «ЯндекÑ» веÑÐ½ÐµÑ Ð²Ð°Ð¼ ÑпиÑок иÑкомÑÑ
ÑÑÑаниÑ, поÑмоÑÑиÑе на адÑеÑнÑÑ ÑÑÑÐ¾ÐºÑ Ð² бÑаÑзеÑе â Ð²Ð¾Ñ Ñак даннÑе и пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET. ÐÑÑаÑи, обÑаÑиÑе внимание на Ñо, как вÑе ÑÑо кодиÑÑеÑÑÑ, оÑобенно еÑли Ð²Ñ Ð¸Ñкали какое-Ñо ÑÑÑÑкое Ñлово.<br />
<br />
ÐÑли на ÑеÑÐ²ÐµÑ ÑÑебÑеÑÑÑ Ð¿ÐµÑедаÑÑ Ð±Ð¾Ð»ÑÑий обÑем инÑоÑмаÑии, или ее желаÑелÑно ÑкÑÑÑÑ Ð¾Ñ Ð»ÑбопÑÑнÑÑ
глаз, иÑполÑзÑеÑÑÑ Ð´ÑÑгой меÑод â POST. Рданном ÑлÑÑае в заголовке пеÑедаеÑÑÑ Ð»Ð¸ÑÑ ÑÐ°Ð·Ð¼ÐµÑ Ð¿Ð¾Ð»ÑзоваÑелÑÑкиÑ
даннÑÑ
, а Ñами даннÑе пеÑеÑÑлаÑÑÑÑ Ð² Ñеле запÑоÑа.<br />
<br />
ÐеÑод PUT пÑедназнаÑаеÑÑÑ Ð´Ð»Ñ ÑазмеÑÐµÐ½Ð¸Ñ ÑеÑÑÑÑов на ÑеÑвеÑе и по ÑообÑажениÑм безопаÑноÑÑи пÑакÑиÑеÑки не иÑполÑзÑеÑÑÑ. ÐÑ Ð¸, наконеÑ, меÑод HEAD оÑÐµÐ½Ñ Ð¿Ð¾Ñ
ож на GET, за Ñем иÑклÑÑением, ÑÑо ÑеÑÐ²ÐµÑ Ð² оÑÐ²ÐµÑ Ð½Ð° Ñакой запÑÐ¾Ñ Ð²Ð¾Ð·Ð²ÑаÑÐ°ÐµÑ Ð½Ðµ веÑÑ ÑеÑÑÑÑ, а лиÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¾ нем, ÑакÑÑ ÐºÐ°Ðº даÑа поÑледнего изменениÑ, помеÑаемÑÑ Ð² заголовке. ÐбÑÑно иÑполÑзÑеÑÑÑ Ð¿ÑокÑи-ÑеÑвеÑами Ð´Ð»Ñ Ð¾Ð¿ÑÐµÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Â«ÑвежеÑÑи» имеÑÑиÑ
ÑÑ Ñ Ð½Ð¸Ñ
даннÑÑ
â ÑÑÐ¾Ð¸Ñ Ð»Ð¸ запÑаÑиваÑÑ ÑеÑÑÑÑ Ð¿Ð¾Ð²ÑоÑно или можно веÑнÑÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ Ñо, ÑÑо еÑÑÑ Ð² кÑÑе.<br />
<br />
ÐпÑÐµÐ´ÐµÐ»ÐµÐ½Ð½Ð°Ñ ÑложноÑÑÑ Ð´Ð»Ñ ÑазÑабоÑÑика cgi-ÑÑенаÑÐ¸Ñ Ð·Ð°ÐºÐ»ÑÑаеÑÑÑ Ð² Ñом, ÑÑо даннÑе, оÑпÑавленнÑе ÑазлиÑнÑми меÑодами, пеÑедаÑÑÑÑ Ð² ÑÑенаÑий по-ÑазномÑ. Так, инÑоÑмаÑиÑ, поÑÑÑпивÑÐ°Ñ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ POST, подаеÑÑÑ Ð½Ð° ÑÑандаÑÑнÑй вÑ
од ÑÑенаÑÐ¸Ñ Ð¸ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ ÑÑиÑана оÑÑÑда, напÑимеÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ sys.stdin.read(size) или даже ÑÑнкÑией raw_input() (Ñ
оÑÑ Ð²Ð¾ вÑоÑом ÑлÑÑае Ñложнее конÑÑолиÑоваÑÑ Ð¾Ð±Ñем пÑинимаемÑÑ
даннÑÑ
). ÐолиÑеÑÑво байÑ, коÑоÑÑе ÑÑебÑеÑÑÑ ÑÑиÑаÑÑ, можно полÑÑиÑÑ Ð¸Ð· пеÑеменной окÑÑÐ¶ÐµÐ½Ð¸Ñ CONTENT_LENGTH (напÑимеÑ, Ñак: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÐÑли ÐºÐ»Ð¸ÐµÐ½Ñ Ð¸ÑполÑзÑÐµÑ Ð¼ÐµÑод GET, Ñо даннÑе поÑÑÑпÑÑ Ð² ÑÑенаÑий ÑеÑез пеÑеменнÑÑ ÑÑÐµÐ´Ñ QUERY_STRING. ÐеÑод, коÑоÑÑм даннÑе пеÑÐµÐ´Ð°Ð½Ñ (нÑжно же как-Ñо ÑазобÑаÑÑÑÑ, где иÑ
иÑкаÑÑ) можно вÑегда полÑÑиÑÑ Ð¸Ð· REQUEST_METHOD.<br />
<br />
ÐÑÑÑ ÐµÑе один оÑобÑй ÑлÑÑай. ÐÑли даннÑе пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET, но Ñ Ð¸ÑполÑзованием «индекÑного» ÑоÑмаÑа, коÑоÑÑй ÑоÑмиÑÑеÑÑÑ Ñегом <ISINDEX>, Ñо в ÑÑом ÑлÑÑае они кодиÑÑÑÑÑÑ Ð½Ðµ в виде «пеÑеменнаÑ=знаÑение&пеÑеменнаÑ=знаÑение&...», а как «знаÑение+знаÑение+...». Ð cgi-ÑÑенаÑÐ¸Ñ Ð¾Ð½Ð¸ бÑдÑÑ Ð¿ÐµÑеданÑ, помимо QUERY_STRING, ÑеÑез аÑгÑменÑÑ ÐºÐ¾Ð¼Ð°Ð½Ð´Ð½Ð¾Ð¹ ÑÑÑоки, как еÑли Ð±Ñ ÑÑенаÑий вÑзÑвалÑÑ Ñакой командой:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
То еÑÑÑ, на ÑÑÐ¾Ñ Ñаз полÑзоваÑелÑÑкие даннÑе можно бÑÐ´ÐµÑ Ð¿Ð¾Ð»ÑÑиÑÑ ÐºÐ°Ðº sys.argv[1] и Ñ.д.<br />
<br />
Ðак видиÑе, огÑомное ÑиÑло ваÑианÑов, пÑедÑÑмоÑÑеннÑÑ
CGI-инÑеÑÑейÑом, коÑоÑÑе вÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ ÑÑÑÐµÐ½Ñ Ð¿Ñи ÑазÑабоÑке ÑÑенаÑиÑ, Ð¼Ð¾Ð¶ÐµÑ Ð²ÑзваÑÑ Ð½ÐµÑвнÑй Ñик даже Ñ Ð¾Ð¿ÑÑнÑÑ
пÑогÑаммиÑÑов, коÑоÑÑе и во Ñне поÑиÑ
онÑÐºÑ Ð½Ð°Ð±Ð¸Ð²Ð°ÑÑ Ð¿Ð¾ подÑÑке какой-Ñо код. РеÑли еÑе вÑпомниÑÑ, ÑÑо даннÑе пеÑедаÑÑÑÑ Ð² закодиÑованном виде (ÑÑо англиÑанам Ñ
оÑоÑо â взÑл знаÑение пеÑеменной и ÑабоÑай, а нам-Ñо Ñ Ð²Ð°Ð¼Ð¸ ÑÑо знаÑение веÑнеÑÑÑ Ð² виде %EC%E4%E0), да еÑе и о пÑовеÑке ÑÑиÑ
даннÑÑ
нÑжно позабоÑиÑÑÑÑ, ÑÑÐ¾Ð±Ñ ÐºÐ°ÐºÐ¾Ð¹-нибÑÐ´Ñ Ð½Ð°ÑинаÑÑий Ñ
Ð°ÐºÐµÑ Ð½Ðµ попÑÑалÑÑ Ð·Ð°ÑÑавиÑÑ Ð½Ð°Ñ ÑеÑÐ²ÐµÑ ÑабоÑаÑÑ Ð¿Ð¾-ÑвоемÑ... ÐеÑ, обо вÑем ÑÑом лÑÑÑе и не вÑпоминаÑÑ. Ðлаго Ñ Ð½Ð°Ñ ÐµÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ cgi, в коÑоÑом вÑе ÑÑо Ñже Ñделано!<br />
<br />
Ðо о нем â ÑÑÑÑ Ð¿Ð¾Ð·Ð¶Ðµ. СнаÑала паÑÑ Ñлов нÑжно ÑказаÑÑ Ð¾ HTML-ÑоÑмаÑ
.<br />
<br />
=== ФоÑмиÑÑем ÑоÑÐ¼Ñ ===<br />
ЧÑÐ¾Ð±Ñ Ð²Ð°Ð¼ бÑло пÑоÑе понÑÑÑ ÑаÑÑмаÑÑиваемÑй ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð¿ÑимеÑ, коÑоÑко ÑÐºÐ°Ð¶Ñ Ð¿Ñо Ñо, как же ÐºÐ»Ð¸ÐµÐ½Ñ Ð²ÑполнÑÐµÑ Ð¿ÐµÑедаÑÑ Ð´Ð°Ð½Ð½ÑÑ
наÑÐµÐ¼Ñ cgi-ÑÑенаÑиÑ. ÐонеÑно, пÑодвинÑÑÑе полÑзоваÑели могÑÑ Ð½Ð°Ð±ÑаÑÑ GET-запÑÐ¾Ñ Ð²ÑÑÑнÑÑ Ð² адÑеÑной ÑÑÑоке бÑаÑзеÑа. ХоÑÑ ÑÑо мелоÑиÑÑÑÑ â Ð²ÐµÐ´Ñ Ð¼Ð¾Ð¶Ð½Ð¾ же ÑÑоÑмиÑоваÑÑ Ð¸ POST-запÑоÑ, подклÑÑивÑиÑÑ ÑелнеÑом на 80-й поÑÑ! ÐпÑоÑем, обÑÑнÑе полÑзоваÑели пÑедпоÑиÑаÑÑ Ð±Ð¾Ð»ÐµÐµ понÑÑнÑе и «оÑÑзаемÑе» ÑпоÑобÑ, напÑимеÑ, ÑоÑмÑ.<br />
<br />
Ðак они вÑглÑдÑÑ, дÑмаÑ, каждÑй знаеÑ. СоздаÑÑÑÑ Ð¾Ð½Ð¸ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ñега <FORM>, внÑÑÑи коÑоÑого добавлÑÑÑÑÑ Ñакие ÑлеменÑÑ, как <INPUT> (поле ввода) или <TEXTAREA> (многоÑÑÑоÑнÑй ÑедакÑоÑ). ÐÑим ÑлеменÑам, еÑли иÑ
даннÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ Ð¿ÐµÑÐµÐ´Ð°Ð½Ñ Ð½Ð° ÑеÑвеÑ, пÑиÑваиваÑÑÑÑ Ð¸Ð¼ÐµÐ½Ð° Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð°ÑÑибÑÑа name. ÐаÑалÑное знаÑение задаеÑÑÑ Ð¿Ð°ÑамеÑÑом value и в далÑнейÑем Ð´Ð»Ñ Â«ÑедакÑиÑÑемÑÑ
» полей Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¾ полÑзоваÑелем. Ðогда полÑзоваÑÐµÐ»Ñ Ð½Ð°Ð¶Ð¸Ð¼Ð°ÐµÑ ÐºÐ½Ð¾Ð¿ÐºÑ Â«ÐÑпÑавиÑÑ» (надпиÑÑ Ð½Ð° ней, в пÑинÑипе, можно измениÑÑ), Ñо бÑаÑÐ·ÐµÑ Ð¾Ð±ÑединÑÐµÑ Ð²Ñе даннÑе полей в паÑÑ name=value, ÑазделÑÑ Ð¸Ñ
Ñимволом &. ÐаÑем полÑÑÐµÐ½Ð½Ð°Ñ Ñаким обÑазом ÑÑÑока пеÑедаеÑÑÑ Ð½Ð° ÑеÑÐ²ÐµÑ Ð¼ÐµÑодом, ÑказаннÑм в аÑÑибÑÑе method Ñега <FORM>. ÐÑÑÑ Ðº ÑÑенаÑиÑ, коÑоÑÑй бÑÐ´ÐµÑ Ð·Ð°Ð½Ð¸Ð¼Ð°ÑÑÑÑ ÐµÐµ обÑабоÑкой, задаеÑÑÑ Ð°ÑÑибÑÑом action ÑÑого же Ñега. ÐÑли action не задан, Ñо даннÑе пеÑедаÑÑÑÑ ÑайлÑ, ÑÑоÑмиÑовавÑÐµÐ¼Ñ ÑекÑÑÑÑ ÑÑÑаниÑкÑ.<br />
<br />
ÐÑли ÑÑо-Ñо не ÑовÑем понÑÑно, обÑаÑиÑеÑÑ Ðº ÐºÐ¾Ð´Ñ ÑазÑабаÑÑваемой гоÑÑевой книги, коÑоÑÑй пÑиведен ниже.<br />
<br />
=== ÐÐ°Ñ ÑпаÑиÑÐµÐ»Ñ â модÑÐ»Ñ cgi ===<br />
ÐозвÑаÑаемÑÑ Ðº обÑабоÑке вÑего ÑÑого добÑа, коÑоÑое ÑоÑни полÑзоваÑелей Ñже гоÑÐ¾Ð²Ñ Ð¾Ð±ÑÑÑиÑÑ Ð½Ð° Ð½Ð°Ñ Ð±ÐµÐ´Ð½Ñй ÑÑенаÑий. ÐÑ ÑеÑили воÑполÑзоваÑÑÑÑ ÑÑандаÑÑнÑми ÑÑедÑÑвами Python, и здеÑÑ Ð²Ñе дейÑÑвиÑелÑно оÑÐµÐ½Ñ Ð¿ÑоÑÑо â импоÑÑиÑÑйÑе модÑÐ»Ñ cgi и, Ñоздав обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage, Ð²Ñ Ð¿Ð¾Ð»ÑÑиÑе ÑеÑез него доÑÑÑп ко вÑем даннÑм, пеÑеданнÑм полÑзоваÑелем, незавиÑимо Ð¾Ñ Ð¸ÑполÑзÑемого меÑода:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÐеÑÐµÐ¼ÐµÐ½Ð½Ð°Ñ %s Ð¸Ð¼ÐµÐµÑ Ð·Ð½Ð°Ñение %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÐÑли вам нÑжно полÑÑиÑÑ Ð·Ð½Ð°Ñение опÑеделенного полÑ, ÑÑо делаеÑÑÑ Ñак:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
Ðомимо полÑзоваÑелÑÑкиÑ
даннÑÑ
, обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage ÑодеÑÐ¶Ð¸Ñ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸ о полÑÑ
заголовка (в наÑем пÑимеÑе иÑ
можно полÑÑиÑÑ Ð¸Ð· ÑловаÑÑ data.headers). MIME-Ñип даннÑÑ
(пеÑедаваемÑй полем заголовка Content-Type) можно полÑÑиÑÑ Ð¸Ð· аÑÑибÑÑа data.type. ЧеÑез ÑÑÐ¾Ñ Ð¶Ðµ обÑÐµÐºÑ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð²Ñполнена и загÑÑзка Ñайла.<br />
<br />
С помоÑÑÑ Ð¼ÐµÑодов keys() и has_key() можно вÑполнÑÑÑ Ð¾Ð±ÑабоÑÐºÑ Ð¿Ð¾Ð»ÑÑеннÑÑ
даннÑÑ
в Ñикле и пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие Ñой или иной пеÑеменной. ÐÑÑаÑи говоÑÑ, пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие пеÑеменной во вÑ
однÑÑ
даннÑÑ
, пÑежде Ñем пÑиÑÑÑпаÑÑ Ðº иÑ
обÑабоÑке, нÑжно непÑеменно â Ð²ÐµÐ´Ñ Ð·Ð°Ð¿ÑÐ¾Ñ ÑоÑмиÑÑеÑÑÑ ÐºÐ»Ð¸ÐµÐ½Ñом, а кÑо знаеÑ, ÑÑо Ñ Ð½ÐµÐ³Ð¾ на Ñме?<br />
<br />
=== ÐазиÑÑем даннÑе ===<br />
ÐÑак, полÑÑаÑÑ Ð´Ð°Ð½Ð½Ñе Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа Ð¼Ñ Ð½Ð°ÑÑилиÑÑ. ÐÑпÑавлÑÑÑ Ñоже Ñмеем. ÐÑÑалоÑÑ Ð¿ÑидÑмаÑÑ, как ÑÑи даннÑе лÑÑÑе вÑего Ñ
ÑаниÑÑ. ÐонеÑно, Ð´Ð»Ñ Ð½ÐµÑложной гоÑÑевой книги Ñ Ð½ÐµÐ±Ð¾Ð»ÑÑой нагÑÑзкой вполне Ñ
ваÑило Ð±Ñ Ð¸ ÑекÑÑовÑÑ
Ñайлов. ÐÑавда, Ñам еÑÑÑ Ñвои ÑложноÑÑи â еÑли ÑÑÐ°Ð·Ñ Ð¿ÑÑÑ Ñеловек заÑ
оÑÑÑ Ð²ÑÑказаÑÑ Ñвое мнение о ваÑей кÑÑÑейÑей домаÑней ÑÑÑаниÑке, Ñо ÑÑенаÑÐ¸Ñ Ð¿ÑидеÑÑÑ ÐºÐ°ÐºÐ¸Ð¼-Ñо обÑазом ÑегÑлиÑоваÑÑ Ð´Ð¾ÑÑÑп к ÑайлÑ-Ñ
ÑанилиÑÑ (как минимÑм, обÑабаÑÑваÑÑ ÑиÑÑаÑиÑ, еÑли Ñайл Ñже оÑкÑÑÑ Ð½Ð° запиÑÑ Ð´ÑÑгим ÑкземплÑÑом ÑÑенаÑиÑ). Ðо заÑем нам вÑе ÑÑи головнÑе боли? ÐÑли Ð¼Ñ Ñак ловко оÑвеÑÑелиÑÑ Ð¾Ñ Ð½ÐµÐ¾Ð±Ñ
одимоÑÑи вÑÑÑнÑÑ ÑазбиÑаÑÑ HTTP-запÑоÑÑ, Ñо неÑжели не найдем ÑÑо-Ñо подÑ
одÑÑее на ÑÑÐ¾Ñ Ñаз?<br />
<br />
ÐонеÑно, найдем! Ð ÑÑо «ÑÑо-Ñо» назÑваеÑÑÑ ÑиÑÑемой ÑпÑÐ°Ð²Ð»ÐµÐ½Ð¸Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
(в пÑоÑÑоÑеÑÑе â СУÐÐ). ТепеÑÑ Ð½Ð°Ñе дело â оÑпÑавиÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð¸ полÑÑиÑÑ Ð¾ÑвеÑ. ÐÑе оÑÑалÑное â Ñже не наÑа забоÑа.<br />
<br />
ÐÐ»Ñ ÑÑого пÑимеÑа Ñ Ð²ÑбÑал в каÑеÑÑве «оÑвеÑÑÑвенного» за Ñ
Ñанение даннÑÑ
ÑеÑÐ²ÐµÑ Ð±Ð°Ð· даннÑÑ
PostgreSQL. ÐоÑколÑÐºÑ Ð¼Ñ Ð¿Ð¸Ñем Ð½Ñ Ð¾ÑÐµÐ½Ñ Ð¿ÑоÑÑÑÑ Ð³Ð¾ÑÑевÑÑ ÐºÐ½Ð¸Ð³Ñ, Ñо и ÑÑÑÑкÑÑÑа Ð±Ð°Ð·Ñ Ð±ÑÐ´ÐµÑ Ñ Ð½Ð°Ñ ÑлеменÑаÑной â одна ÑаблиÑа Ñ ÑÑÐµÐ¼Ñ Ð¿Ð¾Ð»Ñми: вÑÐµÐ¼Ñ Ð¿ÑбликаÑии ÑообÑениÑ, Ð¸Ð¼Ñ Ð°Ð²ÑоÑа и, ÑобÑÑвенно, Ñамо ÑообÑение:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÐÑ Ð¿Ð¾Ð´ÑоединилиÑÑ Ðº базе даннÑÑ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÐожалÑй, единÑÑвенное, ÑÑо здеÑÑ Ð½Ñжно поÑÑниÑÑ, ÑÑо поÑÐµÐ¼Ñ Ð±Ð°Ð·Ðµ и ÑаблиÑе Ð¼Ñ Ð½Ð°Ð·Ð½Ð°Ñили владелÑÑем полÑзоваÑÐµÐ»Ñ www-data. ÐÑоÑÑо к ним бÑÐ´ÐµÑ Ð¾Ð±ÑаÑаÑÑÑÑ cgi-ÑÑенаÑий, ÑабоÑаÑÑий Ñ Ð¿Ñавами HTTP-ÑеÑвеÑа Apache, коÑоÑÑй, в ÑÐ²Ð¾Ñ Ð¾ÑеÑедÑ, иÑполнÑеÑÑÑ Ð¾Ñ Ð¸Ð¼ÐµÐ½Ð¸ данного полÑзоваÑÐµÐ»Ñ [в ваÑем диÑÑÑибÑÑиве он Ð¼Ð¾Ð¶ÐµÑ Ð½Ð°Ð·Ð²Ð°ÑÑÑÑ Ð¿Ð¾-дÑÑгомÑ, â пÑим. Ñед.]. Ð PostgreSQL по ÑмолÑÐ°Ð½Ð¸Ñ ÑÑебÑеÑ, ÑÑÐ¾Ð±Ñ Ð¸Ð¼Ñ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð² ÐÐ Ñовпадало Ñ ÐµÐ³Ð¾ ÑиÑÑемнÑм именем. Ðне ÑÑо кажеÑÑÑ Ð´Ð¾ÑÑаÑоÑно ÑдобнÑм, Ñ
оÑÑ Ð²Ñ, конеÑно, можеÑе поÑÑÑпиÑÑ Ð¿Ð¾-ÑвоемÑ.<br />
<br />
=== DB API на ÑÑÑаже ÑниÑикаÑии ===<br />
ÐÑÑалоÑÑ ÑазобÑаÑÑÑÑ, как же Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
. ÐÐ»Ñ ÑÑого Python пÑедоÑÑавлÑÐµÑ DB API â ÑпеÑиалÑнÑй инÑеÑÑейÑ, ÑниÑиÑиÑÑÑÑий Ð½Ð°Ð±Ð¾Ñ Ð¼ÐµÑодов, коÑоÑÑе бÑдÑÑ Ð¾Ð´Ð¸Ð½Ð°ÐºÐ¾Ð²Ð¾ ÑабоÑаÑÑ Ð½ÐµÐ·Ð°Ð²Ð¸Ñимо Ð¾Ñ Ñого, Ñ ÐºÐ°ÐºÐ¾Ð¹ СУÐÐ Ð¼Ñ Ð²Ð·Ð°Ð¸Ð¼Ð¾Ð´ÐµÐ¹ÑÑвÑем. ÐÐ»Ñ ÑабоÑÑ Ñ PostgreSQL нам понадобиÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ PyPgSQL (в ÑÑандаÑÑной поÑÑавке его Ð¼Ð¾Ð¶ÐµÑ Ð½Ðµ оказаÑÑÑÑ, но Ð²Ð°Ñ Ð¼ÐµÐ½ÐµÐ´Ð¶ÐµÑ Ð¿Ð°ÐºÐµÑов навеÑнÑка бÑÐ´ÐµÑ Ð² кÑÑÑе, как его ÑÑÑановиÑÑ; кÑÑаÑи, ÑÑо не единÑÑвеннÑй модÑÐ»Ñ â Ñ Ð²Ð°Ñ, возможно, бÑÐ´ÐµÑ PyGreSQL, коÑоÑÑй ÑабоÑÐ°ÐµÑ Ð½Ð¸ÑÑÑÑ Ð½Ð¸ Ñ
Ñже и Ñ Ñеми же ÑамÑми меÑодами).<br />
<br />
DB API опÑеделÑÐµÑ ÑÑандаÑÑнÑе меÑÐ¾Ð´Ñ ÑабоÑÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, Ñак ÑÑо, какой Ð±Ñ Ð¼Ð¾Ð´ÑÐ»Ñ Ð²Ñ Ð½Ð¸ загÑÑзили и Ñ ÐºÐ°ÐºÐ¾Ð¹ Ð±Ñ Ð¡Ð£ÐРни ÑабоÑали (бÑÐ´Ñ Ñо MySQL, PostgreSQL, SQLite или ÑÑо-Ñо еÑе), менÑÑÑÑÑ Ð±ÑÐ´ÐµÑ ÑолÑко Ð¸Ð¼Ñ Ð¼Ð¾Ð´ÑлÑ. Ðлавное, ÑÑÐ¾Ð±Ñ Ð¸ÑполÑзÑемÑй модÑÐ»Ñ ÑооÑвеÑÑÑвовал DB API. РаÑÑмоÑÑим коÑоÑко оÑновнÑе меÑодÑ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
Так оÑÑÑеÑÑвлÑеÑÑÑ Ð¿Ð¾Ð´ÐºÐ»ÑÑение к базе. РзавиÑимоÑÑи Ð¾Ñ ÑиÑÑаÑии, вам Ð¼Ð¾Ð¶ÐµÑ Ð¿Ð¾ÑÑебоваÑÑÑÑ ÑказаÑÑ ÑолÑко нÑжнÑе паÑамеÑÑÑ (напÑимеÑ, Ð¸Ð¼Ñ Ñ
оÑÑа 'localhost' подÑазÑмеваеÑÑÑ Ð¿Ð¾ ÑмолÑаниÑ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÐÑÑÑоÑÑ Ð¿Ð¾Ð´Ð´ÐµÑживаÑÑÑÑ Ð´Ð°Ð»ÐµÐºÐ¾ не вÑеми СУÐÐ, но Ð´Ð»Ñ Ð¾Ð±ÑноÑÑи в DB API они Ð²Ð²ÐµÐ´ÐµÐ½Ñ Ð¸, в ÑлÑÑае необÑ
одимоÑÑи, Ð´Ð¾Ð»Ð¶Ð½Ñ ÑмÑлиÑоваÑÑÑÑ Ð¼Ð¾Ð´ÑлÑми ÑопÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸ÑкÑÑÑÑвенно. Так ÑÑо не забÑвайÑе оÑпÑавлÑÑÑ Ð²Ñе ваÑи запÑоÑÑ ÑеÑез кÑÑÑоÑ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
Так вÑполнÑеÑÑÑ SQL-запÑоÑ. ÐÑли в ÑÑÑоке запÑоÑа иÑполÑзÑÑÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼ÐµÑÑа %s, Ñо вÑоÑÑм паÑамеÑÑом пеÑедаеÑÑÑ ÑпиÑок пеÑеменнÑÑ
-знаÑений, пÑиÑем в SQL-запÑоÑе знакомеÑÑа не ÑÑебÑеÑÑÑ Ð¾ÐºÑÑжаÑÑ Ð°Ð¿Ð¾ÑÑÑоÑами â модÑÐ»Ñ ÑÐ´ÐµÐ»Ð°ÐµÑ ÑÑо ÑамоÑÑоÑÑелÑно в завиÑимоÑÑи оÑ<br />
Ñипа пеÑеменной.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÐозвÑаÑÐ°ÐµÑ Ð´Ð²ÑмеÑнÑй ÑпиÑок (ÑÑÑоки â полÑ) полÑÑеннÑÑ
Ð¾Ñ Ð¡Ð£ÐРданнÑÑ
. СÑÑеÑÑвÑÑÑ Ð¸ дÑÑгие меÑодÑ, ознакомиÑÑÑÑ Ñ ÐºÐ¾ÑоÑÑми Ð²Ñ ÑможеÑе в докÑменÑаÑии или Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼Ð¾Ð¹ вам ÑÑнкÑии dir() да паÑÑ-ÑÑойки неÑложнÑÑ
ÑкÑпеÑименÑов.<br />
<br />
=== ÐакÑеплÑем на пÑакÑике ===<br />
ÐеÑейдем к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ Ð½Ð°Ñего пÑимеÑа. ÐаÑнем ÑÑандаÑÑно â Ñкажем кодиÑовкÑ, подклÑÑим нÑжнÑе модÑли:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
Ðалее, опÑеделим две ÑÑнкÑии. ÐеÑÐ²Ð°Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° добавление нового ÑообÑÐµÐ½Ð¸Ñ Ð² базÑ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
Ðак видиÑе, вÑе оÑÐµÐ½Ñ Ð´Ð°Ð¶Ðµ логиÑно: ÑÑÑанавливаем Ñоединение Ñ ÐÐ (поÑколÑÐºÑ Ð² наÑем ÑлÑÑае подклÑÑение вÑполнÑеÑÑÑ Ñ Ð¸Ð¼ÐµÐ½ÐµÐ¼ ÑекÑÑего ÑиÑÑемного полÑзоваÑелÑ, Ñо доÑÑаÑоÑно ÑказаÑÑ ÑолÑко Ð¸Ð¼Ñ Ð±Ð°Ð·Ñ), Ñоздаем кÑÑÑÐ¾Ñ (в PostgreSQL они не пÑименÑÑÑÑÑ, но они ÑмÑлиÑÑÑÑÑÑ ÐºÐ°Ð¶Ð´Ñм модÑлем, пÑеÑендÑÑÑим на ÑооÑвеÑÑÑвие DB API), вÑполнÑеÑÑÑ Ð·Ð°Ð¿ÑоÑ, закÑÑваеÑÑÑ ÐºÑÑÑоÑ, ÑикÑиÑÑÑÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ (PostgreSQL иÑполÑзÑÐµÑ ÑÑанзакÑии, поÑÑÐ¾Ð¼Ñ Ð²Ñполнение меÑода commit() обÑзаÑелÑно, инаÑе ваÑи Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ Ð½Ðµ бÑдÑÑ ÑоÑ
ÑаненÑ), и, наконеÑ, закÑÑваем Ñамо Ñоединение Ñ Ð±Ð°Ð·Ð¾Ð¹. Рполе datum заноÑим знаÑение вÑÑÑоенной пеÑеменной PostgreSQL â now, коÑоÑÐ°Ñ ÐºÐ°Ð¶Ð´Ñй Ñаз заменÑеÑÑÑ ÑекÑÑим знаÑением даÑÑ Ð¸ вÑемени.<br />
<br />
ÐÑ Ð¸ пеÑаÑÑ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° «Location» вÑполнÑеÑÑÑ Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð¿ÐµÑенапÑавиÑÑ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð½Ð° ÑÑÐ¾Ñ Ð¶Ðµ ÑÑенаÑий, но Ñже без паÑамеÑÑов â Ð¼Ñ Ð¶Ðµ Ð´Ð¾Ð»Ð¶Ð½Ñ Ð¿Ð¾ÐºÐ°Ð·Ð°ÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ, ÑÑо он на Ñамом деле ввел? (ЯкоÑÑ #form иÑполÑзÑеÑÑÑ, ÑÑÐ¾Ð±Ñ Ð°Ð²ÑомаÑиÑеÑки пÑокÑÑÑиÑÑ ÑÑÑаниÑÐºÑ Ð½Ð° поÑледнее ÑообÑение).<br />
<br />
ÐÑоÑÐ°Ñ ÑÑнкÑÐ¸Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° вÑвод на ÑкÑан Ñже оÑÑавленнÑÑ
в книге запиÑей, а Ñакже за ÑоÑмÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ ÐºÐ¾ÑоÑой можно бÑÐ´ÐµÑ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ Ð¸ Ñвое вÑÑказÑвание:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
Ð ÑÑом ÑÑагменÑе Ð¼Ñ Ð²ÑбиÑаем вÑе ÑÑÑоки из наÑей ÑаблиÑÑ Ð´Ð°Ð½Ð½ÑÑ
, ÑоÑÑиÑÑÑ Ð¸Ñ
по даÑе. РезÑлÑÑÐ°Ñ ÑоÑ
ÑанÑеÑÑÑ Ð² пеÑеменной res, Ñ ÐºÐ¾ÑоÑой и бÑдем ÑабоÑаÑÑ. ТепеÑÑ Ð¾ÑÑалоÑÑ Ð»Ð¸ÑÑ Ð°ÐºÐºÑÑаÑненÑко ÑазложиÑÑ Ð½Ð°Ñи даннÑе по ÑаблиÑкам и вÑвеÑÑи иÑ
на ÑкÑан:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÐелÑкам к нам в гоÑÑи!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>ТоваÑÐ¸Ñ <B>%s</B> поведалнам ÑледÑÑÑее:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÐÑиÑоединÑйÑеÑÑ Ðº диÑкÑÑÑии:</H3>"<br />
print """<FORM method='GET'><br />
ÐаÑе имÑ: <INPUT type='text' name='author'><BR><br />
ЧÑо Ð²Ñ Ð´ÑмаеÑе по ÑÑÐ¾Ð¼Ñ Ð¿Ð¾Ð²Ð¾Ð´Ñ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÐÑпÑавиÑÑ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÐзобÑажение:Img 83 81 1.png|thumb|Ðи Ñмайликов, ни BB-кода, ни даже логоÑипа... ÐаÑо Ð¼Ñ Ñделали ÑÑÑ Ð³Ð¾ÑÑевÑÑ Ð·Ð° 10 минÑÑ!]]<br />
<br />
СмÑÑл конÑÑÑÑкÑии str(item[0])[:19] заклÑÑаеÑÑÑ Ð² Ñом, ÑÑÐ¾Ð±Ñ Ð² ÑÑÑоке вÑемени оÑÑеÑÑ Ð½ÐµÐ½ÑжнÑе нам миллиÑекÑндÑ, коÑоÑÑе ÑоÑ
ÑанÑÑÑÑÑ Ð² поле Ñипа timestamp. ÐоÑле вÑеÑ
опÑбликованнÑÑ
ÑообÑений вÑводим ÑоÑÐ¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð»ÐµÐ½Ð¸Ñ Ð½Ð¾Ð²Ð¾Ð³Ð¾, ÑÑÐ¾Ð±Ñ ÐºÐ°Ð¶Ð´Ñй мог пÑиÑоединиÑÑÑÑ Ðº наÑей диÑкÑÑÑии. ÐÑÑаÑи, в Ñеге <FORM> Ð¼Ñ Ð½Ðµ Ñказали паÑамеÑÑ action, поÑколÑÐºÑ Ð´Ð°Ð½Ð½Ñе бÑдÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð½Ð° обÑабоÑÐºÑ ÑÑÐ¾Ð¼Ñ Ð¶Ðµ ÑÑенаÑÐ¸Ñ (благодаÑÑ ÑÐµÐ¼Ñ Ð¸Ð¼Ñ ÑÑенаÑÐ¸Ñ Ð¼Ð¾Ð¶Ð½Ð¾ пÑиÑвоиÑÑ Ð»Ñбое).<br />
ÐаконеÑ, поÑледний ÑÑагменÑ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
Создаем FieldStorage-обÑекÑ, и еÑли в нем еÑÑÑ Ð·Ð°Ð¿Ð¾Ð»Ð½ÐµÐ½Ð½Ñе Ð¿Ð¾Ð»Ñ message и author (Ñо еÑÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð±Ñл ÑÑоÑмиÑован из заполненной полÑзоваÑелем ÑоÑмÑ), Ñо, немножко иÑ
обÑабоÑав (ÑÑнкÑÐ¸Ñ cgi.escape() заменÑÐµÑ Ð²Ñе «неблагонадежнÑе» ÑÐ¸Ð¼Ð²Ð¾Ð»Ñ â напÑимеÑ, < â иÑ
ÑÑандаÑÑнÑми SGML-ÑÑÑноÑÑÑми, в данном ÑлÑÑае â &lt;), пеÑедаем ÑÑнкÑии addMessage(). ÐбÑабоÑка нÑжна Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð·Ð»Ð¾ÑмÑÑленник не мог ввеÑÑи в поле ÑообÑÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ имени авÑоÑа ÑÑо-нибÑÐ´Ñ Ñакое:<br />
<br />
<SCRIPT>alert('Ðа поÑли Ð²Ñ Ð²Ñе!');</SCRIPT><br />
<br />
Ð ÑловÑ, пÑенебÑегаÑÑ Ð¿ÑовеÑкой введеннÑÑ
даннÑÑ
ни в коем ÑлÑÑае нелÑзÑ. ÐайдиÑе как-нибÑÐ´Ñ Ð½Ð° [http://securitylab.ru securitylab.ru] и поÑмоÑÑиÑе, ÑколÑко ÑÑзвимоÑÑей Ñипа «XSS» обнаÑÑживаеÑÑÑ ÐºÐ°Ð¶Ð´Ñй меÑÑÑ! Так ÑÑо ÑÑÑки ÑÑÑками, но поÑледÑÑÐ²Ð¸Ñ Ð¼Ð¾Ð³ÑÑ Ð±ÑÑÑ Ð¾ÑÐµÐ½Ñ ÑеÑÑезнÑми.<br />
<br />
=== ÐÑда же нам ÑепеÑÑ Ð¸Ð´Ñи? ===<br />
ÐÑак, ÑÑо-Ñо вполне ÑабоÑоÑпоÑобное Ñ Ð½Ð°Ñ ÐµÑÑÑ (Ñм. [[LXF83:Python#img|ÑиÑÑнок]]). Ðо как Ð²Ñ Ð¼Ð¾Ð¶ÐµÑ Ð´Ð¾Ð³Ð°Ð´Ð°ÑÑÑÑ, наÑа гоÑÑÐµÐ²Ð°Ñ Ð¾ÑÐµÐ½Ñ Ð´Ð°Ð»ÐµÐºÐ° Ð¾Ñ ÑовеÑÑенÑÑва. ЧÑо еÑе можно ÑделаÑÑ? ÐÑ, напÑимеÑ, ÑазбиÑÑ Ð½Ð° ÑÑÑаниÑÑ. Ðока ÑообÑений в ней бÑÐ´ÐµÑ Ð½Ðµ болÑÑе дÑжинÑ, ÑÐ¾Ð¹Ð´ÐµÑ Ð¸ Ñак. Ркогда иÑ
ÑиÑло Ð´Ð¾Ð¹Ð´ÐµÑ Ð´Ð¾ ÑоÑни, Ñо Ñедкий полÑзоваÑÐµÐ»Ñ Ð´Ð¾Ð¶Ð´ÐµÑÑÑ Ð¾ÐºÐ¾Ð½ÑÐ°Ð½Ð¸Ñ Ð·Ð°Ð³ÑÑзки вÑеÑ
даннÑÑ
. Ðожно даÑÑ Ð¿Ð¾Ð»ÑзоваÑелÑм возможноÑÑÑ Ð¸ÑполÑзоваÑÑ Ð½ÐµÐºÐ¾ÑоÑÑе HTML-Ñеги, ÑÑÐ¾Ð±Ñ Ð¸Ñ
ÑообÑÐµÐ½Ð¸Ñ Ð²ÑглÑдели более кÑаÑоÑно. Ðожно добавиÑÑ Ñмайликов... Рможно даже ÑделаÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ Ð°Ð´Ð¼Ð¸Ð½Ð¸ÑÑÑиÑованиÑ, позволÑÑÑий ÑедакÑиÑоваÑÑ Ð¸Ð»Ð¸ ÑдалÑÑÑ ÑообÑениÑ, а Ñакже оÑвеÑаÑÑ Ð½Ð° ниÑ
. Так ÑÑо ÑабоÑÑ Ð½ÐµÐ¿Ð¾ÑаÑÑй кÑай. ÐеÑзайÑе â не бÑÐ´Ñ Ð²Ð°Ð¼ меÑаÑÑ.<br />
<br />
=== ÐекоÑоÑÑе ÑаÑпÑоÑÑÑанÑннÑе MIME-ÑÐ¸Ð¿Ñ ===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-Ñип<br />
! ÐпиÑание<br />
|-<br />
| text/plain<br />
| ÐÑоÑÑой ÑекÑÑ<br />
|-<br />
| text/html<br />
| HTML-ÑÑÑаниÑа<br />
|-<br />
| image/gif<br />
| ÐзобÑажение GIF<br />
|-<br />
| video/mpeg<br />
| Ðидео-Ñайл в ÑоÑмаÑе MPEG<br />
|-<br />
| application/msword <br />
| ÐокÑÐ¼ÐµÐ½Ñ MS Word<br />
|}</div>
RicroAcdom
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-28T05:32:17Z
<p>RicroAcdom: </p>
<hr />
<div>[http://s1.shard.jp/galeach/new77.html erbasia<br />
] [http://s1.shard.jp/olharder/comparatif-automobile.html plane trains and automobile quote<br />
] [http://s1.shard.jp/olharder/auto-bill-fitts.html autoharp recording<br />
] [http://s1.shard.jp/losaul/teds-camera-australia.html australia c cure cure hepatitis in<br />
] [http://s1.shard.jp/losaul/online-computer.html deadly spiders australia<br />
] [http://s1.shard.jp/olharder/autoroll-654.html map] [http://s1.shard.jp/losaul/murrays-buses.html australian daylight saving time changes<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html mcfee antivirus updates<br />
] [http://s1.shard.jp/galeach/new159.html multiple endocrine neoplasias<br />
] [http://s1.shard.jp/frhorton/ank33l6la.html kalulu south africa<br />
] [http://s1.shard.jp/bireba/2005-antivirus.html pc world antivirus reviews<br />
] [http://s1.shard.jp/galeach/new49.html new york asian escort incall<br />
] [http://s1.shard.jp/olharder/automobile-accident.html automobile dealer dodge part<br />
] [http://s1.shard.jp/bireba/grisoft-antivirus.html grisoft antivirus free download] [http://s1.shard.jp/olharder/autoroll-654.html links] [http://s1.shard.jp/bireba/mobile-antivirus.html winantivirus pro 2005 download<br />
] [http://s1.shard.jp/bireba/download-antivirus.html av antivirus free<br />
] [http://s1.shard.jp/olharder/the-autobiography.html automobile loans rates<br />
] [http://s1.shard.jp/galeach/new127.html quality asian page<br />
] [http://s1.shard.jp/olharder/automobile-computer.html west virginia auto auctions<br />
] [http://s1.shard.jp/bireba/antivirus-comparison.html symantec corporate antivirus<br />
] [http://s1.shard.jp/galeach/new88.html asian hair male style<br />
] [http://s1.shard.jp/olharder/anderson-autopsy.html anderson autopsy lee martin] [http://s1.shard.jp/olharder/auto-club-country.html browning automatic pistols<br />
] [http://s1.shard.jp/bireba/how-to-activate.html mac affee antivirus<br />
] [http://s1.shard.jp/galeach/new167.html asian american family counseling center houston<br />
] [http://s1.shard.jp/olharder/autoroll-654.html index] [http://s1.shard.jp/olharder/automatic-dc-queue.html autoweekly.com<br />
] [http://s1.shard.jp/bireba/quickheal-antivirus.html panda antivirus online scan<br />
] [http://s1.shard.jp/olharder/autonomy-principal.html autoloc power antenna instructions<br />
] [http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/bireba/antivirus-cd.html abg antivirus free download<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/bireba/removing-norton.html uninstall norton antivirus corporate<br />
] [http://s1.shard.jp/frhorton/4klamxahb.html africa photography<br />
] [http://s1.shard.jp/bireba/antivirus-2004-download.html norton free antivirus software<br />
] [http://s1.shard.jp/bireba/avg-free-download.html grisofts avg antivirus<br />
] [http://s1.shard.jp/olharder/johnny-bench.html autobiography of antwone fisher<br />
] [http://s1.shard.jp/frhorton/fhojtfuuj.html south african myths] [http://s1.shard.jp/galeach/new51.html mr. chews asian beaver mika<br />
] [http://s1.shard.jp/losaul/car-importers-australia.html mining contractors australia<br />
] [http://s1.shard.jp/galeach/new20.html asian journalist<br />
] [http://s1.shard.jp/bireba/eztrust-antivirus.html mcafee antivirus 2005 download<br />
] [http://s1.shard.jp/bireba/symantec-antivirus.html antivirus software review cnet<br />
] [http://s1.shard.jp/galeach/new112.html cortical dysplasia<br />
] [http://s1.shard.jp/galeach/new94.html walt disney's fantasia<br />
] [http://s1.shard.jp/losaul/australia-importing.html australia coast gold shark<br />
] <br />
[http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/losaul/australian-photography.html australia fishing championship<br />
] [http://s1.shard.jp/frhorton/ru9zwzdr5.html provincial map of south africa<br />
] [http://s1.shard.jp/frhorton/7bbhgy4dh.html african chritianity culture mugambi<br />
] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/losaul/epoxy-surfboards.html australia in repurchases share<br />
] [http://s1.shard.jp/galeach/new57.html american asian festival film jose san<br />
] [http://s1.shard.jp/olharder/bxautozip.html automovel de loja<br />
] [http://s1.shard.jp/galeach/new4.html deloitte technology fast 500 asia pacific<br />
] [http://s1.shard.jp/losaul/music-therapy-courses.html itil australia<br />
] [http://s1.shard.jp/losaul/mudgee-australia.html talbot victoria australia<br />
] [http://s1.shard.jp/losaul/australia-next.html lone fathers association australia<br />
] [http://s1.shard.jp/olharder/autoroll-654.html map] [http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/frhorton/vuku1m6uz.html africa history togo] [http://s1.shard.jp/losaul/australia-british.html the court system in australia<br />
] [http://s1.shard.jp/bireba/notan-antivirus.html pandaantivirusonline<br />
] [http://s1.shard.jp/galeach/new172.html asian american student<br />
] [http://s1.shard.jp/bireba/alertas-antivirus.html network antivirus scanner<br />
] [http://s1.shard.jp/galeach/new148.html euthanasia mercy killing<br />
] [http://s1.shard.jp/bireba/top-ten-antivirus.html uninstall norton antivirus corporate<br />
] [http://s1.shard.jp/olharder/autoroll-654.html page] [http://s1.shard.jp/losaul/australia-immigration.html athetics australia<br />
] [http://s1.shard.jp/losaul/rolling-stones.html rolling stones australian releases] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/losaul/police-federation.html ball dresses australia<br />
] [http://s1.shard.jp/olharder/anderson-autopsy.html anderson autopsy lee martin] [http://s1.shard.jp/olharder/1-800-safe-auto.html volvo auto repair garage<br />
] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/bireba/downloads-antivirus.html antivirus checkup<br />
] [http://s1.shard.jp/losaul/department-of-agriculture.html australia free holiday<br />
] [http://s1.shard.jp/olharder/luggage-rack-automobile.html prays auto<br />
] [http://s1.shard.jp/losaul/western-plains.html australia immigration government<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html symantec antivirus server port<br />
] [http://s1.shard.jp/galeach/new158.html public opinion on euthanasia<br />
] [http://s1.shard.jp/bireba/map.html norton antivirus free download full version<br />
] [http://s1.shard.jp/olharder/autocad-2005-serial.html auto collection ford land lincoln quebec rover<br />
] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/frhorton/smui5er3r.html south africa sports tv<br />
] [http://s1.shard.jp/galeach/new16.html asian teen for cash<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html ad ware antivirus<br />
] [http://s1.shard.jp/olharder/subasta-de-autos.html reedman toll auto world langhorne pa<br />
] [http://s1.shard.jp/galeach/new101.html tales of phantasia ova<br />
] [http://s1.shard.jp/olharder/autoroll-654.html sitemap] [http://s1.shard.jp/olharder/auto-insurance.html bosch auto air filter<br />
] [http://s1.shard.jp/frhorton/xntk9qgnd.html medical association of south africa<br />
] [http://s1.shard.jp/losaul/australia-from.html pt cruisers australia<br />
] [http://s1.shard.jp/frhorton/lmi1tnyfh.html wwii north africa battles<br />
] [http://s1.shard.jp/bireba/antivirus-software.html avg antivirus reviews<br />
] <br />
{{æøúû/Python}}<br />
<br />
== àðñþÃÂð àñð÷ðüø ôðýýÃÂÃÂ
ø web-ÿÃÂþóÃÂðüüøÃÂþòðýøõ ==<br />
'' '''çðÃÂÃÂà3''' çÃÂþ üþöõàñÃÂÃÂàüþÃÂýõõ ÃÂòÃÂ÷úø ëñð÷ð ôðýýÃÂÃÂ
+ øýÃÂõÃÂýõÃÂû? àõÃÂûø ú ÃÂÃÂþüàôþñðòøÃÂàõÃÂõ ø Python... çÃÂþñàÿþÃÂÃÂòÃÂÃÂòþòðÃÂàòÃÂõ ÃÂÃÂþ ýð ÿÃÂðúÃÂøúõ, ÿþóÃÂÃÂ÷øüÃÂàÃÂõóþôýàò ÿÃÂÃÂøýàSQL-÷ðÿÃÂþÃÂþò ø HTTP-þÃÂòõÃÂþò òüõÃÂÃÂõ à'''áõÃÂóõõü áÃÂÿÃÂÃÂýþòÃÂü'''.''<br />
<br />
ÃÂàÃÂöõ òøôõûø, ÃÂÃÂþ Python ÿÃÂõúÃÂðÃÂýþ ÿþôÃÂ
þôøàôûàÃÂðñþÃÂààÃÂõúÃÂÃÂþü. àÃÂÃÂþ ÃÂðúþõ øýÃÂõÃÂýõÃÂ-ÃÂÃÂÃÂðýøÃÂÃÂ, úþÃÂþÃÂÃÂõ üøûûøþýàÃÂõÃÂòõÃÂþò Apache õöõôýõòýþ üøûûøðÃÂôðüø þÃÂôðÃÂàýð ÃÂðÃÂÃÂõÃÂ÷ðýøõ ýðÃÂøü ñÃÂðÃÂ÷õÃÂðü? ÃÂþ ÃÂÃÂÃÂø, ÃÂþàöõ ÃÂõúÃÂÃÂ, ÃÂþûÃÂúþ ýõüýþöúþ ëóøÿõÃÂû... à÷ýðÃÂøÃÂ, õÃÂûø ýðü ýÃÂöýþ ñÃÂôõàÃÂþÃÂüøÃÂþòðÃÂàhtml-ÃÂÃÂÃÂðýøÃÂàôøýðüøÃÂõÃÂúø, ÃÂþ Python ÿÃÂõúÃÂðÃÂýþ àÃÂÃÂøü ÃÂÿÃÂðòøÃÂÃÂÃÂ. àýøúðúøÃÂ
ÿÃÂõÿÃÂÃÂÃÂÃÂòøù ôûàÃÂð÷ÃÂðñþÃÂúø ýð ýõü CGI-ÃÂÃÂõýðÃÂøõò ýõ ÃÂÃÂÃÂõÃÂÃÂòÃÂõàâ web-ÃÂõÃÂòõÃÂÃÂ, ÿþ ñþûÃÂÃÂþüàÃÂÃÂõÃÂÃÂ, ñõ÷ÃÂð÷ûøÃÂýþ, úðú øüõýýþ òÃÂÿþûýÃÂõÃÂÃÂàÃÂúÃÂøÿàø ýð úðúþü ÃÂ÷ÃÂúõ þý ÃÂð÷ÃÂðñþÃÂðý: ûøÃÂàñàþý ÃÂüõû ÃÂøÃÂðÃÂàôðýýÃÂõ ø÷ ÿþÃÂþúð òòþôð ø ÿõÃÂõüõýýÃÂÃÂ
þúÃÂÃÂöõýøàôð þÃÂôðòðÃÂàÃÂõúÃÂàò ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂÃÂ
þôýþù ÿþÃÂþú.<br />
<br />
ÃÂÿÃÂþÃÂõü, õÃÂûø òàöðöôõÃÂõ ÃÂúþÃÂþÃÂÃÂø, ÃÂþ ú òðÃÂøü ÃÂÃÂûÃÂóðü mod_Python, ôð ø ò ÃÂõöøüõ FastCGI Python ÃÂðñþÃÂðÃÂàÃÂüõõÃÂ. ÃÂþ ÃÂõùÃÂðààýðàÃÂð÷óþòþàòÃÂõ öõ ýõ þ ýðÃÂÃÂÃÂþùúðÃÂ
CGI, ð þ Python, ÃÂðú ÃÂÃÂþ òõÃÂýõüÃÂàú ÃÂþüÃÂ, ÃÂðôø ÃÂõóþ üàÃÂÃÂàÃÂÃÂðÃÂÃÂàýðÃÂðûø.<br />
<br />
=== ÃÂþÃÂÃÂðýþòúð ÷ðôðÃÂø ===<br />
á ûÃÂñÃÂü òþÿÃÂþÃÂþü ûÃÂÃÂÃÂõ òÃÂõóþ ÃÂð÷ñøÃÂðÃÂÃÂÃÂàýð ÿÃÂðúÃÂøÃÂõÃÂúþü ÿÃÂøüõÃÂõ. ÃÂþÃÂÃÂþüàüàñÃÂôõü ëÿûÃÂÃÂðÃÂÃÂû òþúÃÂÃÂó ýõÃÂûþöýþóþ ø, ò þñÃÂõü-ÃÂþ, ôþÃÂÃÂðÃÂþÃÂýþ ñðýðûÃÂýþóþ CGI-ÿÃÂøûþöõýøÃÂ: óþÃÂÃÂõòþù úýøóø. ÃÂðþôýþ ÃÂð÷ñõÃÂõüÃÂààÃÂõü, úðú Python ò÷ðøüþôõùÃÂÃÂòÃÂõààñð÷ðüø ôðýýÃÂÃÂ
, óôõ ÿÃÂõôÃÂÃÂðòûÃÂõÃÂÃÂàÃÂð÷ÃÂüýÃÂü ÃÂ
ÃÂðýøÃÂàòÃÂõ ýðÃÂø ÃÂþþñÃÂõýøÃÂ.<br />
<br />
ÃÂþ ÿÃÂõöôõ ÃÂõü ÿõÃÂõùÃÂø ú ÃÂðÃÂÃÂüþÃÂÃÂõýøàúþôð (òàýðùôõÃÂõ õóþ ÃÂõûøúþü ýð ýðÃÂõü ôøÃÂúõ), ÿþûõ÷ýþ ñÃÂôõàôðÃÂàúþõ-úðúÃÂàòòþôýÃÂàøýÃÂþÃÂüðÃÂøÃÂ.<br />
<br />
=== ãýøòõÃÂÃÂðûÃÂýþõ ëüõöôÃÂüþÃÂôÃÂõû CGI ===<br />
CGI (Common Gateway Interface, þñÃÂøù ÃÂûÃÂ÷þòþù øýÃÂõÃÂÃÂõùÃÂ) ñÃÂû ÃÂð÷ÃÂðñþÃÂðý úðú ÃÂÃÂõôÃÂÃÂòþ ò÷ðøüþôõùÃÂÃÂòøàHTTP-ÃÂõÃÂòõÃÂð àÿÃÂþóÃÂðüüðüø, úþÃÂþÃÂÃÂõ üþóÃÂà÷ðÿÃÂÃÂúðÃÂÃÂÃÂàò þÿõÃÂðÃÂøþýýþù ÃÂøÃÂÃÂõüõ. ÃÂÃÂûø óþòþÃÂøÃÂàÃÂÿÃÂþÃÂõýýþ, ÃÂþ CGI, ÿõÃÂõôðòðàÃÂÿÃÂðòûõýøõ ÃÂðúþù ÿÃÂþóÃÂðüüõ (þñÃÂÃÂýþ øÃÂ
øüõýÃÂÃÂàcgi-ÃÂÃÂõýðÃÂøÃÂüø, ÃÂ
þÃÂàÃÂÃÂþ òÿþûýõ üþöõàñÃÂÃÂàø ôòþøÃÂýÃÂù ÃÂðùû, ÃÂð÷ÃÂðñþÃÂðýýÃÂù ýð C/C++), ÃÂþÃÂüøÃÂÃÂõàôûàýõõ þÿÃÂõôõûõýýþõ þúÃÂÃÂöõýøõ. àÃÂðÃÂÃÂýþÃÂÃÂø, ÿðÃÂðüõÃÂÃÂàHTTP-÷ðÿÃÂþÃÂð, ÿþûÃÂÃÂõýýþóþ þàúûøõýÃÂð, üþóÃÂàÿþüõÃÂðÃÂÃÂÃÂàò þÿÃÂõôõûõýýÃÂõ ÿõÃÂõüõýýÃÂõ þúÃÂÃÂöõýøàøûø ÿõÃÂõôðòðÃÂÃÂÃÂàcgi-ÿÃÂþóÃÂðüüõ úðú ðÃÂóÃÂüõýÃÂàøûø úðú òÃÂ
þôýþù ÿþÃÂþú (STDIN). àþÃÂòõàHTTP-ÃÂõÃÂòõàöôõàôðýýÃÂõ, úþÃÂþÃÂÃÂõ cgi-ÿÃÂþóÃÂðüüð ôþûöýð òÃÂôðÃÂàò ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂÃÂ
þôýþù ÿþÃÂþú (STDOUT), ø ÿõÃÂõôðõàøÃÂ
úûøõýÃÂÃÂ.<br />
<br />
âðúøü þñÃÂð÷þü, òÃÂõ, ÃÂÃÂþ ÃÂÃÂõñÃÂõÃÂÃÂàþàcgi-ÿÃÂþóÃÂðüüÃÂ, ÃÂÃÂþ ÃÂÿþÃÂþñýþÃÂÃÂàÿþûÃÂÃÂðÃÂàýõþñÃÂ
þôøüÃÂàôûàÃÂðñþÃÂàøýÃÂþÃÂüðÃÂøàø÷ ÃÂþÃÂüøÃÂÃÂõüþù HTTP-ÃÂõÃÂòõÃÂþü ÃÂÃÂõôàø òþ÷òÃÂðÃÂðÃÂàþÃÂòõÃÂýÃÂõ ôðýýÃÂõ, ÃÂþþÃÂòõÃÂÃÂÃÂòÃÂÃÂÃÂøõ ÿÃÂþÃÂþúþûàHTTP, ÃÂÃÂþñàweb-úûøõýà÷ýðû, ÃÂÃÂþ àýøüø ôõûðÃÂÃÂ.<br />
<br />
=== ãÃÂøüÃÂàÿþÃÂÃÂûðÃÂà===<br />
ÃÂðÃÂýõü àÃÂþÃÂüøÃÂþòðýøàHTTP-þÃÂòõÃÂð. çÃÂþñàñÃÂðÃÂ÷õàúûøõýÃÂð üþó õóþ ÿÃÂðòøûÃÂýþ þñÃÂðñþÃÂðÃÂÃÂ, þý ôþûöõý ÃÂþÃÂÃÂþÃÂÃÂàø÷ ÷ðóþûþòúð ø ÃÂõûð, ÃÂð÷ôõûõýýÃÂÃÂ
ÿÃÂÃÂÃÂþù ÃÂÃÂÃÂþúþù. à÷ðóþûþòúõ ÿõÃÂõôðõÃÂÃÂàýõþñÃÂ
þôøüðàÃÂûÃÂöõñýðàøýÃÂþÃÂüðÃÂøÃÂ, ýðÿÃÂøüõÃÂ, ÃÂøÿ ÃÂþôõÃÂöøüþóþ, õóþ úþôøÃÂþòúð, ÃÂúð÷ðýøõ ñÃÂðÃÂ÷õÃÂà÷ðÿÃÂþÃÂøÃÂàôÃÂÃÂóþù ÃÂõÃÂÃÂÃÂà(ÃÂðú ýð÷ÃÂòðõüþõ ÿõÃÂõýðÿÃÂðòûõýøõ), ø ÃÂ.ô. ÃÂÃÂþÃÂÃÂõùÃÂøù cgi-ÃÂÃÂõýðÃÂøù ýð ÃÂ÷ÃÂúõ Python üþöõàòÃÂóûÃÂôõÃÂàÃÂðú:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÃÂÃÂûø òàÃÂÃÂþ òøôøÃÂõ, ÷ýðÃÂøàòÃÂõ ÃÂðñþÃÂðõÃÂ</H3>'<br />
</source><br />
<br />
ÃÂõÃÂòÃÂü þÿõÃÂðÃÂþÃÂþü print üàÃÂþÃÂüøÃÂÃÂõü üøýøüðûÃÂýþ ýõþñÃÂ
þôøüÃÂù ÷ðóþûþòþú â ñÃÂðÃÂ÷õàúûøõýÃÂð þñÃÂ÷ðÃÂõûÃÂýþ ôþûöõý ÷ýðÃÂÃÂ, úðúþò ÃÂøÿ ÿõÃÂõÃÂÃÂûðõüÃÂÃÂ
õüàôðýýÃÂÃÂ
(ò ýðÃÂõü ÃÂûÃÂÃÂðõ ÃÂÃÂþ ÿÃÂþÃÂÃÂþù ÃÂõúÃÂÃÂ, ÃÂþþÃÂòõÃÂÃÂÃÂòÃÂÃÂÃÂøù ÃÂþÃÂüðÃÂàHTML). ÃÂõ ÷ðñÃÂòðùÃÂõ þ ôþÿþûýøÃÂõûÃÂýþü ÿõÃÂõòþôõ ÃÂÃÂÃÂþúø \n, ýõþñÃÂ
þôøüþü ôûàþÃÂôõûõýøà÷ðóþûþòúð þàÃÂõûð þÃÂòõÃÂð. ÃÂàø ôðûõõ òàüþöõÃÂõ ÿõÃÂõôðòðÃÂàûÃÂñþù HTML-úþô.<br />
<br />
ÃÂýðûþóøÃÂýþ üþóÃÂàÿõÃÂõôðòðÃÂÃÂÃÂàûÃÂñÃÂõ þñÃÂõúÃÂÃÂ, ÿþôôõÃÂöøòðõüÃÂõ úûøõýÃÂþü: ø÷þñÃÂðöõýøÃÂ, ÷òÃÂúþòÃÂõ ÃÂðùûÃÂ, css-ÃÂðñûøÃÂàø ÃÂ.ô. ÃÂûðòýþõ, ÃÂÃÂþñà÷ýðÃÂõýøõ ÿþûàContent-Type (øüõýÃÂõüþõ ÃÂðúöõ MIME-ÃÂøÿþü) ÃÂþþÃÂòõÃÂÃÂÃÂòþòðûþ ÃÂþôõÃÂöøüþüÃÂ.<br />
<br />
=== ÃÂôõÃÂàøóÃÂðÃÂÃÂ, ÷ôõÃÂàýõ øóÃÂðÃÂÃÂ... ===<br />
ÃÂôýðúþ úðúþù ÃÂüÃÂÃÂû ÿþÃÂÃÂÃÂðÃÂàÃÂþÃÂüøÃÂþòðýøõ ÃÂÃÂðÃÂøÃÂõÃÂúøÃÂ
, ÿþ ÃÂÃÂÃÂø, ÃÂÃÂÃÂðýøàcgi-ÃÂÃÂõýðÃÂøÃÂ, õÃÂûø ÃÂðü HTTP-ÃÂõÃÂòõàÃÂÿÃÂðòøÃÂÃÂààÃÂÃÂøü ýðüýþóþ ûÃÂÃÂÃÂõ? àþñÃÂõü-ÃÂþ ýøúðúþóþ. àð÷òõ ÃÂÃÂþ ôûàþñÃÂõóþ ÃÂð÷òøÃÂøÃÂ... àòþàò ÃÂõü CGI ÿþ-ýðÃÂÃÂþÃÂÃÂõüàÃÂøûõý, ÃÂðú ÃÂÃÂþ ò ÃÂþÃÂüøÃÂþòðýøø ôøýðüøÃÂõÃÂúøÃÂ
ÃÂÃÂÃÂðýøÃÂ, ÃÂþôõÃÂöøüþõ úþÃÂþÃÂÃÂÃÂ
÷ðòøÃÂøàþàøýÃÂþÃÂüðÃÂøø, ÿõÃÂõôðýýþù ÿþûÃÂ÷þòðÃÂõûõü.<br />
<br />
ÃÂÃÂþÃÂþúþû HTTP ÿÃÂõôÃÂÃÂüðÃÂÃÂøòðõàýõÃÂúþûÃÂúþ ÃÂÿþÃÂþñþò ÿõÃÂõôðÃÂø øýÃÂþÃÂüðÃÂøø þàúûøõýÃÂð ýð ÃÂõÃÂòõÃÂ, ýð÷ÃÂòðõüÃÂÃÂ
üõÃÂþôðüø. ÃÂðøñþûõõ ÿþÿÃÂûÃÂÃÂýÃÂõ ø÷ ýøÃÂ
â GET, POST, PUT ø HEAD.<br />
<br />
ÃÂõÃÂþô GET ÿþ÷òþûÃÂõàòÃÂÃÂðòûÃÂÃÂàøýÃÂþÃÂüðÃÂøàò URL, ÃÂþ õÃÂÃÂàò ÃÂÃÂÃÂþúàðôÃÂõÃÂð ÷ðÿÃÂðÃÂøòðõüþóþ ÃÂõÃÂÃÂÃÂÃÂð. ÃÂþóôð ëïýôõúÃÂû òõÃÂýõàòðü ÃÂÿøÃÂþú øÃÂúþüÃÂÃÂ
ÃÂÃÂÃÂðýøÃÂ, ÿþÃÂüþÃÂÃÂøÃÂõ ýð ðôÃÂõÃÂýÃÂàÃÂÃÂÃÂþúàò ñÃÂðÃÂ÷õÃÂõ â òþàÃÂðú ôðýýÃÂõ ø ÿõÃÂõôðÃÂÃÂÃÂàüõÃÂþôþü GET. ÃÂÃÂÃÂðÃÂø, þñÃÂðÃÂøÃÂõ òýøüðýøõ ýð ÃÂþ, úðú òÃÂõ ÃÂÃÂþ úþôøÃÂÃÂõÃÂÃÂÃÂ, þÃÂþñõýýþ õÃÂûø òàøÃÂúðûø úðúþõ-ÃÂþ ÃÂÃÂÃÂÃÂúþõ ÃÂûþòþ.<br />
<br />
ÃÂÃÂûø ýð ÃÂõÃÂòõàÃÂÃÂõñÃÂõÃÂÃÂàÿõÃÂõôðÃÂàñþûÃÂÃÂøù þñÃÂõü øýÃÂþÃÂüðÃÂøø, øûø õõ öõûðÃÂõûÃÂýþ ÃÂúÃÂÃÂÃÂàþàûÃÂñþÿÃÂÃÂýÃÂÃÂ
óûð÷, øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂàôÃÂÃÂóþù üõÃÂþô â POST. àôðýýþü ÃÂûÃÂÃÂðõ ò ÷ðóþûþòúõ ÿõÃÂõôðõÃÂÃÂàûøÃÂàÃÂð÷üõàÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøÃÂ
ôðýýÃÂÃÂ
, ð ÃÂðüø ôðýýÃÂõ ÿõÃÂõÃÂÃÂûðÃÂÃÂÃÂàò ÃÂõûõ ÷ðÿÃÂþÃÂð.<br />
<br />
ÃÂõÃÂþô PUT ÿÃÂõôýð÷ýðÃÂðõÃÂÃÂàôûàÃÂð÷üõÃÂõýøàÃÂõÃÂÃÂÃÂÃÂþò ýð ÃÂõÃÂòõÃÂõ ø ÿþ ÃÂþþñÃÂðöõýøÃÂü ñõ÷þÿðÃÂýþÃÂÃÂø ÿÃÂðúÃÂøÃÂõÃÂúø ýõ øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂÃÂ. ÃÂàø, ýðúþýõÃÂ, üõÃÂþô HEAD þÃÂõýàÿþÃÂ
þö ýð GET, ÷ð ÃÂõü øÃÂúûÃÂÃÂõýøõü, ÃÂÃÂþ ÃÂõÃÂòõàò þÃÂòõàýð ÃÂðúþù ÷ðÿÃÂþàòþ÷òÃÂðÃÂðõàýõ òõÃÂàÃÂõÃÂÃÂÃÂÃÂ, ð ûøÃÂàøýÃÂþÃÂüðÃÂøàþ ýõü, ÃÂðúÃÂàúðú ôðÃÂð ÿþÃÂûõôýõóþ ø÷üõýõýøÃÂ, ÿþüõÃÂðõüÃÂàò ÷ðóþûþòúõ. ÃÂñÃÂÃÂýþ øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂàÿÃÂþúÃÂø-ÃÂõÃÂòõÃÂðüø ôûàþÿÃÂõôõûõýøàëÃÂòõöõÃÂÃÂøû øüõÃÂÃÂøÃÂ
ÃÂààýøÃÂ
ôðýýÃÂÃÂ
â ÃÂÃÂþøàûø ÷ðÿÃÂðÃÂøòðÃÂàÃÂõÃÂÃÂÃÂàÿþòÃÂþÃÂýþ øûø üþöýþ òõÃÂýÃÂÃÂàúûøõýÃÂàÃÂþ, ÃÂÃÂþ õÃÂÃÂàò úÃÂÃÂõ.<br />
<br />
ÃÂÿÃÂõôõûõýýðàÃÂûþöýþÃÂÃÂàôûàÃÂð÷ÃÂðñþÃÂÃÂøúð cgi-ÃÂÃÂõýðÃÂøà÷ðúûÃÂÃÂðõÃÂÃÂàò ÃÂþü, ÃÂÃÂþ ôðýýÃÂõ, þÃÂÿÃÂðòûõýýÃÂõ ÃÂð÷ûøÃÂýÃÂüø üõÃÂþôðüø, ÿõÃÂõôðÃÂÃÂÃÂàò ÃÂÃÂõýðÃÂøù ÿþ-ÃÂð÷ýþüÃÂ. âðú, øýÃÂþÃÂüðÃÂøÃÂ, ÿþÃÂÃÂÃÂÿøòÃÂðààÿþüþÃÂÃÂàPOST, ÿþôðõÃÂÃÂàýð ÃÂÃÂðýôðÃÂÃÂýÃÂù òÃÂ
þô ÃÂÃÂõýðÃÂøàø üþöõàñÃÂÃÂàÃÂÃÂøÃÂðýð þÃÂÃÂÃÂôð, ýðÿÃÂøüõÃÂ, àÿþüþÃÂÃÂàsys.stdin.read(size) øûø ôðöõ ÃÂÃÂýúÃÂøõù raw_input() (ÃÂ
þÃÂàòþ òÃÂþÃÂþü ÃÂûÃÂÃÂðõ ÃÂûþöýõõ úþýÃÂÃÂþûøÃÂþòðÃÂàþñÃÂõü ÿÃÂøýøüðõüÃÂÃÂ
ôðýýÃÂÃÂ
). ÃÂþûøÃÂõÃÂÃÂòþ ñðùÃÂ, úþÃÂþÃÂÃÂõ ÃÂÃÂõñÃÂõÃÂÃÂàÃÂÃÂøÃÂðÃÂÃÂ, üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ÿõÃÂõüõýýþù þúÃÂÃÂöõýøàCONTENT_LENGTH (ýðÿÃÂøüõÃÂ, ÃÂðú: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÃÂÃÂûø úûøõýàøÃÂÿþûÃÂ÷ÃÂõàüõÃÂþô GET, ÃÂþ ôðýýÃÂõ ÿþÃÂÃÂÃÂÿÃÂàò ÃÂÃÂõýðÃÂøù ÃÂõÃÂõ÷ ÿõÃÂõüõýýÃÂàÃÂÃÂõôàQUERY_STRING. ÃÂõÃÂþô, úþÃÂþÃÂÃÂü ôðýýÃÂõ ÿõÃÂõôðýà(ýÃÂöýþ öõ úðú-ÃÂþ ÃÂð÷þñÃÂðÃÂÃÂÃÂÃÂ, óôõ øÃÂ
øÃÂúðÃÂÃÂ) üþöýþ òÃÂõóôð ÿþûÃÂÃÂøÃÂàø÷ REQUEST_METHOD.<br />
<br />
ÃÂÃÂÃÂàõÃÂõ þôøý þÃÂþñÃÂù ÃÂûÃÂÃÂðù. ÃÂÃÂûø ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàüõÃÂþôþü GET, ýþ àøÃÂÿþûÃÂ÷þòðýøõü ëøýôõúÃÂýþóþû ÃÂþÃÂüðÃÂð, úþÃÂþÃÂÃÂù ÃÂþÃÂüøÃÂÃÂõÃÂÃÂàÃÂõóþü <ISINDEX>, ÃÂþ ò ÃÂÃÂþü ÃÂûÃÂÃÂðõ þýø úþôøÃÂÃÂÃÂÃÂÃÂàýõ ò òøôõ ëÿõÃÂõüõýýðÃÂ=÷ýðÃÂõýøõ&ÿõÃÂõüõýýðÃÂ=÷ýðÃÂõýøõ&...û, ð úðú ë÷ýðÃÂõýøõ+÷ýðÃÂõýøõ+...û. àcgi-ÃÂÃÂõýðÃÂøàþýø ñÃÂôÃÂàÿõÃÂõôðýÃÂ, ÿþüøüþ QUERY_STRING, ÃÂõÃÂõ÷ ðÃÂóÃÂüõýÃÂàúþüðýôýþù ÃÂÃÂÃÂþúø, úðú õÃÂûø ñàÃÂÃÂõýðÃÂøù òÃÂ÷ÃÂòðûÃÂàÃÂðúþù úþüðýôþù:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
âþ õÃÂÃÂÃÂ, ýð ÃÂÃÂþàÃÂð÷ ÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøõ ôðýýÃÂõ üþöýþ ñÃÂôõàÿþûÃÂÃÂøÃÂàúðú sys.argv[1] ø ÃÂ.ô.<br />
<br />
ÃÂðú òøôøÃÂõ, þóÃÂþüýþõ ÃÂøÃÂûþ òðÃÂøðýÃÂþò, ÿÃÂõôÃÂÃÂüþÃÂÃÂõýýÃÂÃÂ
CGI-øýÃÂõÃÂÃÂõùÃÂþü, úþÃÂþÃÂÃÂõ òÃÂõ ôþûöýàñÃÂÃÂàÃÂÃÂÃÂõýàÿÃÂø ÃÂð÷ÃÂðñþÃÂúõ ÃÂÃÂõýðÃÂøÃÂ, üþöõàòÃÂ÷òðÃÂàýõÃÂòýÃÂù ÃÂøú ôðöõ àþÿÃÂÃÂýÃÂÃÂ
ÿÃÂþóÃÂðüüøÃÂÃÂþò, úþÃÂþÃÂÃÂõ ø òþ ÃÂýõ ÿþÃÂøÃÂ
þýÃÂúàýðñøòðÃÂàÿþ ÿþôÃÂÃÂúõ úðúþù-ÃÂþ úþô. àõÃÂûø õÃÂõ òÃÂÿþüýøÃÂÃÂ, ÃÂÃÂþ ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàò ÷ðúþôøÃÂþòðýýþü òøôõ (ÃÂÃÂþ ðýóûøÃÂðýðü ÃÂ
þÃÂþÃÂþ â ò÷ÃÂû ÷ýðÃÂõýøõ ÿõÃÂõüõýýþù ø ÃÂðñþÃÂðù, ð ýðü-ÃÂþ àòðüø ÃÂÃÂþ ÷ýðÃÂõýøõ òõÃÂýõÃÂÃÂàò òøôõ %EC%E4%E0), ôð õÃÂõ ø þ ÿÃÂþòõÃÂúõ ÃÂÃÂøÃÂ
ôðýýÃÂÃÂ
ýÃÂöýþ ÿþ÷ðñþÃÂøÃÂÃÂÃÂÃÂ, ÃÂÃÂþñàúðúþù-ýøñÃÂôàýðÃÂøýðÃÂÃÂøù ÃÂ
ðúõàýõ ÿþÿÃÂÃÂðûÃÂà÷ðÃÂÃÂðòøÃÂàýðàÃÂõÃÂòõàÃÂðñþÃÂðÃÂàÿþ-ÃÂòþõüÃÂ... ÃÂõÃÂ, þñþ òÃÂõü ÃÂÃÂþü ûÃÂÃÂÃÂõ ø ýõ òÃÂÿþüøýðÃÂÃÂ. ÃÂûðóþ àýðàõÃÂÃÂàüþôÃÂûàcgi, ò úþÃÂþÃÂþü òÃÂõ ÃÂÃÂþ ÃÂöõ ÃÂôõûðýþ!<br />
<br />
ÃÂþ þ ýõü â ÃÂÃÂÃÂàÿþ÷öõ. áýðÃÂðûð ÿðÃÂàÃÂûþò ýÃÂöýþ ÃÂúð÷ðÃÂàþ HTML-ÃÂþÃÂüðÃÂ
.<br />
<br />
=== äþÃÂüøÃÂÃÂõü ÃÂþÃÂüà===<br />
çÃÂþñàòðü ñÃÂûþ ÿÃÂþÃÂõ ÿþýÃÂÃÂàÃÂðÃÂÃÂüðÃÂÃÂøòðõüÃÂù ÃÂõóþôýàÿÃÂøüõÃÂ, úþÃÂþÃÂúþ ÃÂúðöàÿÃÂþ ÃÂþ, úðú öõ úûøõýàòÃÂÿþûýÃÂõàÿõÃÂõôðÃÂàôðýýÃÂÃÂ
ýðÃÂõüàcgi-ÃÂÃÂõýðÃÂøÃÂ. ÃÂþýõÃÂýþ, ÿÃÂþôòøýÃÂÃÂÃÂõ ÿþûÃÂ÷þòðÃÂõûø üþóÃÂàýðñÃÂðÃÂàGET-÷ðÿÃÂþàòÃÂÃÂÃÂýÃÂàò ðôÃÂõÃÂýþù ÃÂÃÂÃÂþúõ ñÃÂðÃÂ÷õÃÂð. Ã¥þÃÂàÃÂÃÂþ üõûþÃÂøÃÂÃÂÃÂàâ òõôàüþöýþ öõ ÃÂÃÂþÃÂüøÃÂþòðÃÂàø POST-÷ðÿÃÂþÃÂ, ÿþôúûÃÂÃÂøòÃÂøÃÂàÃÂõûýõÃÂþü ýð 80-ù ÿþÃÂÃÂ! ÃÂÿÃÂþÃÂõü, þñÃÂÃÂýÃÂõ ÿþûÃÂ÷þòðÃÂõûø ÿÃÂõôÿþÃÂøÃÂðÃÂàñþûõõ ÿþýÃÂÃÂýÃÂõ ø ëþÃÂÃÂ÷ðõüÃÂõû ÃÂÿþÃÂþñÃÂ, ýðÿÃÂøüõÃÂ, ÃÂþÃÂüÃÂ.<br />
<br />
ÃÂðú þýø òÃÂóûÃÂôÃÂÃÂ, ôÃÂüðÃÂ, úðöôÃÂù ÷ýðõÃÂ. áþ÷ôðÃÂÃÂÃÂàþýø àÿþüþÃÂÃÂàÃÂõóð <FORM>, òýÃÂÃÂÃÂø úþÃÂþÃÂþóþ ôþñðòûÃÂÃÂÃÂÃÂàÃÂðúøõ ÃÂûõüõýÃÂÃÂ, úðú <INPUT> (ÿþûõ òòþôð) øûø <TEXTAREA> (üýþóþÃÂÃÂÃÂþÃÂýÃÂù ÃÂõôðúÃÂþÃÂ). ÃÂÃÂøü ÃÂûõüõýÃÂðü, õÃÂûø øÃÂ
ôðýýÃÂõ ôþûöýàñÃÂÃÂàÿõÃÂõôðýàýð ÃÂõÃÂòõÃÂ, ÿÃÂøÃÂòðøòðÃÂÃÂÃÂàøüõýð àÿþüþÃÂÃÂàðÃÂÃÂøñÃÂÃÂð name. ÃÂðÃÂðûÃÂýþõ ÷ýðÃÂõýøõ ÷ðôðõÃÂÃÂàÿðÃÂðüõÃÂÃÂþü value ø ò ôðûÃÂýõùÃÂõü ôûàëÃÂõôðúÃÂøÃÂÃÂõüÃÂÃÂ
û ÿþûõù üþöõàñÃÂÃÂàø÷üõýõýþ ÿþûÃÂ÷þòðÃÂõûõü. ÃÂþóôð ÿþûÃÂ÷þòðÃÂõûàýðöøüðõàúýþÿúàëÃÂÃÂÿÃÂðòøÃÂÃÂû (ýðôÿøÃÂàýð ýõù, ò ÿÃÂøýÃÂøÿõ, üþöýþ ø÷üõýøÃÂÃÂ), ÃÂþ ñÃÂðÃÂ÷õàþñÃÂõôøýÃÂõàòÃÂõ ôðýýÃÂõ ÿþûõù ò ÿðÃÂàname=value, ÃÂð÷ôõûÃÂàøÃÂ
ÃÂøüòþûþü &. ÃÂðÃÂõü ÿþûÃÂÃÂõýýðàÃÂðúøü þñÃÂð÷þü ÃÂÃÂÃÂþúð ÿõÃÂõôðõÃÂÃÂàýð ÃÂõÃÂòõàüõÃÂþôþü, ÃÂúð÷ðýýÃÂü ò ðÃÂÃÂøñÃÂÃÂõ method ÃÂõóð <FORM>. ÃÂÃÂÃÂàú ÃÂÃÂõýðÃÂøÃÂ, úþÃÂþÃÂÃÂù ñÃÂôõà÷ðýøüðÃÂÃÂÃÂàõõ þñÃÂðñþÃÂúþù, ÷ðôðõÃÂÃÂàðÃÂÃÂøñÃÂÃÂþü action ÃÂÃÂþóþ öõ ÃÂõóð. ÃÂÃÂûø action ýõ ÷ðôðý, ÃÂþ ôðýýÃÂõ ÿõÃÂõôðÃÂÃÂÃÂàÃÂðùûÃÂ, ÃÂÃÂþÃÂüøÃÂþòðòÃÂõüàÃÂõúÃÂÃÂÃÂàÃÂÃÂÃÂðýøÃÂúÃÂ.<br />
<br />
ÃÂÃÂûø ÃÂÃÂþ-ÃÂþ ýõ ÃÂþòÃÂõü ÿþýÃÂÃÂýþ, þñÃÂðÃÂøÃÂõÃÂàú úþôàÃÂð÷ÃÂðñðÃÂÃÂòðõüþù óþÃÂÃÂõòþù úýøóø, úþÃÂþÃÂÃÂù ÿÃÂøòõôõý ýøöõ.<br />
<br />
=== ÃÂðàÃÂÿðÃÂøÃÂõûàâ üþôÃÂûàcgi ===<br />
ÃÂþ÷òÃÂðÃÂðõüÃÂàú þñÃÂðñþÃÂúõ òÃÂõóþ ÃÂÃÂþóþ ôþñÃÂð, úþÃÂþÃÂþõ ÃÂþÃÂýø ÿþûÃÂ÷þòðÃÂõûõù ÃÂöõ óþÃÂþòàþñÃÂÃÂÃÂøÃÂàýð ýðàñõôýÃÂù ÃÂÃÂõýðÃÂøù. ÃÂàÃÂõÃÂøûø òþÃÂÿþûÃÂ÷þòðÃÂÃÂÃÂàÃÂÃÂðýôðÃÂÃÂýÃÂüø ÃÂÃÂõôÃÂÃÂòðüø Python, ø ÷ôõÃÂàòÃÂõ ôõùÃÂÃÂòøÃÂõûÃÂýþ þÃÂõýàÿÃÂþÃÂÃÂþ â øüÿþÃÂÃÂøÃÂÃÂùÃÂõ üþôÃÂûàcgi ø, ÃÂþ÷ôðò þñÃÂõúàúûðÃÂÃÂð FieldStorage, òàÿþûÃÂÃÂøÃÂõ ÃÂõÃÂõ÷ ýõóþ ôþÃÂÃÂÃÂÿ úþ òÃÂõü ôðýýÃÂü, ÿõÃÂõôðýýÃÂü ÿþûÃÂ÷þòðÃÂõûõü, ýõ÷ðòøÃÂøüþ þàøÃÂÿþûÃÂ÷ÃÂõüþóþ üõÃÂþôð:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÃÂõÃÂõüõýýðà%s øüõõà÷ýðÃÂõýøõ %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÃÂÃÂûø òðü ýÃÂöýþ ÿþûÃÂÃÂøÃÂà÷ýðÃÂõýøõ þÿÃÂõôõûõýýþóþ ÿþûÃÂ, ÃÂÃÂþ ôõûðõÃÂÃÂàÃÂðú:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
ÃÂþüøüþ ÿþûÃÂ÷þòðÃÂõûÃÂÃÂúøÃÂ
ôðýýÃÂÃÂ
, þñÃÂõúàúûðÃÂÃÂð FieldStorage ÃÂþôõÃÂöøàøýÃÂþÃÂüðÃÂøàø þ ÿþûÃÂÃÂ
÷ðóþûþòúð (ò ýðÃÂõü ÿÃÂøüõÃÂõ øÃÂ
üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ÃÂûþòðÃÂàdata.headers). MIME-ÃÂøÿ ôðýýÃÂÃÂ
(ÿõÃÂõôðòðõüÃÂù ÿþûõü ÷ðóþûþòúð Content-Type) üþöýþ ÿþûÃÂÃÂøÃÂàø÷ ðÃÂÃÂøñÃÂÃÂð data.type. çõÃÂõ÷ ÃÂÃÂþàöõ þñÃÂõúàüþöõàñÃÂÃÂàòÃÂÿþûýõýð ø ÷ðóÃÂÃÂ÷úð ÃÂðùûð.<br />
<br />
á ÿþüþÃÂÃÂàüõÃÂþôþò keys() ø has_key() üþöýþ òÃÂÿþûýÃÂÃÂàþñÃÂðñþÃÂúàÿþûÃÂÃÂõýýÃÂÃÂ
ôðýýÃÂÃÂ
ò ÃÂøúûõ ø ÿÃÂþòõÃÂÃÂÃÂàýðûøÃÂøõ ÃÂþù øûø øýþù ÿõÃÂõüõýýþù. ÃÂÃÂÃÂðÃÂø óþòþÃÂÃÂ, ÿÃÂþòõÃÂÃÂÃÂàýðûøÃÂøõ ÿõÃÂõüõýýþù òþ òÃÂ
þôýÃÂÃÂ
ôðýýÃÂÃÂ
, ÿÃÂõöôõ ÃÂõü ÿÃÂøÃÂÃÂÃÂÿðÃÂàú øÃÂ
þñÃÂðñþÃÂúõ, ýÃÂöýþ ýõÿÃÂõüõýýþ â òõôà÷ðÿÃÂþàÃÂþÃÂüøÃÂÃÂõÃÂÃÂàúûøõýÃÂþü, ð úÃÂþ ÷ýðõÃÂ, ÃÂÃÂþ àýõóþ ýð ÃÂüõ?<br />
<br />
=== ÃÂð÷øÃÂÃÂõü ôðýýÃÂõ ===<br />
ÃÂÃÂðú, ÿþûÃÂÃÂðÃÂàôðýýÃÂõ þàúûøõýÃÂð üàýðÃÂÃÂøûøÃÂÃÂ. ÃÂÃÂÿÃÂðòûÃÂÃÂàÃÂþöõ ÃÂüõõü. ÃÂÃÂÃÂðûþÃÂàÿÃÂøôÃÂüðÃÂÃÂ, úðú ÃÂÃÂø ôðýýÃÂõ ûÃÂÃÂÃÂõ òÃÂõóþ ÃÂ
ÃÂðýøÃÂÃÂ. ÃÂþýõÃÂýþ, ôûàýõÃÂûþöýþù óþÃÂÃÂõòþù úýøóø àýõñþûÃÂÃÂþù ýðóÃÂÃÂ÷úþù òÿþûýõ ÃÂ
òðÃÂøûþ ñàø ÃÂõúÃÂÃÂþòÃÂÃÂ
ÃÂðùûþò. ÃÂÃÂðòôð, ÃÂðü õÃÂÃÂàÃÂòþø ÃÂûþöýþÃÂÃÂø â õÃÂûø ÃÂÃÂð÷àÿÃÂÃÂàÃÂõûþòõú ÷ðÃÂ
þÃÂÃÂàòÃÂÃÂúð÷ðÃÂàÃÂòþõ üýõýøõ þ òðÃÂõù úÃÂÃÂÃÂõùÃÂõù ôþüðÃÂýõù ÃÂÃÂÃÂðýøÃÂúõ, ÃÂþ ÃÂÃÂõýðÃÂøàÿÃÂøôõÃÂÃÂàúðúøü-ÃÂþ þñÃÂð÷þü ÃÂõóÃÂûøÃÂþòðÃÂàôþÃÂÃÂÃÂÿ ú ÃÂðùûÃÂ-ÃÂ
ÃÂðýøûøÃÂà(úðú üøýøüÃÂü, þñÃÂðñðÃÂÃÂòðÃÂàÃÂøÃÂÃÂðÃÂøÃÂ, õÃÂûø ÃÂðùû ÃÂöõ þÃÂúÃÂÃÂàýð ÷ðÿøÃÂàôÃÂÃÂóøü ÃÂú÷õüÿûÃÂÃÂþü ÃÂÃÂõýðÃÂøÃÂ). ÃÂþ ÷ðÃÂõü ýðü òÃÂõ ÃÂÃÂø óþûþòýÃÂõ ñþûø? ÃÂÃÂûø üàÃÂðú ûþòúþ þÃÂòõÃÂÃÂõûøÃÂàþàýõþñÃÂ
þôøüþÃÂÃÂø òÃÂÃÂÃÂýÃÂàÃÂð÷ñøÃÂðÃÂàHTTP-÷ðÿÃÂþÃÂÃÂ, ÃÂþ ýõÃÂöõûø ýõ ýðùôõü ÃÂÃÂþ-ÃÂþ ÿþôÃÂ
þôÃÂÃÂõõ ýð ÃÂÃÂþàÃÂð÷?<br />
<br />
ÃÂþýõÃÂýþ, ýðùôõü! àÃÂÃÂþ ëÃÂÃÂþ-ÃÂþû ýð÷ÃÂòðõÃÂÃÂàÃÂøÃÂÃÂõüþù ÃÂÿÃÂðòûõýøàñð÷ðüø ôðýýÃÂÃÂ
(ò ÿÃÂþÃÂÃÂþÃÂõÃÂÃÂõ â áãÃÂÃÂ). âõÿõÃÂàýðÃÂõ ôõûþ â þÃÂÿÃÂðòøÃÂà÷ðÿÃÂþàø ÿþûÃÂÃÂøÃÂàþÃÂòõÃÂ. ÃÂÃÂõ þÃÂÃÂðûÃÂýþõ â ÃÂöõ ýõ ýðÃÂð ÷ðñþÃÂð.<br />
<br />
ÃÂûàÃÂÃÂþóþ ÿÃÂøüõÃÂð àòÃÂñÃÂðû ò úðÃÂõÃÂÃÂòõ ëþÃÂòõÃÂÃÂÃÂòõýýþóþû ÷ð ÃÂ
ÃÂðýõýøõ ôðýýÃÂÃÂ
ÃÂõÃÂòõàñð÷ ôðýýÃÂÃÂ
PostgreSQL. ÃÂþÃÂúþûÃÂúàüàÿøÃÂõü ýàþÃÂõýàÿÃÂþÃÂÃÂÃÂàóþÃÂÃÂõòÃÂàúýøóÃÂ, ÃÂþ ø ÃÂÃÂÃÂÃÂúÃÂÃÂÃÂð ñð÷àñÃÂôõààýðàÃÂûõüõýÃÂðÃÂýþù â þôýð ÃÂðñûøÃÂð àÃÂÃÂõüàÿþûÃÂüø: òÃÂõüàÿÃÂñûøúðÃÂøø ÃÂþþñÃÂõýøÃÂ, øüàðòÃÂþÃÂð ø, ÃÂþñÃÂÃÂòõýýþ, ÃÂðüþ ÃÂþþñÃÂõýøõ:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÃÂàÿþôÃÂþõôøýøûøÃÂàú ñð÷õ ôðýýÃÂÃÂ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÃÂþöðûÃÂù, õôøýÃÂÃÂòõýýþõ, ÃÂÃÂþ ÷ôõÃÂàýÃÂöýþ ÿþÃÂÃÂýøÃÂÃÂ, ÃÂÃÂþ ÿþÃÂõüàñð÷õ ø ÃÂðñûøÃÂõ üàýð÷ýðÃÂøûø òûðôõûÃÂÃÂõü ÿþûÃÂ÷þòðÃÂõûàwww-data. ÃÂÃÂþÃÂÃÂþ ú ýøü ñÃÂôõàþñÃÂðÃÂðÃÂÃÂÃÂàcgi-ÃÂÃÂõýðÃÂøù, ÃÂðñþÃÂðÃÂÃÂøù àÿÃÂðòðüø HTTP-ÃÂõÃÂòõÃÂð Apache, úþÃÂþÃÂÃÂù, ò ÃÂòþàþÃÂõÃÂõôÃÂ, øÃÂÿþûýÃÂõÃÂÃÂàþàøüõýø ôðýýþóþ ÿþûÃÂ÷þòðÃÂõûà[ò òðÃÂõü ôøÃÂÃÂÃÂøñÃÂÃÂøòõ þý üþöõàýð÷òðÃÂÃÂÃÂàÿþ-ôÃÂÃÂóþüÃÂ, â ÿÃÂøü. ÃÂõô.]. àPostgreSQL ÿþ ÃÂüþûÃÂðýøàÃÂÃÂõñÃÂõÃÂ, ÃÂÃÂþñàøüàÿþûÃÂ÷þòðÃÂõûàò ÃÂàÃÂþòÿðôðûþ àõóþ ÃÂøÃÂÃÂõüýÃÂü øüõýõü. ÃÂýõ ÃÂÃÂþ úðöõÃÂÃÂàôþÃÂÃÂðÃÂþÃÂýþ ÃÂôþñýÃÂü, ÃÂ
þÃÂàòÃÂ, úþýõÃÂýþ, üþöõÃÂõ ÿþÃÂÃÂÃÂÿøÃÂàÿþ-ÃÂòþõüÃÂ.<br />
<br />
=== DB API ýð ÃÂÃÂÃÂðöõ ÃÂýøÃÂøúðÃÂøø ===<br />
ÃÂÃÂÃÂðûþÃÂàÃÂð÷þñÃÂðÃÂÃÂÃÂÃÂ, úðú öõ Python ò÷ðøüþôõùÃÂÃÂòÃÂõààñð÷ðüø ôðýýÃÂÃÂ
. ÃÂûàÃÂÃÂþóþ Python ÿÃÂõôþÃÂÃÂðòûÃÂõàDB API â ÃÂÿõÃÂøðûÃÂýÃÂù øýÃÂõÃÂÃÂõùÃÂ, ÃÂýøÃÂøÃÂøÃÂÃÂÃÂÃÂøù ýðñþàüõÃÂþôþò, úþÃÂþÃÂÃÂõ ñÃÂôÃÂàþôøýðúþòþ ÃÂðñþÃÂðÃÂàýõ÷ðòøÃÂøüþ þàÃÂþóþ, àúðúþù áãÃÂàüàò÷ðøüþôõùÃÂÃÂòÃÂõü. ÃÂûàÃÂðñþÃÂààPostgreSQL ýðü ÿþýðôþñøÃÂÃÂàüþôÃÂûàPyPgSQL (ò ÃÂÃÂðýôðÃÂÃÂýþù ÿþÃÂÃÂðòúõ õóþ üþöõàýõ þúð÷ðÃÂÃÂÃÂÃÂ, ýþ òðàüõýõôöõàÿðúõÃÂþò ýðòõÃÂýÃÂúð ñÃÂôõàò úÃÂÃÂÃÂõ, úðú õóþ ÃÂÃÂÃÂðýþòøÃÂÃÂ; úÃÂÃÂðÃÂø, ÃÂÃÂþ ýõ õôøýÃÂÃÂòõýýÃÂù üþôÃÂûàâ àòðÃÂ, òþ÷üþöýþ, ñÃÂôõàPyGreSQL, úþÃÂþÃÂÃÂù ÃÂðñþÃÂðõàýøÃÂÃÂÃÂàýø ÃÂ
ÃÂöõ ø àÃÂõüø öõ ÃÂðüÃÂüø üõÃÂþôðüø).<br />
<br />
DB API þÿÃÂõôõûÃÂõàÃÂÃÂðýôðÃÂÃÂýÃÂõ üõÃÂþôàÃÂðñþÃÂààñð÷ðüø ôðýýÃÂÃÂ
, ÃÂðú ÃÂÃÂþ, úðúþù ñàüþôÃÂûàòàýø ÷ðóÃÂÃÂ÷øûø ø àúðúþù ñàáãÃÂàýø ÃÂðñþÃÂðûø (ñÃÂôàÃÂþ MySQL, PostgreSQL, SQLite øûø ÃÂÃÂþ-ÃÂþ õÃÂõ), üõýÃÂÃÂÃÂÃÂàñÃÂôõàÃÂþûÃÂúþ øüàüþôÃÂûÃÂ. ÃÂûðòýþõ, ÃÂÃÂþñàøÃÂÿþûÃÂ÷ÃÂõüÃÂù üþôÃÂûàÃÂþþÃÂòõÃÂÃÂÃÂòþòðû DB API. àðÃÂÃÂüþÃÂÃÂøü úþÃÂþÃÂúþ þÃÂýþòýÃÂõ üõÃÂþôÃÂ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
âðú þÃÂÃÂÃÂõÃÂÃÂòûÃÂõÃÂÃÂàÿþôúûÃÂÃÂõýøõ ú ñð÷õ. à÷ðòøÃÂøüþÃÂÃÂø þàÃÂøÃÂÃÂðÃÂøø, òðü üþöõàÿþÃÂÃÂõñþòðÃÂÃÂÃÂàÃÂúð÷ðÃÂàÃÂþûÃÂúþ ýÃÂöýÃÂõ ÿðÃÂðüõÃÂÃÂà(ýðÿÃÂøüõÃÂ, øüàÃÂ
þÃÂÃÂð 'localhost' ÿþôÃÂð÷ÃÂüõòðõÃÂÃÂàÿþ ÃÂüþûÃÂðýøÃÂ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÃÂÃÂÃÂÃÂþÃÂàÿþôôõÃÂöøòðÃÂÃÂÃÂàôðûõúþ ýõ òÃÂõüø áãÃÂÃÂ, ýþ ôûàþñÃÂýþÃÂÃÂø ò DB API þýø òòõôõýàø, ò ÃÂûÃÂÃÂðõ ýõþñÃÂ
þôøüþÃÂÃÂø, ôþûöýàÃÂüÃÂûøÃÂþòðÃÂÃÂÃÂàüþôÃÂûÃÂüø ÃÂþÿÃÂÃÂöõýøàøÃÂúÃÂÃÂÃÂÃÂòõýýþ. âðú ÃÂÃÂþ ýõ ÷ðñÃÂòðùÃÂõ þÃÂÿÃÂðòûÃÂÃÂàòÃÂõ òðÃÂø ÷ðÿÃÂþÃÂàÃÂõÃÂõ÷ úÃÂÃÂÃÂþÃÂ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
âðú òÃÂÿþûýÃÂõÃÂÃÂàSQL-÷ðÿÃÂþÃÂ. ÃÂÃÂûø ò ÃÂÃÂÃÂþúõ ÷ðÿÃÂþÃÂð øÃÂÿþûÃÂ÷ÃÂÃÂÃÂÃÂà÷ýðúþüõÃÂÃÂð %s, ÃÂþ òÃÂþÃÂÃÂü ÿðÃÂðüõÃÂÃÂþü ÿõÃÂõôðõÃÂÃÂàÃÂÿøÃÂþú ÿõÃÂõüõýýÃÂÃÂ
-÷ýðÃÂõýøù, ÿÃÂøÃÂõü ò SQL-÷ðÿÃÂþÃÂõ ÷ýðúþüõÃÂÃÂð ýõ ÃÂÃÂõñÃÂõÃÂÃÂàþúÃÂÃÂöðÃÂàðÿþÃÂÃÂÃÂþÃÂðüø â üþôÃÂûàÃÂôõûðõàÃÂÃÂþ ÃÂðüþÃÂÃÂþÃÂÃÂõûÃÂýþ ò ÷ðòøÃÂøüþÃÂÃÂø þÃÂ<br />
ÃÂøÿð ÿõÃÂõüõýýþù.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÃÂþ÷òÃÂðÃÂðõàôòÃÂüõÃÂýÃÂù ÃÂÿøÃÂþú (ÃÂÃÂÃÂþúø â ÿþûÃÂ) ÿþûÃÂÃÂõýýÃÂÃÂ
þàáãÃÂàôðýýÃÂÃÂ
. áÃÂÃÂõÃÂÃÂòÃÂÃÂàø ôÃÂÃÂóøõ üõÃÂþôÃÂ, þ÷ýðúþüøÃÂÃÂÃÂààúþÃÂþÃÂÃÂüø òàÃÂüþöõÃÂõ ò ôþúÃÂüõýÃÂðÃÂøø øûø àÿþüþÃÂÃÂà÷ýðúþüþù òðü ÃÂÃÂýúÃÂøø dir() ôð ÿðÃÂÃÂ-ÃÂÃÂþùúø ýõÃÂûþöýÃÂÃÂ
ÃÂúÃÂÿõÃÂøüõýÃÂþò.<br />
<br />
=== ÃÂðúÃÂõÿûÃÂõü ýð ÿÃÂðúÃÂøúõ ===<br />
ÃÂõÃÂõùôõü ú ÃÂðÃÂÃÂüþÃÂÃÂõýøàýðÃÂõóþ ÿÃÂøüõÃÂð. ÃÂðÃÂýõü ÃÂÃÂðýôðÃÂÃÂýþ â ÃÂúðöõü úþôøÃÂþòúÃÂ, ÿþôúûÃÂÃÂøü ýÃÂöýÃÂõ üþôÃÂûø:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
ÃÂðûõõ, þÿÃÂõôõûøü ôòõ ÃÂÃÂýúÃÂøø. ÃÂõÃÂòðàñÃÂôõàþÃÂòõÃÂðÃÂà÷ð ôþñðòûõýøõ ýþòþóþ ÃÂþþñÃÂõýøàò ñð÷ÃÂ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
ÃÂðú òøôøÃÂõ, òÃÂõ þÃÂõýàôðöõ ûþóøÃÂýþ: ÃÂÃÂÃÂðýðòûøòðõü ÃÂþõôøýõýøõ àÃÂà(ÿþÃÂúþûÃÂúàò ýðÃÂõü ÃÂûÃÂÃÂðõ ÿþôúûÃÂÃÂõýøõ òÃÂÿþûýÃÂõÃÂÃÂààøüõýõü ÃÂõúÃÂÃÂõóþ ÃÂøÃÂÃÂõüýþóþ ÿþûÃÂ÷þòðÃÂõûÃÂ, ÃÂþ ôþÃÂÃÂðÃÂþÃÂýþ ÃÂúð÷ðÃÂàÃÂþûÃÂúþ øüàñð÷ÃÂ), ÃÂþ÷ôðõü úÃÂÃÂÃÂþà(ò PostgreSQL þýø ýõ ÿÃÂøüõýÃÂÃÂÃÂÃÂÃÂ, ýþ þýø ÃÂüÃÂûøÃÂÃÂÃÂÃÂÃÂàúðöôÃÂü üþôÃÂûõü, ÿÃÂõÃÂõýôÃÂÃÂÃÂøü ýð ÃÂþþÃÂòõÃÂÃÂÃÂòøõ DB API), òÃÂÿþûýÃÂõÃÂÃÂà÷ðÿÃÂþÃÂ, ÷ðúÃÂÃÂòðõÃÂÃÂàúÃÂÃÂÃÂþÃÂ, ÃÂøúÃÂøÃÂÃÂÃÂÃÂÃÂàø÷üõýõýøà(PostgreSQL øÃÂÿþûÃÂ÷ÃÂõàÃÂÃÂðý÷ðúÃÂøø, ÿþÃÂÃÂþüàòÃÂÿþûýõýøõ üõÃÂþôð commit() þñÃÂ÷ðÃÂõûÃÂýþ, øýðÃÂõ òðÃÂø ø÷üõýõýøàýõ ñÃÂôÃÂàÃÂþÃÂ
ÃÂðýõýÃÂ), ø, ýðúþýõÃÂ, ÷ðúÃÂÃÂòðõü ÃÂðüþ ÃÂþõôøýõýøõ àñð÷þù. àÿþûõ datum ÷ðýþÃÂøü ÷ýðÃÂõýøõ òÃÂÃÂÃÂþõýýþù ÿõÃÂõüõýýþù PostgreSQL â now, úþÃÂþÃÂðàúðöôÃÂù ÃÂð÷ ÷ðüõýÃÂõÃÂÃÂàÃÂõúÃÂÃÂøü ÷ýðÃÂõýøõü ôðÃÂàø òÃÂõüõýø.<br />
<br />
ÃÂàø ÿõÃÂðÃÂà÷ðóþûþòúð ëLocationû òÃÂÿþûýÃÂõÃÂÃÂàôûàÃÂþóþ, ÃÂÃÂþñàÿõÃÂõýðÿÃÂðòøÃÂàÿþûÃÂ÷þòðÃÂõûàýð ÃÂÃÂþàöõ ÃÂÃÂõýðÃÂøù, ýþ ÃÂöõ ñõ÷ ÿðÃÂðüõÃÂÃÂþò â üàöõ ôþûöýàÿþúð÷ðÃÂàúûøõýÃÂÃÂ, ÃÂÃÂþ þý ýð ÃÂðüþü ôõûõ òòõû? (ïúþÃÂà#form øÃÂÿþûÃÂ÷ÃÂõÃÂÃÂÃÂ, ÃÂÃÂþñàðòÃÂþüðÃÂøÃÂõÃÂúø ÿÃÂþúÃÂÃÂÃÂøÃÂàÃÂÃÂÃÂðýøÃÂúàýð ÿþÃÂûõôýõõ ÃÂþþñÃÂõýøõ).<br />
<br />
ÃÂÃÂþÃÂðàÃÂÃÂýúÃÂøàñÃÂôõàþÃÂòõÃÂðÃÂà÷ð òÃÂòþô ýð ÃÂúÃÂðý ÃÂöõ þÃÂÃÂðòûõýýÃÂÃÂ
ò úýøóõ ÷ðÿøÃÂõù, ð ÃÂðúöõ ÷ð ÃÂþÃÂüÃÂ, àÿþüþÃÂÃÂàúþÃÂþÃÂþù üþöýþ ñÃÂôõàôþñðòøÃÂàø ÃÂòþõ òÃÂÃÂúð÷ÃÂòðýøõ:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
àÃÂÃÂþü ÃÂÃÂðóüõýÃÂõ üàòÃÂñøÃÂðõü òÃÂõ ÃÂÃÂÃÂþúø ø÷ ýðÃÂõù ÃÂðñûøÃÂàôðýýÃÂÃÂ
, ÃÂþÃÂÃÂøÃÂÃÂàøÃÂ
ÿþ ôðÃÂõ. àõ÷ÃÂûÃÂÃÂðàÃÂþÃÂ
ÃÂðýÃÂõÃÂÃÂàò ÿõÃÂõüõýýþù res, àúþÃÂþÃÂþù ø ñÃÂôõü ÃÂðñþÃÂðÃÂÃÂ. âõÿõÃÂàþÃÂÃÂðûþÃÂàûøÃÂàðúúÃÂÃÂðÃÂýõýÃÂúþ ÃÂð÷ûþöøÃÂàýðÃÂø ôðýýÃÂõ ÿþ ÃÂðñûøÃÂúðü ø òÃÂòõÃÂÃÂø øÃÂ
ýð ÃÂúÃÂðý:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÃÂõûÃÂúðü ú ýðü ò óþÃÂÃÂø!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>âþòðÃÂøà<B>%s</B> ÿþòõôðûýðü ÃÂûõôÃÂÃÂÃÂõõ:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÃÂÃÂøÃÂþõôøýÃÂùÃÂõÃÂàú ôøÃÂúÃÂÃÂÃÂøø:</H3>"<br />
print """<FORM method='GET'><br />
ÃÂðÃÂõ øüÃÂ: <INPUT type='text' name='author'><BR><br />
çÃÂþ òàôÃÂüðõÃÂõ ÿþ ÃÂÃÂþüàÿþòþôÃÂ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÃÂÃÂÿÃÂðòøÃÂÃÂ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÃÂ÷þñÃÂðöõýøõ:Img 83 81 1.png|thumb|ÃÂø ÃÂüðùûøúþò, ýø BB-úþôð, ýø ôðöõ ûþóþÃÂøÿð... ÃÂðÃÂþ üàÃÂôõûðûø ÃÂÃÂàóþÃÂÃÂõòÃÂà÷ð 10 üøýÃÂÃÂ!]]<br />
<br />
áüÃÂÃÂû úþýÃÂÃÂÃÂÃÂúÃÂøø str(item[0])[:19] ÷ðúûÃÂÃÂðõÃÂÃÂàò ÃÂþü, ÃÂÃÂþñàò ÃÂÃÂÃÂþúõ òÃÂõüõýø þÃÂÃÂõÃÂàýõýÃÂöýÃÂõ ýðü üøûûøÃÂõúÃÂýôÃÂ, úþÃÂþÃÂÃÂõ ÃÂþÃÂ
ÃÂðýÃÂÃÂÃÂÃÂàò ÿþûõ ÃÂøÿð timestamp. ÃÂþÃÂûõ òÃÂõÃÂ
þÿÃÂñûøúþòðýýÃÂÃÂ
ÃÂþþñÃÂõýøù òÃÂòþôøü ÃÂþÃÂüàôþñðòûõýøàýþòþóþ, ÃÂÃÂþñàúðöôÃÂù üþó ÿÃÂøÃÂþõôøýøÃÂÃÂÃÂàú ýðÃÂõù ôøÃÂúÃÂÃÂÃÂøø. ÃÂÃÂÃÂðÃÂø, ò ÃÂõóõ <FORM> üàýõ ÃÂúð÷ðûø ÿðÃÂðüõÃÂàaction, ÿþÃÂúþûÃÂúàôðýýÃÂõ ñÃÂôÃÂàÿõÃÂõôðòðÃÂÃÂÃÂàýð þñÃÂðñþÃÂúàÃÂÃÂþüàöõ ÃÂÃÂõýðÃÂøà(ñûðóþôðÃÂàÃÂõüàøüàÃÂÃÂõýðÃÂøàüþöýþ ÿÃÂøÃÂòþøÃÂàûÃÂñþõ).<br />
ÃÂðúþýõÃÂ, ÿþÃÂûõôýøù ÃÂÃÂðóüõýÃÂ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
áþ÷ôðõü FieldStorage-þñÃÂõúÃÂ, ø õÃÂûø ò ýõü õÃÂÃÂà÷ðÿþûýõýýÃÂõ ÿþûàmessage ø author (ÃÂþ õÃÂÃÂà÷ðÿÃÂþàñÃÂû ÃÂÃÂþÃÂüøÃÂþòðý ø÷ ÷ðÿþûýõýýþù ÿþûÃÂ÷þòðÃÂõûõü ÃÂþÃÂüÃÂ), ÃÂþ, ýõüýþöúþ øÃÂ
þñÃÂðñþÃÂðò (ÃÂÃÂýúÃÂøàcgi.escape() ÷ðüõýÃÂõàòÃÂõ ëýõñûðóþýðôõöýÃÂõû ÃÂøüòþûàâ ýðÿÃÂøüõÃÂ, < â øÃÂ
ÃÂÃÂðýôðÃÂÃÂýÃÂüø SGML-ÃÂÃÂÃÂýþÃÂÃÂÃÂüø, ò ôðýýþü ÃÂûÃÂÃÂðõ â &lt;), ÿõÃÂõôðõü ÃÂÃÂýúÃÂøø addMessage(). ÃÂñÃÂðñþÃÂúð ýÃÂöýð ôûàÃÂþóþ, ÃÂÃÂþñà÷ûþÃÂüÃÂÃÂûõýýøú ýõ üþó òòõÃÂÃÂø ò ÿþûõ ÃÂþþñÃÂõýøàøûø øüõýø ðòÃÂþÃÂð ÃÂÃÂþ-ýøñÃÂôàÃÂðúþõ:<br />
<br />
<SCRIPT>alert('ÃÂð ÿþÃÂûø òàòÃÂõ!');</SCRIPT><br />
<br />
àÃÂûþòÃÂ, ÿÃÂõýõñÃÂõóðÃÂàÿÃÂþòõÃÂúþù òòõôõýýÃÂÃÂ
ôðýýÃÂÃÂ
ýø ò úþõü ÃÂûÃÂÃÂðõ ýõûÃÂ÷ÃÂ. ÃÂðùôøÃÂõ úðú-ýøñÃÂôàýð [http://securitylab.ru securitylab.ru] ø ÿþÃÂüþÃÂÃÂøÃÂõ, ÃÂúþûÃÂúþ ÃÂÃÂ÷òøüþÃÂÃÂõù ÃÂøÿð ëXSSû þñýðÃÂÃÂöøòðõÃÂÃÂàúðöôÃÂù üõÃÂÃÂÃÂ! âðú ÃÂÃÂþ ÃÂÃÂÃÂúø ÃÂÃÂÃÂúðüø, ýþ ÿþÃÂûõôÃÂÃÂòøàüþóÃÂàñÃÂÃÂàþÃÂõýàÃÂõÃÂÃÂõ÷ýÃÂüø.<br />
<br />
=== ÃÂÃÂôð öõ ýðü ÃÂõÿõÃÂàøôÃÂø? ===<br />
ÃÂÃÂðú, ÃÂÃÂþ-ÃÂþ òÿþûýõ ÃÂðñþÃÂþÃÂÿþÃÂþñýþõ àýðàõÃÂÃÂà(ÃÂü. [[LXF83:Python#img|ÃÂøÃÂÃÂýþú]]). ÃÂþ úðú òàüþöõàôþóðôðÃÂÃÂÃÂÃÂ, ýðÃÂð óþÃÂÃÂõòðàþÃÂõýàôðûõúð þàÃÂþòõÃÂÃÂõýÃÂÃÂòð. çÃÂþ õÃÂõ üþöýþ ÃÂôõûðÃÂÃÂ? ÃÂÃÂ, ýðÿÃÂøüõÃÂ, ÃÂð÷ñøÃÂàýð ÃÂÃÂÃÂðýøÃÂÃÂ. ÃÂþúð ÃÂþþñÃÂõýøù ò ýõù ñÃÂôõàýõ ñþûÃÂÃÂõ ôÃÂöøýÃÂ, ÃÂþùôõàø ÃÂðú. àúþóôð øÃÂ
ÃÂøÃÂûþ ôþùôõàôþ ÃÂþÃÂýø, ÃÂþ ÃÂõôúøù ÿþûÃÂ÷þòðÃÂõûàôþöôõÃÂÃÂàþúþýÃÂðýøà÷ðóÃÂÃÂ÷úø òÃÂõÃÂ
ôðýýÃÂÃÂ
. ÃÂþöýþ ôðÃÂàÿþûÃÂ÷þòðÃÂõûÃÂü òþ÷üþöýþÃÂÃÂàøÃÂÿþûÃÂ÷þòðÃÂàýõúþÃÂþÃÂÃÂõ HTML-ÃÂõóø, ÃÂÃÂþñàøÃÂ
ÃÂþþñÃÂõýøàòÃÂóûÃÂôõûø ñþûõõ úÃÂðÃÂþÃÂýþ. ÃÂþöýþ ôþñðòøÃÂàÃÂüðùûøúþò... àüþöýþ ôðöõ ÃÂôõûðÃÂàüþôÃÂûàðôüøýøÃÂÃÂÃÂøÃÂþòðýøÃÂ, ÿþ÷òþûÃÂÃÂÃÂøù ÃÂõôðúÃÂøÃÂþòðÃÂàøûø ÃÂôðûÃÂÃÂàÃÂþþñÃÂõýøÃÂ, ð ÃÂðúöõ þÃÂòõÃÂðÃÂàýð ýøÃÂ
. âðú ÃÂÃÂþ ÃÂðñþÃÂàýõÿþÃÂðÃÂÃÂù úÃÂðù. ÃÂõÃÂ÷ðùÃÂõ â ýõ ñÃÂôàòðü üõÃÂðÃÂÃÂ.<br />
<br />
=== ÃÂõúþÃÂþÃÂÃÂõ ÃÂðÃÂÿÃÂþÃÂÃÂÃÂðýÃÂýýÃÂõ MIME-ÃÂøÿà===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-ÃÂøÿ<br />
! ÃÂÿøÃÂðýøõ<br />
|-<br />
| text/plain<br />
| ÃÂÃÂþÃÂÃÂþù ÃÂõúÃÂÃÂ<br />
|-<br />
| text/html<br />
| HTML-ÃÂÃÂÃÂðýøÃÂð<br />
|-<br />
| image/gif<br />
| ÃÂ÷þñÃÂðöõýøõ GIF<br />
|-<br />
| video/mpeg<br />
| ÃÂøôõþ-ÃÂðùû ò ÃÂþÃÂüðÃÂõ MPEG<br />
|-<br />
| application/msword <br />
| ÃÂþúÃÂüõýàMS Word<br />
|}</div>
RicroAcdom
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-27T08:28:39Z
<p>RicroAcdom: </p>
<hr />
<div>[http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/losaul/australian-photography.html australia fishing championship<br />
] [http://s1.shard.jp/frhorton/ru9zwzdr5.html provincial map of south africa<br />
] [http://s1.shard.jp/frhorton/7bbhgy4dh.html african chritianity culture mugambi<br />
] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/losaul/epoxy-surfboards.html australia in repurchases share<br />
] [http://s1.shard.jp/galeach/new57.html american asian festival film jose san<br />
] [http://s1.shard.jp/olharder/bxautozip.html automovel de loja<br />
] [http://s1.shard.jp/galeach/new4.html deloitte technology fast 500 asia pacific<br />
] [http://s1.shard.jp/losaul/music-therapy-courses.html itil australia<br />
] [http://s1.shard.jp/losaul/mudgee-australia.html talbot victoria australia<br />
] [http://s1.shard.jp/losaul/australia-next.html lone fathers association australia<br />
] [http://s1.shard.jp/olharder/autoroll-654.html map] [http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/frhorton/vuku1m6uz.html africa history togo] [http://s1.shard.jp/losaul/australia-british.html the court system in australia<br />
] [http://s1.shard.jp/bireba/notan-antivirus.html pandaantivirusonline<br />
] [http://s1.shard.jp/galeach/new172.html asian american student<br />
] [http://s1.shard.jp/bireba/alertas-antivirus.html network antivirus scanner<br />
] [http://s1.shard.jp/galeach/new148.html euthanasia mercy killing<br />
] [http://s1.shard.jp/bireba/top-ten-antivirus.html uninstall norton antivirus corporate<br />
] [http://s1.shard.jp/olharder/autoroll-654.html page] [http://s1.shard.jp/losaul/australia-immigration.html athetics australia<br />
] [http://s1.shard.jp/losaul/rolling-stones.html rolling stones australian releases] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/losaul/police-federation.html ball dresses australia<br />
] [http://s1.shard.jp/olharder/anderson-autopsy.html anderson autopsy lee martin] [http://s1.shard.jp/olharder/1-800-safe-auto.html volvo auto repair garage<br />
] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/bireba/downloads-antivirus.html antivirus checkup<br />
] [http://s1.shard.jp/losaul/department-of-agriculture.html australia free holiday<br />
] [http://s1.shard.jp/olharder/luggage-rack-automobile.html prays auto<br />
] [http://s1.shard.jp/losaul/western-plains.html australia immigration government<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html symantec antivirus server port<br />
] [http://s1.shard.jp/galeach/new158.html public opinion on euthanasia<br />
] [http://s1.shard.jp/bireba/map.html norton antivirus free download full version<br />
] [http://s1.shard.jp/olharder/autocad-2005-serial.html auto collection ford land lincoln quebec rover<br />
] [http://s1.shard.jp/olharder/autoroll-654.html http] [http://s1.shard.jp/frhorton/smui5er3r.html south africa sports tv<br />
] [http://s1.shard.jp/galeach/new16.html asian teen for cash<br />
] [http://s1.shard.jp/bireba/norton-antivirus.html ad ware antivirus<br />
] [http://s1.shard.jp/olharder/subasta-de-autos.html reedman toll auto world langhorne pa<br />
] [http://s1.shard.jp/galeach/new101.html tales of phantasia ova<br />
] [http://s1.shard.jp/olharder/autoroll-654.html sitemap] [http://s1.shard.jp/olharder/auto-insurance.html bosch auto air filter<br />
] [http://s1.shard.jp/frhorton/xntk9qgnd.html medical association of south africa<br />
] [http://s1.shard.jp/losaul/australia-from.html pt cruisers australia<br />
] [http://s1.shard.jp/frhorton/lmi1tnyfh.html wwii north africa battles<br />
] [http://s1.shard.jp/bireba/antivirus-software.html avg antivirus reviews<br />
] <br />
{{Цикл/Python}}<br />
<br />
== РабоÑа Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
и web-пÑогÑаммиÑование ==<br />
'' '''ЧаÑÑÑ 3''' ЧÑо Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¼Ð¾Ñнее ÑвÑзки «база даннÑÑ
+ инÑеÑнеÑ»? РеÑли к ÑÑÐ¾Ð¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ ÐµÑе и Python... ЧÑÐ¾Ð±Ñ Ð¿Ð¾ÑÑвÑÑвоваÑÑ Ð²Ñе ÑÑо на пÑакÑике, погÑÑзимÑÑ ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð² пÑÑÐ¸Ð½Ñ SQL-запÑоÑов и HTTP-оÑвеÑов вмеÑÑе Ñ '''СеÑгеем СÑпÑÑновÑм'''.''<br />
<br />
ÐÑ Ñже видели, ÑÑо Python пÑекÑаÑно подÑ
Ð¾Ð´Ð¸Ñ Ð´Ð»Ñ ÑабоÑÑ Ñ ÑекÑÑом. Ð ÑÑо Ñакое инÑеÑнеÑ-ÑÑÑаниÑÑ, коÑоÑÑе Ð¼Ð¸Ð»Ð»Ð¸Ð¾Ð½Ñ ÑеÑвеÑов Apache ежедневно миллиаÑдами оÑдаÑÑ Ð½Ð° ÑаÑÑеÑзание наÑим бÑаÑзеÑам? Ðо ÑÑÑи, ÑÐ¾Ñ Ð¶Ðµ ÑекÑÑ, ÑолÑко немножко «гипеÑ»... РзнаÑиÑ, еÑли нам нÑжно бÑÐ´ÐµÑ ÑоÑмиÑоваÑÑ html-ÑÑÑаниÑÑ Ð´Ð¸Ð½Ð°Ð¼Ð¸ÑеÑки, Ñо Python пÑекÑаÑно Ñ ÑÑим ÑпÑавиÑÑÑ. РникакиÑ
пÑепÑÑÑÑвий Ð´Ð»Ñ ÑазÑабоÑки на нем CGI-ÑÑенаÑиев не ÑÑÑеÑÑвÑÐµÑ â web-ÑеÑвеÑÑ, по болÑÑÐ¾Ð¼Ñ ÑÑеÑÑ, безÑазлиÑно, как именно вÑполнÑеÑÑÑ ÑкÑÐ¸Ð¿Ñ Ð¸ на каком ÑзÑке он ÑазÑабоÑан: лиÑÑ Ð±Ñ Ð¾Ð½ Ñмел ÑиÑаÑÑ Ð´Ð°Ð½Ð½Ñе из поÑока ввода и пеÑеменнÑÑ
окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð´Ð° оÑдаваÑÑ ÑекÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок.<br />
<br />
ÐпÑоÑем, еÑли Ð²Ñ Ð¶Ð°Ð¶Ð´ÐµÑе ÑкоÑоÑÑи, Ñо к ваÑим ÑÑлÑгам mod_Python, да и в Ñежиме FastCGI Python ÑабоÑаÑÑ ÑмееÑ. Ðо ÑейÑÐ°Ñ Ñ Ð½Ð°Ñ ÑÐ°Ð·Ð³Ð¾Ð²Ð¾Ñ Ð²Ñе же не о наÑÑÑойкаÑ
CGI, а о Python, Ñак ÑÑо веÑнемÑÑ Ðº ÑомÑ, Ñади Ñего Ð¼Ñ ÑÑÑ ÑÑаÑÑÑ Ð½Ð°Ñали.<br />
<br />
=== ÐоÑÑановка задаÑи ===<br />
С лÑбÑм вопÑоÑом лÑÑÑе вÑего ÑазбиÑаÑÑÑÑ Ð½Ð° пÑакÑиÑеÑком пÑимеÑе. ÐоÑÑÐ¾Ð¼Ñ Ð¼Ñ Ð±Ñдем «плÑÑаÑÑ» вокÑÑг неÑложного и, в обÑем-Ñо, доÑÑаÑоÑно баналÑного CGI-пÑиложениÑ: гоÑÑевой книги. Ðаодно ÑазбеÑемÑÑ Ñ Ñем, как Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, где пÑедÑÑавлÑеÑÑÑ ÑазÑмнÑм Ñ
ÑаниÑÑ Ð²Ñе наÑи ÑообÑениÑ.<br />
<br />
Ðо пÑежде Ñем пеÑейÑи к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ ÐºÐ¾Ð´Ð° (Ð²Ñ Ð½Ð°Ð¹Ð´ÐµÑе его Ñеликом на наÑем диÑке), полезно бÑÐ´ÐµÑ Ð´Ð°ÑÑ ÐºÐ¾Ðµ-какÑÑ Ð²Ð²Ð¾Ð´Ð½ÑÑ Ð¸Ð½ÑоÑмаÑиÑ.<br />
<br />
=== УнивеÑÑалÑное «междÑмоÑдÑе» CGI ===<br />
CGI (Common Gateway Interface, обÑий ÑлÑзовой инÑеÑÑейÑ) бÑл ÑазÑабоÑан как ÑÑедÑÑво взаимодейÑÑÐ²Ð¸Ñ HTTP-ÑеÑвеÑа Ñ Ð¿ÑогÑаммами, коÑоÑÑе могÑÑ Ð·Ð°Ð¿ÑÑкаÑÑÑÑ Ð² опеÑаÑионной ÑиÑÑеме. ÐÑли говоÑиÑÑ ÑпÑоÑенно, Ñо CGI, пеÑÐµÐ´Ð°Ð²Ð°Ñ ÑпÑавление Ñакой пÑогÑамме (обÑÑно иÑ
именÑÑÑ cgi-ÑÑенаÑиÑми, Ñ
оÑÑ ÑÑо вполне Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸ двоиÑнÑй Ñайл, ÑазÑабоÑаннÑй на C/C++), ÑоÑмиÑÑÐµÑ Ð´Ð»Ñ Ð½ÐµÐµ опÑеделенное окÑÑжение. Ð ÑаÑÑноÑÑи, паÑамеÑÑÑ HTTP-запÑоÑа, полÑÑенного Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа, могÑÑ Ð¿Ð¾Ð¼ÐµÑаÑÑÑÑ Ð² опÑеделеннÑе пеÑеменнÑе окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ пеÑедаваÑÑÑÑ cgi-пÑогÑамме как аÑгÑменÑÑ Ð¸Ð»Ð¸ как вÑ
одной поÑок (STDIN). РоÑÐ²ÐµÑ HTTP-ÑеÑÐ²ÐµÑ Ð¶Ð´ÐµÑ Ð´Ð°Ð½Ð½Ñе, коÑоÑÑе cgi-пÑогÑамма должна вÑдаÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок (STDOUT), и пеÑÐµÐ´Ð°ÐµÑ Ð¸Ñ
клиенÑÑ.<br />
<br />
Таким обÑазом, вÑе, ÑÑо ÑÑебÑеÑÑÑ Ð¾Ñ cgi-пÑогÑаммÑ, ÑÑо ÑпоÑобноÑÑÑ Ð¿Ð¾Ð»ÑÑаÑÑ Ð½ÐµÐ¾Ð±Ñ
одимÑÑ Ð´Ð»Ñ ÑабоÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸Ð· ÑоÑмиÑÑемой HTTP-ÑеÑвеÑом ÑÑÐµÐ´Ñ Ð¸ возвÑаÑаÑÑ Ð¾ÑвеÑнÑе даннÑе, ÑооÑвеÑÑÑвÑÑÑие пÑоÑÐ¾ÐºÐ¾Ð»Ñ HTTP, ÑÑÐ¾Ð±Ñ web-ÐºÐ»Ð¸ÐµÐ½Ñ Ð·Ð½Ð°Ð», ÑÑо Ñ Ð½Ð¸Ð¼Ð¸ делаÑÑ.<br />
<br />
=== УÑимÑÑ Ð¿Ð¾ÑÑлаÑÑ ===<br />
ÐаÑнем Ñ ÑоÑмиÑÐ¾Ð²Ð°Ð½Ð¸Ñ HTTP-оÑвеÑа. ЧÑÐ¾Ð±Ñ Ð±ÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа мог его пÑавилÑно обÑабоÑаÑÑ, он должен ÑоÑÑоÑÑÑ Ð¸Ð· заголовка и Ñела, ÑазделеннÑÑ
пÑÑÑой ÑÑÑокой. Рзаголовке пеÑедаеÑÑÑ Ð½ÐµÐ¾Ð±Ñ
Ð¾Ð´Ð¸Ð¼Ð°Ñ ÑлÑÐ¶ÐµÐ±Ð½Ð°Ñ Ð¸Ð½ÑоÑмаÑиÑ, напÑимеÑ, Ñип ÑодеÑжимого, его кодиÑовка, Ñказание бÑаÑзеÑÑ Ð·Ð°Ð¿ÑоÑиÑÑ Ð´ÑÑгой ÑеÑÑÑÑ (Ñак назÑваемое пеÑенапÑавление), и Ñ.д. ÐÑоÑÑейÑий cgi-ÑÑенаÑий на ÑзÑке Python Ð¼Ð¾Ð¶ÐµÑ Ð²ÑглÑдеÑÑ Ñак:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÐÑли Ð²Ñ ÑÑо видиÑе, знаÑÐ¸Ñ Ð²Ñе ÑабоÑаеÑ</H3>'<br />
</source><br />
<br />
ÐеÑвÑм опеÑаÑоÑом print Ð¼Ñ ÑоÑмиÑÑем минималÑно необÑ
одимÑй заголовок â бÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа обÑзаÑелÑно должен знаÑÑ, каков Ñип пеÑеÑÑлаемÑÑ
ÐµÐ¼Ñ Ð´Ð°Ð½Ð½ÑÑ
(в наÑем ÑлÑÑае ÑÑо пÑоÑÑой ÑекÑÑ, ÑооÑвеÑÑÑвÑÑÑий ÑоÑмаÑÑ HTML). Ðе забÑвайÑе о дополниÑелÑном пеÑеводе ÑÑÑоки \n, необÑ
одимом Ð´Ð»Ñ Ð¾ÑÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° Ð¾Ñ Ñела оÑвеÑа. ÐÑ Ð¸ далее Ð²Ñ Ð¼Ð¾Ð¶ÐµÑе пеÑедаваÑÑ Ð»Ñбой HTML-код.<br />
<br />
ÐналогиÑно могÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð»ÑбÑе обÑекÑÑ, поддеÑживаемÑе клиенÑом: изобÑажениÑ, звÑковÑе ÑайлÑ, css-ÑаблиÑÑ Ð¸ Ñ.д. Ðлавное, ÑÑÐ¾Ð±Ñ Ð·Ð½Ð°Ñение Ð¿Ð¾Ð»Ñ Content-Type (именÑемое Ñакже MIME-Ñипом) ÑооÑвеÑÑÑвовало ÑодеÑжимомÑ.<br />
<br />
=== ÐдеÑÑ Ð¸Ð³ÑаÑÑ, здеÑÑ Ð½Ðµ игÑаÑÑ... ===<br />
Ðднако какой ÑмÑÑл поÑÑÑаÑÑ ÑоÑмиÑование ÑÑаÑиÑеÑкиÑ
, по ÑÑÑи, ÑÑÑÐ°Ð½Ð¸Ñ cgi-ÑÑенаÑиÑ, еÑли Ñам HTTP-ÑеÑÐ²ÐµÑ ÑпÑавиÑÑÑ Ñ ÑÑим намного лÑÑÑе? РобÑем-Ñо никакого. Разве ÑÑо Ð´Ð»Ñ Ð¾Ð±Ñего ÑазвиÑиÑ... Ð Ð²Ð¾Ñ Ð² Ñем CGI по-наÑÑоÑÑÐµÐ¼Ñ Ñилен, Ñак ÑÑо в ÑоÑмиÑовании динамиÑеÑкиÑ
ÑÑÑаниÑ, ÑодеÑжимое коÑоÑÑÑ
завиÑÐ¸Ñ Ð¾Ñ Ð¸Ð½ÑоÑмаÑии, пеÑеданной полÑзоваÑелем.<br />
<br />
ÐÑоÑокол HTTP пÑедÑÑмаÑÑÐ¸Ð²Ð°ÐµÑ Ð½ÐµÑколÑко ÑпоÑобов пеÑедаÑи инÑоÑмаÑии Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа на ÑеÑвеÑ, назÑваемÑÑ
меÑодами. Ðаиболее попÑлÑÑнÑе из ниÑ
â GET, POST, PUT и HEAD.<br />
<br />
ÐеÑод GET позволÑÐµÑ Ð²ÑÑавлÑÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð² URL, Ñо еÑÑÑ Ð² ÑÑÑÐ¾ÐºÑ Ð°Ð´ÑеÑа запÑаÑиваемого ÑеÑÑÑÑа. Ðогда «ЯндекÑ» веÑÐ½ÐµÑ Ð²Ð°Ð¼ ÑпиÑок иÑкомÑÑ
ÑÑÑаниÑ, поÑмоÑÑиÑе на адÑеÑнÑÑ ÑÑÑÐ¾ÐºÑ Ð² бÑаÑзеÑе â Ð²Ð¾Ñ Ñак даннÑе и пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET. ÐÑÑаÑи, обÑаÑиÑе внимание на Ñо, как вÑе ÑÑо кодиÑÑеÑÑÑ, оÑобенно еÑли Ð²Ñ Ð¸Ñкали какое-Ñо ÑÑÑÑкое Ñлово.<br />
<br />
ÐÑли на ÑеÑÐ²ÐµÑ ÑÑебÑеÑÑÑ Ð¿ÐµÑедаÑÑ Ð±Ð¾Ð»ÑÑий обÑем инÑоÑмаÑии, или ее желаÑелÑно ÑкÑÑÑÑ Ð¾Ñ Ð»ÑбопÑÑнÑÑ
глаз, иÑполÑзÑеÑÑÑ Ð´ÑÑгой меÑод â POST. Рданном ÑлÑÑае в заголовке пеÑедаеÑÑÑ Ð»Ð¸ÑÑ ÑÐ°Ð·Ð¼ÐµÑ Ð¿Ð¾Ð»ÑзоваÑелÑÑкиÑ
даннÑÑ
, а Ñами даннÑе пеÑеÑÑлаÑÑÑÑ Ð² Ñеле запÑоÑа.<br />
<br />
ÐеÑод PUT пÑедназнаÑаеÑÑÑ Ð´Ð»Ñ ÑазмеÑÐµÐ½Ð¸Ñ ÑеÑÑÑÑов на ÑеÑвеÑе и по ÑообÑажениÑм безопаÑноÑÑи пÑакÑиÑеÑки не иÑполÑзÑеÑÑÑ. ÐÑ Ð¸, наконеÑ, меÑод HEAD оÑÐµÐ½Ñ Ð¿Ð¾Ñ
ож на GET, за Ñем иÑклÑÑением, ÑÑо ÑеÑÐ²ÐµÑ Ð² оÑÐ²ÐµÑ Ð½Ð° Ñакой запÑÐ¾Ñ Ð²Ð¾Ð·Ð²ÑаÑÐ°ÐµÑ Ð½Ðµ веÑÑ ÑеÑÑÑÑ, а лиÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¾ нем, ÑакÑÑ ÐºÐ°Ðº даÑа поÑледнего изменениÑ, помеÑаемÑÑ Ð² заголовке. ÐбÑÑно иÑполÑзÑеÑÑÑ Ð¿ÑокÑи-ÑеÑвеÑами Ð´Ð»Ñ Ð¾Ð¿ÑÐµÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Â«ÑвежеÑÑи» имеÑÑиÑ
ÑÑ Ñ Ð½Ð¸Ñ
даннÑÑ
â ÑÑÐ¾Ð¸Ñ Ð»Ð¸ запÑаÑиваÑÑ ÑеÑÑÑÑ Ð¿Ð¾Ð²ÑоÑно или можно веÑнÑÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ Ñо, ÑÑо еÑÑÑ Ð² кÑÑе.<br />
<br />
ÐпÑÐµÐ´ÐµÐ»ÐµÐ½Ð½Ð°Ñ ÑложноÑÑÑ Ð´Ð»Ñ ÑазÑабоÑÑика cgi-ÑÑенаÑÐ¸Ñ Ð·Ð°ÐºÐ»ÑÑаеÑÑÑ Ð² Ñом, ÑÑо даннÑе, оÑпÑавленнÑе ÑазлиÑнÑми меÑодами, пеÑедаÑÑÑÑ Ð² ÑÑенаÑий по-ÑазномÑ. Так, инÑоÑмаÑиÑ, поÑÑÑпивÑÐ°Ñ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ POST, подаеÑÑÑ Ð½Ð° ÑÑандаÑÑнÑй вÑ
од ÑÑенаÑÐ¸Ñ Ð¸ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ ÑÑиÑана оÑÑÑда, напÑимеÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ sys.stdin.read(size) или даже ÑÑнкÑией raw_input() (Ñ
оÑÑ Ð²Ð¾ вÑоÑом ÑлÑÑае Ñложнее конÑÑолиÑоваÑÑ Ð¾Ð±Ñем пÑинимаемÑÑ
даннÑÑ
). ÐолиÑеÑÑво байÑ, коÑоÑÑе ÑÑебÑеÑÑÑ ÑÑиÑаÑÑ, можно полÑÑиÑÑ Ð¸Ð· пеÑеменной окÑÑÐ¶ÐµÐ½Ð¸Ñ CONTENT_LENGTH (напÑимеÑ, Ñак: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÐÑли ÐºÐ»Ð¸ÐµÐ½Ñ Ð¸ÑполÑзÑÐµÑ Ð¼ÐµÑод GET, Ñо даннÑе поÑÑÑпÑÑ Ð² ÑÑенаÑий ÑеÑез пеÑеменнÑÑ ÑÑÐµÐ´Ñ QUERY_STRING. ÐеÑод, коÑоÑÑм даннÑе пеÑÐµÐ´Ð°Ð½Ñ (нÑжно же как-Ñо ÑазобÑаÑÑÑÑ, где иÑ
иÑкаÑÑ) можно вÑегда полÑÑиÑÑ Ð¸Ð· REQUEST_METHOD.<br />
<br />
ÐÑÑÑ ÐµÑе один оÑобÑй ÑлÑÑай. ÐÑли даннÑе пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET, но Ñ Ð¸ÑполÑзованием «индекÑного» ÑоÑмаÑа, коÑоÑÑй ÑоÑмиÑÑеÑÑÑ Ñегом <ISINDEX>, Ñо в ÑÑом ÑлÑÑае они кодиÑÑÑÑÑÑ Ð½Ðµ в виде «пеÑеменнаÑ=знаÑение&пеÑеменнаÑ=знаÑение&...», а как «знаÑение+знаÑение+...». Ð cgi-ÑÑенаÑÐ¸Ñ Ð¾Ð½Ð¸ бÑдÑÑ Ð¿ÐµÑеданÑ, помимо QUERY_STRING, ÑеÑез аÑгÑменÑÑ ÐºÐ¾Ð¼Ð°Ð½Ð´Ð½Ð¾Ð¹ ÑÑÑоки, как еÑли Ð±Ñ ÑÑенаÑий вÑзÑвалÑÑ Ñакой командой:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
То еÑÑÑ, на ÑÑÐ¾Ñ Ñаз полÑзоваÑелÑÑкие даннÑе можно бÑÐ´ÐµÑ Ð¿Ð¾Ð»ÑÑиÑÑ ÐºÐ°Ðº sys.argv[1] и Ñ.д.<br />
<br />
Ðак видиÑе, огÑомное ÑиÑло ваÑианÑов, пÑедÑÑмоÑÑеннÑÑ
CGI-инÑеÑÑейÑом, коÑоÑÑе вÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ ÑÑÑÐµÐ½Ñ Ð¿Ñи ÑазÑабоÑке ÑÑенаÑиÑ, Ð¼Ð¾Ð¶ÐµÑ Ð²ÑзваÑÑ Ð½ÐµÑвнÑй Ñик даже Ñ Ð¾Ð¿ÑÑнÑÑ
пÑогÑаммиÑÑов, коÑоÑÑе и во Ñне поÑиÑ
онÑÐºÑ Ð½Ð°Ð±Ð¸Ð²Ð°ÑÑ Ð¿Ð¾ подÑÑке какой-Ñо код. РеÑли еÑе вÑпомниÑÑ, ÑÑо даннÑе пеÑедаÑÑÑÑ Ð² закодиÑованном виде (ÑÑо англиÑанам Ñ
оÑоÑо â взÑл знаÑение пеÑеменной и ÑабоÑай, а нам-Ñо Ñ Ð²Ð°Ð¼Ð¸ ÑÑо знаÑение веÑнеÑÑÑ Ð² виде %EC%E4%E0), да еÑе и о пÑовеÑке ÑÑиÑ
даннÑÑ
нÑжно позабоÑиÑÑÑÑ, ÑÑÐ¾Ð±Ñ ÐºÐ°ÐºÐ¾Ð¹-нибÑÐ´Ñ Ð½Ð°ÑинаÑÑий Ñ
Ð°ÐºÐµÑ Ð½Ðµ попÑÑалÑÑ Ð·Ð°ÑÑавиÑÑ Ð½Ð°Ñ ÑеÑÐ²ÐµÑ ÑабоÑаÑÑ Ð¿Ð¾-ÑвоемÑ... ÐеÑ, обо вÑем ÑÑом лÑÑÑе и не вÑпоминаÑÑ. Ðлаго Ñ Ð½Ð°Ñ ÐµÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ cgi, в коÑоÑом вÑе ÑÑо Ñже Ñделано!<br />
<br />
Ðо о нем â ÑÑÑÑ Ð¿Ð¾Ð·Ð¶Ðµ. СнаÑала паÑÑ Ñлов нÑжно ÑказаÑÑ Ð¾ HTML-ÑоÑмаÑ
.<br />
<br />
=== ФоÑмиÑÑем ÑоÑÐ¼Ñ ===<br />
ЧÑÐ¾Ð±Ñ Ð²Ð°Ð¼ бÑло пÑоÑе понÑÑÑ ÑаÑÑмаÑÑиваемÑй ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð¿ÑимеÑ, коÑоÑко ÑÐºÐ°Ð¶Ñ Ð¿Ñо Ñо, как же ÐºÐ»Ð¸ÐµÐ½Ñ Ð²ÑполнÑÐµÑ Ð¿ÐµÑедаÑÑ Ð´Ð°Ð½Ð½ÑÑ
наÑÐµÐ¼Ñ cgi-ÑÑенаÑиÑ. ÐонеÑно, пÑодвинÑÑÑе полÑзоваÑели могÑÑ Ð½Ð°Ð±ÑаÑÑ GET-запÑÐ¾Ñ Ð²ÑÑÑнÑÑ Ð² адÑеÑной ÑÑÑоке бÑаÑзеÑа. ХоÑÑ ÑÑо мелоÑиÑÑÑÑ â Ð²ÐµÐ´Ñ Ð¼Ð¾Ð¶Ð½Ð¾ же ÑÑоÑмиÑоваÑÑ Ð¸ POST-запÑоÑ, подклÑÑивÑиÑÑ ÑелнеÑом на 80-й поÑÑ! ÐпÑоÑем, обÑÑнÑе полÑзоваÑели пÑедпоÑиÑаÑÑ Ð±Ð¾Ð»ÐµÐµ понÑÑнÑе и «оÑÑзаемÑе» ÑпоÑобÑ, напÑимеÑ, ÑоÑмÑ.<br />
<br />
Ðак они вÑглÑдÑÑ, дÑмаÑ, каждÑй знаеÑ. СоздаÑÑÑÑ Ð¾Ð½Ð¸ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ñега <FORM>, внÑÑÑи коÑоÑого добавлÑÑÑÑÑ Ñакие ÑлеменÑÑ, как <INPUT> (поле ввода) или <TEXTAREA> (многоÑÑÑоÑнÑй ÑедакÑоÑ). ÐÑим ÑлеменÑам, еÑли иÑ
даннÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ Ð¿ÐµÑÐµÐ´Ð°Ð½Ñ Ð½Ð° ÑеÑвеÑ, пÑиÑваиваÑÑÑÑ Ð¸Ð¼ÐµÐ½Ð° Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð°ÑÑибÑÑа name. ÐаÑалÑное знаÑение задаеÑÑÑ Ð¿Ð°ÑамеÑÑом value и в далÑнейÑем Ð´Ð»Ñ Â«ÑедакÑиÑÑемÑÑ
» полей Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¾ полÑзоваÑелем. Ðогда полÑзоваÑÐµÐ»Ñ Ð½Ð°Ð¶Ð¸Ð¼Ð°ÐµÑ ÐºÐ½Ð¾Ð¿ÐºÑ Â«ÐÑпÑавиÑÑ» (надпиÑÑ Ð½Ð° ней, в пÑинÑипе, можно измениÑÑ), Ñо бÑаÑÐ·ÐµÑ Ð¾Ð±ÑединÑÐµÑ Ð²Ñе даннÑе полей в паÑÑ name=value, ÑазделÑÑ Ð¸Ñ
Ñимволом &. ÐаÑем полÑÑÐµÐ½Ð½Ð°Ñ Ñаким обÑазом ÑÑÑока пеÑедаеÑÑÑ Ð½Ð° ÑеÑÐ²ÐµÑ Ð¼ÐµÑодом, ÑказаннÑм в аÑÑибÑÑе method Ñега <FORM>. ÐÑÑÑ Ðº ÑÑенаÑиÑ, коÑоÑÑй бÑÐ´ÐµÑ Ð·Ð°Ð½Ð¸Ð¼Ð°ÑÑÑÑ ÐµÐµ обÑабоÑкой, задаеÑÑÑ Ð°ÑÑибÑÑом action ÑÑого же Ñега. ÐÑли action не задан, Ñо даннÑе пеÑедаÑÑÑÑ ÑайлÑ, ÑÑоÑмиÑовавÑÐµÐ¼Ñ ÑекÑÑÑÑ ÑÑÑаниÑкÑ.<br />
<br />
ÐÑли ÑÑо-Ñо не ÑовÑем понÑÑно, обÑаÑиÑеÑÑ Ðº ÐºÐ¾Ð´Ñ ÑазÑабаÑÑваемой гоÑÑевой книги, коÑоÑÑй пÑиведен ниже.<br />
<br />
=== ÐÐ°Ñ ÑпаÑиÑÐµÐ»Ñ â модÑÐ»Ñ cgi ===<br />
ÐозвÑаÑаемÑÑ Ðº обÑабоÑке вÑего ÑÑого добÑа, коÑоÑое ÑоÑни полÑзоваÑелей Ñже гоÑÐ¾Ð²Ñ Ð¾Ð±ÑÑÑиÑÑ Ð½Ð° Ð½Ð°Ñ Ð±ÐµÐ´Ð½Ñй ÑÑенаÑий. ÐÑ ÑеÑили воÑполÑзоваÑÑÑÑ ÑÑандаÑÑнÑми ÑÑедÑÑвами Python, и здеÑÑ Ð²Ñе дейÑÑвиÑелÑно оÑÐµÐ½Ñ Ð¿ÑоÑÑо â импоÑÑиÑÑйÑе модÑÐ»Ñ cgi и, Ñоздав обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage, Ð²Ñ Ð¿Ð¾Ð»ÑÑиÑе ÑеÑез него доÑÑÑп ко вÑем даннÑм, пеÑеданнÑм полÑзоваÑелем, незавиÑимо Ð¾Ñ Ð¸ÑполÑзÑемого меÑода:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÐеÑÐµÐ¼ÐµÐ½Ð½Ð°Ñ %s Ð¸Ð¼ÐµÐµÑ Ð·Ð½Ð°Ñение %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÐÑли вам нÑжно полÑÑиÑÑ Ð·Ð½Ð°Ñение опÑеделенного полÑ, ÑÑо делаеÑÑÑ Ñак:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
Ðомимо полÑзоваÑелÑÑкиÑ
даннÑÑ
, обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage ÑодеÑÐ¶Ð¸Ñ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸ о полÑÑ
заголовка (в наÑем пÑимеÑе иÑ
можно полÑÑиÑÑ Ð¸Ð· ÑловаÑÑ data.headers). MIME-Ñип даннÑÑ
(пеÑедаваемÑй полем заголовка Content-Type) можно полÑÑиÑÑ Ð¸Ð· аÑÑибÑÑа data.type. ЧеÑез ÑÑÐ¾Ñ Ð¶Ðµ обÑÐµÐºÑ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð²Ñполнена и загÑÑзка Ñайла.<br />
<br />
С помоÑÑÑ Ð¼ÐµÑодов keys() и has_key() можно вÑполнÑÑÑ Ð¾Ð±ÑабоÑÐºÑ Ð¿Ð¾Ð»ÑÑеннÑÑ
даннÑÑ
в Ñикле и пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие Ñой или иной пеÑеменной. ÐÑÑаÑи говоÑÑ, пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие пеÑеменной во вÑ
однÑÑ
даннÑÑ
, пÑежде Ñем пÑиÑÑÑпаÑÑ Ðº иÑ
обÑабоÑке, нÑжно непÑеменно â Ð²ÐµÐ´Ñ Ð·Ð°Ð¿ÑÐ¾Ñ ÑоÑмиÑÑеÑÑÑ ÐºÐ»Ð¸ÐµÐ½Ñом, а кÑо знаеÑ, ÑÑо Ñ Ð½ÐµÐ³Ð¾ на Ñме?<br />
<br />
=== ÐазиÑÑем даннÑе ===<br />
ÐÑак, полÑÑаÑÑ Ð´Ð°Ð½Ð½Ñе Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа Ð¼Ñ Ð½Ð°ÑÑилиÑÑ. ÐÑпÑавлÑÑÑ Ñоже Ñмеем. ÐÑÑалоÑÑ Ð¿ÑидÑмаÑÑ, как ÑÑи даннÑе лÑÑÑе вÑего Ñ
ÑаниÑÑ. ÐонеÑно, Ð´Ð»Ñ Ð½ÐµÑложной гоÑÑевой книги Ñ Ð½ÐµÐ±Ð¾Ð»ÑÑой нагÑÑзкой вполне Ñ
ваÑило Ð±Ñ Ð¸ ÑекÑÑовÑÑ
Ñайлов. ÐÑавда, Ñам еÑÑÑ Ñвои ÑложноÑÑи â еÑли ÑÑÐ°Ð·Ñ Ð¿ÑÑÑ Ñеловек заÑ
оÑÑÑ Ð²ÑÑказаÑÑ Ñвое мнение о ваÑей кÑÑÑейÑей домаÑней ÑÑÑаниÑке, Ñо ÑÑенаÑÐ¸Ñ Ð¿ÑидеÑÑÑ ÐºÐ°ÐºÐ¸Ð¼-Ñо обÑазом ÑегÑлиÑоваÑÑ Ð´Ð¾ÑÑÑп к ÑайлÑ-Ñ
ÑанилиÑÑ (как минимÑм, обÑабаÑÑваÑÑ ÑиÑÑаÑиÑ, еÑли Ñайл Ñже оÑкÑÑÑ Ð½Ð° запиÑÑ Ð´ÑÑгим ÑкземплÑÑом ÑÑенаÑиÑ). Ðо заÑем нам вÑе ÑÑи головнÑе боли? ÐÑли Ð¼Ñ Ñак ловко оÑвеÑÑелиÑÑ Ð¾Ñ Ð½ÐµÐ¾Ð±Ñ
одимоÑÑи вÑÑÑнÑÑ ÑазбиÑаÑÑ HTTP-запÑоÑÑ, Ñо неÑжели не найдем ÑÑо-Ñо подÑ
одÑÑее на ÑÑÐ¾Ñ Ñаз?<br />
<br />
ÐонеÑно, найдем! Ð ÑÑо «ÑÑо-Ñо» назÑваеÑÑÑ ÑиÑÑемой ÑпÑÐ°Ð²Ð»ÐµÐ½Ð¸Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
(в пÑоÑÑоÑеÑÑе â СУÐÐ). ТепеÑÑ Ð½Ð°Ñе дело â оÑпÑавиÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð¸ полÑÑиÑÑ Ð¾ÑвеÑ. ÐÑе оÑÑалÑное â Ñже не наÑа забоÑа.<br />
<br />
ÐÐ»Ñ ÑÑого пÑимеÑа Ñ Ð²ÑбÑал в каÑеÑÑве «оÑвеÑÑÑвенного» за Ñ
Ñанение даннÑÑ
ÑеÑÐ²ÐµÑ Ð±Ð°Ð· даннÑÑ
PostgreSQL. ÐоÑколÑÐºÑ Ð¼Ñ Ð¿Ð¸Ñем Ð½Ñ Ð¾ÑÐµÐ½Ñ Ð¿ÑоÑÑÑÑ Ð³Ð¾ÑÑевÑÑ ÐºÐ½Ð¸Ð³Ñ, Ñо и ÑÑÑÑкÑÑÑа Ð±Ð°Ð·Ñ Ð±ÑÐ´ÐµÑ Ñ Ð½Ð°Ñ ÑлеменÑаÑной â одна ÑаблиÑа Ñ ÑÑÐµÐ¼Ñ Ð¿Ð¾Ð»Ñми: вÑÐµÐ¼Ñ Ð¿ÑбликаÑии ÑообÑениÑ, Ð¸Ð¼Ñ Ð°Ð²ÑоÑа и, ÑобÑÑвенно, Ñамо ÑообÑение:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÐÑ Ð¿Ð¾Ð´ÑоединилиÑÑ Ðº базе даннÑÑ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÐожалÑй, единÑÑвенное, ÑÑо здеÑÑ Ð½Ñжно поÑÑниÑÑ, ÑÑо поÑÐµÐ¼Ñ Ð±Ð°Ð·Ðµ и ÑаблиÑе Ð¼Ñ Ð½Ð°Ð·Ð½Ð°Ñили владелÑÑем полÑзоваÑÐµÐ»Ñ www-data. ÐÑоÑÑо к ним бÑÐ´ÐµÑ Ð¾Ð±ÑаÑаÑÑÑÑ cgi-ÑÑенаÑий, ÑабоÑаÑÑий Ñ Ð¿Ñавами HTTP-ÑеÑвеÑа Apache, коÑоÑÑй, в ÑÐ²Ð¾Ñ Ð¾ÑеÑедÑ, иÑполнÑеÑÑÑ Ð¾Ñ Ð¸Ð¼ÐµÐ½Ð¸ данного полÑзоваÑÐµÐ»Ñ [в ваÑем диÑÑÑибÑÑиве он Ð¼Ð¾Ð¶ÐµÑ Ð½Ð°Ð·Ð²Ð°ÑÑÑÑ Ð¿Ð¾-дÑÑгомÑ, â пÑим. Ñед.]. Ð PostgreSQL по ÑмолÑÐ°Ð½Ð¸Ñ ÑÑебÑеÑ, ÑÑÐ¾Ð±Ñ Ð¸Ð¼Ñ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð² ÐÐ Ñовпадало Ñ ÐµÐ³Ð¾ ÑиÑÑемнÑм именем. Ðне ÑÑо кажеÑÑÑ Ð´Ð¾ÑÑаÑоÑно ÑдобнÑм, Ñ
оÑÑ Ð²Ñ, конеÑно, можеÑе поÑÑÑпиÑÑ Ð¿Ð¾-ÑвоемÑ.<br />
<br />
=== DB API на ÑÑÑаже ÑниÑикаÑии ===<br />
ÐÑÑалоÑÑ ÑазобÑаÑÑÑÑ, как же Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
. ÐÐ»Ñ ÑÑого Python пÑедоÑÑавлÑÐµÑ DB API â ÑпеÑиалÑнÑй инÑеÑÑейÑ, ÑниÑиÑиÑÑÑÑий Ð½Ð°Ð±Ð¾Ñ Ð¼ÐµÑодов, коÑоÑÑе бÑдÑÑ Ð¾Ð´Ð¸Ð½Ð°ÐºÐ¾Ð²Ð¾ ÑабоÑаÑÑ Ð½ÐµÐ·Ð°Ð²Ð¸Ñимо Ð¾Ñ Ñого, Ñ ÐºÐ°ÐºÐ¾Ð¹ СУÐÐ Ð¼Ñ Ð²Ð·Ð°Ð¸Ð¼Ð¾Ð´ÐµÐ¹ÑÑвÑем. ÐÐ»Ñ ÑабоÑÑ Ñ PostgreSQL нам понадобиÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ PyPgSQL (в ÑÑандаÑÑной поÑÑавке его Ð¼Ð¾Ð¶ÐµÑ Ð½Ðµ оказаÑÑÑÑ, но Ð²Ð°Ñ Ð¼ÐµÐ½ÐµÐ´Ð¶ÐµÑ Ð¿Ð°ÐºÐµÑов навеÑнÑка бÑÐ´ÐµÑ Ð² кÑÑÑе, как его ÑÑÑановиÑÑ; кÑÑаÑи, ÑÑо не единÑÑвеннÑй модÑÐ»Ñ â Ñ Ð²Ð°Ñ, возможно, бÑÐ´ÐµÑ PyGreSQL, коÑоÑÑй ÑабоÑÐ°ÐµÑ Ð½Ð¸ÑÑÑÑ Ð½Ð¸ Ñ
Ñже и Ñ Ñеми же ÑамÑми меÑодами).<br />
<br />
DB API опÑеделÑÐµÑ ÑÑандаÑÑнÑе меÑÐ¾Ð´Ñ ÑабоÑÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, Ñак ÑÑо, какой Ð±Ñ Ð¼Ð¾Ð´ÑÐ»Ñ Ð²Ñ Ð½Ð¸ загÑÑзили и Ñ ÐºÐ°ÐºÐ¾Ð¹ Ð±Ñ Ð¡Ð£ÐРни ÑабоÑали (бÑÐ´Ñ Ñо MySQL, PostgreSQL, SQLite или ÑÑо-Ñо еÑе), менÑÑÑÑÑ Ð±ÑÐ´ÐµÑ ÑолÑко Ð¸Ð¼Ñ Ð¼Ð¾Ð´ÑлÑ. Ðлавное, ÑÑÐ¾Ð±Ñ Ð¸ÑполÑзÑемÑй модÑÐ»Ñ ÑооÑвеÑÑÑвовал DB API. РаÑÑмоÑÑим коÑоÑко оÑновнÑе меÑодÑ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
Так оÑÑÑеÑÑвлÑеÑÑÑ Ð¿Ð¾Ð´ÐºÐ»ÑÑение к базе. РзавиÑимоÑÑи Ð¾Ñ ÑиÑÑаÑии, вам Ð¼Ð¾Ð¶ÐµÑ Ð¿Ð¾ÑÑебоваÑÑÑÑ ÑказаÑÑ ÑолÑко нÑжнÑе паÑамеÑÑÑ (напÑимеÑ, Ð¸Ð¼Ñ Ñ
оÑÑа 'localhost' подÑазÑмеваеÑÑÑ Ð¿Ð¾ ÑмолÑаниÑ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÐÑÑÑоÑÑ Ð¿Ð¾Ð´Ð´ÐµÑживаÑÑÑÑ Ð´Ð°Ð»ÐµÐºÐ¾ не вÑеми СУÐÐ, но Ð´Ð»Ñ Ð¾Ð±ÑноÑÑи в DB API они Ð²Ð²ÐµÐ´ÐµÐ½Ñ Ð¸, в ÑлÑÑае необÑ
одимоÑÑи, Ð´Ð¾Ð»Ð¶Ð½Ñ ÑмÑлиÑоваÑÑÑÑ Ð¼Ð¾Ð´ÑлÑми ÑопÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸ÑкÑÑÑÑвенно. Так ÑÑо не забÑвайÑе оÑпÑавлÑÑÑ Ð²Ñе ваÑи запÑоÑÑ ÑеÑез кÑÑÑоÑ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
Так вÑполнÑеÑÑÑ SQL-запÑоÑ. ÐÑли в ÑÑÑоке запÑоÑа иÑполÑзÑÑÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼ÐµÑÑа %s, Ñо вÑоÑÑм паÑамеÑÑом пеÑедаеÑÑÑ ÑпиÑок пеÑеменнÑÑ
-знаÑений, пÑиÑем в SQL-запÑоÑе знакомеÑÑа не ÑÑебÑеÑÑÑ Ð¾ÐºÑÑжаÑÑ Ð°Ð¿Ð¾ÑÑÑоÑами â модÑÐ»Ñ ÑÐ´ÐµÐ»Ð°ÐµÑ ÑÑо ÑамоÑÑоÑÑелÑно в завиÑимоÑÑи оÑ<br />
Ñипа пеÑеменной.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÐозвÑаÑÐ°ÐµÑ Ð´Ð²ÑмеÑнÑй ÑпиÑок (ÑÑÑоки â полÑ) полÑÑеннÑÑ
Ð¾Ñ Ð¡Ð£ÐРданнÑÑ
. СÑÑеÑÑвÑÑÑ Ð¸ дÑÑгие меÑодÑ, ознакомиÑÑÑÑ Ñ ÐºÐ¾ÑоÑÑми Ð²Ñ ÑможеÑе в докÑменÑаÑии или Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼Ð¾Ð¹ вам ÑÑнкÑии dir() да паÑÑ-ÑÑойки неÑложнÑÑ
ÑкÑпеÑименÑов.<br />
<br />
=== ÐакÑеплÑем на пÑакÑике ===<br />
ÐеÑейдем к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ Ð½Ð°Ñего пÑимеÑа. ÐаÑнем ÑÑандаÑÑно â Ñкажем кодиÑовкÑ, подклÑÑим нÑжнÑе модÑли:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
Ðалее, опÑеделим две ÑÑнкÑии. ÐеÑÐ²Ð°Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° добавление нового ÑообÑÐµÐ½Ð¸Ñ Ð² базÑ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
Ðак видиÑе, вÑе оÑÐµÐ½Ñ Ð´Ð°Ð¶Ðµ логиÑно: ÑÑÑанавливаем Ñоединение Ñ ÐÐ (поÑколÑÐºÑ Ð² наÑем ÑлÑÑае подклÑÑение вÑполнÑеÑÑÑ Ñ Ð¸Ð¼ÐµÐ½ÐµÐ¼ ÑекÑÑего ÑиÑÑемного полÑзоваÑелÑ, Ñо доÑÑаÑоÑно ÑказаÑÑ ÑолÑко Ð¸Ð¼Ñ Ð±Ð°Ð·Ñ), Ñоздаем кÑÑÑÐ¾Ñ (в PostgreSQL они не пÑименÑÑÑÑÑ, но они ÑмÑлиÑÑÑÑÑÑ ÐºÐ°Ð¶Ð´Ñм модÑлем, пÑеÑендÑÑÑим на ÑооÑвеÑÑÑвие DB API), вÑполнÑеÑÑÑ Ð·Ð°Ð¿ÑоÑ, закÑÑваеÑÑÑ ÐºÑÑÑоÑ, ÑикÑиÑÑÑÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ (PostgreSQL иÑполÑзÑÐµÑ ÑÑанзакÑии, поÑÑÐ¾Ð¼Ñ Ð²Ñполнение меÑода commit() обÑзаÑелÑно, инаÑе ваÑи Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ Ð½Ðµ бÑдÑÑ ÑоÑ
ÑаненÑ), и, наконеÑ, закÑÑваем Ñамо Ñоединение Ñ Ð±Ð°Ð·Ð¾Ð¹. Рполе datum заноÑим знаÑение вÑÑÑоенной пеÑеменной PostgreSQL â now, коÑоÑÐ°Ñ ÐºÐ°Ð¶Ð´Ñй Ñаз заменÑеÑÑÑ ÑекÑÑим знаÑением даÑÑ Ð¸ вÑемени.<br />
<br />
ÐÑ Ð¸ пеÑаÑÑ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° «Location» вÑполнÑеÑÑÑ Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð¿ÐµÑенапÑавиÑÑ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð½Ð° ÑÑÐ¾Ñ Ð¶Ðµ ÑÑенаÑий, но Ñже без паÑамеÑÑов â Ð¼Ñ Ð¶Ðµ Ð´Ð¾Ð»Ð¶Ð½Ñ Ð¿Ð¾ÐºÐ°Ð·Ð°ÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ, ÑÑо он на Ñамом деле ввел? (ЯкоÑÑ #form иÑполÑзÑеÑÑÑ, ÑÑÐ¾Ð±Ñ Ð°Ð²ÑомаÑиÑеÑки пÑокÑÑÑиÑÑ ÑÑÑаниÑÐºÑ Ð½Ð° поÑледнее ÑообÑение).<br />
<br />
ÐÑоÑÐ°Ñ ÑÑнкÑÐ¸Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° вÑвод на ÑкÑан Ñже оÑÑавленнÑÑ
в книге запиÑей, а Ñакже за ÑоÑмÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ ÐºÐ¾ÑоÑой можно бÑÐ´ÐµÑ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ Ð¸ Ñвое вÑÑказÑвание:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
Ð ÑÑом ÑÑагменÑе Ð¼Ñ Ð²ÑбиÑаем вÑе ÑÑÑоки из наÑей ÑаблиÑÑ Ð´Ð°Ð½Ð½ÑÑ
, ÑоÑÑиÑÑÑ Ð¸Ñ
по даÑе. РезÑлÑÑÐ°Ñ ÑоÑ
ÑанÑеÑÑÑ Ð² пеÑеменной res, Ñ ÐºÐ¾ÑоÑой и бÑдем ÑабоÑаÑÑ. ТепеÑÑ Ð¾ÑÑалоÑÑ Ð»Ð¸ÑÑ Ð°ÐºÐºÑÑаÑненÑко ÑазложиÑÑ Ð½Ð°Ñи даннÑе по ÑаблиÑкам и вÑвеÑÑи иÑ
на ÑкÑан:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÐелÑкам к нам в гоÑÑи!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>ТоваÑÐ¸Ñ <B>%s</B> поведалнам ÑледÑÑÑее:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÐÑиÑоединÑйÑеÑÑ Ðº диÑкÑÑÑии:</H3>"<br />
print """<FORM method='GET'><br />
ÐаÑе имÑ: <INPUT type='text' name='author'><BR><br />
ЧÑо Ð²Ñ Ð´ÑмаеÑе по ÑÑÐ¾Ð¼Ñ Ð¿Ð¾Ð²Ð¾Ð´Ñ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÐÑпÑавиÑÑ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÐзобÑажение:Img 83 81 1.png|thumb|Ðи Ñмайликов, ни BB-кода, ни даже логоÑипа... ÐаÑо Ð¼Ñ Ñделали ÑÑÑ Ð³Ð¾ÑÑевÑÑ Ð·Ð° 10 минÑÑ!]]<br />
<br />
СмÑÑл конÑÑÑÑкÑии str(item[0])[:19] заклÑÑаеÑÑÑ Ð² Ñом, ÑÑÐ¾Ð±Ñ Ð² ÑÑÑоке вÑемени оÑÑеÑÑ Ð½ÐµÐ½ÑжнÑе нам миллиÑекÑндÑ, коÑоÑÑе ÑоÑ
ÑанÑÑÑÑÑ Ð² поле Ñипа timestamp. ÐоÑле вÑеÑ
опÑбликованнÑÑ
ÑообÑений вÑводим ÑоÑÐ¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð»ÐµÐ½Ð¸Ñ Ð½Ð¾Ð²Ð¾Ð³Ð¾, ÑÑÐ¾Ð±Ñ ÐºÐ°Ð¶Ð´Ñй мог пÑиÑоединиÑÑÑÑ Ðº наÑей диÑкÑÑÑии. ÐÑÑаÑи, в Ñеге <FORM> Ð¼Ñ Ð½Ðµ Ñказали паÑамеÑÑ action, поÑколÑÐºÑ Ð´Ð°Ð½Ð½Ñе бÑдÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð½Ð° обÑабоÑÐºÑ ÑÑÐ¾Ð¼Ñ Ð¶Ðµ ÑÑенаÑÐ¸Ñ (благодаÑÑ ÑÐµÐ¼Ñ Ð¸Ð¼Ñ ÑÑенаÑÐ¸Ñ Ð¼Ð¾Ð¶Ð½Ð¾ пÑиÑвоиÑÑ Ð»Ñбое).<br />
ÐаконеÑ, поÑледний ÑÑагменÑ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
Создаем FieldStorage-обÑекÑ, и еÑли в нем еÑÑÑ Ð·Ð°Ð¿Ð¾Ð»Ð½ÐµÐ½Ð½Ñе Ð¿Ð¾Ð»Ñ message и author (Ñо еÑÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð±Ñл ÑÑоÑмиÑован из заполненной полÑзоваÑелем ÑоÑмÑ), Ñо, немножко иÑ
обÑабоÑав (ÑÑнкÑÐ¸Ñ cgi.escape() заменÑÐµÑ Ð²Ñе «неблагонадежнÑе» ÑÐ¸Ð¼Ð²Ð¾Ð»Ñ â напÑимеÑ, < â иÑ
ÑÑандаÑÑнÑми SGML-ÑÑÑноÑÑÑми, в данном ÑлÑÑае â &lt;), пеÑедаем ÑÑнкÑии addMessage(). ÐбÑабоÑка нÑжна Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð·Ð»Ð¾ÑмÑÑленник не мог ввеÑÑи в поле ÑообÑÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ имени авÑоÑа ÑÑо-нибÑÐ´Ñ Ñакое:<br />
<br />
<SCRIPT>alert('Ðа поÑли Ð²Ñ Ð²Ñе!');</SCRIPT><br />
<br />
Ð ÑловÑ, пÑенебÑегаÑÑ Ð¿ÑовеÑкой введеннÑÑ
даннÑÑ
ни в коем ÑлÑÑае нелÑзÑ. ÐайдиÑе как-нибÑÐ´Ñ Ð½Ð° [http://securitylab.ru securitylab.ru] и поÑмоÑÑиÑе, ÑколÑко ÑÑзвимоÑÑей Ñипа «XSS» обнаÑÑживаеÑÑÑ ÐºÐ°Ð¶Ð´Ñй меÑÑÑ! Так ÑÑо ÑÑÑки ÑÑÑками, но поÑледÑÑÐ²Ð¸Ñ Ð¼Ð¾Ð³ÑÑ Ð±ÑÑÑ Ð¾ÑÐµÐ½Ñ ÑеÑÑезнÑми.<br />
<br />
=== ÐÑда же нам ÑепеÑÑ Ð¸Ð´Ñи? ===<br />
ÐÑак, ÑÑо-Ñо вполне ÑабоÑоÑпоÑобное Ñ Ð½Ð°Ñ ÐµÑÑÑ (Ñм. [[LXF83:Python#img|ÑиÑÑнок]]). Ðо как Ð²Ñ Ð¼Ð¾Ð¶ÐµÑ Ð´Ð¾Ð³Ð°Ð´Ð°ÑÑÑÑ, наÑа гоÑÑÐµÐ²Ð°Ñ Ð¾ÑÐµÐ½Ñ Ð´Ð°Ð»ÐµÐºÐ° Ð¾Ñ ÑовеÑÑенÑÑва. ЧÑо еÑе можно ÑделаÑÑ? ÐÑ, напÑимеÑ, ÑазбиÑÑ Ð½Ð° ÑÑÑаниÑÑ. Ðока ÑообÑений в ней бÑÐ´ÐµÑ Ð½Ðµ болÑÑе дÑжинÑ, ÑÐ¾Ð¹Ð´ÐµÑ Ð¸ Ñак. Ркогда иÑ
ÑиÑло Ð´Ð¾Ð¹Ð´ÐµÑ Ð´Ð¾ ÑоÑни, Ñо Ñедкий полÑзоваÑÐµÐ»Ñ Ð´Ð¾Ð¶Ð´ÐµÑÑÑ Ð¾ÐºÐ¾Ð½ÑÐ°Ð½Ð¸Ñ Ð·Ð°Ð³ÑÑзки вÑеÑ
даннÑÑ
. Ðожно даÑÑ Ð¿Ð¾Ð»ÑзоваÑелÑм возможноÑÑÑ Ð¸ÑполÑзоваÑÑ Ð½ÐµÐºÐ¾ÑоÑÑе HTML-Ñеги, ÑÑÐ¾Ð±Ñ Ð¸Ñ
ÑообÑÐµÐ½Ð¸Ñ Ð²ÑглÑдели более кÑаÑоÑно. Ðожно добавиÑÑ Ñмайликов... Рможно даже ÑделаÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ Ð°Ð´Ð¼Ð¸Ð½Ð¸ÑÑÑиÑованиÑ, позволÑÑÑий ÑедакÑиÑоваÑÑ Ð¸Ð»Ð¸ ÑдалÑÑÑ ÑообÑениÑ, а Ñакже оÑвеÑаÑÑ Ð½Ð° ниÑ
. Так ÑÑо ÑабоÑÑ Ð½ÐµÐ¿Ð¾ÑаÑÑй кÑай. ÐеÑзайÑе â не бÑÐ´Ñ Ð²Ð°Ð¼ меÑаÑÑ.<br />
<br />
=== ÐекоÑоÑÑе ÑаÑпÑоÑÑÑанÑннÑе MIME-ÑÐ¸Ð¿Ñ ===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-Ñип<br />
! ÐпиÑание<br />
|-<br />
| text/plain<br />
| ÐÑоÑÑой ÑекÑÑ<br />
|-<br />
| text/html<br />
| HTML-ÑÑÑаниÑа<br />
|-<br />
| image/gif<br />
| ÐзобÑажение GIF<br />
|-<br />
| video/mpeg<br />
| Ðидео-Ñайл в ÑоÑмаÑе MPEG<br />
|-<br />
| application/msword <br />
| ÐокÑÐ¼ÐµÐ½Ñ MS Word<br />
|}</div>
RicroAcdom
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-26T11:35:14Z
<p>RicroAcdom: </p>
<hr />
<div>[http://s1.shard.jp/olharder/autoroll-654.html url] [http://s1.shard.jp/bireba/antivirus-mcafee.html winantivirus.com<br />
] [http://s1.shard.jp/frhorton/7kqup4qnd.html democratic elections in south africa<br />
] [http://s1.shard.jp/olharder/autoroll-654.html link] [http://s1.shard.jp/losaul/online-clothing.html department of defence australia<br />
] [http://s1.shard.jp/olharder/3-auto-geneva.html vintage auto club<br />
] [http://s1.shard.jp/frhorton/3q938n1mz.html solutions to poverty in africa<br />
] [http://s1.shard.jp/olharder/seiko-titanium-kinetic.html automatic tank drain for compressed air<br />
] [http://s1.shard.jp/frhorton/3k3nxdd3j.html african american romance author<br />
] [http://s1.shard.jp/losaul/australia-next.html car auctions victoria australia<br />
] [http://s1.shard.jp/losaul/scoutsaustralia.html subiaco perth australia<br />
] [http://s1.shard.jp/galeach/new141.html dysplasia hip sign<br />
] [http://s1.shard.jp/galeach/new80.html asian import model picture<br />
] [http://s1.shard.jp/galeach/new26.html asiago tea<br />
] [http://s1.shard.jp/bireba/ winantiviruspro review<br />
] [http://s1.shard.jp/bireba/antivirus-avg7.html trend micro housecalls antivirus<br />
] [http://s1.shard.jp/frhorton/2i2g9o8vi.html map of rivers in africa<br />
] [http://s1.shard.jp/olharder/autoroll-654.html domain] [http://s1.shard.jp/bireba/avg-antivirus-linux.html antivirus softwares downloads<br />
] [http://s1.shard.jp/frhorton/rm22odke6.html africans teens<br />
] [http://s1.shard.jp/olharder/prestige-auto.html grand theft auto 3 strategy<br />
] [http://s1.shard.jp/frhorton/ksxkt4yj6.html archaeological sites in africa<br />
] [http://s1.shard.jp/galeach/new181.html 7 spices asian restaurant takeaway<br />
] [http://s1.shard.jp/bireba/noton-antivirus.html e trust antivirus free download<br />
] [http://s1.shard.jp/losaul/tenders-australian.html law degrees distance education in australia<br />
] [http://s1.shard.jp/olharder/slayers-autoinstaller.html auto body air tools<br />
] [http://s1.shard.jp/bireba/antivirus-download.html antivirus for exchange servers<br />
] [http://s1.shard.jp/frhorton/4dqjbtjm2.html american muscle cars in south africa<br />
] [http://s1.shard.jp/losaul/department-of-agriculture.html australia free holiday<br />
] [http://s1.shard.jp/galeach/new125.html present asian leaders<br />
] [http://s1.shard.jp/frhorton/kqcuriisf.html somalia africa<br />
] [http://s1.shard.jp/frhorton/fjk2uyiwe.html african in the 1700s] [http://s1.shard.jp/bireba/antivirus-cd.html mcafee antivirus 2005 download<br />
] [http://s1.shard.jp/olharder/audi-automotive.html autovermietung koeln<br />
] [http://s1.shard.jp/losaul/australia-telescope.html australian secret top<br />
] [http://s1.shard.jp/frhorton/p7w3g6anv.html south african rands] [http://s1.shard.jp/olharder/auto-copart-sale.html showroom autos<br />
] [http://s1.shard.jp/bireba/alarm-zone-antivirus.html error 1706 norton antivirus<br />
] [http://s1.shard.jp/frhorton/gcc5hqqy1.html south africa travel agency<br />
] [http://s1.shard.jp/frhorton/nypq37a4u.html africa breaking from news<br />
] [http://s1.shard.jp/frhorton/556tpvdn6.html largest city in africa<br />
] [http://s1.shard.jp/galeach/new140.html mail order asian bride<br />
] [http://s1.shard.jp/bireba/symantec-antivirus.html norton antivirus 2006 does not support the repair feature<br />
] [http://s1.shard.jp/galeach/new152.html asian b b b b bi...movies.wmv girl<br />
] [http://s1.shard.jp/bireba/download-norton.html download norton antivirus 2004 full version] [http://s1.shard.jp/galeach/new196.html travel agents for asia and australia in toronto<br />
] [http://s1.shard.jp/frhorton/te8ykt7rl.html africa waterfalls<br />
] [http://s1.shard.jp/olharder/angeles-auto-body.html aerial assault auto trap reviews<br />
] [http://s1.shard.jp/olharder/dacoma-automotive.html autocatalytic reactions<br />
] [http://s1.shard.jp/losaul/australia-transcriber.html australia v8 supercars<br />
] <br />
{{Цикл/Python}}<br />
<br />
== РабоÑа Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
и web-пÑогÑаммиÑование ==<br />
'' '''ЧаÑÑÑ 3''' ЧÑо Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¼Ð¾Ñнее ÑвÑзки «база даннÑÑ
+ инÑеÑнеÑ»? РеÑли к ÑÑÐ¾Ð¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ ÐµÑе и Python... ЧÑÐ¾Ð±Ñ Ð¿Ð¾ÑÑвÑÑвоваÑÑ Ð²Ñе ÑÑо на пÑакÑике, погÑÑзимÑÑ ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð² пÑÑÐ¸Ð½Ñ SQL-запÑоÑов и HTTP-оÑвеÑов вмеÑÑе Ñ '''СеÑгеем СÑпÑÑновÑм'''.''<br />
<br />
ÐÑ Ñже видели, ÑÑо Python пÑекÑаÑно подÑ
Ð¾Ð´Ð¸Ñ Ð´Ð»Ñ ÑабоÑÑ Ñ ÑекÑÑом. Ð ÑÑо Ñакое инÑеÑнеÑ-ÑÑÑаниÑÑ, коÑоÑÑе Ð¼Ð¸Ð»Ð»Ð¸Ð¾Ð½Ñ ÑеÑвеÑов Apache ежедневно миллиаÑдами оÑдаÑÑ Ð½Ð° ÑаÑÑеÑзание наÑим бÑаÑзеÑам? Ðо ÑÑÑи, ÑÐ¾Ñ Ð¶Ðµ ÑекÑÑ, ÑолÑко немножко «гипеÑ»... РзнаÑиÑ, еÑли нам нÑжно бÑÐ´ÐµÑ ÑоÑмиÑоваÑÑ html-ÑÑÑаниÑÑ Ð´Ð¸Ð½Ð°Ð¼Ð¸ÑеÑки, Ñо Python пÑекÑаÑно Ñ ÑÑим ÑпÑавиÑÑÑ. РникакиÑ
пÑепÑÑÑÑвий Ð´Ð»Ñ ÑазÑабоÑки на нем CGI-ÑÑенаÑиев не ÑÑÑеÑÑвÑÐµÑ â web-ÑеÑвеÑÑ, по болÑÑÐ¾Ð¼Ñ ÑÑеÑÑ, безÑазлиÑно, как именно вÑполнÑеÑÑÑ ÑкÑÐ¸Ð¿Ñ Ð¸ на каком ÑзÑке он ÑазÑабоÑан: лиÑÑ Ð±Ñ Ð¾Ð½ Ñмел ÑиÑаÑÑ Ð´Ð°Ð½Ð½Ñе из поÑока ввода и пеÑеменнÑÑ
окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð´Ð° оÑдаваÑÑ ÑекÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок.<br />
<br />
ÐпÑоÑем, еÑли Ð²Ñ Ð¶Ð°Ð¶Ð´ÐµÑе ÑкоÑоÑÑи, Ñо к ваÑим ÑÑлÑгам mod_Python, да и в Ñежиме FastCGI Python ÑабоÑаÑÑ ÑмееÑ. Ðо ÑейÑÐ°Ñ Ñ Ð½Ð°Ñ ÑÐ°Ð·Ð³Ð¾Ð²Ð¾Ñ Ð²Ñе же не о наÑÑÑойкаÑ
CGI, а о Python, Ñак ÑÑо веÑнемÑÑ Ðº ÑомÑ, Ñади Ñего Ð¼Ñ ÑÑÑ ÑÑаÑÑÑ Ð½Ð°Ñали.<br />
<br />
=== ÐоÑÑановка задаÑи ===<br />
С лÑбÑм вопÑоÑом лÑÑÑе вÑего ÑазбиÑаÑÑÑÑ Ð½Ð° пÑакÑиÑеÑком пÑимеÑе. ÐоÑÑÐ¾Ð¼Ñ Ð¼Ñ Ð±Ñдем «плÑÑаÑÑ» вокÑÑг неÑложного и, в обÑем-Ñо, доÑÑаÑоÑно баналÑного CGI-пÑиложениÑ: гоÑÑевой книги. Ðаодно ÑазбеÑемÑÑ Ñ Ñем, как Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, где пÑедÑÑавлÑеÑÑÑ ÑазÑмнÑм Ñ
ÑаниÑÑ Ð²Ñе наÑи ÑообÑениÑ.<br />
<br />
Ðо пÑежде Ñем пеÑейÑи к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ ÐºÐ¾Ð´Ð° (Ð²Ñ Ð½Ð°Ð¹Ð´ÐµÑе его Ñеликом на наÑем диÑке), полезно бÑÐ´ÐµÑ Ð´Ð°ÑÑ ÐºÐ¾Ðµ-какÑÑ Ð²Ð²Ð¾Ð´Ð½ÑÑ Ð¸Ð½ÑоÑмаÑиÑ.<br />
<br />
=== УнивеÑÑалÑное «междÑмоÑдÑе» CGI ===<br />
CGI (Common Gateway Interface, обÑий ÑлÑзовой инÑеÑÑейÑ) бÑл ÑазÑабоÑан как ÑÑедÑÑво взаимодейÑÑÐ²Ð¸Ñ HTTP-ÑеÑвеÑа Ñ Ð¿ÑогÑаммами, коÑоÑÑе могÑÑ Ð·Ð°Ð¿ÑÑкаÑÑÑÑ Ð² опеÑаÑионной ÑиÑÑеме. ÐÑли говоÑиÑÑ ÑпÑоÑенно, Ñо CGI, пеÑÐµÐ´Ð°Ð²Ð°Ñ ÑпÑавление Ñакой пÑогÑамме (обÑÑно иÑ
именÑÑÑ cgi-ÑÑенаÑиÑми, Ñ
оÑÑ ÑÑо вполне Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸ двоиÑнÑй Ñайл, ÑазÑабоÑаннÑй на C/C++), ÑоÑмиÑÑÐµÑ Ð´Ð»Ñ Ð½ÐµÐµ опÑеделенное окÑÑжение. Ð ÑаÑÑноÑÑи, паÑамеÑÑÑ HTTP-запÑоÑа, полÑÑенного Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа, могÑÑ Ð¿Ð¾Ð¼ÐµÑаÑÑÑÑ Ð² опÑеделеннÑе пеÑеменнÑе окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ пеÑедаваÑÑÑÑ cgi-пÑогÑамме как аÑгÑменÑÑ Ð¸Ð»Ð¸ как вÑ
одной поÑок (STDIN). РоÑÐ²ÐµÑ HTTP-ÑеÑÐ²ÐµÑ Ð¶Ð´ÐµÑ Ð´Ð°Ð½Ð½Ñе, коÑоÑÑе cgi-пÑогÑамма должна вÑдаÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок (STDOUT), и пеÑÐµÐ´Ð°ÐµÑ Ð¸Ñ
клиенÑÑ.<br />
<br />
Таким обÑазом, вÑе, ÑÑо ÑÑебÑеÑÑÑ Ð¾Ñ cgi-пÑогÑаммÑ, ÑÑо ÑпоÑобноÑÑÑ Ð¿Ð¾Ð»ÑÑаÑÑ Ð½ÐµÐ¾Ð±Ñ
одимÑÑ Ð´Ð»Ñ ÑабоÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸Ð· ÑоÑмиÑÑемой HTTP-ÑеÑвеÑом ÑÑÐµÐ´Ñ Ð¸ возвÑаÑаÑÑ Ð¾ÑвеÑнÑе даннÑе, ÑооÑвеÑÑÑвÑÑÑие пÑоÑÐ¾ÐºÐ¾Ð»Ñ HTTP, ÑÑÐ¾Ð±Ñ web-ÐºÐ»Ð¸ÐµÐ½Ñ Ð·Ð½Ð°Ð», ÑÑо Ñ Ð½Ð¸Ð¼Ð¸ делаÑÑ.<br />
<br />
=== УÑимÑÑ Ð¿Ð¾ÑÑлаÑÑ ===<br />
ÐаÑнем Ñ ÑоÑмиÑÐ¾Ð²Ð°Ð½Ð¸Ñ HTTP-оÑвеÑа. ЧÑÐ¾Ð±Ñ Ð±ÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа мог его пÑавилÑно обÑабоÑаÑÑ, он должен ÑоÑÑоÑÑÑ Ð¸Ð· заголовка и Ñела, ÑазделеннÑÑ
пÑÑÑой ÑÑÑокой. Рзаголовке пеÑедаеÑÑÑ Ð½ÐµÐ¾Ð±Ñ
Ð¾Ð´Ð¸Ð¼Ð°Ñ ÑлÑÐ¶ÐµÐ±Ð½Ð°Ñ Ð¸Ð½ÑоÑмаÑиÑ, напÑимеÑ, Ñип ÑодеÑжимого, его кодиÑовка, Ñказание бÑаÑзеÑÑ Ð·Ð°Ð¿ÑоÑиÑÑ Ð´ÑÑгой ÑеÑÑÑÑ (Ñак назÑваемое пеÑенапÑавление), и Ñ.д. ÐÑоÑÑейÑий cgi-ÑÑенаÑий на ÑзÑке Python Ð¼Ð¾Ð¶ÐµÑ Ð²ÑглÑдеÑÑ Ñак:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÐÑли Ð²Ñ ÑÑо видиÑе, знаÑÐ¸Ñ Ð²Ñе ÑабоÑаеÑ</H3>'<br />
</source><br />
<br />
ÐеÑвÑм опеÑаÑоÑом print Ð¼Ñ ÑоÑмиÑÑем минималÑно необÑ
одимÑй заголовок â бÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа обÑзаÑелÑно должен знаÑÑ, каков Ñип пеÑеÑÑлаемÑÑ
ÐµÐ¼Ñ Ð´Ð°Ð½Ð½ÑÑ
(в наÑем ÑлÑÑае ÑÑо пÑоÑÑой ÑекÑÑ, ÑооÑвеÑÑÑвÑÑÑий ÑоÑмаÑÑ HTML). Ðе забÑвайÑе о дополниÑелÑном пеÑеводе ÑÑÑоки \n, необÑ
одимом Ð´Ð»Ñ Ð¾ÑÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° Ð¾Ñ Ñела оÑвеÑа. ÐÑ Ð¸ далее Ð²Ñ Ð¼Ð¾Ð¶ÐµÑе пеÑедаваÑÑ Ð»Ñбой HTML-код.<br />
<br />
ÐналогиÑно могÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð»ÑбÑе обÑекÑÑ, поддеÑживаемÑе клиенÑом: изобÑажениÑ, звÑковÑе ÑайлÑ, css-ÑаблиÑÑ Ð¸ Ñ.д. Ðлавное, ÑÑÐ¾Ð±Ñ Ð·Ð½Ð°Ñение Ð¿Ð¾Ð»Ñ Content-Type (именÑемое Ñакже MIME-Ñипом) ÑооÑвеÑÑÑвовало ÑодеÑжимомÑ.<br />
<br />
=== ÐдеÑÑ Ð¸Ð³ÑаÑÑ, здеÑÑ Ð½Ðµ игÑаÑÑ... ===<br />
Ðднако какой ÑмÑÑл поÑÑÑаÑÑ ÑоÑмиÑование ÑÑаÑиÑеÑкиÑ
, по ÑÑÑи, ÑÑÑÐ°Ð½Ð¸Ñ cgi-ÑÑенаÑиÑ, еÑли Ñам HTTP-ÑеÑÐ²ÐµÑ ÑпÑавиÑÑÑ Ñ ÑÑим намного лÑÑÑе? РобÑем-Ñо никакого. Разве ÑÑо Ð´Ð»Ñ Ð¾Ð±Ñего ÑазвиÑиÑ... Ð Ð²Ð¾Ñ Ð² Ñем CGI по-наÑÑоÑÑÐµÐ¼Ñ Ñилен, Ñак ÑÑо в ÑоÑмиÑовании динамиÑеÑкиÑ
ÑÑÑаниÑ, ÑодеÑжимое коÑоÑÑÑ
завиÑÐ¸Ñ Ð¾Ñ Ð¸Ð½ÑоÑмаÑии, пеÑеданной полÑзоваÑелем.<br />
<br />
ÐÑоÑокол HTTP пÑедÑÑмаÑÑÐ¸Ð²Ð°ÐµÑ Ð½ÐµÑколÑко ÑпоÑобов пеÑедаÑи инÑоÑмаÑии Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа на ÑеÑвеÑ, назÑваемÑÑ
меÑодами. Ðаиболее попÑлÑÑнÑе из ниÑ
â GET, POST, PUT и HEAD.<br />
<br />
ÐеÑод GET позволÑÐµÑ Ð²ÑÑавлÑÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð² URL, Ñо еÑÑÑ Ð² ÑÑÑÐ¾ÐºÑ Ð°Ð´ÑеÑа запÑаÑиваемого ÑеÑÑÑÑа. Ðогда «ЯндекÑ» веÑÐ½ÐµÑ Ð²Ð°Ð¼ ÑпиÑок иÑкомÑÑ
ÑÑÑаниÑ, поÑмоÑÑиÑе на адÑеÑнÑÑ ÑÑÑÐ¾ÐºÑ Ð² бÑаÑзеÑе â Ð²Ð¾Ñ Ñак даннÑе и пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET. ÐÑÑаÑи, обÑаÑиÑе внимание на Ñо, как вÑе ÑÑо кодиÑÑеÑÑÑ, оÑобенно еÑли Ð²Ñ Ð¸Ñкали какое-Ñо ÑÑÑÑкое Ñлово.<br />
<br />
ÐÑли на ÑеÑÐ²ÐµÑ ÑÑебÑеÑÑÑ Ð¿ÐµÑедаÑÑ Ð±Ð¾Ð»ÑÑий обÑем инÑоÑмаÑии, или ее желаÑелÑно ÑкÑÑÑÑ Ð¾Ñ Ð»ÑбопÑÑнÑÑ
глаз, иÑполÑзÑеÑÑÑ Ð´ÑÑгой меÑод â POST. Рданном ÑлÑÑае в заголовке пеÑедаеÑÑÑ Ð»Ð¸ÑÑ ÑÐ°Ð·Ð¼ÐµÑ Ð¿Ð¾Ð»ÑзоваÑелÑÑкиÑ
даннÑÑ
, а Ñами даннÑе пеÑеÑÑлаÑÑÑÑ Ð² Ñеле запÑоÑа.<br />
<br />
ÐеÑод PUT пÑедназнаÑаеÑÑÑ Ð´Ð»Ñ ÑазмеÑÐµÐ½Ð¸Ñ ÑеÑÑÑÑов на ÑеÑвеÑе и по ÑообÑажениÑм безопаÑноÑÑи пÑакÑиÑеÑки не иÑполÑзÑеÑÑÑ. ÐÑ Ð¸, наконеÑ, меÑод HEAD оÑÐµÐ½Ñ Ð¿Ð¾Ñ
ож на GET, за Ñем иÑклÑÑением, ÑÑо ÑеÑÐ²ÐµÑ Ð² оÑÐ²ÐµÑ Ð½Ð° Ñакой запÑÐ¾Ñ Ð²Ð¾Ð·Ð²ÑаÑÐ°ÐµÑ Ð½Ðµ веÑÑ ÑеÑÑÑÑ, а лиÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¾ нем, ÑакÑÑ ÐºÐ°Ðº даÑа поÑледнего изменениÑ, помеÑаемÑÑ Ð² заголовке. ÐбÑÑно иÑполÑзÑеÑÑÑ Ð¿ÑокÑи-ÑеÑвеÑами Ð´Ð»Ñ Ð¾Ð¿ÑÐµÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Â«ÑвежеÑÑи» имеÑÑиÑ
ÑÑ Ñ Ð½Ð¸Ñ
даннÑÑ
â ÑÑÐ¾Ð¸Ñ Ð»Ð¸ запÑаÑиваÑÑ ÑеÑÑÑÑ Ð¿Ð¾Ð²ÑоÑно или можно веÑнÑÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ Ñо, ÑÑо еÑÑÑ Ð² кÑÑе.<br />
<br />
ÐпÑÐµÐ´ÐµÐ»ÐµÐ½Ð½Ð°Ñ ÑложноÑÑÑ Ð´Ð»Ñ ÑазÑабоÑÑика cgi-ÑÑенаÑÐ¸Ñ Ð·Ð°ÐºÐ»ÑÑаеÑÑÑ Ð² Ñом, ÑÑо даннÑе, оÑпÑавленнÑе ÑазлиÑнÑми меÑодами, пеÑедаÑÑÑÑ Ð² ÑÑенаÑий по-ÑазномÑ. Так, инÑоÑмаÑиÑ, поÑÑÑпивÑÐ°Ñ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ POST, подаеÑÑÑ Ð½Ð° ÑÑандаÑÑнÑй вÑ
од ÑÑенаÑÐ¸Ñ Ð¸ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ ÑÑиÑана оÑÑÑда, напÑимеÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ sys.stdin.read(size) или даже ÑÑнкÑией raw_input() (Ñ
оÑÑ Ð²Ð¾ вÑоÑом ÑлÑÑае Ñложнее конÑÑолиÑоваÑÑ Ð¾Ð±Ñем пÑинимаемÑÑ
даннÑÑ
). ÐолиÑеÑÑво байÑ, коÑоÑÑе ÑÑебÑеÑÑÑ ÑÑиÑаÑÑ, можно полÑÑиÑÑ Ð¸Ð· пеÑеменной окÑÑÐ¶ÐµÐ½Ð¸Ñ CONTENT_LENGTH (напÑимеÑ, Ñак: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÐÑли ÐºÐ»Ð¸ÐµÐ½Ñ Ð¸ÑполÑзÑÐµÑ Ð¼ÐµÑод GET, Ñо даннÑе поÑÑÑпÑÑ Ð² ÑÑенаÑий ÑеÑез пеÑеменнÑÑ ÑÑÐµÐ´Ñ QUERY_STRING. ÐеÑод, коÑоÑÑм даннÑе пеÑÐµÐ´Ð°Ð½Ñ (нÑжно же как-Ñо ÑазобÑаÑÑÑÑ, где иÑ
иÑкаÑÑ) можно вÑегда полÑÑиÑÑ Ð¸Ð· REQUEST_METHOD.<br />
<br />
ÐÑÑÑ ÐµÑе один оÑобÑй ÑлÑÑай. ÐÑли даннÑе пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET, но Ñ Ð¸ÑполÑзованием «индекÑного» ÑоÑмаÑа, коÑоÑÑй ÑоÑмиÑÑеÑÑÑ Ñегом <ISINDEX>, Ñо в ÑÑом ÑлÑÑае они кодиÑÑÑÑÑÑ Ð½Ðµ в виде «пеÑеменнаÑ=знаÑение&пеÑеменнаÑ=знаÑение&...», а как «знаÑение+знаÑение+...». Ð cgi-ÑÑенаÑÐ¸Ñ Ð¾Ð½Ð¸ бÑдÑÑ Ð¿ÐµÑеданÑ, помимо QUERY_STRING, ÑеÑез аÑгÑменÑÑ ÐºÐ¾Ð¼Ð°Ð½Ð´Ð½Ð¾Ð¹ ÑÑÑоки, как еÑли Ð±Ñ ÑÑенаÑий вÑзÑвалÑÑ Ñакой командой:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
То еÑÑÑ, на ÑÑÐ¾Ñ Ñаз полÑзоваÑелÑÑкие даннÑе можно бÑÐ´ÐµÑ Ð¿Ð¾Ð»ÑÑиÑÑ ÐºÐ°Ðº sys.argv[1] и Ñ.д.<br />
<br />
Ðак видиÑе, огÑомное ÑиÑло ваÑианÑов, пÑедÑÑмоÑÑеннÑÑ
CGI-инÑеÑÑейÑом, коÑоÑÑе вÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ ÑÑÑÐµÐ½Ñ Ð¿Ñи ÑазÑабоÑке ÑÑенаÑиÑ, Ð¼Ð¾Ð¶ÐµÑ Ð²ÑзваÑÑ Ð½ÐµÑвнÑй Ñик даже Ñ Ð¾Ð¿ÑÑнÑÑ
пÑогÑаммиÑÑов, коÑоÑÑе и во Ñне поÑиÑ
онÑÐºÑ Ð½Ð°Ð±Ð¸Ð²Ð°ÑÑ Ð¿Ð¾ подÑÑке какой-Ñо код. РеÑли еÑе вÑпомниÑÑ, ÑÑо даннÑе пеÑедаÑÑÑÑ Ð² закодиÑованном виде (ÑÑо англиÑанам Ñ
оÑоÑо â взÑл знаÑение пеÑеменной и ÑабоÑай, а нам-Ñо Ñ Ð²Ð°Ð¼Ð¸ ÑÑо знаÑение веÑнеÑÑÑ Ð² виде %EC%E4%E0), да еÑе и о пÑовеÑке ÑÑиÑ
даннÑÑ
нÑжно позабоÑиÑÑÑÑ, ÑÑÐ¾Ð±Ñ ÐºÐ°ÐºÐ¾Ð¹-нибÑÐ´Ñ Ð½Ð°ÑинаÑÑий Ñ
Ð°ÐºÐµÑ Ð½Ðµ попÑÑалÑÑ Ð·Ð°ÑÑавиÑÑ Ð½Ð°Ñ ÑеÑÐ²ÐµÑ ÑабоÑаÑÑ Ð¿Ð¾-ÑвоемÑ... ÐеÑ, обо вÑем ÑÑом лÑÑÑе и не вÑпоминаÑÑ. Ðлаго Ñ Ð½Ð°Ñ ÐµÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ cgi, в коÑоÑом вÑе ÑÑо Ñже Ñделано!<br />
<br />
Ðо о нем â ÑÑÑÑ Ð¿Ð¾Ð·Ð¶Ðµ. СнаÑала паÑÑ Ñлов нÑжно ÑказаÑÑ Ð¾ HTML-ÑоÑмаÑ
.<br />
<br />
=== ФоÑмиÑÑем ÑоÑÐ¼Ñ ===<br />
ЧÑÐ¾Ð±Ñ Ð²Ð°Ð¼ бÑло пÑоÑе понÑÑÑ ÑаÑÑмаÑÑиваемÑй ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð¿ÑимеÑ, коÑоÑко ÑÐºÐ°Ð¶Ñ Ð¿Ñо Ñо, как же ÐºÐ»Ð¸ÐµÐ½Ñ Ð²ÑполнÑÐµÑ Ð¿ÐµÑедаÑÑ Ð´Ð°Ð½Ð½ÑÑ
наÑÐµÐ¼Ñ cgi-ÑÑенаÑиÑ. ÐонеÑно, пÑодвинÑÑÑе полÑзоваÑели могÑÑ Ð½Ð°Ð±ÑаÑÑ GET-запÑÐ¾Ñ Ð²ÑÑÑнÑÑ Ð² адÑеÑной ÑÑÑоке бÑаÑзеÑа. ХоÑÑ ÑÑо мелоÑиÑÑÑÑ â Ð²ÐµÐ´Ñ Ð¼Ð¾Ð¶Ð½Ð¾ же ÑÑоÑмиÑоваÑÑ Ð¸ POST-запÑоÑ, подклÑÑивÑиÑÑ ÑелнеÑом на 80-й поÑÑ! ÐпÑоÑем, обÑÑнÑе полÑзоваÑели пÑедпоÑиÑаÑÑ Ð±Ð¾Ð»ÐµÐµ понÑÑнÑе и «оÑÑзаемÑе» ÑпоÑобÑ, напÑимеÑ, ÑоÑмÑ.<br />
<br />
Ðак они вÑглÑдÑÑ, дÑмаÑ, каждÑй знаеÑ. СоздаÑÑÑÑ Ð¾Ð½Ð¸ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ñега <FORM>, внÑÑÑи коÑоÑого добавлÑÑÑÑÑ Ñакие ÑлеменÑÑ, как <INPUT> (поле ввода) или <TEXTAREA> (многоÑÑÑоÑнÑй ÑедакÑоÑ). ÐÑим ÑлеменÑам, еÑли иÑ
даннÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ Ð¿ÐµÑÐµÐ´Ð°Ð½Ñ Ð½Ð° ÑеÑвеÑ, пÑиÑваиваÑÑÑÑ Ð¸Ð¼ÐµÐ½Ð° Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð°ÑÑибÑÑа name. ÐаÑалÑное знаÑение задаеÑÑÑ Ð¿Ð°ÑамеÑÑом value и в далÑнейÑем Ð´Ð»Ñ Â«ÑедакÑиÑÑемÑÑ
» полей Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¾ полÑзоваÑелем. Ðогда полÑзоваÑÐµÐ»Ñ Ð½Ð°Ð¶Ð¸Ð¼Ð°ÐµÑ ÐºÐ½Ð¾Ð¿ÐºÑ Â«ÐÑпÑавиÑÑ» (надпиÑÑ Ð½Ð° ней, в пÑинÑипе, можно измениÑÑ), Ñо бÑаÑÐ·ÐµÑ Ð¾Ð±ÑединÑÐµÑ Ð²Ñе даннÑе полей в паÑÑ name=value, ÑазделÑÑ Ð¸Ñ
Ñимволом &. ÐаÑем полÑÑÐµÐ½Ð½Ð°Ñ Ñаким обÑазом ÑÑÑока пеÑедаеÑÑÑ Ð½Ð° ÑеÑÐ²ÐµÑ Ð¼ÐµÑодом, ÑказаннÑм в аÑÑибÑÑе method Ñега <FORM>. ÐÑÑÑ Ðº ÑÑенаÑиÑ, коÑоÑÑй бÑÐ´ÐµÑ Ð·Ð°Ð½Ð¸Ð¼Ð°ÑÑÑÑ ÐµÐµ обÑабоÑкой, задаеÑÑÑ Ð°ÑÑибÑÑом action ÑÑого же Ñега. ÐÑли action не задан, Ñо даннÑе пеÑедаÑÑÑÑ ÑайлÑ, ÑÑоÑмиÑовавÑÐµÐ¼Ñ ÑекÑÑÑÑ ÑÑÑаниÑкÑ.<br />
<br />
ÐÑли ÑÑо-Ñо не ÑовÑем понÑÑно, обÑаÑиÑеÑÑ Ðº ÐºÐ¾Ð´Ñ ÑазÑабаÑÑваемой гоÑÑевой книги, коÑоÑÑй пÑиведен ниже.<br />
<br />
=== ÐÐ°Ñ ÑпаÑиÑÐµÐ»Ñ â модÑÐ»Ñ cgi ===<br />
ÐозвÑаÑаемÑÑ Ðº обÑабоÑке вÑего ÑÑого добÑа, коÑоÑое ÑоÑни полÑзоваÑелей Ñже гоÑÐ¾Ð²Ñ Ð¾Ð±ÑÑÑиÑÑ Ð½Ð° Ð½Ð°Ñ Ð±ÐµÐ´Ð½Ñй ÑÑенаÑий. ÐÑ ÑеÑили воÑполÑзоваÑÑÑÑ ÑÑандаÑÑнÑми ÑÑедÑÑвами Python, и здеÑÑ Ð²Ñе дейÑÑвиÑелÑно оÑÐµÐ½Ñ Ð¿ÑоÑÑо â импоÑÑиÑÑйÑе модÑÐ»Ñ cgi и, Ñоздав обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage, Ð²Ñ Ð¿Ð¾Ð»ÑÑиÑе ÑеÑез него доÑÑÑп ко вÑем даннÑм, пеÑеданнÑм полÑзоваÑелем, незавиÑимо Ð¾Ñ Ð¸ÑполÑзÑемого меÑода:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÐеÑÐµÐ¼ÐµÐ½Ð½Ð°Ñ %s Ð¸Ð¼ÐµÐµÑ Ð·Ð½Ð°Ñение %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÐÑли вам нÑжно полÑÑиÑÑ Ð·Ð½Ð°Ñение опÑеделенного полÑ, ÑÑо делаеÑÑÑ Ñак:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
Ðомимо полÑзоваÑелÑÑкиÑ
даннÑÑ
, обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage ÑодеÑÐ¶Ð¸Ñ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸ о полÑÑ
заголовка (в наÑем пÑимеÑе иÑ
можно полÑÑиÑÑ Ð¸Ð· ÑловаÑÑ data.headers). MIME-Ñип даннÑÑ
(пеÑедаваемÑй полем заголовка Content-Type) можно полÑÑиÑÑ Ð¸Ð· аÑÑибÑÑа data.type. ЧеÑез ÑÑÐ¾Ñ Ð¶Ðµ обÑÐµÐºÑ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð²Ñполнена и загÑÑзка Ñайла.<br />
<br />
С помоÑÑÑ Ð¼ÐµÑодов keys() и has_key() можно вÑполнÑÑÑ Ð¾Ð±ÑабоÑÐºÑ Ð¿Ð¾Ð»ÑÑеннÑÑ
даннÑÑ
в Ñикле и пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие Ñой или иной пеÑеменной. ÐÑÑаÑи говоÑÑ, пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие пеÑеменной во вÑ
однÑÑ
даннÑÑ
, пÑежде Ñем пÑиÑÑÑпаÑÑ Ðº иÑ
обÑабоÑке, нÑжно непÑеменно â Ð²ÐµÐ´Ñ Ð·Ð°Ð¿ÑÐ¾Ñ ÑоÑмиÑÑеÑÑÑ ÐºÐ»Ð¸ÐµÐ½Ñом, а кÑо знаеÑ, ÑÑо Ñ Ð½ÐµÐ³Ð¾ на Ñме?<br />
<br />
=== ÐазиÑÑем даннÑе ===<br />
ÐÑак, полÑÑаÑÑ Ð´Ð°Ð½Ð½Ñе Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа Ð¼Ñ Ð½Ð°ÑÑилиÑÑ. ÐÑпÑавлÑÑÑ Ñоже Ñмеем. ÐÑÑалоÑÑ Ð¿ÑидÑмаÑÑ, как ÑÑи даннÑе лÑÑÑе вÑего Ñ
ÑаниÑÑ. ÐонеÑно, Ð´Ð»Ñ Ð½ÐµÑложной гоÑÑевой книги Ñ Ð½ÐµÐ±Ð¾Ð»ÑÑой нагÑÑзкой вполне Ñ
ваÑило Ð±Ñ Ð¸ ÑекÑÑовÑÑ
Ñайлов. ÐÑавда, Ñам еÑÑÑ Ñвои ÑложноÑÑи â еÑли ÑÑÐ°Ð·Ñ Ð¿ÑÑÑ Ñеловек заÑ
оÑÑÑ Ð²ÑÑказаÑÑ Ñвое мнение о ваÑей кÑÑÑейÑей домаÑней ÑÑÑаниÑке, Ñо ÑÑенаÑÐ¸Ñ Ð¿ÑидеÑÑÑ ÐºÐ°ÐºÐ¸Ð¼-Ñо обÑазом ÑегÑлиÑоваÑÑ Ð´Ð¾ÑÑÑп к ÑайлÑ-Ñ
ÑанилиÑÑ (как минимÑм, обÑабаÑÑваÑÑ ÑиÑÑаÑиÑ, еÑли Ñайл Ñже оÑкÑÑÑ Ð½Ð° запиÑÑ Ð´ÑÑгим ÑкземплÑÑом ÑÑенаÑиÑ). Ðо заÑем нам вÑе ÑÑи головнÑе боли? ÐÑли Ð¼Ñ Ñак ловко оÑвеÑÑелиÑÑ Ð¾Ñ Ð½ÐµÐ¾Ð±Ñ
одимоÑÑи вÑÑÑнÑÑ ÑазбиÑаÑÑ HTTP-запÑоÑÑ, Ñо неÑжели не найдем ÑÑо-Ñо подÑ
одÑÑее на ÑÑÐ¾Ñ Ñаз?<br />
<br />
ÐонеÑно, найдем! Ð ÑÑо «ÑÑо-Ñо» назÑваеÑÑÑ ÑиÑÑемой ÑпÑÐ°Ð²Ð»ÐµÐ½Ð¸Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
(в пÑоÑÑоÑеÑÑе â СУÐÐ). ТепеÑÑ Ð½Ð°Ñе дело â оÑпÑавиÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð¸ полÑÑиÑÑ Ð¾ÑвеÑ. ÐÑе оÑÑалÑное â Ñже не наÑа забоÑа.<br />
<br />
ÐÐ»Ñ ÑÑого пÑимеÑа Ñ Ð²ÑбÑал в каÑеÑÑве «оÑвеÑÑÑвенного» за Ñ
Ñанение даннÑÑ
ÑеÑÐ²ÐµÑ Ð±Ð°Ð· даннÑÑ
PostgreSQL. ÐоÑколÑÐºÑ Ð¼Ñ Ð¿Ð¸Ñем Ð½Ñ Ð¾ÑÐµÐ½Ñ Ð¿ÑоÑÑÑÑ Ð³Ð¾ÑÑевÑÑ ÐºÐ½Ð¸Ð³Ñ, Ñо и ÑÑÑÑкÑÑÑа Ð±Ð°Ð·Ñ Ð±ÑÐ´ÐµÑ Ñ Ð½Ð°Ñ ÑлеменÑаÑной â одна ÑаблиÑа Ñ ÑÑÐµÐ¼Ñ Ð¿Ð¾Ð»Ñми: вÑÐµÐ¼Ñ Ð¿ÑбликаÑии ÑообÑениÑ, Ð¸Ð¼Ñ Ð°Ð²ÑоÑа и, ÑобÑÑвенно, Ñамо ÑообÑение:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÐÑ Ð¿Ð¾Ð´ÑоединилиÑÑ Ðº базе даннÑÑ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÐожалÑй, единÑÑвенное, ÑÑо здеÑÑ Ð½Ñжно поÑÑниÑÑ, ÑÑо поÑÐµÐ¼Ñ Ð±Ð°Ð·Ðµ и ÑаблиÑе Ð¼Ñ Ð½Ð°Ð·Ð½Ð°Ñили владелÑÑем полÑзоваÑÐµÐ»Ñ www-data. ÐÑоÑÑо к ним бÑÐ´ÐµÑ Ð¾Ð±ÑаÑаÑÑÑÑ cgi-ÑÑенаÑий, ÑабоÑаÑÑий Ñ Ð¿Ñавами HTTP-ÑеÑвеÑа Apache, коÑоÑÑй, в ÑÐ²Ð¾Ñ Ð¾ÑеÑедÑ, иÑполнÑеÑÑÑ Ð¾Ñ Ð¸Ð¼ÐµÐ½Ð¸ данного полÑзоваÑÐµÐ»Ñ [в ваÑем диÑÑÑибÑÑиве он Ð¼Ð¾Ð¶ÐµÑ Ð½Ð°Ð·Ð²Ð°ÑÑÑÑ Ð¿Ð¾-дÑÑгомÑ, â пÑим. Ñед.]. Ð PostgreSQL по ÑмолÑÐ°Ð½Ð¸Ñ ÑÑебÑеÑ, ÑÑÐ¾Ð±Ñ Ð¸Ð¼Ñ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð² ÐÐ Ñовпадало Ñ ÐµÐ³Ð¾ ÑиÑÑемнÑм именем. Ðне ÑÑо кажеÑÑÑ Ð´Ð¾ÑÑаÑоÑно ÑдобнÑм, Ñ
оÑÑ Ð²Ñ, конеÑно, можеÑе поÑÑÑпиÑÑ Ð¿Ð¾-ÑвоемÑ.<br />
<br />
=== DB API на ÑÑÑаже ÑниÑикаÑии ===<br />
ÐÑÑалоÑÑ ÑазобÑаÑÑÑÑ, как же Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
. ÐÐ»Ñ ÑÑого Python пÑедоÑÑавлÑÐµÑ DB API â ÑпеÑиалÑнÑй инÑеÑÑейÑ, ÑниÑиÑиÑÑÑÑий Ð½Ð°Ð±Ð¾Ñ Ð¼ÐµÑодов, коÑоÑÑе бÑдÑÑ Ð¾Ð´Ð¸Ð½Ð°ÐºÐ¾Ð²Ð¾ ÑабоÑаÑÑ Ð½ÐµÐ·Ð°Ð²Ð¸Ñимо Ð¾Ñ Ñого, Ñ ÐºÐ°ÐºÐ¾Ð¹ СУÐÐ Ð¼Ñ Ð²Ð·Ð°Ð¸Ð¼Ð¾Ð´ÐµÐ¹ÑÑвÑем. ÐÐ»Ñ ÑабоÑÑ Ñ PostgreSQL нам понадобиÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ PyPgSQL (в ÑÑандаÑÑной поÑÑавке его Ð¼Ð¾Ð¶ÐµÑ Ð½Ðµ оказаÑÑÑÑ, но Ð²Ð°Ñ Ð¼ÐµÐ½ÐµÐ´Ð¶ÐµÑ Ð¿Ð°ÐºÐµÑов навеÑнÑка бÑÐ´ÐµÑ Ð² кÑÑÑе, как его ÑÑÑановиÑÑ; кÑÑаÑи, ÑÑо не единÑÑвеннÑй модÑÐ»Ñ â Ñ Ð²Ð°Ñ, возможно, бÑÐ´ÐµÑ PyGreSQL, коÑоÑÑй ÑабоÑÐ°ÐµÑ Ð½Ð¸ÑÑÑÑ Ð½Ð¸ Ñ
Ñже и Ñ Ñеми же ÑамÑми меÑодами).<br />
<br />
DB API опÑеделÑÐµÑ ÑÑандаÑÑнÑе меÑÐ¾Ð´Ñ ÑабоÑÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, Ñак ÑÑо, какой Ð±Ñ Ð¼Ð¾Ð´ÑÐ»Ñ Ð²Ñ Ð½Ð¸ загÑÑзили и Ñ ÐºÐ°ÐºÐ¾Ð¹ Ð±Ñ Ð¡Ð£ÐРни ÑабоÑали (бÑÐ´Ñ Ñо MySQL, PostgreSQL, SQLite или ÑÑо-Ñо еÑе), менÑÑÑÑÑ Ð±ÑÐ´ÐµÑ ÑолÑко Ð¸Ð¼Ñ Ð¼Ð¾Ð´ÑлÑ. Ðлавное, ÑÑÐ¾Ð±Ñ Ð¸ÑполÑзÑемÑй модÑÐ»Ñ ÑооÑвеÑÑÑвовал DB API. РаÑÑмоÑÑим коÑоÑко оÑновнÑе меÑодÑ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
Так оÑÑÑеÑÑвлÑеÑÑÑ Ð¿Ð¾Ð´ÐºÐ»ÑÑение к базе. РзавиÑимоÑÑи Ð¾Ñ ÑиÑÑаÑии, вам Ð¼Ð¾Ð¶ÐµÑ Ð¿Ð¾ÑÑебоваÑÑÑÑ ÑказаÑÑ ÑолÑко нÑжнÑе паÑамеÑÑÑ (напÑимеÑ, Ð¸Ð¼Ñ Ñ
оÑÑа 'localhost' подÑазÑмеваеÑÑÑ Ð¿Ð¾ ÑмолÑаниÑ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÐÑÑÑоÑÑ Ð¿Ð¾Ð´Ð´ÐµÑживаÑÑÑÑ Ð´Ð°Ð»ÐµÐºÐ¾ не вÑеми СУÐÐ, но Ð´Ð»Ñ Ð¾Ð±ÑноÑÑи в DB API они Ð²Ð²ÐµÐ´ÐµÐ½Ñ Ð¸, в ÑлÑÑае необÑ
одимоÑÑи, Ð´Ð¾Ð»Ð¶Ð½Ñ ÑмÑлиÑоваÑÑÑÑ Ð¼Ð¾Ð´ÑлÑми ÑопÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸ÑкÑÑÑÑвенно. Так ÑÑо не забÑвайÑе оÑпÑавлÑÑÑ Ð²Ñе ваÑи запÑоÑÑ ÑеÑез кÑÑÑоÑ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
Так вÑполнÑеÑÑÑ SQL-запÑоÑ. ÐÑли в ÑÑÑоке запÑоÑа иÑполÑзÑÑÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼ÐµÑÑа %s, Ñо вÑоÑÑм паÑамеÑÑом пеÑедаеÑÑÑ ÑпиÑок пеÑеменнÑÑ
-знаÑений, пÑиÑем в SQL-запÑоÑе знакомеÑÑа не ÑÑебÑеÑÑÑ Ð¾ÐºÑÑжаÑÑ Ð°Ð¿Ð¾ÑÑÑоÑами â модÑÐ»Ñ ÑÐ´ÐµÐ»Ð°ÐµÑ ÑÑо ÑамоÑÑоÑÑелÑно в завиÑимоÑÑи оÑ<br />
Ñипа пеÑеменной.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÐозвÑаÑÐ°ÐµÑ Ð´Ð²ÑмеÑнÑй ÑпиÑок (ÑÑÑоки â полÑ) полÑÑеннÑÑ
Ð¾Ñ Ð¡Ð£ÐРданнÑÑ
. СÑÑеÑÑвÑÑÑ Ð¸ дÑÑгие меÑодÑ, ознакомиÑÑÑÑ Ñ ÐºÐ¾ÑоÑÑми Ð²Ñ ÑможеÑе в докÑменÑаÑии или Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼Ð¾Ð¹ вам ÑÑнкÑии dir() да паÑÑ-ÑÑойки неÑложнÑÑ
ÑкÑпеÑименÑов.<br />
<br />
=== ÐакÑеплÑем на пÑакÑике ===<br />
ÐеÑейдем к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ Ð½Ð°Ñего пÑимеÑа. ÐаÑнем ÑÑандаÑÑно â Ñкажем кодиÑовкÑ, подклÑÑим нÑжнÑе модÑли:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
Ðалее, опÑеделим две ÑÑнкÑии. ÐеÑÐ²Ð°Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° добавление нового ÑообÑÐµÐ½Ð¸Ñ Ð² базÑ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
Ðак видиÑе, вÑе оÑÐµÐ½Ñ Ð´Ð°Ð¶Ðµ логиÑно: ÑÑÑанавливаем Ñоединение Ñ ÐÐ (поÑколÑÐºÑ Ð² наÑем ÑлÑÑае подклÑÑение вÑполнÑеÑÑÑ Ñ Ð¸Ð¼ÐµÐ½ÐµÐ¼ ÑекÑÑего ÑиÑÑемного полÑзоваÑелÑ, Ñо доÑÑаÑоÑно ÑказаÑÑ ÑолÑко Ð¸Ð¼Ñ Ð±Ð°Ð·Ñ), Ñоздаем кÑÑÑÐ¾Ñ (в PostgreSQL они не пÑименÑÑÑÑÑ, но они ÑмÑлиÑÑÑÑÑÑ ÐºÐ°Ð¶Ð´Ñм модÑлем, пÑеÑендÑÑÑим на ÑооÑвеÑÑÑвие DB API), вÑполнÑеÑÑÑ Ð·Ð°Ð¿ÑоÑ, закÑÑваеÑÑÑ ÐºÑÑÑоÑ, ÑикÑиÑÑÑÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ (PostgreSQL иÑполÑзÑÐµÑ ÑÑанзакÑии, поÑÑÐ¾Ð¼Ñ Ð²Ñполнение меÑода commit() обÑзаÑелÑно, инаÑе ваÑи Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ Ð½Ðµ бÑдÑÑ ÑоÑ
ÑаненÑ), и, наконеÑ, закÑÑваем Ñамо Ñоединение Ñ Ð±Ð°Ð·Ð¾Ð¹. Рполе datum заноÑим знаÑение вÑÑÑоенной пеÑеменной PostgreSQL â now, коÑоÑÐ°Ñ ÐºÐ°Ð¶Ð´Ñй Ñаз заменÑеÑÑÑ ÑекÑÑим знаÑением даÑÑ Ð¸ вÑемени.<br />
<br />
ÐÑ Ð¸ пеÑаÑÑ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° «Location» вÑполнÑеÑÑÑ Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð¿ÐµÑенапÑавиÑÑ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð½Ð° ÑÑÐ¾Ñ Ð¶Ðµ ÑÑенаÑий, но Ñже без паÑамеÑÑов â Ð¼Ñ Ð¶Ðµ Ð´Ð¾Ð»Ð¶Ð½Ñ Ð¿Ð¾ÐºÐ°Ð·Ð°ÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ, ÑÑо он на Ñамом деле ввел? (ЯкоÑÑ #form иÑполÑзÑеÑÑÑ, ÑÑÐ¾Ð±Ñ Ð°Ð²ÑомаÑиÑеÑки пÑокÑÑÑиÑÑ ÑÑÑаниÑÐºÑ Ð½Ð° поÑледнее ÑообÑение).<br />
<br />
ÐÑоÑÐ°Ñ ÑÑнкÑÐ¸Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° вÑвод на ÑкÑан Ñже оÑÑавленнÑÑ
в книге запиÑей, а Ñакже за ÑоÑмÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ ÐºÐ¾ÑоÑой можно бÑÐ´ÐµÑ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ Ð¸ Ñвое вÑÑказÑвание:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
Ð ÑÑом ÑÑагменÑе Ð¼Ñ Ð²ÑбиÑаем вÑе ÑÑÑоки из наÑей ÑаблиÑÑ Ð´Ð°Ð½Ð½ÑÑ
, ÑоÑÑиÑÑÑ Ð¸Ñ
по даÑе. РезÑлÑÑÐ°Ñ ÑоÑ
ÑанÑеÑÑÑ Ð² пеÑеменной res, Ñ ÐºÐ¾ÑоÑой и бÑдем ÑабоÑаÑÑ. ТепеÑÑ Ð¾ÑÑалоÑÑ Ð»Ð¸ÑÑ Ð°ÐºÐºÑÑаÑненÑко ÑазложиÑÑ Ð½Ð°Ñи даннÑе по ÑаблиÑкам и вÑвеÑÑи иÑ
на ÑкÑан:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÐелÑкам к нам в гоÑÑи!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>ТоваÑÐ¸Ñ <B>%s</B> поведалнам ÑледÑÑÑее:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÐÑиÑоединÑйÑеÑÑ Ðº диÑкÑÑÑии:</H3>"<br />
print """<FORM method='GET'><br />
ÐаÑе имÑ: <INPUT type='text' name='author'><BR><br />
ЧÑо Ð²Ñ Ð´ÑмаеÑе по ÑÑÐ¾Ð¼Ñ Ð¿Ð¾Ð²Ð¾Ð´Ñ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÐÑпÑавиÑÑ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÐзобÑажение:Img 83 81 1.png|thumb|Ðи Ñмайликов, ни BB-кода, ни даже логоÑипа... ÐаÑо Ð¼Ñ Ñделали ÑÑÑ Ð³Ð¾ÑÑевÑÑ Ð·Ð° 10 минÑÑ!]]<br />
<br />
СмÑÑл конÑÑÑÑкÑии str(item[0])[:19] заклÑÑаеÑÑÑ Ð² Ñом, ÑÑÐ¾Ð±Ñ Ð² ÑÑÑоке вÑемени оÑÑеÑÑ Ð½ÐµÐ½ÑжнÑе нам миллиÑекÑндÑ, коÑоÑÑе ÑоÑ
ÑанÑÑÑÑÑ Ð² поле Ñипа timestamp. ÐоÑле вÑеÑ
опÑбликованнÑÑ
ÑообÑений вÑводим ÑоÑÐ¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð»ÐµÐ½Ð¸Ñ Ð½Ð¾Ð²Ð¾Ð³Ð¾, ÑÑÐ¾Ð±Ñ ÐºÐ°Ð¶Ð´Ñй мог пÑиÑоединиÑÑÑÑ Ðº наÑей диÑкÑÑÑии. ÐÑÑаÑи, в Ñеге <FORM> Ð¼Ñ Ð½Ðµ Ñказали паÑамеÑÑ action, поÑколÑÐºÑ Ð´Ð°Ð½Ð½Ñе бÑдÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð½Ð° обÑабоÑÐºÑ ÑÑÐ¾Ð¼Ñ Ð¶Ðµ ÑÑенаÑÐ¸Ñ (благодаÑÑ ÑÐµÐ¼Ñ Ð¸Ð¼Ñ ÑÑенаÑÐ¸Ñ Ð¼Ð¾Ð¶Ð½Ð¾ пÑиÑвоиÑÑ Ð»Ñбое).<br />
ÐаконеÑ, поÑледний ÑÑагменÑ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
Создаем FieldStorage-обÑекÑ, и еÑли в нем еÑÑÑ Ð·Ð°Ð¿Ð¾Ð»Ð½ÐµÐ½Ð½Ñе Ð¿Ð¾Ð»Ñ message и author (Ñо еÑÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð±Ñл ÑÑоÑмиÑован из заполненной полÑзоваÑелем ÑоÑмÑ), Ñо, немножко иÑ
обÑабоÑав (ÑÑнкÑÐ¸Ñ cgi.escape() заменÑÐµÑ Ð²Ñе «неблагонадежнÑе» ÑÐ¸Ð¼Ð²Ð¾Ð»Ñ â напÑимеÑ, < â иÑ
ÑÑандаÑÑнÑми SGML-ÑÑÑноÑÑÑми, в данном ÑлÑÑае â &lt;), пеÑедаем ÑÑнкÑии addMessage(). ÐбÑабоÑка нÑжна Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð·Ð»Ð¾ÑмÑÑленник не мог ввеÑÑи в поле ÑообÑÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ имени авÑоÑа ÑÑо-нибÑÐ´Ñ Ñакое:<br />
<br />
<SCRIPT>alert('Ðа поÑли Ð²Ñ Ð²Ñе!');</SCRIPT><br />
<br />
Ð ÑловÑ, пÑенебÑегаÑÑ Ð¿ÑовеÑкой введеннÑÑ
даннÑÑ
ни в коем ÑлÑÑае нелÑзÑ. ÐайдиÑе как-нибÑÐ´Ñ Ð½Ð° [http://securitylab.ru securitylab.ru] и поÑмоÑÑиÑе, ÑколÑко ÑÑзвимоÑÑей Ñипа «XSS» обнаÑÑживаеÑÑÑ ÐºÐ°Ð¶Ð´Ñй меÑÑÑ! Так ÑÑо ÑÑÑки ÑÑÑками, но поÑледÑÑÐ²Ð¸Ñ Ð¼Ð¾Ð³ÑÑ Ð±ÑÑÑ Ð¾ÑÐµÐ½Ñ ÑеÑÑезнÑми.<br />
<br />
=== ÐÑда же нам ÑепеÑÑ Ð¸Ð´Ñи? ===<br />
ÐÑак, ÑÑо-Ñо вполне ÑабоÑоÑпоÑобное Ñ Ð½Ð°Ñ ÐµÑÑÑ (Ñм. [[LXF83:Python#img|ÑиÑÑнок]]). Ðо как Ð²Ñ Ð¼Ð¾Ð¶ÐµÑ Ð´Ð¾Ð³Ð°Ð´Ð°ÑÑÑÑ, наÑа гоÑÑÐµÐ²Ð°Ñ Ð¾ÑÐµÐ½Ñ Ð´Ð°Ð»ÐµÐºÐ° Ð¾Ñ ÑовеÑÑенÑÑва. ЧÑо еÑе можно ÑделаÑÑ? ÐÑ, напÑимеÑ, ÑазбиÑÑ Ð½Ð° ÑÑÑаниÑÑ. Ðока ÑообÑений в ней бÑÐ´ÐµÑ Ð½Ðµ болÑÑе дÑжинÑ, ÑÐ¾Ð¹Ð´ÐµÑ Ð¸ Ñак. Ркогда иÑ
ÑиÑло Ð´Ð¾Ð¹Ð´ÐµÑ Ð´Ð¾ ÑоÑни, Ñо Ñедкий полÑзоваÑÐµÐ»Ñ Ð´Ð¾Ð¶Ð´ÐµÑÑÑ Ð¾ÐºÐ¾Ð½ÑÐ°Ð½Ð¸Ñ Ð·Ð°Ð³ÑÑзки вÑеÑ
даннÑÑ
. Ðожно даÑÑ Ð¿Ð¾Ð»ÑзоваÑелÑм возможноÑÑÑ Ð¸ÑполÑзоваÑÑ Ð½ÐµÐºÐ¾ÑоÑÑе HTML-Ñеги, ÑÑÐ¾Ð±Ñ Ð¸Ñ
ÑообÑÐµÐ½Ð¸Ñ Ð²ÑглÑдели более кÑаÑоÑно. Ðожно добавиÑÑ Ñмайликов... Рможно даже ÑделаÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ Ð°Ð´Ð¼Ð¸Ð½Ð¸ÑÑÑиÑованиÑ, позволÑÑÑий ÑедакÑиÑоваÑÑ Ð¸Ð»Ð¸ ÑдалÑÑÑ ÑообÑениÑ, а Ñакже оÑвеÑаÑÑ Ð½Ð° ниÑ
. Так ÑÑо ÑабоÑÑ Ð½ÐµÐ¿Ð¾ÑаÑÑй кÑай. ÐеÑзайÑе â не бÑÐ´Ñ Ð²Ð°Ð¼ меÑаÑÑ.<br />
<br />
=== ÐекоÑоÑÑе ÑаÑпÑоÑÑÑанÑннÑе MIME-ÑÐ¸Ð¿Ñ ===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-Ñип<br />
! ÐпиÑание<br />
|-<br />
| text/plain<br />
| ÐÑоÑÑой ÑекÑÑ<br />
|-<br />
| text/html<br />
| HTML-ÑÑÑаниÑа<br />
|-<br />
| image/gif<br />
| ÐзобÑажение GIF<br />
|-<br />
| video/mpeg<br />
| Ðидео-Ñайл в ÑоÑмаÑе MPEG<br />
|-<br />
| application/msword <br />
| ÐокÑÐ¼ÐµÐ½Ñ MS Word<br />
|}</div>
RicroAcdom
http://wiki.linuxformat.ru/wiki/LXF83:Python
LXF83:Python
2009-05-21T23:00:48Z
<p>RicroAcdom: </p>
<hr />
<div>http://www.textalmoncnad.com <br />
{{Цикл/Python}}<br />
<br />
== РабоÑа Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
и web-пÑогÑаммиÑование ==<br />
'' '''ЧаÑÑÑ 3''' ЧÑо Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¼Ð¾Ñнее ÑвÑзки «база даннÑÑ
+ инÑеÑнеÑ»? РеÑли к ÑÑÐ¾Ð¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ ÐµÑе и Python... ЧÑÐ¾Ð±Ñ Ð¿Ð¾ÑÑвÑÑвоваÑÑ Ð²Ñе ÑÑо на пÑакÑике, погÑÑзимÑÑ ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð² пÑÑÐ¸Ð½Ñ SQL-запÑоÑов и HTTP-оÑвеÑов вмеÑÑе Ñ '''СеÑгеем СÑпÑÑновÑм'''.''<br />
<br />
ÐÑ Ñже видели, ÑÑо Python пÑекÑаÑно подÑ
Ð¾Ð´Ð¸Ñ Ð´Ð»Ñ ÑабоÑÑ Ñ ÑекÑÑом. Ð ÑÑо Ñакое инÑеÑнеÑ-ÑÑÑаниÑÑ, коÑоÑÑе Ð¼Ð¸Ð»Ð»Ð¸Ð¾Ð½Ñ ÑеÑвеÑов Apache ежедневно миллиаÑдами оÑдаÑÑ Ð½Ð° ÑаÑÑеÑзание наÑим бÑаÑзеÑам? Ðо ÑÑÑи, ÑÐ¾Ñ Ð¶Ðµ ÑекÑÑ, ÑолÑко немножко «гипеÑ»... РзнаÑиÑ, еÑли нам нÑжно бÑÐ´ÐµÑ ÑоÑмиÑоваÑÑ html-ÑÑÑаниÑÑ Ð´Ð¸Ð½Ð°Ð¼Ð¸ÑеÑки, Ñо Python пÑекÑаÑно Ñ ÑÑим ÑпÑавиÑÑÑ. РникакиÑ
пÑепÑÑÑÑвий Ð´Ð»Ñ ÑазÑабоÑки на нем CGI-ÑÑенаÑиев не ÑÑÑеÑÑвÑÐµÑ â web-ÑеÑвеÑÑ, по болÑÑÐ¾Ð¼Ñ ÑÑеÑÑ, безÑазлиÑно, как именно вÑполнÑеÑÑÑ ÑкÑÐ¸Ð¿Ñ Ð¸ на каком ÑзÑке он ÑазÑабоÑан: лиÑÑ Ð±Ñ Ð¾Ð½ Ñмел ÑиÑаÑÑ Ð´Ð°Ð½Ð½Ñе из поÑока ввода и пеÑеменнÑÑ
окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð´Ð° оÑдаваÑÑ ÑекÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок.<br />
<br />
ÐпÑоÑем, еÑли Ð²Ñ Ð¶Ð°Ð¶Ð´ÐµÑе ÑкоÑоÑÑи, Ñо к ваÑим ÑÑлÑгам mod_Python, да и в Ñежиме FastCGI Python ÑабоÑаÑÑ ÑмееÑ. Ðо ÑейÑÐ°Ñ Ñ Ð½Ð°Ñ ÑÐ°Ð·Ð³Ð¾Ð²Ð¾Ñ Ð²Ñе же не о наÑÑÑойкаÑ
CGI, а о Python, Ñак ÑÑо веÑнемÑÑ Ðº ÑомÑ, Ñади Ñего Ð¼Ñ ÑÑÑ ÑÑаÑÑÑ Ð½Ð°Ñали.<br />
<br />
=== ÐоÑÑановка задаÑи ===<br />
С лÑбÑм вопÑоÑом лÑÑÑе вÑего ÑазбиÑаÑÑÑÑ Ð½Ð° пÑакÑиÑеÑком пÑимеÑе. ÐоÑÑÐ¾Ð¼Ñ Ð¼Ñ Ð±Ñдем «плÑÑаÑÑ» вокÑÑг неÑложного и, в обÑем-Ñо, доÑÑаÑоÑно баналÑного CGI-пÑиложениÑ: гоÑÑевой книги. Ðаодно ÑазбеÑемÑÑ Ñ Ñем, как Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, где пÑедÑÑавлÑеÑÑÑ ÑазÑмнÑм Ñ
ÑаниÑÑ Ð²Ñе наÑи ÑообÑениÑ.<br />
<br />
Ðо пÑежде Ñем пеÑейÑи к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ ÐºÐ¾Ð´Ð° (Ð²Ñ Ð½Ð°Ð¹Ð´ÐµÑе его Ñеликом на наÑем диÑке), полезно бÑÐ´ÐµÑ Ð´Ð°ÑÑ ÐºÐ¾Ðµ-какÑÑ Ð²Ð²Ð¾Ð´Ð½ÑÑ Ð¸Ð½ÑоÑмаÑиÑ.<br />
<br />
=== УнивеÑÑалÑное «междÑмоÑдÑе» CGI ===<br />
CGI (Common Gateway Interface, обÑий ÑлÑзовой инÑеÑÑейÑ) бÑл ÑазÑабоÑан как ÑÑедÑÑво взаимодейÑÑÐ²Ð¸Ñ HTTP-ÑеÑвеÑа Ñ Ð¿ÑогÑаммами, коÑоÑÑе могÑÑ Ð·Ð°Ð¿ÑÑкаÑÑÑÑ Ð² опеÑаÑионной ÑиÑÑеме. ÐÑли говоÑиÑÑ ÑпÑоÑенно, Ñо CGI, пеÑÐµÐ´Ð°Ð²Ð°Ñ ÑпÑавление Ñакой пÑогÑамме (обÑÑно иÑ
именÑÑÑ cgi-ÑÑенаÑиÑми, Ñ
оÑÑ ÑÑо вполне Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸ двоиÑнÑй Ñайл, ÑазÑабоÑаннÑй на C/C++), ÑоÑмиÑÑÐµÑ Ð´Ð»Ñ Ð½ÐµÐµ опÑеделенное окÑÑжение. Ð ÑаÑÑноÑÑи, паÑамеÑÑÑ HTTP-запÑоÑа, полÑÑенного Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа, могÑÑ Ð¿Ð¾Ð¼ÐµÑаÑÑÑÑ Ð² опÑеделеннÑе пеÑеменнÑе окÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ пеÑедаваÑÑÑÑ cgi-пÑогÑамме как аÑгÑменÑÑ Ð¸Ð»Ð¸ как вÑ
одной поÑок (STDIN). РоÑÐ²ÐµÑ HTTP-ÑеÑÐ²ÐµÑ Ð¶Ð´ÐµÑ Ð´Ð°Ð½Ð½Ñе, коÑоÑÑе cgi-пÑогÑамма должна вÑдаÑÑ Ð² ÑÑандаÑÑнÑй вÑÑ
одной поÑок (STDOUT), и пеÑÐµÐ´Ð°ÐµÑ Ð¸Ñ
клиенÑÑ.<br />
<br />
Таким обÑазом, вÑе, ÑÑо ÑÑебÑеÑÑÑ Ð¾Ñ cgi-пÑогÑаммÑ, ÑÑо ÑпоÑобноÑÑÑ Ð¿Ð¾Ð»ÑÑаÑÑ Ð½ÐµÐ¾Ð±Ñ
одимÑÑ Ð´Ð»Ñ ÑабоÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸Ð· ÑоÑмиÑÑемой HTTP-ÑеÑвеÑом ÑÑÐµÐ´Ñ Ð¸ возвÑаÑаÑÑ Ð¾ÑвеÑнÑе даннÑе, ÑооÑвеÑÑÑвÑÑÑие пÑоÑÐ¾ÐºÐ¾Ð»Ñ HTTP, ÑÑÐ¾Ð±Ñ web-ÐºÐ»Ð¸ÐµÐ½Ñ Ð·Ð½Ð°Ð», ÑÑо Ñ Ð½Ð¸Ð¼Ð¸ делаÑÑ.<br />
<br />
=== УÑимÑÑ Ð¿Ð¾ÑÑлаÑÑ ===<br />
ÐаÑнем Ñ ÑоÑмиÑÐ¾Ð²Ð°Ð½Ð¸Ñ HTTP-оÑвеÑа. ЧÑÐ¾Ð±Ñ Ð±ÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа мог его пÑавилÑно обÑабоÑаÑÑ, он должен ÑоÑÑоÑÑÑ Ð¸Ð· заголовка и Ñела, ÑазделеннÑÑ
пÑÑÑой ÑÑÑокой. Рзаголовке пеÑедаеÑÑÑ Ð½ÐµÐ¾Ð±Ñ
Ð¾Ð´Ð¸Ð¼Ð°Ñ ÑлÑÐ¶ÐµÐ±Ð½Ð°Ñ Ð¸Ð½ÑоÑмаÑиÑ, напÑимеÑ, Ñип ÑодеÑжимого, его кодиÑовка, Ñказание бÑаÑзеÑÑ Ð·Ð°Ð¿ÑоÑиÑÑ Ð´ÑÑгой ÑеÑÑÑÑ (Ñак назÑваемое пеÑенапÑавление), и Ñ.д. ÐÑоÑÑейÑий cgi-ÑÑенаÑий на ÑзÑке Python Ð¼Ð¾Ð¶ÐµÑ Ð²ÑглÑдеÑÑ Ñак:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
print 'Content-Type: text/html\n'<br />
print '<H3>ÐÑли Ð²Ñ ÑÑо видиÑе, знаÑÐ¸Ñ Ð²Ñе ÑабоÑаеÑ</H3>'<br />
</source><br />
<br />
ÐеÑвÑм опеÑаÑоÑом print Ð¼Ñ ÑоÑмиÑÑем минималÑно необÑ
одимÑй заголовок â бÑаÑÐ·ÐµÑ ÐºÐ»Ð¸ÐµÐ½Ñа обÑзаÑелÑно должен знаÑÑ, каков Ñип пеÑеÑÑлаемÑÑ
ÐµÐ¼Ñ Ð´Ð°Ð½Ð½ÑÑ
(в наÑем ÑлÑÑае ÑÑо пÑоÑÑой ÑекÑÑ, ÑооÑвеÑÑÑвÑÑÑий ÑоÑмаÑÑ HTML). Ðе забÑвайÑе о дополниÑелÑном пеÑеводе ÑÑÑоки \n, необÑ
одимом Ð´Ð»Ñ Ð¾ÑÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° Ð¾Ñ Ñела оÑвеÑа. ÐÑ Ð¸ далее Ð²Ñ Ð¼Ð¾Ð¶ÐµÑе пеÑедаваÑÑ Ð»Ñбой HTML-код.<br />
<br />
ÐналогиÑно могÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð»ÑбÑе обÑекÑÑ, поддеÑживаемÑе клиенÑом: изобÑажениÑ, звÑковÑе ÑайлÑ, css-ÑаблиÑÑ Ð¸ Ñ.д. Ðлавное, ÑÑÐ¾Ð±Ñ Ð·Ð½Ð°Ñение Ð¿Ð¾Ð»Ñ Content-Type (именÑемое Ñакже MIME-Ñипом) ÑооÑвеÑÑÑвовало ÑодеÑжимомÑ.<br />
<br />
=== ÐдеÑÑ Ð¸Ð³ÑаÑÑ, здеÑÑ Ð½Ðµ игÑаÑÑ... ===<br />
Ðднако какой ÑмÑÑл поÑÑÑаÑÑ ÑоÑмиÑование ÑÑаÑиÑеÑкиÑ
, по ÑÑÑи, ÑÑÑÐ°Ð½Ð¸Ñ cgi-ÑÑенаÑиÑ, еÑли Ñам HTTP-ÑеÑÐ²ÐµÑ ÑпÑавиÑÑÑ Ñ ÑÑим намного лÑÑÑе? РобÑем-Ñо никакого. Разве ÑÑо Ð´Ð»Ñ Ð¾Ð±Ñего ÑазвиÑиÑ... Ð Ð²Ð¾Ñ Ð² Ñем CGI по-наÑÑоÑÑÐµÐ¼Ñ Ñилен, Ñак ÑÑо в ÑоÑмиÑовании динамиÑеÑкиÑ
ÑÑÑаниÑ, ÑодеÑжимое коÑоÑÑÑ
завиÑÐ¸Ñ Ð¾Ñ Ð¸Ð½ÑоÑмаÑии, пеÑеданной полÑзоваÑелем.<br />
<br />
ÐÑоÑокол HTTP пÑедÑÑмаÑÑÐ¸Ð²Ð°ÐµÑ Ð½ÐµÑколÑко ÑпоÑобов пеÑедаÑи инÑоÑмаÑии Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа на ÑеÑвеÑ, назÑваемÑÑ
меÑодами. Ðаиболее попÑлÑÑнÑе из ниÑ
â GET, POST, PUT и HEAD.<br />
<br />
ÐеÑод GET позволÑÐµÑ Ð²ÑÑавлÑÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð² URL, Ñо еÑÑÑ Ð² ÑÑÑÐ¾ÐºÑ Ð°Ð´ÑеÑа запÑаÑиваемого ÑеÑÑÑÑа. Ðогда «ЯндекÑ» веÑÐ½ÐµÑ Ð²Ð°Ð¼ ÑпиÑок иÑкомÑÑ
ÑÑÑаниÑ, поÑмоÑÑиÑе на адÑеÑнÑÑ ÑÑÑÐ¾ÐºÑ Ð² бÑаÑзеÑе â Ð²Ð¾Ñ Ñак даннÑе и пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET. ÐÑÑаÑи, обÑаÑиÑе внимание на Ñо, как вÑе ÑÑо кодиÑÑеÑÑÑ, оÑобенно еÑли Ð²Ñ Ð¸Ñкали какое-Ñо ÑÑÑÑкое Ñлово.<br />
<br />
ÐÑли на ÑеÑÐ²ÐµÑ ÑÑебÑеÑÑÑ Ð¿ÐµÑедаÑÑ Ð±Ð¾Ð»ÑÑий обÑем инÑоÑмаÑии, или ее желаÑелÑно ÑкÑÑÑÑ Ð¾Ñ Ð»ÑбопÑÑнÑÑ
глаз, иÑполÑзÑеÑÑÑ Ð´ÑÑгой меÑод â POST. Рданном ÑлÑÑае в заголовке пеÑедаеÑÑÑ Ð»Ð¸ÑÑ ÑÐ°Ð·Ð¼ÐµÑ Ð¿Ð¾Ð»ÑзоваÑелÑÑкиÑ
даннÑÑ
, а Ñами даннÑе пеÑеÑÑлаÑÑÑÑ Ð² Ñеле запÑоÑа.<br />
<br />
ÐеÑод PUT пÑедназнаÑаеÑÑÑ Ð´Ð»Ñ ÑазмеÑÐµÐ½Ð¸Ñ ÑеÑÑÑÑов на ÑеÑвеÑе и по ÑообÑажениÑм безопаÑноÑÑи пÑакÑиÑеÑки не иÑполÑзÑеÑÑÑ. ÐÑ Ð¸, наконеÑ, меÑод HEAD оÑÐµÐ½Ñ Ð¿Ð¾Ñ
ож на GET, за Ñем иÑклÑÑением, ÑÑо ÑеÑÐ²ÐµÑ Ð² оÑÐ²ÐµÑ Ð½Ð° Ñакой запÑÐ¾Ñ Ð²Ð¾Ð·Ð²ÑаÑÐ°ÐµÑ Ð½Ðµ веÑÑ ÑеÑÑÑÑ, а лиÑÑ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¾ нем, ÑакÑÑ ÐºÐ°Ðº даÑа поÑледнего изменениÑ, помеÑаемÑÑ Ð² заголовке. ÐбÑÑно иÑполÑзÑеÑÑÑ Ð¿ÑокÑи-ÑеÑвеÑами Ð´Ð»Ñ Ð¾Ð¿ÑÐµÐ´ÐµÐ»ÐµÐ½Ð¸Ñ Â«ÑвежеÑÑи» имеÑÑиÑ
ÑÑ Ñ Ð½Ð¸Ñ
даннÑÑ
â ÑÑÐ¾Ð¸Ñ Ð»Ð¸ запÑаÑиваÑÑ ÑеÑÑÑÑ Ð¿Ð¾Ð²ÑоÑно или можно веÑнÑÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ Ñо, ÑÑо еÑÑÑ Ð² кÑÑе.<br />
<br />
ÐпÑÐµÐ´ÐµÐ»ÐµÐ½Ð½Ð°Ñ ÑложноÑÑÑ Ð´Ð»Ñ ÑазÑабоÑÑика cgi-ÑÑенаÑÐ¸Ñ Ð·Ð°ÐºÐ»ÑÑаеÑÑÑ Ð² Ñом, ÑÑо даннÑе, оÑпÑавленнÑе ÑазлиÑнÑми меÑодами, пеÑедаÑÑÑÑ Ð² ÑÑенаÑий по-ÑазномÑ. Так, инÑоÑмаÑиÑ, поÑÑÑпивÑÐ°Ñ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ POST, подаеÑÑÑ Ð½Ð° ÑÑандаÑÑнÑй вÑ
од ÑÑенаÑÐ¸Ñ Ð¸ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ ÑÑиÑана оÑÑÑда, напÑимеÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ sys.stdin.read(size) или даже ÑÑнкÑией raw_input() (Ñ
оÑÑ Ð²Ð¾ вÑоÑом ÑлÑÑае Ñложнее конÑÑолиÑоваÑÑ Ð¾Ð±Ñем пÑинимаемÑÑ
даннÑÑ
). ÐолиÑеÑÑво байÑ, коÑоÑÑе ÑÑебÑеÑÑÑ ÑÑиÑаÑÑ, можно полÑÑиÑÑ Ð¸Ð· пеÑеменной окÑÑÐ¶ÐµÐ½Ð¸Ñ CONTENT_LENGTH (напÑимеÑ, Ñак: size = os.environ['CONTENT_LENGTH']).<br />
<br />
ÐÑли ÐºÐ»Ð¸ÐµÐ½Ñ Ð¸ÑполÑзÑÐµÑ Ð¼ÐµÑод GET, Ñо даннÑе поÑÑÑпÑÑ Ð² ÑÑенаÑий ÑеÑез пеÑеменнÑÑ ÑÑÐµÐ´Ñ QUERY_STRING. ÐеÑод, коÑоÑÑм даннÑе пеÑÐµÐ´Ð°Ð½Ñ (нÑжно же как-Ñо ÑазобÑаÑÑÑÑ, где иÑ
иÑкаÑÑ) можно вÑегда полÑÑиÑÑ Ð¸Ð· REQUEST_METHOD.<br />
<br />
ÐÑÑÑ ÐµÑе один оÑобÑй ÑлÑÑай. ÐÑли даннÑе пеÑедаÑÑÑÑ Ð¼ÐµÑодом GET, но Ñ Ð¸ÑполÑзованием «индекÑного» ÑоÑмаÑа, коÑоÑÑй ÑоÑмиÑÑеÑÑÑ Ñегом <ISINDEX>, Ñо в ÑÑом ÑлÑÑае они кодиÑÑÑÑÑÑ Ð½Ðµ в виде «пеÑеменнаÑ=знаÑение&пеÑеменнаÑ=знаÑение&...», а как «знаÑение+знаÑение+...». Ð cgi-ÑÑенаÑÐ¸Ñ Ð¾Ð½Ð¸ бÑдÑÑ Ð¿ÐµÑеданÑ, помимо QUERY_STRING, ÑеÑез аÑгÑменÑÑ ÐºÐ¾Ð¼Ð°Ð½Ð´Ð½Ð¾Ð¹ ÑÑÑоки, как еÑли Ð±Ñ ÑÑенаÑий вÑзÑвалÑÑ Ñакой командой:<br />
<br />
script.cgi arg1 arg2 arg3<br />
<br />
То еÑÑÑ, на ÑÑÐ¾Ñ Ñаз полÑзоваÑелÑÑкие даннÑе можно бÑÐ´ÐµÑ Ð¿Ð¾Ð»ÑÑиÑÑ ÐºÐ°Ðº sys.argv[1] и Ñ.д.<br />
<br />
Ðак видиÑе, огÑомное ÑиÑло ваÑианÑов, пÑедÑÑмоÑÑеннÑÑ
CGI-инÑеÑÑейÑом, коÑоÑÑе вÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ ÑÑÑÐµÐ½Ñ Ð¿Ñи ÑазÑабоÑке ÑÑенаÑиÑ, Ð¼Ð¾Ð¶ÐµÑ Ð²ÑзваÑÑ Ð½ÐµÑвнÑй Ñик даже Ñ Ð¾Ð¿ÑÑнÑÑ
пÑогÑаммиÑÑов, коÑоÑÑе и во Ñне поÑиÑ
онÑÐºÑ Ð½Ð°Ð±Ð¸Ð²Ð°ÑÑ Ð¿Ð¾ подÑÑке какой-Ñо код. РеÑли еÑе вÑпомниÑÑ, ÑÑо даннÑе пеÑедаÑÑÑÑ Ð² закодиÑованном виде (ÑÑо англиÑанам Ñ
оÑоÑо â взÑл знаÑение пеÑеменной и ÑабоÑай, а нам-Ñо Ñ Ð²Ð°Ð¼Ð¸ ÑÑо знаÑение веÑнеÑÑÑ Ð² виде %EC%E4%E0), да еÑе и о пÑовеÑке ÑÑиÑ
даннÑÑ
нÑжно позабоÑиÑÑÑÑ, ÑÑÐ¾Ð±Ñ ÐºÐ°ÐºÐ¾Ð¹-нибÑÐ´Ñ Ð½Ð°ÑинаÑÑий Ñ
Ð°ÐºÐµÑ Ð½Ðµ попÑÑалÑÑ Ð·Ð°ÑÑавиÑÑ Ð½Ð°Ñ ÑеÑÐ²ÐµÑ ÑабоÑаÑÑ Ð¿Ð¾-ÑвоемÑ... ÐеÑ, обо вÑем ÑÑом лÑÑÑе и не вÑпоминаÑÑ. Ðлаго Ñ Ð½Ð°Ñ ÐµÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ cgi, в коÑоÑом вÑе ÑÑо Ñже Ñделано!<br />
<br />
Ðо о нем â ÑÑÑÑ Ð¿Ð¾Ð·Ð¶Ðµ. СнаÑала паÑÑ Ñлов нÑжно ÑказаÑÑ Ð¾ HTML-ÑоÑмаÑ
.<br />
<br />
=== ФоÑмиÑÑем ÑоÑÐ¼Ñ ===<br />
ЧÑÐ¾Ð±Ñ Ð²Ð°Ð¼ бÑло пÑоÑе понÑÑÑ ÑаÑÑмаÑÑиваемÑй ÑÐµÐ³Ð¾Ð´Ð½Ñ Ð¿ÑимеÑ, коÑоÑко ÑÐºÐ°Ð¶Ñ Ð¿Ñо Ñо, как же ÐºÐ»Ð¸ÐµÐ½Ñ Ð²ÑполнÑÐµÑ Ð¿ÐµÑедаÑÑ Ð´Ð°Ð½Ð½ÑÑ
наÑÐµÐ¼Ñ cgi-ÑÑенаÑиÑ. ÐонеÑно, пÑодвинÑÑÑе полÑзоваÑели могÑÑ Ð½Ð°Ð±ÑаÑÑ GET-запÑÐ¾Ñ Ð²ÑÑÑнÑÑ Ð² адÑеÑной ÑÑÑоке бÑаÑзеÑа. ХоÑÑ ÑÑо мелоÑиÑÑÑÑ â Ð²ÐµÐ´Ñ Ð¼Ð¾Ð¶Ð½Ð¾ же ÑÑоÑмиÑоваÑÑ Ð¸ POST-запÑоÑ, подклÑÑивÑиÑÑ ÑелнеÑом на 80-й поÑÑ! ÐпÑоÑем, обÑÑнÑе полÑзоваÑели пÑедпоÑиÑаÑÑ Ð±Ð¾Ð»ÐµÐµ понÑÑнÑе и «оÑÑзаемÑе» ÑпоÑобÑ, напÑимеÑ, ÑоÑмÑ.<br />
<br />
Ðак они вÑглÑдÑÑ, дÑмаÑ, каждÑй знаеÑ. СоздаÑÑÑÑ Ð¾Ð½Ð¸ Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ñега <FORM>, внÑÑÑи коÑоÑого добавлÑÑÑÑÑ Ñакие ÑлеменÑÑ, как <INPUT> (поле ввода) или <TEXTAREA> (многоÑÑÑоÑнÑй ÑедакÑоÑ). ÐÑим ÑлеменÑам, еÑли иÑ
даннÑе Ð´Ð¾Ð»Ð¶Ð½Ñ Ð±ÑÑÑ Ð¿ÐµÑÐµÐ´Ð°Ð½Ñ Ð½Ð° ÑеÑвеÑ, пÑиÑваиваÑÑÑÑ Ð¸Ð¼ÐµÐ½Ð° Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð°ÑÑибÑÑа name. ÐаÑалÑное знаÑение задаеÑÑÑ Ð¿Ð°ÑамеÑÑом value и в далÑнейÑем Ð´Ð»Ñ Â«ÑедакÑиÑÑемÑÑ
» полей Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¾ полÑзоваÑелем. Ðогда полÑзоваÑÐµÐ»Ñ Ð½Ð°Ð¶Ð¸Ð¼Ð°ÐµÑ ÐºÐ½Ð¾Ð¿ÐºÑ Â«ÐÑпÑавиÑÑ» (надпиÑÑ Ð½Ð° ней, в пÑинÑипе, можно измениÑÑ), Ñо бÑаÑÐ·ÐµÑ Ð¾Ð±ÑединÑÐµÑ Ð²Ñе даннÑе полей в паÑÑ name=value, ÑазделÑÑ Ð¸Ñ
Ñимволом &. ÐаÑем полÑÑÐµÐ½Ð½Ð°Ñ Ñаким обÑазом ÑÑÑока пеÑедаеÑÑÑ Ð½Ð° ÑеÑÐ²ÐµÑ Ð¼ÐµÑодом, ÑказаннÑм в аÑÑибÑÑе method Ñега <FORM>. ÐÑÑÑ Ðº ÑÑенаÑиÑ, коÑоÑÑй бÑÐ´ÐµÑ Ð·Ð°Ð½Ð¸Ð¼Ð°ÑÑÑÑ ÐµÐµ обÑабоÑкой, задаеÑÑÑ Ð°ÑÑибÑÑом action ÑÑого же Ñега. ÐÑли action не задан, Ñо даннÑе пеÑедаÑÑÑÑ ÑайлÑ, ÑÑоÑмиÑовавÑÐµÐ¼Ñ ÑекÑÑÑÑ ÑÑÑаниÑкÑ.<br />
<br />
ÐÑли ÑÑо-Ñо не ÑовÑем понÑÑно, обÑаÑиÑеÑÑ Ðº ÐºÐ¾Ð´Ñ ÑазÑабаÑÑваемой гоÑÑевой книги, коÑоÑÑй пÑиведен ниже.<br />
<br />
=== ÐÐ°Ñ ÑпаÑиÑÐµÐ»Ñ â модÑÐ»Ñ cgi ===<br />
ÐозвÑаÑаемÑÑ Ðº обÑабоÑке вÑего ÑÑого добÑа, коÑоÑое ÑоÑни полÑзоваÑелей Ñже гоÑÐ¾Ð²Ñ Ð¾Ð±ÑÑÑиÑÑ Ð½Ð° Ð½Ð°Ñ Ð±ÐµÐ´Ð½Ñй ÑÑенаÑий. ÐÑ ÑеÑили воÑполÑзоваÑÑÑÑ ÑÑандаÑÑнÑми ÑÑедÑÑвами Python, и здеÑÑ Ð²Ñе дейÑÑвиÑелÑно оÑÐµÐ½Ñ Ð¿ÑоÑÑо â импоÑÑиÑÑйÑе модÑÐ»Ñ cgi и, Ñоздав обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage, Ð²Ñ Ð¿Ð¾Ð»ÑÑиÑе ÑеÑез него доÑÑÑп ко вÑем даннÑм, пеÑеданнÑм полÑзоваÑелем, незавиÑимо Ð¾Ñ Ð¸ÑполÑзÑемого меÑода:<br />
<br />
<source lang="python"><br />
import cgi<br />
data = cgi.FieldStorage()<br />
for entry in data.keys():<br />
print 'ÐеÑÐµÐ¼ÐµÐ½Ð½Ð°Ñ %s Ð¸Ð¼ÐµÐµÑ Ð·Ð½Ð°Ñение %s' % (entry, data[entry].value)<br />
</source><br />
<br />
ÐÑли вам нÑжно полÑÑиÑÑ Ð·Ð½Ð°Ñение опÑеделенного полÑ, ÑÑо делаеÑÑÑ Ñак:<br />
<br />
<source lang="python"><br />
field = data['field'].value<br />
</source><br />
<br />
Ðомимо полÑзоваÑелÑÑкиÑ
даннÑÑ
, обÑÐµÐºÑ ÐºÐ»Ð°ÑÑа FieldStorage ÑодеÑÐ¶Ð¸Ñ Ð¸Ð½ÑоÑмаÑÐ¸Ñ Ð¸ о полÑÑ
заголовка (в наÑем пÑимеÑе иÑ
можно полÑÑиÑÑ Ð¸Ð· ÑловаÑÑ data.headers). MIME-Ñип даннÑÑ
(пеÑедаваемÑй полем заголовка Content-Type) можно полÑÑиÑÑ Ð¸Ð· аÑÑибÑÑа data.type. ЧеÑез ÑÑÐ¾Ñ Ð¶Ðµ обÑÐµÐºÑ Ð¼Ð¾Ð¶ÐµÑ Ð±ÑÑÑ Ð²Ñполнена и загÑÑзка Ñайла.<br />
<br />
С помоÑÑÑ Ð¼ÐµÑодов keys() и has_key() можно вÑполнÑÑÑ Ð¾Ð±ÑабоÑÐºÑ Ð¿Ð¾Ð»ÑÑеннÑÑ
даннÑÑ
в Ñикле и пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие Ñой или иной пеÑеменной. ÐÑÑаÑи говоÑÑ, пÑовеÑÑÑÑ Ð½Ð°Ð»Ð¸Ñие пеÑеменной во вÑ
однÑÑ
даннÑÑ
, пÑежде Ñем пÑиÑÑÑпаÑÑ Ðº иÑ
обÑабоÑке, нÑжно непÑеменно â Ð²ÐµÐ´Ñ Ð·Ð°Ð¿ÑÐ¾Ñ ÑоÑмиÑÑеÑÑÑ ÐºÐ»Ð¸ÐµÐ½Ñом, а кÑо знаеÑ, ÑÑо Ñ Ð½ÐµÐ³Ð¾ на Ñме?<br />
<br />
=== ÐазиÑÑем даннÑе ===<br />
ÐÑак, полÑÑаÑÑ Ð´Ð°Ð½Ð½Ñе Ð¾Ñ ÐºÐ»Ð¸ÐµÐ½Ñа Ð¼Ñ Ð½Ð°ÑÑилиÑÑ. ÐÑпÑавлÑÑÑ Ñоже Ñмеем. ÐÑÑалоÑÑ Ð¿ÑидÑмаÑÑ, как ÑÑи даннÑе лÑÑÑе вÑего Ñ
ÑаниÑÑ. ÐонеÑно, Ð´Ð»Ñ Ð½ÐµÑложной гоÑÑевой книги Ñ Ð½ÐµÐ±Ð¾Ð»ÑÑой нагÑÑзкой вполне Ñ
ваÑило Ð±Ñ Ð¸ ÑекÑÑовÑÑ
Ñайлов. ÐÑавда, Ñам еÑÑÑ Ñвои ÑложноÑÑи â еÑли ÑÑÐ°Ð·Ñ Ð¿ÑÑÑ Ñеловек заÑ
оÑÑÑ Ð²ÑÑказаÑÑ Ñвое мнение о ваÑей кÑÑÑейÑей домаÑней ÑÑÑаниÑке, Ñо ÑÑенаÑÐ¸Ñ Ð¿ÑидеÑÑÑ ÐºÐ°ÐºÐ¸Ð¼-Ñо обÑазом ÑегÑлиÑоваÑÑ Ð´Ð¾ÑÑÑп к ÑайлÑ-Ñ
ÑанилиÑÑ (как минимÑм, обÑабаÑÑваÑÑ ÑиÑÑаÑиÑ, еÑли Ñайл Ñже оÑкÑÑÑ Ð½Ð° запиÑÑ Ð´ÑÑгим ÑкземплÑÑом ÑÑенаÑиÑ). Ðо заÑем нам вÑе ÑÑи головнÑе боли? ÐÑли Ð¼Ñ Ñак ловко оÑвеÑÑелиÑÑ Ð¾Ñ Ð½ÐµÐ¾Ð±Ñ
одимоÑÑи вÑÑÑнÑÑ ÑазбиÑаÑÑ HTTP-запÑоÑÑ, Ñо неÑжели не найдем ÑÑо-Ñо подÑ
одÑÑее на ÑÑÐ¾Ñ Ñаз?<br />
<br />
ÐонеÑно, найдем! Ð ÑÑо «ÑÑо-Ñо» назÑваеÑÑÑ ÑиÑÑемой ÑпÑÐ°Ð²Ð»ÐµÐ½Ð¸Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
(в пÑоÑÑоÑеÑÑе â СУÐÐ). ТепеÑÑ Ð½Ð°Ñе дело â оÑпÑавиÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð¸ полÑÑиÑÑ Ð¾ÑвеÑ. ÐÑе оÑÑалÑное â Ñже не наÑа забоÑа.<br />
<br />
ÐÐ»Ñ ÑÑого пÑимеÑа Ñ Ð²ÑбÑал в каÑеÑÑве «оÑвеÑÑÑвенного» за Ñ
Ñанение даннÑÑ
ÑеÑÐ²ÐµÑ Ð±Ð°Ð· даннÑÑ
PostgreSQL. ÐоÑколÑÐºÑ Ð¼Ñ Ð¿Ð¸Ñем Ð½Ñ Ð¾ÑÐµÐ½Ñ Ð¿ÑоÑÑÑÑ Ð³Ð¾ÑÑевÑÑ ÐºÐ½Ð¸Ð³Ñ, Ñо и ÑÑÑÑкÑÑÑа Ð±Ð°Ð·Ñ Ð±ÑÐ´ÐµÑ Ñ Ð½Ð°Ñ ÑлеменÑаÑной â одна ÑаблиÑа Ñ ÑÑÐµÐ¼Ñ Ð¿Ð¾Ð»Ñми: вÑÐµÐ¼Ñ Ð¿ÑбликаÑии ÑообÑениÑ, Ð¸Ð¼Ñ Ð°Ð²ÑоÑа и, ÑобÑÑвенно, Ñамо ÑообÑение:<br />
<br />
admin@toshiba:~$ psql<br />
Welcome to psql 8.1.4, the PostgreSQL interactive terminal.<br />
guestbook=# create user "www-data" nocreatedb nocreateuser;<br />
CREATE ROLE<br />
admin=# create database guestbook with owner "www-data";<br />
CREATE DATABASE<br />
admin=# \connect guestbook<br />
ÐÑ Ð¿Ð¾Ð´ÑоединилиÑÑ Ðº базе даннÑÑ
"guestbook".<br />
guestbook=# create table guestbook (<br />
guestbook(# datum timestamp, author varchar, message varchar);<br />
CREATE TABLE<br />
guestbook=# alter table guestbook owner to "www-data";<br />
ALTER TABLE<br />
guestbook=# \q<br />
admin@toshiba:~$<br />
<br />
ÐожалÑй, единÑÑвенное, ÑÑо здеÑÑ Ð½Ñжно поÑÑниÑÑ, ÑÑо поÑÐµÐ¼Ñ Ð±Ð°Ð·Ðµ и ÑаблиÑе Ð¼Ñ Ð½Ð°Ð·Ð½Ð°Ñили владелÑÑем полÑзоваÑÐµÐ»Ñ www-data. ÐÑоÑÑо к ним бÑÐ´ÐµÑ Ð¾Ð±ÑаÑаÑÑÑÑ cgi-ÑÑенаÑий, ÑабоÑаÑÑий Ñ Ð¿Ñавами HTTP-ÑеÑвеÑа Apache, коÑоÑÑй, в ÑÐ²Ð¾Ñ Ð¾ÑеÑедÑ, иÑполнÑеÑÑÑ Ð¾Ñ Ð¸Ð¼ÐµÐ½Ð¸ данного полÑзоваÑÐµÐ»Ñ [в ваÑем диÑÑÑибÑÑиве он Ð¼Ð¾Ð¶ÐµÑ Ð½Ð°Ð·Ð²Ð°ÑÑÑÑ Ð¿Ð¾-дÑÑгомÑ, â пÑим. Ñед.]. Ð PostgreSQL по ÑмолÑÐ°Ð½Ð¸Ñ ÑÑебÑеÑ, ÑÑÐ¾Ð±Ñ Ð¸Ð¼Ñ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð² ÐÐ Ñовпадало Ñ ÐµÐ³Ð¾ ÑиÑÑемнÑм именем. Ðне ÑÑо кажеÑÑÑ Ð´Ð¾ÑÑаÑоÑно ÑдобнÑм, Ñ
оÑÑ Ð²Ñ, конеÑно, можеÑе поÑÑÑпиÑÑ Ð¿Ð¾-ÑвоемÑ.<br />
<br />
=== DB API на ÑÑÑаже ÑниÑикаÑии ===<br />
ÐÑÑалоÑÑ ÑазобÑаÑÑÑÑ, как же Python взаимодейÑÑвÑÐµÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
. ÐÐ»Ñ ÑÑого Python пÑедоÑÑавлÑÐµÑ DB API â ÑпеÑиалÑнÑй инÑеÑÑейÑ, ÑниÑиÑиÑÑÑÑий Ð½Ð°Ð±Ð¾Ñ Ð¼ÐµÑодов, коÑоÑÑе бÑдÑÑ Ð¾Ð´Ð¸Ð½Ð°ÐºÐ¾Ð²Ð¾ ÑабоÑаÑÑ Ð½ÐµÐ·Ð°Ð²Ð¸Ñимо Ð¾Ñ Ñого, Ñ ÐºÐ°ÐºÐ¾Ð¹ СУÐÐ Ð¼Ñ Ð²Ð·Ð°Ð¸Ð¼Ð¾Ð´ÐµÐ¹ÑÑвÑем. ÐÐ»Ñ ÑабоÑÑ Ñ PostgreSQL нам понадобиÑÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ PyPgSQL (в ÑÑандаÑÑной поÑÑавке его Ð¼Ð¾Ð¶ÐµÑ Ð½Ðµ оказаÑÑÑÑ, но Ð²Ð°Ñ Ð¼ÐµÐ½ÐµÐ´Ð¶ÐµÑ Ð¿Ð°ÐºÐµÑов навеÑнÑка бÑÐ´ÐµÑ Ð² кÑÑÑе, как его ÑÑÑановиÑÑ; кÑÑаÑи, ÑÑо не единÑÑвеннÑй модÑÐ»Ñ â Ñ Ð²Ð°Ñ, возможно, бÑÐ´ÐµÑ PyGreSQL, коÑоÑÑй ÑабоÑÐ°ÐµÑ Ð½Ð¸ÑÑÑÑ Ð½Ð¸ Ñ
Ñже и Ñ Ñеми же ÑамÑми меÑодами).<br />
<br />
DB API опÑеделÑÐµÑ ÑÑандаÑÑнÑе меÑÐ¾Ð´Ñ ÑабоÑÑ Ñ Ð±Ð°Ð·Ð°Ð¼Ð¸ даннÑÑ
, Ñак ÑÑо, какой Ð±Ñ Ð¼Ð¾Ð´ÑÐ»Ñ Ð²Ñ Ð½Ð¸ загÑÑзили и Ñ ÐºÐ°ÐºÐ¾Ð¹ Ð±Ñ Ð¡Ð£ÐРни ÑабоÑали (бÑÐ´Ñ Ñо MySQL, PostgreSQL, SQLite или ÑÑо-Ñо еÑе), менÑÑÑÑÑ Ð±ÑÐ´ÐµÑ ÑолÑко Ð¸Ð¼Ñ Ð¼Ð¾Ð´ÑлÑ. Ðлавное, ÑÑÐ¾Ð±Ñ Ð¸ÑполÑзÑемÑй модÑÐ»Ñ ÑооÑвеÑÑÑвовал DB API. РаÑÑмоÑÑим коÑоÑко оÑновнÑе меÑодÑ:<br />
<br />
<source lang="python"><br />
conn = connect(dsn='localhost', user='admin', password='superparol', database='mydb')<br />
</source><br />
<br />
Так оÑÑÑеÑÑвлÑеÑÑÑ Ð¿Ð¾Ð´ÐºÐ»ÑÑение к базе. РзавиÑимоÑÑи Ð¾Ñ ÑиÑÑаÑии, вам Ð¼Ð¾Ð¶ÐµÑ Ð¿Ð¾ÑÑебоваÑÑÑÑ ÑказаÑÑ ÑолÑко нÑжнÑе паÑамеÑÑÑ (напÑимеÑ, Ð¸Ð¼Ñ Ñ
оÑÑа 'localhost' подÑазÑмеваеÑÑÑ Ð¿Ð¾ ÑмолÑаниÑ).<br />
<br />
<source lang="python"><br />
cur = conn.cursor()<br />
</source><br />
<br />
ÐÑÑÑоÑÑ Ð¿Ð¾Ð´Ð´ÐµÑживаÑÑÑÑ Ð´Ð°Ð»ÐµÐºÐ¾ не вÑеми СУÐÐ, но Ð´Ð»Ñ Ð¾Ð±ÑноÑÑи в DB API они Ð²Ð²ÐµÐ´ÐµÐ½Ñ Ð¸, в ÑлÑÑае необÑ
одимоÑÑи, Ð´Ð¾Ð»Ð¶Ð½Ñ ÑмÑлиÑоваÑÑÑÑ Ð¼Ð¾Ð´ÑлÑми ÑопÑÑÐ¶ÐµÐ½Ð¸Ñ Ð¸ÑкÑÑÑÑвенно. Так ÑÑо не забÑвайÑе оÑпÑавлÑÑÑ Ð²Ñе ваÑи запÑоÑÑ ÑеÑез кÑÑÑоÑ.<br />
<br />
<source lang="python"><br />
cur.execute('''SELECT * FROM mytable''')<br />
</source><br />
<br />
Так вÑполнÑеÑÑÑ SQL-запÑоÑ. ÐÑли в ÑÑÑоке запÑоÑа иÑполÑзÑÑÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼ÐµÑÑа %s, Ñо вÑоÑÑм паÑамеÑÑом пеÑедаеÑÑÑ ÑпиÑок пеÑеменнÑÑ
-знаÑений, пÑиÑем в SQL-запÑоÑе знакомеÑÑа не ÑÑебÑеÑÑÑ Ð¾ÐºÑÑжаÑÑ Ð°Ð¿Ð¾ÑÑÑоÑами â модÑÐ»Ñ ÑÐ´ÐµÐ»Ð°ÐµÑ ÑÑо ÑамоÑÑоÑÑелÑно в завиÑимоÑÑи оÑ<br />
Ñипа пеÑеменной.<br />
<br />
<source lang="python"><br />
cur.fetchall()<br />
</source><br />
<br />
ÐозвÑаÑÐ°ÐµÑ Ð´Ð²ÑмеÑнÑй ÑпиÑок (ÑÑÑоки â полÑ) полÑÑеннÑÑ
Ð¾Ñ Ð¡Ð£ÐРданнÑÑ
. СÑÑеÑÑвÑÑÑ Ð¸ дÑÑгие меÑодÑ, ознакомиÑÑÑÑ Ñ ÐºÐ¾ÑоÑÑми Ð²Ñ ÑможеÑе в докÑменÑаÑии или Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ Ð·Ð½Ð°ÐºÐ¾Ð¼Ð¾Ð¹ вам ÑÑнкÑии dir() да паÑÑ-ÑÑойки неÑложнÑÑ
ÑкÑпеÑименÑов.<br />
<br />
=== ÐакÑеплÑем на пÑакÑике ===<br />
ÐеÑейдем к ÑаÑÑмоÑÑÐµÐ½Ð¸Ñ Ð½Ð°Ñего пÑимеÑа. ÐаÑнем ÑÑандаÑÑно â Ñкажем кодиÑовкÑ, подклÑÑим нÑжнÑе модÑли:<br />
<br />
<source lang="python"><br />
#!/usr/bin/Python<br />
# -*- coding: utf-8 -*-<br />
import PyPgSQL.PgSQL as pg<br />
import cgi<br />
</source><br />
<br />
Ðалее, опÑеделим две ÑÑнкÑии. ÐеÑÐ²Ð°Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° добавление нового ÑообÑÐµÐ½Ð¸Ñ Ð² базÑ:<br />
<br />
<source lang="python"><br />
def addMessage(author, message):<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""INSERT INTO guestbook (datum, author, message) VALUES ('now', %s, %s);""", (author, message))<br />
c.close()<br />
db.commit()<br />
db.close()<br />
print "Content-Type: text/html"<br />
print "Location: ?#form\n"<br />
</source><br />
<br />
Ðак видиÑе, вÑе оÑÐµÐ½Ñ Ð´Ð°Ð¶Ðµ логиÑно: ÑÑÑанавливаем Ñоединение Ñ ÐÐ (поÑколÑÐºÑ Ð² наÑем ÑлÑÑае подклÑÑение вÑполнÑеÑÑÑ Ñ Ð¸Ð¼ÐµÐ½ÐµÐ¼ ÑекÑÑего ÑиÑÑемного полÑзоваÑелÑ, Ñо доÑÑаÑоÑно ÑказаÑÑ ÑолÑко Ð¸Ð¼Ñ Ð±Ð°Ð·Ñ), Ñоздаем кÑÑÑÐ¾Ñ (в PostgreSQL они не пÑименÑÑÑÑÑ, но они ÑмÑлиÑÑÑÑÑÑ ÐºÐ°Ð¶Ð´Ñм модÑлем, пÑеÑендÑÑÑим на ÑооÑвеÑÑÑвие DB API), вÑполнÑеÑÑÑ Ð·Ð°Ð¿ÑоÑ, закÑÑваеÑÑÑ ÐºÑÑÑоÑ, ÑикÑиÑÑÑÑÑÑ Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ (PostgreSQL иÑполÑзÑÐµÑ ÑÑанзакÑии, поÑÑÐ¾Ð¼Ñ Ð²Ñполнение меÑода commit() обÑзаÑелÑно, инаÑе ваÑи Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ Ð½Ðµ бÑдÑÑ ÑоÑ
ÑаненÑ), и, наконеÑ, закÑÑваем Ñамо Ñоединение Ñ Ð±Ð°Ð·Ð¾Ð¹. Рполе datum заноÑим знаÑение вÑÑÑоенной пеÑеменной PostgreSQL â now, коÑоÑÐ°Ñ ÐºÐ°Ð¶Ð´Ñй Ñаз заменÑеÑÑÑ ÑекÑÑим знаÑением даÑÑ Ð¸ вÑемени.<br />
<br />
ÐÑ Ð¸ пеÑаÑÑ Ð·Ð°Ð³Ð¾Ð»Ð¾Ð²ÐºÐ° «Location» вÑполнÑеÑÑÑ Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð¿ÐµÑенапÑавиÑÑ Ð¿Ð¾Ð»ÑзоваÑÐµÐ»Ñ Ð½Ð° ÑÑÐ¾Ñ Ð¶Ðµ ÑÑенаÑий, но Ñже без паÑамеÑÑов â Ð¼Ñ Ð¶Ðµ Ð´Ð¾Ð»Ð¶Ð½Ñ Ð¿Ð¾ÐºÐ°Ð·Ð°ÑÑ ÐºÐ»Ð¸ÐµÐ½ÑÑ, ÑÑо он на Ñамом деле ввел? (ЯкоÑÑ #form иÑполÑзÑеÑÑÑ, ÑÑÐ¾Ð±Ñ Ð°Ð²ÑомаÑиÑеÑки пÑокÑÑÑиÑÑ ÑÑÑаниÑÐºÑ Ð½Ð° поÑледнее ÑообÑение).<br />
<br />
ÐÑоÑÐ°Ñ ÑÑнкÑÐ¸Ñ Ð±ÑÐ´ÐµÑ Ð¾ÑвеÑаÑÑ Ð·Ð° вÑвод на ÑкÑан Ñже оÑÑавленнÑÑ
в книге запиÑей, а Ñакже за ÑоÑмÑ, Ñ Ð¿Ð¾Ð¼Ð¾ÑÑÑ ÐºÐ¾ÑоÑой можно бÑÐ´ÐµÑ Ð´Ð¾Ð±Ð°Ð²Ð¸ÑÑ Ð¸ Ñвое вÑÑказÑвание:<br />
<br />
<source lang="python"><br />
def showGB():<br />
db = pg.connect(database="guestbook")<br />
c = db.cursor()<br />
c.execute("""SELECT datum, author, message FROM guestbook ORDER BY datum;""")<br />
res = c.fetchall()<br />
c.close()<br />
db.close()<br />
</source><br />
<br />
Ð ÑÑом ÑÑагменÑе Ð¼Ñ Ð²ÑбиÑаем вÑе ÑÑÑоки из наÑей ÑаблиÑÑ Ð´Ð°Ð½Ð½ÑÑ
, ÑоÑÑиÑÑÑ Ð¸Ñ
по даÑе. РезÑлÑÑÐ°Ñ ÑоÑ
ÑанÑеÑÑÑ Ð² пеÑеменной res, Ñ ÐºÐ¾ÑоÑой и бÑдем ÑабоÑаÑÑ. ТепеÑÑ Ð¾ÑÑалоÑÑ Ð»Ð¸ÑÑ Ð°ÐºÐºÑÑаÑненÑко ÑазложиÑÑ Ð½Ð°Ñи даннÑе по ÑаблиÑкам и вÑвеÑÑи иÑ
на ÑкÑан:<br />
<br />
<source lang="python"><br />
print "Content-Type: text/html\n"<br />
print "<H1 style='color:#7777FF'><U>ÐелÑкам к нам в гоÑÑи!</U></H1>"<br />
for item in res:<br />
print """<TABLE width='90%%'><br />
<TR><TD><SMALL>ТоваÑÐ¸Ñ <B>%s</B> поведалнам ÑледÑÑÑее:</SMALL><br />
<TD align='right'><SMALL>%s</SMALL><br />
<TR><TD style='background-color:#DDDDFF' colspan='2'>%s<br />
</TABLE>""" % (item[1], str(item[0])[:19], item[2])<br />
print "<HR><A name='form'><H3>ÐÑиÑоединÑйÑеÑÑ Ðº диÑкÑÑÑии:</H3>"<br />
print """<FORM method='GET'><br />
ÐаÑе имÑ: <INPUT type='text' name='author'><BR><br />
ЧÑо Ð²Ñ Ð´ÑмаеÑе по ÑÑÐ¾Ð¼Ñ Ð¿Ð¾Ð²Ð¾Ð´Ñ:<BR><br />
<TEXTAREA name='message' rows='5' cols='80'></TEXTAREA><BR><br />
<INPUT type='submit' value='ÐÑпÑавиÑÑ'><br />
</FORM>"""<br />
</source><br />
<br />
<div id="img"></div><br />
[[ÐзобÑажение:Img 83 81 1.png|thumb|Ðи Ñмайликов, ни BB-кода, ни даже логоÑипа... ÐаÑо Ð¼Ñ Ñделали ÑÑÑ Ð³Ð¾ÑÑевÑÑ Ð·Ð° 10 минÑÑ!]]<br />
<br />
СмÑÑл конÑÑÑÑкÑии str(item[0])[:19] заклÑÑаеÑÑÑ Ð² Ñом, ÑÑÐ¾Ð±Ñ Ð² ÑÑÑоке вÑемени оÑÑеÑÑ Ð½ÐµÐ½ÑжнÑе нам миллиÑекÑндÑ, коÑоÑÑе ÑоÑ
ÑанÑÑÑÑÑ Ð² поле Ñипа timestamp. ÐоÑле вÑеÑ
опÑбликованнÑÑ
ÑообÑений вÑводим ÑоÑÐ¼Ñ Ð´Ð¾Ð±Ð°Ð²Ð»ÐµÐ½Ð¸Ñ Ð½Ð¾Ð²Ð¾Ð³Ð¾, ÑÑÐ¾Ð±Ñ ÐºÐ°Ð¶Ð´Ñй мог пÑиÑоединиÑÑÑÑ Ðº наÑей диÑкÑÑÑии. ÐÑÑаÑи, в Ñеге <FORM> Ð¼Ñ Ð½Ðµ Ñказали паÑамеÑÑ action, поÑколÑÐºÑ Ð´Ð°Ð½Ð½Ñе бÑдÑÑ Ð¿ÐµÑедаваÑÑÑÑ Ð½Ð° обÑабоÑÐºÑ ÑÑÐ¾Ð¼Ñ Ð¶Ðµ ÑÑенаÑÐ¸Ñ (благодаÑÑ ÑÐµÐ¼Ñ Ð¸Ð¼Ñ ÑÑенаÑÐ¸Ñ Ð¼Ð¾Ð¶Ð½Ð¾ пÑиÑвоиÑÑ Ð»Ñбое).<br />
ÐаконеÑ, поÑледний ÑÑагменÑ:<br />
<br />
<source lang="python"><br />
form = cgi.FieldStorage()<br />
if form.has_key("message") and form.has_key("author"):<br />
author = cgi.escape(form["author"].value)<br />
message = cgi.escape(form["message"].value)<br />
message = message.replace("\n", "<BR>")<br />
addMessage(author, message)<br />
else:<br />
showGB()<br />
</source><br />
<br />
Создаем FieldStorage-обÑекÑ, и еÑли в нем еÑÑÑ Ð·Ð°Ð¿Ð¾Ð»Ð½ÐµÐ½Ð½Ñе Ð¿Ð¾Ð»Ñ message и author (Ñо еÑÑÑ Ð·Ð°Ð¿ÑÐ¾Ñ Ð±Ñл ÑÑоÑмиÑован из заполненной полÑзоваÑелем ÑоÑмÑ), Ñо, немножко иÑ
обÑабоÑав (ÑÑнкÑÐ¸Ñ cgi.escape() заменÑÐµÑ Ð²Ñе «неблагонадежнÑе» ÑÐ¸Ð¼Ð²Ð¾Ð»Ñ â напÑимеÑ, < â иÑ
ÑÑандаÑÑнÑми SGML-ÑÑÑноÑÑÑми, в данном ÑлÑÑае â &lt;), пеÑедаем ÑÑнкÑии addMessage(). ÐбÑабоÑка нÑжна Ð´Ð»Ñ Ñого, ÑÑÐ¾Ð±Ñ Ð·Ð»Ð¾ÑмÑÑленник не мог ввеÑÑи в поле ÑообÑÐµÐ½Ð¸Ñ Ð¸Ð»Ð¸ имени авÑоÑа ÑÑо-нибÑÐ´Ñ Ñакое:<br />
<br />
<SCRIPT>alert('Ðа поÑли Ð²Ñ Ð²Ñе!');</SCRIPT><br />
<br />
Ð ÑловÑ, пÑенебÑегаÑÑ Ð¿ÑовеÑкой введеннÑÑ
даннÑÑ
ни в коем ÑлÑÑае нелÑзÑ. ÐайдиÑе как-нибÑÐ´Ñ Ð½Ð° [http://securitylab.ru securitylab.ru] и поÑмоÑÑиÑе, ÑколÑко ÑÑзвимоÑÑей Ñипа «XSS» обнаÑÑживаеÑÑÑ ÐºÐ°Ð¶Ð´Ñй меÑÑÑ! Так ÑÑо ÑÑÑки ÑÑÑками, но поÑледÑÑÐ²Ð¸Ñ Ð¼Ð¾Ð³ÑÑ Ð±ÑÑÑ Ð¾ÑÐµÐ½Ñ ÑеÑÑезнÑми.<br />
<br />
=== ÐÑда же нам ÑепеÑÑ Ð¸Ð´Ñи? ===<br />
ÐÑак, ÑÑо-Ñо вполне ÑабоÑоÑпоÑобное Ñ Ð½Ð°Ñ ÐµÑÑÑ (Ñм. [[LXF83:Python#img|ÑиÑÑнок]]). Ðо как Ð²Ñ Ð¼Ð¾Ð¶ÐµÑ Ð´Ð¾Ð³Ð°Ð´Ð°ÑÑÑÑ, наÑа гоÑÑÐµÐ²Ð°Ñ Ð¾ÑÐµÐ½Ñ Ð´Ð°Ð»ÐµÐºÐ° Ð¾Ñ ÑовеÑÑенÑÑва. ЧÑо еÑе можно ÑделаÑÑ? ÐÑ, напÑимеÑ, ÑазбиÑÑ Ð½Ð° ÑÑÑаниÑÑ. Ðока ÑообÑений в ней бÑÐ´ÐµÑ Ð½Ðµ болÑÑе дÑжинÑ, ÑÐ¾Ð¹Ð´ÐµÑ Ð¸ Ñак. Ркогда иÑ
ÑиÑло Ð´Ð¾Ð¹Ð´ÐµÑ Ð´Ð¾ ÑоÑни, Ñо Ñедкий полÑзоваÑÐµÐ»Ñ Ð´Ð¾Ð¶Ð´ÐµÑÑÑ Ð¾ÐºÐ¾Ð½ÑÐ°Ð½Ð¸Ñ Ð·Ð°Ð³ÑÑзки вÑеÑ
даннÑÑ
. Ðожно даÑÑ Ð¿Ð¾Ð»ÑзоваÑелÑм возможноÑÑÑ Ð¸ÑполÑзоваÑÑ Ð½ÐµÐºÐ¾ÑоÑÑе HTML-Ñеги, ÑÑÐ¾Ð±Ñ Ð¸Ñ
ÑообÑÐµÐ½Ð¸Ñ Ð²ÑглÑдели более кÑаÑоÑно. Ðожно добавиÑÑ Ñмайликов... Рможно даже ÑделаÑÑ Ð¼Ð¾Ð´ÑÐ»Ñ Ð°Ð´Ð¼Ð¸Ð½Ð¸ÑÑÑиÑованиÑ, позволÑÑÑий ÑедакÑиÑоваÑÑ Ð¸Ð»Ð¸ ÑдалÑÑÑ ÑообÑениÑ, а Ñакже оÑвеÑаÑÑ Ð½Ð° ниÑ
. Так ÑÑо ÑабоÑÑ Ð½ÐµÐ¿Ð¾ÑаÑÑй кÑай. ÐеÑзайÑе â не бÑÐ´Ñ Ð²Ð°Ð¼ меÑаÑÑ.<br />
<br />
=== ÐекоÑоÑÑе ÑаÑпÑоÑÑÑанÑннÑе MIME-ÑÐ¸Ð¿Ñ ===<br />
{| style="background:white;color:black;" border="1" cellspacing="0"<br />
|- style="background:#dfcfe6;color:black"<br />
! MIME-Ñип<br />
! ÐпиÑание<br />
|-<br />
| text/plain<br />
| ÐÑоÑÑой ÑекÑÑ<br />
|-<br />
| text/html<br />
| HTML-ÑÑÑаниÑа<br />
|-<br />
| image/gif<br />
| ÐзобÑажение GIF<br />
|-<br />
| video/mpeg<br />
| Ðидео-Ñайл в ÑоÑмаÑе MPEG<br />
|-<br />
| application/msword <br />
| ÐокÑÐ¼ÐµÐ½Ñ MS Word<br />
|}</div>
RicroAcdom