Maintenance

Site is under maintenance — quizzes are still available.

Go to quizzes
Sponsored Reserved space — layout preview until AdSense is connected

Generate a Monthly Calendar PDF in Python

Create a Python utility that generates a monthly calendar PDF using ReportLab, with weekday headers and day numbers laid out in a grid.

Medium Python 3.9+ Jun 28, 2026 Files & data 2 views 0 copies

Requires third-party packages — install first
pip install reportlab

Python code

41 lines
Python 3.9+
from calendar import TextCalendar
from datetime import datetime
from reportlab.lib.pagesizes import letter
from reportlab.pdfgen import canvas
import os

def generate_monthly_calendar_pdf(year, month, filename="calendar.pdf"):
    cal = TextCalendar()
    days = cal.monthdays2calendar(year, month)
    
    month_name = datetime(year, month, 1).strftime("%B %Y")
    c = canvas.Canvas(filename, pagesize=letter)
    width, height = letter
    
    c.setFont("Helvetica-Bold", 24)
    c.drawCentredString(width / 2, height - 60, month_name)
    
    cell_width = (width - 40) / 7
    cell_height = 30
    start_y = height - 100
    
    days_header = ["Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"]
    for i, day in enumerate(days_header):
        x = 20 + i * cell_width
        c.setFont("Helvetica-Bold", 10)
        c.drawString(x + 5, start_y + 5, day)
    
    for row_idx, week in enumerate(days):
        y = start_y - (row_idx + 1) * (cell_height + 5)
        for col_idx, (day_num, _) in enumerate(week):
            if day_num != 0:
                x = 20 + col_idx * cell_width
                c.setFont("Helvetica", 9)
                c.drawString(x + 3, y + 3, str(day_num))
    
    c.save()
    return os.path.abspath(filename)

if __name__ == "__main__":
    path = generate_monthly_calendar_pdf(2025, 3, "march_2025.pdf")
    print(f"Calendar PDF saved to: {path}")

Output

stdout
Calendar PDF saved to: /full/path/to/march_2025.pdf

How it works

The code uses TextCalendar.monthdays2calendar to get the day numbers and their weekday positions for each week of the month. ReportLab's canvas.Canvas draws the title, weekday headers, and day numbers at calculated coordinates. The grid layout divides the page width by 7 to compute equal cell widths. Saving the canvas produces a PDF file at the specified path.

Common mistakes

  • Forgetting to install reportlab via pip before running the script
  • Using monthdayscalendar instead of monthdays2calendar, which omits weekday info
  • Not adjusting fonts or cell sizes for months with 5 or 6 weeks, causing overflow
  • Hardcoding paths without os.path.abspath for cross-platform compatibility

Variations

  1. Use `from calendar import HTMLCalendar` to generate an HTML calendar instead
  2. Add event annotations by modifying the draw loop to include text underneath day numbers

Real-world use cases

  • Distributing printable shift schedules or appointment calendars to team members
  • Creating branded monthly planners for marketing or sales content
  • Generating date-stamped worksheets or activity logs for classroom use

Sponsored

Sponsored Reserved space — layout preview until AdSense is connected

Run locally

This sample needs third-party packages, so it cannot run in the browser IDE. Copy the code above, install the packages shown at the top, then run it in your own Python environment.

More from Files & data

Related tutorials and quizzes for this topic.