一、参考
BaseHTTPServer wiki
vsftpd 安装包
二、名词解释
三、正文
1. http协议
1.1 server端
使用BaseHTTPServer
构造简单的server端,用于接收http GET请求,传输文件
from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer
class MyHandler(BaseHTTPRequestHandler):
def do_GET(self):
print('--get file--', self.path)
mime_type = 'application/pdf'
file_name = self.path.split('/')[-1]
f = open(self.path)
self.send_response(200)
self.send_header('Content-type', mime_type)
self.send_header('Content-Disposition', 'attachment; filename=%s' % file_name)
self.end_headers()
self.wfile.write(f.read())
f.close()
return
try:
server = HTTPServer(('server_a_host', server_a_port), MyHandler)
server.serve_forever()
except Exception as e:
print('error', str(e))
~
1.2 client端
使用requests
模块,直接构造http GET请求
import requests
def get_file(file_path):
print('---start get file---', file_path)
url = 'http://server_a_host:server_a_port'
url = url + file_path
res = requests.get(url=url)
print(res.status_code, res.text)
if __name__ == '__main__':
file_path = '/data/test.pdf'
get_file(file_path=file_path)
1.3 tcpdump录制pcap包
在client server中录制接收到的http文件流量包
tcpdump -i network_card_name 'host server_a_host and port server_a_port' -w /tmp/http_test.pcap
2. ftp协议
2.1 vsftpd服务
2.1.1 yum安装
2.1.2 开启服务
2.1.3 配置服务
配置文件路径为/etc/vsftpd/vsftpd.conf
修改参数, anonymous_enable=NO
, local_root=/data/ftp_data
配置后,重启vsftpd服务
2.2 ftp客户端
2.2.1 安装ftp客户端
yum install ftp
2.2.2 读写文件
ftp ftpd_server_host
get test.txt /tmp/test.txt
2.3 tcpdump录制pcap包
在ftpd server端录制pcap包
tcpdump -i network_card_name host client_host_name -w /home/ftp.pcap
3. smtp协议
3.1 smtp服务端
利用smtpd
模块创建smtp server服务
from __future__ import print_function
from datetime import datetime
import asyncore
from smtpd import SMTPServer
class EmlServer(SMTPServer):
no = 0
def process_message(self, peer, mailfrom, rcpttos, data):
print('----receive smtp email----')
filename = '%s-%d.eml' % (datetime.now().strftime('%Y%m%d%H%M%S'), self.no)
f = open(filename, 'w')
f.write(data)
f.close()
print('%s saved.' % filename)
self.no += 1
def run():
# start the smtp server
foo = EmlServer((server_a_host, server_a_port), None)
try:
asyncore.loop()
except KeyboardInterrupt:
pass
if __name__ == '__main__':
run()
3.2 smtp客户端
利用python内置模块smtplib
,创建一个smtp client端请求,发送一个smtp邮件,附件为一个pdf文件
客户端为server_b_host
import smtplib
from email import encoders
from email.mime.base import MIMEBase
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
subject = "An email with attachment"
body = "an email with attachment sent from server_a"
sender_email = "[email protected]"
receiver_email = "[email protected]"
# Create a multipart message and set headers
message = MIMEMultipart()
message["From"] = sender_email
message["To"] = receiver_email
message["Subject"] = subject
message["Bcc"] = receiver_email # Recommended for mass emails
# Add body to email
message.attach(MIMEText(body, "plain"))
filename = "/data/smtp/test_file_name.pdf"
# Open PDF file in binary mode
with open(filename, "rb") as attachment:
part = MIMEBase("application", "octet-stream")
part.set_payload(attachment.read())
# Encode file in ASCII characters to send by email
encoders.encode_base64(part)
# Add header as key/value pair to attachment part
part.add_header(
"Content-Disposition", "attachment; filename=test_file_name",
)
# Add attachment to message and convert message to string
message.attach(part)
text = message.as_string()
# Log in to server using secure context and send email
server = smtplib.SMTP(server_a_host, server_a_port)
server.sendmail(sender_email, receiver_email, text)
3.3 tcpdump录制pcap包
在smtp服务端,使用tcpdump录制pcap包
tcpdump -i network_card_name host server_b_host and port server_a_port -w /tmp/smtp.pcap
4. pop3协议
4.1 pop3服务端
使用已有网易邮箱,当作server端
4.2 pop3客户端
利用poplib
模块,实现邮件获取和邮件附件下载
# -*- coding:utf-8 -*-
import poplib
from email.parser import Parser
from email.header import decode_header
from email.header import Header
class Pop3Client(object):
def __init__(self, user, password, eamil_server):
self.user = user
self.password = password
self.pop3_server = eamil_server
def guess_charset(self, msg):
charset = msg.get_charset()
if charset is None:
content_type = msg.get('Content-Type', '').lower()
pos = content_type.find('charset=')
if pos >= 0:
charset = content_type[pos + 8:].strip()
return charset
def get_content(self, msg):
content = ''
content_type = msg.get_content_type()
print('content_type:', content_type)
if content_type == 'text/plain':
content = msg.get_payload(decode=True)
charset = self.guess_charset(msg)
if charset:
content = content.decode(charset)
return content
def get_att(self, msg_in):
attachment_files = []
for part in msg_in.walk():
file_name = part.get_param("name")
if file_name:
h = Header(file_name)
dh = decode_header(h)
filename = dh[0][0]
if dh[0][1]:
filename = filename.decode(dh[0][1])
data = part.get_payload(decode=True)
att_file = open(filename, 'wb')
att_file.write(data)
att_file.close()
attachment_files.append(filename)
else:
print(self.get_content(part))
return attachment_files
def start(self):
pop3_server = poplib.POP3(self.pop3_server, 110, timeout=10)
print(pop3_server.getwelcome().decode('utf-8'))
pop3_server.user(self.user)
pop3_server.pass_(self.password)
resp, mails, octets = pop3_server.list()
resp, lines, octets = pop3_server.retr(len(mails))
msg_content = b'\r\n'.join(lines).decode('utf-8')
msg = Parser().parsestr(msg_content)
attach_file = self.get_att(msg)
print(attach_file)
pop3_server.quit()
if __name__ == '__main__':
user = '163_user'
password = '163_password'
eamil_server = 'pop.163.com'
pop3_client = Pop3Client(
user=user,
password=password,
eamil_server=eamil_server
)
pop3_client.start()
4.3 tcpdump录制pcap包
tcpdump -i network_card_name host pop.163.com