Less Popular Python Modules That Every Programmer Should Know


Every popular general-purpose programming language has a fully-featured, well-organized standard library that helps programmers use pre-developed functions or classes to boost their coding productivity. Some programming languages offer pre-imported objects or functions to access the standard library, i.e., JavaScript. Meanwhile, some languages provide separate importable modules. Python’s standard library has many helpful pre-developed importable modules that expose various self-explanatory classes and functions.

Every Python programmer typically knows about popular, general-purpose standard library modules like re, datetime, math, random, etc. These are only a few modules that the complete Python standard library offers. Python offers many inbuilt standard modules to boost your coding productivity and reduce your external dependency list.

In this story, I’ll list some Less Popular but helpful inbuilt Python standard library modules that you can use to boost your coding productivity!

Handling IP Address Data with the ipaddress Module

programmers often use Python to create DevOps automation scripts and computer networking-related programs, so storing and manipulating IP address data becomes a general requirement in Python. The inbuilt ipaddress module offers pre-developed classes for IP v4 and v6 to store and manipulate IP addresses and network configurations.

For example, you can create an IP v4 address object from a string or integer as follows:

import ipaddress

addr_1 = ipaddress.ip_address('192.150.1.2')
addr_2 = ipaddress.ip_address(202)

print(addr_1) # 192.150.1.2
print(addr_2) # 0.0.0.202

print(type(addr_1)) # <class 'ipaddress.IPv4Address'>

We can use traditional arithmetic operators with IP address objects for comparisons and data manipulations. For example, you can increase/decrease and compare IP address objects, as demonstrated in the following code snippet:

import ipaddress

addr = ipaddress.ip_address('192.150.1.2')

print(addr + 2) # 192.150.1.4
print(addr - 10) # 192.150.0.248

print(addr - 2 == ipaddress.ip_address('192.150.1.0') ) # True
print(addr <= ipaddress.ip_address('192.150.1.0') ) # False

This module also lets you work with computer networks by providing a network configuration using the CIDR notation. For example, the following code snippet prints all available host IPs of the 192.150.100.0/24 network configuration:

import ipaddress

net = ipaddress.ip_network('192.150.100.0/24')

print(type(net)) # <class 'ipaddress.IPv4Network'>

for h in net.hosts():
print(h)

Creating Interactive Shells with the cmd Module

There are two types of CLI programs: process-based programs and interactive shells. Process-based CLI programs typically offer various commands and options to execute processes that terminate the CLI program after the execution. Meanwhile, interactive CLI programs accept commands by running a neverending command execution loop. The official Python REPL is a great example of an interactive shell.

The inbuilt cmd module offers a pre-developed class to create interactive shells in Python. You can extend the cmd.Cmd class with your own Python class and implement commands as follows:

import cmd

class Calc(cmd.Cmd):
prompt = 'calc > '
intro = 'Welcome to Calc. Use add, sub, and help commands'

def do_add(self, args):
'Adds two integers and returns the result'
a, b = map(int, args.split())
print(a + b)

def do_sub(self, args):
'Subtracts two integers and returns the result'
a, b = map(int, args.split())
print(a - b)


if __name__ == '__main__':
Calc().cmdloop()

The above interactive CLI program implements add and sub commands that accept two arguments each. For example, you can enter add 10 5 to perform arithmetic addition on 10 and 5 integer parameters. This command-line shell creation class is so flexible and customizable — it lets you customize the prompt and the welcome message, as shown in the above code snippet.

This module automatically creates help commands that print information about each command. Experiment with the above code by running available commands:

A sample interactive shell made using the cmd module, a screen recording by the author

You can add a new command by creating a function with the do_ prefix and using a doc comment for the help command. The cmd module doesn’t parse command-line options in a programmer-friendly way, but you can undoubtedly integrate the argparse module with cmd to implement options for available commands.

We cannot leave without mentioning Bash when we talk about interactive shells. Learn modern Bash scripting techniques from the following story:

Using decimal and fractions Modules for Arithmetic Processing

Every popular programming language typically offers an inbuilt floating point type for representing floating point numbers. However, these inbuilt floating point numbers internally use C language’s hardware-level double or float data type that uses the IEEE-754 standard floating point representation. This standard creates rounding issues with some decimal numbers:

print(0.1 + 0.2 == 0.3)    # False
print(0.1 + 0.2) # 0.30000000000000004

The inbuilt decimal module offers an alternative software-based implementation to handle decimal numbers without rounding issues for more accurate decimal calculations:

from decimal import Decimal

print(Decimal('0.1') + Decimal('0.2')) # 0.3

As you can see in the above example, you can use traditional arithmetic operators with decimal objects.

The inbuilt fractions module helps us store and calculate rational numbers. This module offers the Fraction class with the following constructors to easily create rational numbers:

class fractions.Fraction(numerator=0, denominator=1)
class fractions.Fraction(other_fraction)
class fractions.Fraction(float)
class fractions.Fraction(decimal)
class fractions.Fraction(string)

The Fraction class also works with arithmetic operators similar to the Decimal class, as shown in the following code snippet:

from fractions import Fraction

print(Fraction('1/2') + Fraction('1/6')) # 2/3
print(Fraction(1, 8) * 2) # 1/4
print(Fraction(0.1) / Fraction(0.2)) # 1/2

The fractions module uses a Python-based implementation using some functions from the standard math module:

The source code of the fraction addition, a screenshot by the author

Using the Enum Module for Creating Enumerations

Most programming languages offer an inbuilt enum type to create a group of constants that we can easily assign to other identifiers. For example, you can use an enum object to represent weekdays or a pre-defined color set. In the past, Python didn’t offer an inbuilt way to create enums, so programmers used alternative approaches with constants, dictionaries, and custom enum classes.

Python introduced the standard enum module with the 3.4 version to offer a fully-featured solution for creating enumerated values.

The enum module enables a class-based and functional way to initialize enumeration sets:

from enum import Enum

class AppMode(Enum):
DEBUG = 1
PRODUCTION = 2
TEST = 3

mode = AppMode.DEBUG
print(mode == AppMode.DEBUG) # True

Priority = Enum('Priority', ['LOW', 'MEDIUM', 'CRITICAL'])

print([e.name for e in Priority]) # ['LOW', 'MEDIUM', 'CRITICAL']

You can even create flags that work with bitwise operations using the Flag class from this module. This feature is so helpful for creating bitwise-operations-supported options for Python library development.

Look at the following example that stores multiple flag values on a single identifier using bitwise operations:

from enum import Flag, auto

class LauncherConfig(Flag):
CENTERED_WINDOW = auto()
SHOW_FRAME = auto()
DARK_THEME = auto()

config = LauncherConfig.SHOW_FRAME | LauncherConfig.DARK_THEME

print(config) # LauncherConfig.DARK_THEME|SHOW_FRAME
print(LauncherConfig.DARK_THEME in config) # True

Productive Metaprogramming with the inspect Module

Metaprogramming refers to a programming concept that processes the program structure itself as data. The metaprogramming concept helps us boost coding productivity by reducing code lines required for a specific development requirement. For example, you can call all available methods of an object by inspecting its methods rather than writing every class method statically by hand.

Python offers some inbuilt functions for basic metaprogramming. It also offers the fully-featured inspect module for advanced metaprogramming needs.

Look at the following code snippet that calls all methods of a simple object:

import inspect

class A:
def a(self):
print('a')
def b(self):
print('b')
def c(self):
print('c')

a = A()
for _, m in inspect.getmembers(a, predicate=inspect.ismethod):
m() # a b c

This module offers a productive way to inspect callable functions. Look at the following sample code snippet prints function parameters on the console:

import inspect

def display(name: str, score: int = 50):
print('Hello %s, your score is %d.' % (name, score))

sig = inspect.signature(display)

for p in sig.parameters.values():
print(p)

The signature() function returns all parameters of the given callable function using an ordered dictionary data structure. It extracts parameter names, type hints, and default values, as shown in the following preview:

Inspecting parameters of a function using the inspect module, a screenshot by the author

The PythonFire open-source project turns Python source codes into fully-featured CLI programs using the inspect module. Try building something awesome using the inspect module!

Learn Less Popular Python use cases from the following story:

Using textwrap and colorsys Convenience Modules

Sometimes, programming languages offer pre-developed functions or classes for popular general algorithms to boost programmer productivity. Python offers textwrap with text-wrapping algorithms and colorsys with color system conversion algorithms.

The textwrap module offers pre-developed functions to wrap, shorten, indent, and dedent textual data. Look at the following code that wraps a long paragraph:

import textwrap

s = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aliquam pulvinar tellus sit amet libero viverra feugiat. Curabitur id ultrices metus. Donec lacinia, turpis et fermentum porta, nisl turpis eleifend orci, vel bibendum sapien massa et nisi'

print(textwrap.fill(s, width=50))

The above code snippet applies line-break characters based on the given width and prints a properly wrapped paragraph as follows:

Wrapping a paragraph using the textwrap module in Python, a screenshot by the author

This module also offers a function to shorten long paragraphs based on a given character count and suffix, as shown in the following code snippet:

print(textwrap.shorten(s, 20, placeholder='...'))
# Lorem ipsum dolor...

Python also provides several color conversion convenience functions via the colorsys module to convert color values between popular color systems like RGB, HSV, etc.

Look at the following example code snippet that converts an HSV color value to RGB:

import colorsys

print(colorsys.hsv_to_rgb(1, 0.5, 0.2)) # (0.2, 0.1, 0.1)

This module doesn’t offer an inbuilt function to convert these 0–1-scaled values to hexadecimal representation, but you can do it yourself easily by multiplying values by 255:

import colorsys

print('#%.2x%.2x%.2x' % tuple(round(x * 255) \
for x in colorsys.hsv_to_rgb(1, 0.5, 0.2))) # #331a1a