Python CGI编程(转自易百)
Python CGI编程
什么是CGI ?
公共网关接口或CGI,Web服务器和一个自定义的脚本之间交换信息是是一组定义的标准..
CGI规范在由NCSA和NCSA定义的CGI保持如下:
公共网关接口或CGI,如HTTP服务器信息服务器的标准接口是外部网关方案.
当前版本CGI/1.1和CGI/1.2.
网页浏览
理解CGI的概念,让我们看看会发生什么,当我们点击一个超链接到浏览特定网页或URL.
您的浏览器触点的HTTP Web服务器,即需求的URL ie.文件名.
Web服务器解析URL,如果发现该文件,然后发送回浏览器,否则发送错误消息表明您已经请求一个错误的文件.
Web浏览器从Web服务器的响应,并显示收到的文件或错误消息.
但是,它可能设立的HTTP服务器,因此,只要在某个目录中的文件被请求文件送回,而是作为一个程序执行,任何方案产出发送您的浏览器来显示。这个函数被调用的通用网关接口或CGI程序称为CGI脚本。这些CGI程序可以是一个Python脚本,Perl脚本,shell脚本,C或C+ +程序等.
CGI架构图

Web服务器的支持与配置
进行CGI编程之前,确保您的Web服务器,支持CGI,它被配置为CGI程序处理。所有的HTTP服务器执行CGI程序都保存在一个预先配置的目录。这个目录被称为CGI目录,并按照惯例,它被命名为/ var/www/cgi-bin目录。约定CGI文件.cgi扩展名,但你可以保持你的Python扩展的文件.py.
默认情况下,Linux服务器配置只运行在cgi-bin目录中的/var/www脚本。如果你想指定的任何其他运行CGI脚本的目录,内容在httpd.conf文件中的下列行:
AllowOverride None Options ExecCGI Order allow,deny Allow from allOptions All
在这里,我假设你有Web服务器,并成功运行,你可以运行任何其他CGI程序像Perl或shell等.
第一个CGI 程序
下面是一个简单的链接,链接到CGI脚本名为hello.py。此文件被保存在/var/www/cgi-bin目录,它有以下内容。运行CGI程序之前,确保你有CHAGE模式使用 UNIX命令chmod命令 755 hello.py,使文件的可执行文件.
#!/usr/bin/python print "Content-type:text/html\r\n\r\n" print '' print '' print 'Hello Word - First CGI Program' print '' print '' print '
Hello Word! This is my first CGI program
' print '' print ''
如果你点击hello.py然后,这将产生以下输出:
Hello Word! This is my first CGI program |
这个的hello.py脚本是一个简单的Python脚本,这是写在stdout文件,即它的输出浏览器的屏幕。有一个重要的和额外的功能,这是第一行要打印的内容类型:文本/html\R\N\R\N。此行被发送回浏览器,并指定内容类型的浏览器屏幕上显示。现在,你必须理解CGI的基本概念,可以使用Python写了许多复杂的CGI程序。这个脚本可以与任何其他扩展系统交换,如RDBMS的信息.
HTTP 头
该行的内容类型:文本/html\R\N\R\n是理解的内容被发送到浏览器的HTTP头的一部分。所有的HTTP报头,将在下列表格
HTTP Field Name: Field Content For Example Content-type: text/html\r\n\r\n
还有其他一些重要的HTTP头,你会经常使用的CGI编程.
| Header | Description |
|---|---|
| Content-type: | A MIME string defining the format of the file being returned. Example is Content-type:text/html |
| Expires: Date | The date the information becomes invalid. This should be used by the browser to decide when a page needs to be refreshed. A valid date string should be in the format 01 Jan 1998 12:00:00 GMT. |
| Location: URL | The URL that should be returned instead of the URL requested. You can use this filed to redirect a request to any file. |
| Last-modified: Date | The date of last modification of the resource. |
| Content-length: N | The length, in bytes, of the data being returned. The browser uses this value to report the estimated download time for a file. |
| Set-Cookie: String | Set the cookie passed through the string |
CGI环境变量
所有的CGI程序,将有机会获得以下环境变量。编写任何CGI程序,这些变量发挥了重要作用.
| Variable Name | Description |
| CONTENT_TYPE | The data type of the content. Used when the client is sending attached content to the server. For example file upload etc. |
| CONTENT_LENGTH | The length of the query information. It's available only for POST requests |
| HTTP_COOKIE | Return the set cookies in the form of key & value pair. |
| HTTP_USER_AGENT | The User-Agent request-header field contains information about the user agent originating the request. Its name of the web browser. |
| PATH_INFO | The path for the CGI script. |
| QUERY_STRING | The URL-encoded information that is sent with GET method request. |
| REMOTE_ADDR | The IP address of the remote host making the request. This can be useful for logging or for authentication purpose. |
| REMOTE_HOST | The fully qualified name of the host making the request. If this information is not available then REMOTE_ADDR can be used to get IR address. |
| REQUEST_METHOD | The method used to make the request. The most common methods are GET and POST. |
| SCRIPT_FILENAME | The full path to the CGI script. |
| SCRIPT_NAME | The name of the CGI script. |
| SERVER_NAME | The server's hostname or IP Address |
| SERVER_SOFTWARE | The name and version of the software the server is running. |
这里是小的CGI程序列出所有的CGI变量。
#!/usr/bin/python import os print "Content-type: text/html\r\n\r\n"; print "Environment<\br>"; for param in os.environ.keys(): print "%20s: %s<\br>" % (param,os.environ[param])
GET和POST 方法
你所遇到的许多情况下,当您需要从您的浏览器,Web服务器,并最终给你的CGI程序传递一些信息。最常用的浏览器使用两种方法将此信息传递到Web服务器。这些方法是GET方法和POST方法.
使用GET方法传递信息:
GET方法发送编码的用户信息添加到页面请求。分隔页和编码信息?字符作为如下:
http://www.test.com/cgi-bin/hello.py?key1=value1&key2=value2
GET方法是defualt从浏览器向Web服务器的方法来传递信息,它会产生一个很长的字符串出现在浏览器的位置:框。切勿使用GET方法,如果你有密码或其他敏感信息传递给服务器。 GET方法尺寸limtation:只有1024个字符,可以在请求字符串.
此信息通过使用QUERY_STRING的头,将通过QUERY_STRING环境变量在你的CGI程序访问
你可以通过简单的连接键和值对非常久远的任何URL的信息,或您可以使用HTML标签来传递信息,使用GET方法.
简单 URL 例子 : Get 方法
这里是一个简单的URL使用GET方法,这将通过两个值hello_get.py方案.
下面是hello_get.py的脚本来处理给定的输入网页浏览器。我们要使用CGI模块,这使得它很容易访问传递的信息:
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
first_name = form.getvalue('first_name')
last_name = form.getvalue('last_name')
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Hello - Second CGI Program"
print ""
print ""
print "
Hello %s %s
" % (first_name, last_name) print "" print ""
This would generate following result:
Hello ZARA ALI |
简单的FORM 例子:GET方法
下面是一个简单的例子,通过这两个值,使用HTML表单和提交按钮。我们将使用相同的CGI脚本hello_get.py的处理此输入.
First Name:Last Name:
这里是上述形式的实际输出,输入第一个和最后一个名称,然后点击提交按钮来查看结果.
First Name:
Last Name:
使用POST方法传递信息:
更可靠的信息传递给CGI程序的一般方法是POST方法。这包装完全相同的方式为GET方法的信息,而是它作为一个文本字符串发送后?在URL中发送它作为一个单独的消息。此消息来自标准输入的形式到CGI脚本.
下面是同hello_get.py脚本处理的GET以及POST方法.
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
first_name = form.getvalue('first_name')
last_name = form.getvalue('last_name')
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Hello - Second CGI Program"
print ""
print ""
print "
Hello %s %s
" % (first_name, last_name) print "" print ""
让我们再次看同以上相同的例子,其中通过两个值,使用HTML表单和提交按钮。我们将使用相同的CGI脚本hello_get.py的处理此输入.
First Name:Last Name:
这里是上述形式的实际输出,输入第一个和最后一个名称,然后点击提交按钮来查看结果.
First Name:
Last Name:
传递复选框(checkbox)数据给CGI程序
复选框用于多个选项被选中时,.
这里有两个复选框的形式例如HTML代码
Maths Physics
这段代码的结果是下面的形式
Maths Physics
下面是checkbox.cgi脚本来处理给定的输入网页浏览器“复选框按钮.
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
if form.getvalue('maths'):
math_flag = "ON"
else:
math_flag = "OFF"
if form.getvalue('physics'):
physics_flag = "ON"
else:
physics_flag = "OFF"
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Checkbox - Third CGI Program"
print ""
print ""
print "
CheckBox Maths is : %s
" % math_flag print "
CheckBox Physics is : %s
" % physics_flag print "" print ""
单选按钮数据传递给CGI程序
单选按钮被选中时,只有一个选项是必需的.
这里是两个单选按钮的形式例如HTML代码:
MathsPhysics
这段代码的结果是下面的形式
Maths Physics Physics
下面是radiobutton.py脚本来处理单选按钮的网页浏览器输入.
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
if form.getvalue(" subject'):="" subject="form.getvalue('subject')" else:="" print="" "content-type:text="" html\r\n\r\n"="" ""="" "radio="" -="" fourth="" cgi="" program"="" "<h2="">Selected Subject is %s" % subject
print ""
print ""
文本区域数据传递到CGI程序
TEXTAREA元素时使用多行文字要传递给CGI程序.
这里是一个textarea框的形式例如HTML代码:
Type your text here...
下面是textarea.cgi的脚本来处理给定的输入网页浏览器.
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
if form.getvalue('textcontent'):
text_content = form.getvalue('textcontent')
else:
text_content = "Not entered"
print "Content-type:text/html\r\n\r\n"
print ""
print "";
print "Text Area - Fifth CGI Program"
print ""
print ""
print "
Entered Text Content is %s
" % text_content print ""
通过下拉框数据到CGI程序
下拉框是用来当我们有很多可供选择,但只有一个或两个将被选中.
这里是一个下拉框的例子表单的HTML代码
MathsPhysics
这段代码的结果是下面的形式

下面是dropdown.py脚本来处理给定的输入网页浏览器.
#!/usr/bin/python
# Import modules for CGI handling
import cgi, cgitb
# Create instance of FieldStorage
form = cgi.FieldStorage()
# Get data from fields
if form.getvalue('dropdown'):
subject = form.getvalue('dropdown')
else:
subject = "Not entered"
print "Content-type:text/html\r\n\r\n"
print ""
print ""
print "Dropdown Box - Sixth CGI Program"
print ""
print ""
print "
Selected Subject is %s
" % subject print "" print ""
使用CGI中的Cookies
HTTP协议是无状态的协议。但是,对于一个商业网站,它需要保持不同的页面之间的会话信息。例如,一个用户注册完成后,许多网页结束。但如何保持用户会话信息的所有网页.
在许多情况下,使用Cookie的记忆和跟踪首选项,购买,佣金,其他更好的游客体验或网站统计所需的信息是最有效的方法.
它如何工作?
你的服务器发送一些数据到访问者的浏览器Cookie的形式。浏览器可以接受的cookie。如果是这样,它是作为一个访问者的硬盘驱动器上的纯文本记录存储。现在,当游客到达另一个网站上的网页,cookie是用于检索。一旦检索,您的服务器知道/记得存储.
Cookie是一个纯文本的数据5可变长度字段记录:
Expires : cookie将到期日期。如果是空白,访问者退出浏览器时,cookie将到期.
Domain : 您的网站域名.
Path : 目录或网页设置cookie的路径。这可能是空白的,如果你想从任何目录或页面的cookie检索.
Secure : 目录或网页设置cookie的路径。这可能是空白的,如果你想从任何目录或页面的cookie检索.
Name=Value : Cookies是键和值对的形式设置和retrviewed.
设置Cookies
这是很容易发送到浏览器的cookies。这些cookie将被发送HTTP头之前的内容类型提交。假设你要设置用户名和密码的cookie。因此Cookie的设置将做如下
#!/usr/bin/python print "Set-Cookie:UserID=XYZ;\r\n" print "Set-Cookie:Password=XYZ123;\r\n" print "Set-Cookie:Expires=Tuesday, 31-Dec-2007 23:12:40 GMT";\r\n" print "Set-Cookie:Domain=www.yiibai.com;\r\n" print "Set-Cookie:Path=/perl;\n" print "Content-type:text/html\r\n\r\n" ...........Rest of the HTML Content....
从这个例子中,你必须了解如何设置Cookie。我们使用设置CookieHTTP的头设置Cookie.
在这里,它是可选的设置Cookie的属性,如过期,域和路径。值得注意的是,Cookie的之前发送行头 "Content-type:text/html\r\n\r\n.
找回Cookie
这是非常方便地检索所有的设置Cookie。 Cookie是存储在CGI环境变量HTTP_COOKIE的,他们将有以下的形式.
key1=value1;key2=value2;key3=value3....
下面是一个如何获取Cookie的例子.
#!/usr/bin/python
# Import modules for CGI handling
from os import environ
import cgi, cgitb
if environ.has_key('HTTP_COOKIE'):
for cookie in map(strip, split(environ['HTTP_COOKIE'], ';')):
(key, value ) = split(cookie, '=');
if key == "UserID":
user_id = value
if key == "Password":
password = value
print "User ID = %s" % user_id
print "Password = %s" % password
这将产生以下结果由上面的脚本设置的cookie:
User ID = XYZ Password = XYZ123
文件上传的例子:
上传文件的HTML表单必须有enctype属性设置了multipart / form-数据。与该文件类型的输入标记将创建一个“浏览”按钮.
File:
这段代码的结果是下面的形式:

注: 上面的例子已被禁用,故意人上传的文件保存在我们的服务器上。但你可以尝试上面的代码与您的服务器.
这里是处理文件上传的的脚本save_file.py:
#!/usr/bin/python
import cgi, os
import cgitb; cgitb.enable()
form = cgi.FieldStorage()
# Get filename here.
fileitem = form['filename']
# Test if the file was uploaded
if fileitem.filename:
# strip leading path from file name to avoid
# directory traversal attacks
fn = os.path.basename(fileitem.filename)
open('/tmp/' + fn, 'wb').write(fileitem.file.read())
message = 'The file "' + fn + '" was uploaded successfully'
else:
message = 'No file was uploaded'
print """\
Content-Type: text/html\n
%s
""" % (message,)
Note:如果你是以上脚本运行在Unix / Linux,那么你会采取如下替换文件分隔,否则您的Windows上述open()语句应该正常工作.
fn = os.path.basename(fileitem.filename.replace("\\", "/" ))
如何提高“文件下载”对话框 ?
有时你想给其中一个用户点击一个链接,它会弹出“文件下载”对话框的用户,而不是显示实际内容的选项。这是很容易的,将通过HTTP头achived。
这个HTTP头会从上一节中提到的头是不同的.
例如,如果你想从一个给定的链接文件名文件下载,那么它的语法如下.
#!/usr/bin/python
# HTTP Header
print "Content-Type:application/octet-stream; name=\"FileName\"\r\n";
print "Content-Disposition: attachment; filename=\"FileName\"\r\n\n";
# Actual File Content will go hear.
fo = open("foo.txt", "rb")
str = fo.read();
print str
# Close opend file
fo.close()
Python CGI编程(转自易百)的更多相关文章
- python CGI编程-----简单的本地使用(1)
本章节需要安装python开发工具,window平台安装地址:https://www.python.org/downloads/windows/,linux安装地址:https://www.pytho ...
- python CGI 编程实践
文章更新于:2020-03-05 注1:安装 python 参见: python 的安装使用和基本语法 注2:配置 web 环境参见: Windows&linux使用集成环境搭建 web 服务 ...
- 转:python cgi编程
转:http://www.runoob.com/Python/python-cgi.html 什么是CGI CGI 目前由NCSA维护,NCSA定义CGI如下: CGI(Common Gateway ...
- 吴裕雄--天生自然python学习笔记:Python CGI编程
什么是CGI CGI 目前由NCSA维护,NCSA定义CGI如下: CGI(Common Gateway Interface),通用网关接口,它是一段程序,运行在服务器上如:HTTP服务器,提供同客户 ...
- Python CGI编程和CGIHTTPServer
Python2.7 的CGIHTTPServer 可以作为一个简单的HTTP服务器,能够调用cgi脚本 1 在任意目录下创建一个特殊的目录 cgi-bin ,用于存放自己写的脚本(.py或.cgi) ...
- python CGI编程Apache配置
1. 编辑http.conf,添加两行,路径可以自定义 <Directory "C:/AppServ/www/cgi-bin"> AllowOverride None ...
- Python CGI编程
CGI(Common Gateway Interface)通用网关接口,它是一段程序,运行在服务器上.如:HTTP服务器,提供同客户端HTML页面的接口. CGI程序可以是python脚本,PERL脚 ...
- Common Gateway Interface Python CGI编程
https://en.wikipedia.org/wiki/Gateway_(telecommunications) In telecommunications, the term gateway r ...
- 彻底解决python cgi 编程出现的编码问题
Answering this for late-comers because I don't think that the posted answers get to the root of the ...
随机推荐
- 初用Linux, 安装Ubuntu16.04+NVIDIA387+CUDA8.0+cudnn5.1+TensorFlow1.0.1
因为最近Deep Learning十分热门, 装一下TensorFlow学习一下. 本文主要介绍安装流程, 将自己遇到的问题说明出来, 并记录自己如何处理, 原理方面并没有能力解释. 由于本人之前从来 ...
- Android 事件统计
title: Android 事件统计 1.写在前面的话 最近都在看framework的东西,也几天没有写什么东西,今天有点时间写下上次面试遇到的一个问题.问题大概是这样的,如果我需要统计页面的点击事 ...
- 实例PK(Vue服务端渲染 VS Vue浏览器端渲染)
Vue 2.0 开始支持服务端渲染的功能,所以本文章也是基于vue 2.0以上版本.网上对于服务端渲染的资料还是比较少,最经典的莫过于Vue作者尤雨溪大神的 vue-hacker-news.本人在公司 ...
- iOS开发之UIPickerView
1.使用方法 UIPickerView使用和UITableView大致类似.首先设置ViewController为数据源,然后遵守数据源协议< UIPickerViewDataRecouce&g ...
- Dive in python Chapter4 实例
def info(object,spacing=10,collapse=1): """Print methods and doc strings. Takes modul ...
- Windows 10 Creaters Update 画中画模式和窗口高斯模糊
在Windows 10 Creaters Update中,可以给窗口设置高斯模糊了,只要几行代码! <Grid Loaded="Grid_Loaded"> <Gr ...
- iOS性能之其他
本篇文章是个引用,因为这些技术我都只是研究过,但是并没有在项目中使用,也没有深入研究,所以只能当做一个笔记了 网络请求 现在大多数的网络请求都是使用的json格式(相信没有APP再使用XML格式了吧) ...
- XML配置文件的命名空间与Spring配置文件中的头
一直以来,写Spring配置文件,都是把其他配置文件的头拷贝过来,最多改改版本号,也不清楚哪些是需要的,到底是干嘛的.今天整理一下,拒绝再无脑copy. 一.Spring配置文件常见的配置头 < ...
- 给自己的 MAC 添加一个桌面日历
使用 Ubuntu 做自己的办公环境用了将近三年,最近换了新款的 MBP,系统都用的很舒服. 不过 Ubuntu 是在我的 TP W540上部署的,而 W540 + 电源适配太重了(我的电池是9芯的) ...
- poptest老李谈数据库优化总结
poptest老李谈数据库优化总结 poptest是国内唯一一家培养测试开发工程师的培训机构,以学员能胜任自动化测试,性能测试,测试工具开发等工作为目标.如果对课程感兴趣,请大家咨询qq:9088 ...