If you're learning Python, you've probably run into the words "module" and "package" pretty early on, often in the very first line of a script that starts with import. These two concepts are fundamental to how Python code is organized, and understanding them properly will make your code cleaner, more reusable, and much easier to manage as your projects grow.
In this guide you'll learn exactly what a module is, what a package is, how they're different, and how to build your own from scratch with working examples.
What Is a Module?
A module is simply a single Python file containing code, whether that's functions, classes, or variables, that you can reuse in other files. Any .py file you write is technically a module the moment another file imports it.
Example: Creating a Module
Create a file called greetings.py:
# greetings.py
def say_hello(name):
return f"Hello, {name}!"
def say_goodbye(name):
return f"Goodbye, {name}!"Now, in a separate file called main.py, you can import and use that module:
# main.py
import greetings
print(greetings.say_hello("Marshall"))
print(greetings.say_goodbye("Marshall"))Output:
Hello, Marshall!
Goodbye, Marshall!That's it. greetings.py is now a reusable module you can import into any script in the same folder.
Different Ways to Import a Module
Python gives you a few different ways to bring a module's contents into your file, depending on how much of it you need.
# Import the whole module
import greetings
greetings.say_hello("Marshall")
# Import a specific function only
from greetings import say_hello
say_hello("Marshall")
# Import with an alias for shorter code
import greetings as g
g.say_hello("Marshall")
# Import everything (generally not recommended)
from greetings import *
say_hello("Marshall")Using from greetings import * is convenient but can cause naming conflicts in larger projects, so most Python developers prefer being explicit about what they import.
What Is a Package?
A package is essentially a folder that contains multiple related modules, grouped together so they can be organized and imported as a unit. What makes a folder a package (in Python versions before 3.3, and still common practice today) is the presence of a special file called __init__.py.
Example: Creating a Package
my_app/
├── main.py
└── tools/
├── __init__.py
├── math_helpers.py
└── string_helpers.pytools/math_helpers.py:
def add(a, b):
return a + b
def multiply(a, b):
return a * btools/string_helpers.py:
def to_uppercase(text):
return text.upper()
def reverse_text(text):
return text[::-1]tools/__init__.py can be left empty, or used to control what gets exposed when the package is imported:
# tools/__init__.py
from .math_helpers import add, multiply
from .string_helpers import to_uppercase, reverse_textNow in main.py, you can import from the package like this:
# main.py
from tools import add, multiply, to_uppercase
print(add(4, 6))
print(multiply(3, 5))
print(to_uppercase("python packages"))Output:
10
15
PYTHON PACKAGESModule vs Package: The Key Difference
| Concept | What It Is | Example |
|---|---|---|
| Module | A single .py file | greetings.py |
| Package | A folder of related modules | tools/ containing several .py files |
Think of a module as one tool, and a package as a toolbox holding several related tools grouped together.
Built In vs Third Party Modules and Packages
Python code generally falls into three categories:
- Built in modules, which come with Python itself and require no installation, such as
math,os,datetime, andrandom.
import math
import random
print(math.sqrt(16))
print(random.randint(1, 10))- Third party packages, which are installed separately using
pip, such asrequests,numpy, orpandas.
pip install requestsimport requests
response = requests.get("https://api.example.com")
print(response.status_code)- Your own modules and packages, like the
greetings.pymodule andtoolspackage built earlier in this guide.
Common Mistakes Beginners Make
- Forgetting the
.pyextension confusion. When importing, you never include.pyin the import statement. Useimport greetings, notimport greetings.py. - Circular imports. This happens when two modules try to import each other, creating a loop. Restructure shared logic into a third module both files can import from instead.
- Import errors due to file location. Python looks for modules relative to the file being run, so if your folder structure is off, you'll see a
ModuleNotFoundError. Double check your working directory and folder layout. - Overusing
import *. It might feel like a shortcut, but it makes it unclear where a function actually came from, especially in larger codebases.
Conclusion
Modules and packages are the building blocks of organized Python code. A module lets you split code into reusable files, and a package lets you group related modules together into a coherent structure. Once you're comfortable creating and importing your own, you'll find it much easier to read, use, and contribute to larger Python projects, including the massive ecosystem of third party packages available through pip.
Start small: pull a few functions out of your next script into their own module, and get comfortable importing them. That habit alone will make your code noticeably cleaner as your projects grow.
Hit me with a comment!