目录
https://www.runoob.com/python3/python3-cgi-programming.html
2.5文件下载对话框
https://www.runoob.com/python3/python3-cgi-programming.html
菜鸟教程
继上一篇,以下.py文件均放在xampp的cgi-bin下
先解决一下中文乱码问题:
1.修改apache的httpd.conf文件,新增下面
AddDefaultCharset off
2.原页面中文乱码
3.去掉页面内的下面代码
4.重启apache再运行一次
中文显示正常
1.一个简单的CGI脚本输出CGI的环境变量
#!D:/python/python.exe (这里改成自己的)
# -*- coding: utf-8 -*-
import os
print("Content-type: text/html")
print()
print("<meta charset=\"utf-8\">")
print("<b>环境变量</b><br>")
print("<ul>")
for key in os.environ.keys():
print("<li><span style='color:green'>%30s </span> : %s </li>" % (key, os.environ[key]))
print("</ul>")
页面:
2.GET和POST方法
2.1 GET请求
- GET 请求可被缓存
- GET 请求保留在浏览器历史记录中
- GET 请求可被收藏为书签
- GET 请求不应在处理敏感数据时使用
- GET 请求有长度限制
- GET 请求只应当用于取回数据
#!D:/python/python.exe
# -*- coding: utf-8 -*-
# CGI处理模块
import cgi
# 创建 FieldStorage 的实例化
form = cgi.FieldStorage()
# 获取数据
site_name = form.getvalue('name')
site_age = form.getvalue('age')
print("Content-type:text/html")
print()
print("<html>")
print("<head>")
print("<title>菜鸟教程 CGI 测试实例</title>")
print("</head>")
print("<body>")
print("<h2>女朋友名字:%s 年龄:%s</h2>" % (site_name, site_age))
print("</body>")
print("</html>")
打开链接:
http://localhost/cgi-bin/get.py?name=ctt&age=19
运行成功
2.1.1用GET的简单的表单实例
以下是一个通过HTML的表单使用GET方法向服务器发送两个数据,提交的服务器脚本是get.py文件,get.html 代码如下:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<form action="/cgi-bin/get.py" method="get">
女朋友名称: <input type="text" name="name"> <br />
年龄: <input type="text" name="age" />
<input type="submit" value="提交" />
</form>
</body>
</html>
这个文件放在xampp/htdocs下
点击:提交
2.2 POST请求
使用POST方法向服务器传递数据是更安全可靠的,像一些敏感信息如用户密码等需要使用POST传输数据。
文件一样的位置,把get改成了post
2.2.1 通过CGI程序传递checkbox数据
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<form action="/cgi-bin/post.py" method="POST" target="_blank">
<input type="checkbox" name="runoob" value="on" /> 菜鸟教程
<input type="checkbox" name="google" value="on" /> Google
<input type="submit" value="选择站点" />
</form>
</body>
</html>
#!D:/python/python.exe
# 引入 CGI 处理模块
import cgi
# 创建 FieldStorage的实例
form = cgi.FieldStorage()
# 接收字段数据
if form.getvalue('google'):
google_flag = "是"
else:
google_flag = "否"
if form.getvalue('runoob'):
runoob_flag = "是"
else:
runoob_flag = "否"
print("Content-type:text/html")
print()
print("<html>")
print("<head>")
print("<title>菜鸟教程 CGI 测试实例</title>")
print("</head>")
print("<body>")
print("<h2> 菜鸟教程是否选择了 : %s</h2>" % runoob_flag)
print("<h2> Google 是否选择了 : %s</h2>" % google_flag)
print("</body>")
print("</html>")
2.3 CGI中使用Cookie
在 http 协议一个很大的缺点就是不对用户身份的进行判断,这样给编程人员带来很大的不便, 而 cookie 功能的出现弥补了这个不足。
cookie 就是在客户访问脚本的同时,通过客户的浏览器,在客户硬盘上写入纪录数据 ,当下次客户访问脚本时取回数据信息,从而达到身份判别的功能,cookie 常用在身份校验中。
cookie的语法
http cookie的发送是通过http头部来实现的,他早于文件的传递,头部set-cookie的语法如下:
Set-cookie:name=name;expires=date;path=path;domain=domain;secure
- name=name: 需要设置cookie的值(name不能使用";"和","号),有多个name值时用 ";" 分隔,例如:name1=name1;name2=name2;name3=name3。
- 期限expires=date: cookie的有效期限,格式: expires="Wdy,DD-Mon-YYYY HH:MM:SS"
- path=path: 设置cookie支持的路径,如果path是一个路径,则cookie对这个目录下的所有文件及子目录生效,例如: path="/cgi-bin/",如果path是一个文件,则cookie指对这个文件生效,例如:path="/cgi-bin/cookie.cgi"。
- 域名domain=domain: 对cookie生效的域名,例如:domain="www.runoob.com"
- 安全secure: 如果给出此标志,表示cookie只能通过SSL协议的https服务器来传递。
- cookie的接收是通过设置环境变量HTTP_COOKIE来实现的,CGI程序可以通过检索该变量获取cookie信息。
#!/usr/bin/python3
#
print ('Content-Type: text/html')
print ('Set-Cookie: name="菜鸟教程";expires=Wed, 28 Aug 2016 18:30:00 GMT')
print ()
print ("""
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<h1>Cookie set OK!</h1>
</body>
</html>
""")
#!/usr/bin/python3
# 导入模块
import os
import http.cookies
print ("Content-type: text/html")
print ()
print ("""
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<h1>读取cookie信息</h1>
""")
if 'HTTP_COOKIE' in os.environ:
cookie_string=os.environ.get('HTTP_COOKIE')
c= http.cookies.SimpleCookie()
# c=Cookie.SimpleCookie()
c.load(cookie_string)
try:
data=c['name'].value
print ("cookie data: "+data+"<br>")
except KeyError:
print ("cookie 没有设置或者已过去<br>")
print ("""
</body>
</html>
""")
1
2.4文件上传实例
HTML设置上传文件的表单需要设置 enctype 属性为 multipart/form-data,代码如下所示:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<form enctype="multipart/form-data"
action="/cgi-bin/save_file.py" method="post">
<p>选中文件: <input type="file" name="filename" /></p>
<p><input type="submit" value="上传" /></p>
</form>
</body>
</html>
save_file.py脚本文件代码如下:
#!/usr/bin/python3
import cgi, os
import cgitb; cgitb.enable()
form = cgi.FieldStorage()
# 获取文件名
fileitem = form['filename']
# 检测文件是否上传
if fileitem.filename:
# 设置文件路径
fn = os.path.basename(fileitem.filename)
open('/tmp/' + fn, 'wb').write(fileitem.file.read())
message = '文件 "' + fn + '" 上传成功'
else:
message = '文件没有上传'
print ("""\
Content-Type: text/html\n
<html>
<head>
<meta charset="utf-8">
<title>菜鸟教程(runoob.com)</title>
</head>
<body>
<p>%s</p>
</body>
</html>
""" % (message,))
将以上代码保存到 save_file.py,并修改 save_file.py 权限:
chmod 755 save_file.py
以上 cookie 设置颜色 Gif 如下所示:
如果你使用的系统是Unix/Linux,你必须替换文件分隔符,在window下只需要使用open()语句即可:
fn = os.path.basename(fileitem.filename.replace("\\", "/" ))
2.5文件下载对话框
我们先在当前目录下创建 foo.txt 文件,用于程序的下载。
文件下载通过设置HTTP头信息来实现,功能代码如下:
#!/usr/bin/python3
# HTTP 头部
print ("Content-Disposition: attachment; filename=\"foo.txt\"")
print ()
# 打开文件
fo = open("foo.txt", "rb")
str = fo.read();
print (str)
# 关闭文件
fo.close()