web服务-2、四种方法实现并发服务器-多线程,多进程,协程,(单进程-单线程-非堵塞)
知识点:1、使用多线程,多进程,协程完成web并发服务器 2、单进程-单线程-非堵塞也可以实现并发服务器
1、多进程和协程的代码在下面注释掉的部分,我把三种写在一起了
import socket
import re
import threading
import multiprocessing
import gevent """服务器收发数据"""
def web_server(new_socket): datas = new_socket.recv(1024).decode('utf-8') # 接收浏览器请求的数据
print(datas)
data1 = datas.splitlines()
res = re.match("[^/]+(/[^ ]*)", data1[0]) # 使用正则获取到请求头部中的的第一行中的请求地址对象
if res: # 判断如果请求地址有内容
file_name = res.group(1) # 获取正则对象中的内容
if file_name == '/': # 如果地址是‘/’,也就是请求地址后面没有带指的页面,即主页
file_name = '/index.html'
try:
data = open('./html'+file_name,'rb') # 获取请求的资源在服务器中的文件
except:
data_body = 'HTTP 404 NOT FOUND/1.1\r\n' # 服务器发送消息的头部需要换行,用\r\n
data_body += '\r\n' # 头部和body需要空一行
data_body += '<h1>not found</h1>' # 服务器没找到浏览器需要的资源,返回的html页面
new_socket.send(data_body.encode('utf-8')) # 发送给浏览器
else:
data_head = 'HTTP 200 OK/1.1\r\n' # 请求成功,服务器返回200
data_head += '\r\n'
data_body = data.read()
data.close() # 关闭文件
new_socket.send(data_head.encode('utf-8'))
new_socket.send(data_body)
new_socket.close() # 关闭新的客户端套接字 """主程序入口"""
def main():
tcp_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM) # 创建套接字
tcp_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) # 防止下一次使用该服务器端口被占用情况
tcp_socket.bind(('127.0.0.1', 7789)) # 服务器绑定地址和端口
tcp_socket.listen(128) # 监听套接字
while True:
new_socket, adrees = tcp_socket.accept()
# 1、多进程实现并发服务
# p = multiprocessing.Process(target=web_server, args=(new_socket,))
# p.start() # 2、协程实现并发服务
# p = gevent.spawn(web_server, new_socket)
# p.start() # 3、多线程实现并发服务
t = threading.Thread(target=web_server, args=(new_socket,))
t.start()
t.join()
new_socket.close()
tcp_socket.close() # 关闭监听套接字
if __name__ == '__main__':
main()
运行效果:
浏览器访问本地,会显示一个界面,而且可以开多个浏览器一起运行
2、单进程-单线程-非堵塞也可以实现并发服务器
"""利用单进程-单线程-非堵塞也可以实现web并发服务(即不用多线程,多进程,协程)
思路:1、设置套接字为非堵塞
2、在接收客户端处:因为是非堵塞,所以要捕捉异常,当有客户端进来,新客户端的套接字也要设置非堵塞
还需要判断接recv是否是有数据,没有数据说明客户端断开连接,关闭套接字 """ def main():
main_socket = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
main_socket.bind(('127.0.0.1',7785))
main_socket.listen(128)
main_socket.setblocking(False)
socket_list = list()
while True:
time.sleep(1)
try:
new_socket,new_adress = main_socket.accept()
except:
print('没有客户端进来,请稍等.....')
else:
print('一个新的客户端进来了......')
new_socket.setblocking(False)
socket_list.append(new_socket)
for client in socket_list:
try:
recv_data = client.recv(1024).decode('utf-8')
except:
print('客户端没有发送过来数据')
else:
print('无异常')
if recv_data:
print('客户端发来了消息')
print(recv_data)
data1 = recv_data.splitlines()
res = re.match("[^/]+(/[^ ]*)", data1[0])
if res:
file_name = res.group(1)
print('--------------' + res.group(1))
if file_name == '/':
file_name = '/index.html'
try:
data = open('./html' + file_name, 'rb')
except:
data_body = 'HTTP 404 NOT FOUND/1.1\r\n'
data_body += '\r\n'
data_body += '<h1>not found</h1>'
client.send(data_body.encode('utf-8'))
else:
data_body = data.read()
data.close()
data_head = 'HTTP 200 OK/1.1\r\n'
data_head += 'Content-Length:%d\r\n' % len(data_body)
data_head += '\r\n'
reponse = (data_head.encode('utf-8')+data_body)
client.send(reponse)
else:
client.close()
socket_list.remove(client)
main_socket.close() if __name__ == '__main__':
main()
web服务-2、四种方法实现并发服务器-多线程,多进程,协程,(单进程-单线程-非堵塞)的更多相关文章
- web服务-3、epoll高效率实现并发服务器
知识点: 之前写的四种方法实现并发服务效率都还是低,早期的服务器采用的是select和poll方式,select这种方式的特点是轮询所有套接字去一个个看有没有事件发生,但是装套接字的列表长度是有限制的 ...
- Python并发编程——多线程与协程
Pythpn并发编程--多线程与协程 目录 Pythpn并发编程--多线程与协程 1. 进程与线程 1.1 概念上 1.2 多进程与多线程--同时执行多个任务 2. 并发和并行 3. Python多线 ...
- Tomcat中部署WEB项目的四种方法
对Tomcat部署web应用的方式总结,常见的有以下四种: 1.[使用控制台部署] 访问Http://localhost:8080,并通过Tomcat Manager登录,进入部署界面即可. 2.[利 ...
- [Web 前端] 018 css 清除浮动的四种方法
清除浮动的四种方法 加 clear: ...(见例1) 父级上增加属性 overflow:hidden(见例2.1) 在最后一个子元素的后面加一个空的 div,给它一个样式属性 clear: both ...
- Tomcat系列(11)——Tomcat 部署web应用的4种方法
核心内容 1.在Tomcat中有四种部署Web应用的方式,分别是: (1)利用Tomcat自动部署(项目直接拷贝OR WAR包拷贝 到webapps下) (2)利用控制台进行部署(tomcat的man ...
- 使用Spring Security3的四种方法概述
使用Spring Security3的四种方法概述 那么在Spring Security3的使用中,有4种方法: 一种是全部利用配置文件,将用户.权限.资源(url)硬编码在xml文件中,已经实现过, ...
- Springboot 优雅停止服务的几种方法
在使用Springboot的时候,都要涉及到服务的停止和启动,当我们停止服务的时候,很多时候大家都是kill -9 直接把程序进程杀掉,这样程序不会执行优雅的关闭.而且一些没有执行完的程序就会直接退出 ...
- ASP.NET 使用 Dispose 释放资源的四种方法
Dispose 和 Finalize 是运行的 .NET 和 .NET Core 应用程序释放占用的资源的两种方法.通常,如果应用程序中有非托管资源,应该显式地释放这些资源占用的资源. 由于 Fina ...
- linux下配置ip地址四种方法(图文方法)
主要是用第四种方法 (1)Ifconfig命令 第一种使用ifconfig命令配置网卡的ip地址.此命令通常用来零时的测试用,计算机启动后 ip地址的配置将自动失效.具体用法如下.Ipconfig ...
随机推荐
- 【LR9】【LOJ561】CommonAnts 的调和数 数论 筛法
题目大意 有一个长度为 \(n\) 的序列. 有 \(m\) 次修改,每次给你 \(x,y\),令 \(\forall 1\leq i\leq \lfloor\frac{n}{x}\rfloor,a_ ...
- Java项目模板设置
/** * * @ClassName ${PACKAGE_NAME}.${NAME} * @description ${DESCRIPTION} * @author lisongyu * @creat ...
- 深入理解JVM(4)——对象的创建和访问
1.对象的创建 在语言层面上,创建对象(例如克隆,反序列化)通常仅仅是一个new关键字而已. 在虚拟机中,对象(文中讨论的对象限于普通 Java 对象,不包括数组和 Class 对象等)的创建过程如下 ...
- com.android.support:appcompat-v7:27.+问题解决
新建的项目就报下面的错误,问题指向了app/build.gradle,看起来是版本兼容的问题. 解决方案: 1.查看sdk tools的版本:26.1.1 远程依赖包是27.+,而我们的s ...
- python 学习地址
本章主要记录学习python过程中借鉴的一些网站,并感谢这些博主辛勤付出. python官网:https://www.python.org/ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ...
- JDBC 关闭数据库连接与自动提交【转】
// Jdbc关闭数据库连接时,会隐含一个提交事务的操作 private final static String DB_DRIVER = "oracle.jdbc.driver.Oracle ...
- 第七节:语法总结(1)(自动属性、out参数、对象初始化器、var和dynamic等)
一. 语法糖简介 语法糖也译为糖衣语法,是由英国计算机科学家彼得·约翰·兰达(Peter J. Landin)发明的一个术语,指计算机语言中添加的某种语法,这种语法对语言的功能并没有影响,但是更方 ...
- latex beamer 添加页码
导言中加 \setbeamertemplate{footline}[frame number]
- Shell 自动安装 JDK
1. 脚本文件 installjdk.sh 注意: EOF 前后不能有空格 #!/bin/bash BASE_SERVER=192.168.1.11 yum install -y wget wget ...
- C# 处理文件的压缩与解压
最近做了一个关于winform 程序更新下载的功能,大概思路是,程序检测到服务端系统版本号发生改变,系统需要更新:这时请求服务端更新地址,下载更新包到程序的根目录,更新包是一个压缩包,下载完后再把压缩 ...