To write a simple tomcat-like server, you first need to figure out these points:
1. Roles and functions of the Client and the Server
Role A requests data from role B. A can be regarded as the client and B as the server. The main responsibility of the client is to send the request and receive the request information returned by the server according to the request sent by itself, while the main responsibility of the server is to receive the request and return the request data.
2. What a browser is and how it works
We often say B/S, C/S architecture, the so-called B/S refers to browser/server, C/S refers to Client/Server, B/S architecture is actually applied to the browser program, as long as the last in the browser to show the B/S architecture, not in the browser to show the C/S architecture, such as the common League of Legends game. But the essence of only C/S architecture, because the browser is a special client.
What makes browsers special is that there are three main engines underneath:
- DOM parsing engine: i.e. the browser can parse HTML
- Style parsing engine: i.e. browsers can parse CSS
- Script parsing engine: i.e. the browser can parse JAVASCRIPT.
3. Socket
The above mentioned client-server, how to realize the connection between them and data transfer, which is Socket, every programming language has Socket programming, the role of the Socket is to provide the ability to network communications
4. HTTP protocol and the difference between HTTP and TCP/TP
Clients and servers realize the ability to communicate over the network through sockets, which enables the transfer of data. The protocol is to standardize data transmission, that is to say, between the client and the server to transmit data in accordance with certain norms and standards, not blind transmission.
TCP/IP (Transmission Control Protocol/Internet Protocol): Transmission Control Protocol/Internet Protocol
HTTP (HyperText Transfer Protocol): HyperText Transfer Protocol.
TCP/TP Differences.
To make an analogy, TCP/TP is the road and HTTP is the car on the road, so HTTP must be on top of TCP/TP.
HTTP is mainly used in the web program, designed at the beginning is to provide a way to publish and receive HTML pages, so that may be very abstract and difficult to understand. Specifically when we go to visit a website, we only need to get the content based on this site (such as html, css, JavaScript). But we grab the browser to receive the resource package (you can use the Fiddler tool) found that in addition to the web page needs to be the entity content and some of the following information:
HTTP/1.1 200 OK
Cache-Control: private
Content-Type: text/plain; charset=utf-8
Content-Encoding: gzip
Vary: Accept-Encoding
Server: Microsoft-IIS/7.5
X-AspNet-Version: 4.0.30319
X-Powered-By:
Date: Tue, 24 Jan 2017 03:25:23 GMT
Connection: close
Content-Length: 661
This is the http protocol specification, such as Content-Type is to say that the transmission of the file format, Content-Encoding specifies the encoding format. Not only the above, very much, about the meaning of these parameters here do not go one by one introduction!
5. Meaning of URLs
URL (Uniform Resource Locator), that is, we often say that the URL, directly to the resolution of a URL to illustrate him: http://198.2.17.25:8080/webapp/
What this means is to find a server with IP 198.2.17.25 in the directory webapp
But we often see URLs like this:/archive/2005/12/10/
In fact, this is the same as the above, but here there is a domain name resolution, can be resolved to the corresponding IP address
After figuring out the above five points, start writing the code
import socket import sys import getFileContent # Declare an IP and port to be bound, here the local address is used server_address = ('localhost', 8080) class WebServer(): def run(self): print >>, 'starting up on %s port %s' % server_address # Instantiate a socket sock=(socket.AF_INET,socket.SOCK_STREAM) #Bind IPs and ports (server_address) #Setup Listening (1) # Here first give a dead loop, in fact, here is the need for multi-threading, and then the subsequent version will be implemented while True: # Accept the client's request and get the request information and the requested port information connection, client_address = () print >>, 'waiting for a connection' try: # Get request information data = (1024) if data: # Send request messages ((data)) finally: () if __name__ == '__main__': server=WebServer() ()
Very clear and concise.()
The server returns information to the browser, but the data sent must follow the HTTP protocol specification
It is the HTTP protocol specification that is processed for the sent data.
import sys import os # Get information about the data to be sent def getHtmlFile(data): msgSendtoClient="" requestType=data[0:("/")].rstrip() # Determine if it's a GET request or a POST request if requestType=="GET": msgSendtoClient=responseGetRequest(data,msgSendtoClient) if requestType=="POST": msgSendtoClient=responsePostRequest(data,msgSendtoClient) return msgSendtoClient # Open the file, here do not write directly, the second is to go to fetch the file to be sent to write again def getFile(msgSendtoClient,file): for line in file: msgSendtoClient+=line return msgSendtoClient # A way to filter out requests def getMidStr(data,startStr,endStr): startIndex = (startStr) if startIndex>=0: startIndex += len(startStr) endIndex = (endStr) return data[startIndex:endIndex] # Get the size of the data to be sent, according to the HTTP protocol specification, to specify in advance the size of the content of the entity to be sent def getFileSize(fileobject): (0,2) size = () return size # Setting up encoding formats and file types def setParaAndContext(msgSendtoClient,type,file,openFileType): msgSendtoClient+="Content-Type: "+type+";charset=utf-8" msgSendtoClient+="Content-Length: "+str(getFileSize(open(file,"r")))+"\n"+"\n" htmlFile=open(file,openFileType) msgSendtoClient=getFile(msgSendtoClient,htmlFile) return msgSendtoClient # Return data from GET requests def responseGetRequest(data,msgSendtoClient): return responseRequest(getMidStr(data,'GET /','HTTP/1.1'),msgSendtoClient) Return data from #POST requests def responsePostRequest(data,msgSendtoClient): return responseRequest(getMidStr(data,'POST /','HTTP/1.1'),msgSendtoClient) # Request return data def responseRequest(getRequestPath,msgSendtoClient): headFile=open("","r") msgSendtoClient=getFile(msgSendtoClient,headFile) if getRequestPath==" ": msgSendtoClient=setParaAndContext(msgSendtoClient,"text/html","","r") else: rootPath=getRequestPath if (rootPath) and (rootPath): if ".html" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"text/html",rootPath,"r") if ".css" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"text/css",rootPath,"r") if ".js" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"application/x-javascript",rootPath,"r") if ".gif" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"image/gif",rootPath,"rb") if ".doc" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"application/msword",rootPath,"rb") if ".mp4" in rootPath: msgSendtoClient=setParaAndContext(msgSendtoClient,"video/mpeg4",rootPath,"rb") else: msgSendtoClient=setParaAndContext(msgSendtoClient,"application/x-javascript","","r") return msgSendtoClient
Github source download./Jiashengp/Python_httpServer
This is the whole content of this article.