11.2.1.2 find service information
In addition to the IP address, each socket address includes an integer port number. Many applications can run on the same host and listen to an IP address, but only one socket can use the port of that address at a time. By combining IP address, protocol and port number, a communication channel can be uniquely identified and messages sent through a socket can reach the correct destination. Some port numbers have been pre assigned to specific protocols. For example, an email server using SMTP uses TCP to complete communication on port 25, and a Web client and server use port 80 to complete HTTP communication. You can use getservbyname() to find the port number and standard name of the network service.
import socket from urllib.parse import urlparse URLS = [ 'http://www.python.org', 'https://www.mybank.com', 'ftp://prep.ai.mit.edu', 'gopher://gopher.micro.umn.edu', 'smtp://mail.example.com', 'imap://mail.example.com', 'pop3://pop.example.com', 'pop3s://pop.example.com', ] for url in URLS: parsed_url = urlparse(url) port = socket.getservbyname(parsed_url.scheme) print('{:>6} : {}'.format(parsed_url.scheme,port))
Although the standardized service is unlikely to change the port, it is better to use a system call to find the port value instead of hard coding out the port number in the program, so it will be more flexible when adding new services in the future.
Operation result:
To reverse complete the service port lookup, use getservtype().
import socket from urllib.parse import urlunparse for port in [80,443,21,70,25,143,993,110,995]: url = '{}://example.com/'.format(socket.getservbyport(port)) print(url)
To construct a service URL from any address, this reverse lookup is useful.
Operation result:
You can use getprotobyname() to get the port number assigned to a transport protocol.
import socket def get_constants(prefix): """Create a dictionary mapping socket module constants to their names. """ return { getattr(socket,n):n for n in dir(socket) if n.startswith(prefix) } protocols = get_constants('IPPROTO_') for name in ['icmp','udp','tcp']: proto_num = socket.getprotobyname(name) const_name = protocols[proto_num] print('{:>4} -> {:2d} (socket.{:<12} = {:2d})'.format( name,proto_num,const_name, getattr(socket,const_name)))
The protocol code value is standardized and defined as a constant in socket. These protocol codes are prefixed with IPPROTO.
Operation result: