Web服务器本质上是一个提供Web服务的应用程序,运行在服务器上,用于处理HTTP请求和响应。它接收来自客户端(通常是浏览器)的HTTP请求,根据请求的URL、参数等信息生成HTTP响应,并将响应返回给客户端,完成客户端的请求。Web服务器可以使用多种编程语言和技术实现,通过对套接字的处理并遵循HTML等浏览器兼容格式即可实现。

如果需要自行实现一个Web服务器则本质上就是需要完成套接字的处理,并在处理时增加遵循HTTP格式的头部数据即可,如下是一个简单的支持Web服务器的套接字程序,该程序运行后会在本机的80端口侦听,当用于通过浏览器访问时则会自动传输一段话。

import socket

def handle_request(client):
buf = client.recv(1024)
client.send(bytes("HTTP/1.1 200 OK\r\n\r\n","UTF-8"))
client.send(bytes("<b>Hello lyshark</b>","UTF-8")) if __name__ == "__main__":
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.bind(("localhost",80))
sock.listen(5) while True:
connection, address = sock.accept()
handle_request(connection)
connection.close()

运行上述代码片段,读者可自行打开浏览器并访问http://localhost:80端口,则此时会弹出一段问候语,说明我们的服务器已经可以被浏览器解析了。

当然上述代码还有很大的优化空间,首先要解决的问题是让页面具有动态渲染的功能,此处我们可以采用jinja2模板,该模板允许在Web应用程序中渲染HTML,其主要特点是可配置性高、快速、安全且易于使用,使用时读者需要自行执行pip install jinja2来安装此模板,至此我们就可以在Web服务器带啊吗中使用模板引擎进行输出。

如下代码片段则是一个使用了make_server类的服务器实现,在代码中我们定义了一个url_func列表用于存储路由规则,路由规则代表的是当有浏览器访问服务器时则自动使用特定规则内的特定函数处理这个规则,在代码中我们分别定义了两个路由函数,其中index()用于展示首页信息,而jinja()则用于展示模板渲染功能实现,至此读者需要在主目录下分别创建两个文件index.html代表网站主页,而jinja.html则代表模板渲染页面,我们以jinja.html为例创建如下代码;

<body>
<h1>{{name}}</h1>
<ul>
{% for item in user_list %}
<li>{{item}}</li>
{% endfor %}
</ul>
</body>

接着编写服务器程序,在jinja()路由函数内通过读取jinja.html文件并使用template.render()函数给特定的变量传入不同的参数,当页面渲染好以后,则通过return将该请求返回给RunServer函数,再由该函数return [response,]返回给被调用客户。

from wsgiref.simple_server import make_server
from jinja2 import Template # /index/的路由函数
def index():
with open("./index.html","r",encoding="utf-8")as fp:
recv = fp.read()
return recv.encode("utf-8") # /jinja/的路由函数
def jinja():
with open("./jinja.html","r",encoding="utf-8")as fp:
data = fp.read()
template = Template(data)
recv = template.render(name='John Doe', user_list=['lyshark', 'wang'])
return recv.encode("utf-8") # 定义路由规则
url_func = [
('/index/',index),('/jinja/',jinja)] def RunServer(environ,star_response):
star_response("200 OK",[('Content-Type','text/html;charset=urf-8')])
url = environ["PATH_INFO"]
rAddr = environ["REMOTE_ADDR"]
rHost = environ["HTTP_HOST"]
print("[+] 根域名: {} 路径: {} 目标IP: {}".format(rHost,url,rAddr))
func = None
for i in url_func:
if i[0] == url:
func = i[1]
break
if func:
response = func()
else:
response = b"** 404 not found **"
return [response,] if __name__ == "__main__":
httpd = make_server("0.0.0.0",80,RunServer)
print("[*] 服务已启动 0.0.0.0:80")
httpd.serve_forever()

运行上述代码,读者可以打开浏览器并访问localhost/jinja/路径,此时即可看到经过选然后的HTML页面,如下图所示;

21.12 Python 实现网站服务器的更多相关文章

  1. 手写网站服务器~用Python手动实现一个简单的服务器,不借助任何框架在浏览器中输出任意内容

    写在前面的一些P话: 在公司网站开发中,我们往往借助于Flask.Django等网站开发框架去提高网站开发效率.那么在面试后端开发工程师的时候,面试官可能就会问到网站开发的底层原理是什么? 我们不止仅 ...

  2. Python监控网站接口值

    Python监控网站接口值: #!/usr/bin/env python # -*- coding: utf-8 -*- __author__ = 'liudong' import urllib,sy ...

  3. 在云主机上基于nginx部署基于Flask的网站服务器 (自己部署 )

    1.申请云主机 a.阿里云 (注意:阿里云的服务器需要手动添加安全规则使能80端口) b.腾讯云 2.把网站服务器程序拷贝到云主机 3.远程登录云主机 4.解压网站服务器程序 yum install ...

  4. Python 绝技 —— UDP 服务器与客户端

    i春秋作家:wasrehpic 0x00 前言 在上一篇文章「Python 绝技 —— TCP 服务器与客户端」中,介绍了传输层的核心协议 TCP ,并运用 Python 脚本的 socket 模块演 ...

  5. python批量操作Linux服务器脚本,key登录(执行命令、上传、下载)(二)

       -*-   2 #批量操作linux服务器(执行命令,上传,下载)   3 #!/usr/bin/python   4 import paramiko   5 import datetime   ...

  6. CentOS7 实战部署tomcat网站服务器

    简介:实战演练tomcat网站服务器的搭建 Tomcat:是一个开源免费的Web应用服务器,性能稳定,是目前比较流行的Web应用服务器   tomcat官网下载: https://tomcat.apa ...

  7. Python 创建本地服务器环境生成二维码

    一. 需求 公司要做一个H5手机端适配页面,因技术问题所以H5是外包的,每次前端给我们源码,我们把源码传到服务器让其他人访问看是否存在bug,这个不是很麻烦吗?有人说,可以让前端在他们的服务器上先托管 ...

  8. IIS网站服务器性能优化指南(转载)

    原文网址:http://www.phontol.com/20090507_419416_1.html       Windows Server自带的互联网信息服务器(Internet Informat ...

  9. 针对phpStudy网站服务器的入侵

    今天客户服务器上出现报警,查找了下原因,发现根目录下有wk.php E:\phpStudy\MySQL\bin\mysqld.exe, Version: (MySQL Community Server ...

  10. python批量操作Linux服务器脚本,ssh密码登录(执行命令、上传、下载)(一)

     -*-          paramiko.util.log_to_file(         ssh = paramiko.SSHClient()          ssh.set_missing ...

随机推荐

  1. AI绘画,Midjourney极简入门

    前几天看报道说: 一位小哥用AI绘画工具Midjourney生成的作品,在美国科罗拉多州博览会的艺术比赛中获得了第一名. 作者表示,他多次调整了输入的提示词,生成了100多幅画作,经过数周的修改和挑选 ...

  2. Codeforces Round #669 (Div. 2) A、B题题解

    Problem A - Ahahahahahahahaha https://codeforces.com/contest/1407/problem/A 题意: 给定一个偶数数组(元素值 0,1),在删 ...

  3. mysql和redis库存扣减和优化

    前言 大流量情况下的库存是老生常谈的问题了,在这里我整理一下mysql和redis应对扣除库存的方案,采用jmeter进行压测. JMETER设置 库存初始值50,线程数量1000个,1秒以内启动全部 ...

  4. Intellij IDEA安装与配置教程(Windows版)

    Intellij IDEA(简称IDEA)是Java语言的集成开发环境,在业界公认为是一款优秀的Java开发工具.分为Community社区版(免费)和Untimate终极版(付费). IDEA是一款 ...

  5. 传统单节点网站的 Serverless 上云

    什么是函数?刚刚考完数学没多久的我,脑里立马想到的是自变量.因变量.函数值,也就是y=f(x).当然,在计算机里,函数function往往指的是一段被定义好的代码程序,我们可以通过传参调用这个定义好的 ...

  6. [Err] 1055 - Expression #1 of ORDER BY clause is not in GROUP BY clause 解决

    Navicat 连接mysql 执行 CREATE TABLE  语句 执行成功后总是包如下错误 [Err] 1055 - Expression #1 of ORDER BY clause is no ...

  7. vue学习笔记 十、状态管理基础结构

    系列导航 vue学习笔记 一.环境搭建 vue学习笔记 二.环境搭建+项目创建 vue学习笔记 三.文件和目录结构 vue学习笔记 四.定义组件(组件基本结构) vue学习笔记 五.创建子组件实例 v ...

  8. 如何将接口的返回值中所需信息提取出来作为其他接口的入参使用(postman与jmeter的使用)

    一.背景: 偶尔会用到一个场景,两个接口之前的调用有依赖关系,将其中一个的返回参数中的部分信息取出来作为入参在第二个接口中使用,代码内是比较好实现,只要定义一个变量,用于参数传递. 如果是测试过程中使 ...

  9. linux 服务器运行jmeter 进行服务性能压测

    本文为博主原创,转载请注明出处: 起初需要了解项目服务的性能和瓶颈,就想要用 jmeter 进行压测,刚开始都是启动本地的jmeter 压测服务器上项目服务的性能,发现服务器的 cpu 和内存等一直升 ...

  10. Redis 缓存与数据库数据不一致问题

    Redis缓存与数据库数据不一致问题是指在使用Redis作为缓存系统时,由于缓存和数据库之间的操作没有同步或处理不当,导致缓存中的数据与数据库中的数据不同步,产生数据不一致的情况. 现象: 数据库更新 ...