dmesg --follow
[ 68673720.000 ] posts.x: @davidsenra you will love this!  |   [ 68673600.000 ] posts.x: https://t.co/vhJifvV8y9  |   [ 68673600.000 ] posts.x: This Jay-Z documentary, In 8, is exceptional! Nearly 6 hours of intimate conversation between @sc and the brilliant @RickRubin. It’s rare to get such…  |   [ 68662260.000 ] posts.x: Full talk on turning re-prompted fixes into linters, including the OpenAPI drift fix and the skill-writing whack-a-mole:  |   [ 68662260.000 ] posts.x: Re-prompting an agent to fix the same sloppy pattern over and over isn't a workflow, it's a sign the rule should live in code, not in your head…  |   [ 68650020.000 ] posts.x: ↻ @willcb: me: kinda fucked up how many people are offloading their whole lives to muse or instinct or grokbot or whatever claude: yeah  |   [ 68650020.000 ] posts.x: ↻ @iamdevloper: signs you've become the senior dev: you're the only one who understands the deploy script you're the only one who remembe…  |   [ 68649720.000 ] posts.x: Gooooooooood morning! Brazil Oberon Cerrado. Roasted 110 seconds past first crack. Milk chocolate and almond.  |   [ 68647800.000 ] posts.x: @Saanvi_dhillon “Git expert” is a weird flex, though, isn’t it?  |   [ 68610720.000 ] posts.x: @sujee_dev @dkundel @aiDotEngineer Thanks mate!  |   [ 68600580.000 ] posts.x: Full talk on the Codex app server protocol and what you can build on top of the Codex harness:  |   [ 68600580.000 ] posts.x: A lot of engineers assume building their own agent interface means writing their own agent harness from scratch. @dkundel, Developer Experience Lead…  |   [ 68564580.000 ] posts.x: Full talk on why Reducto deleted their all-in-one MCP server and rebuilt it around fewer, state-aware tools and visible agent uncertainty:  |   [ 68564580.000 ] posts.x: A single massive MCP file worked fine as a curated demo and broke the moment Reducto's own team got hold of it. @abhiarya, who works on product…  |  
corey@gallon.me:~/til$

How to Add Custom HTML Pages to a Pelican Site

FIGURE 1 ⋅ How to Add Custom HTML Pages to a Pelican Site

Introduction

Pelican is a powerful static site generator written in Python, primarily designed for blogs. However, sometimes you need to include custom HTML pages that don't fit into Pelican's standard content model. This guide explains how to add standalone HTML pages to your Pelican site while preserving their exact formatting and functionality.

Method: Using Static Files

The most reliable method for adding custom HTML pages to a Pelican site is to use the static files approach. This method bypasses Pelican's content processing system and treats your HTML file as a static asset.

Step 1: Create a Static Directory

First, create a static directory inside your Pelican project's content folder:

mkdir -p content/static

Step 2: Add Your HTML File

Copy your custom HTML file to the static directory:

cp your-custom-page.html content/static/

Step 3: Configure Pelican

Edit your pelicanconf.py file to include the following settings:

# Include static directory in static paths
STATIC_PATHS = ['images', 'static']  # Add other paths as needed

# Exclude static directory from content processing
ARTICLE_EXCLUDES = ['static']
PAGE_EXCLUDES = ['static']

# Optional: Configure a specific URL for your page
EXTRA_PATH_METADATA = {
    'static/your-custom-page.html': {'path': 'custom-page/index.html'},
}

This configuration does three important things:

  • STATIC_PATHS tells Pelican to copy files from the static directory to the output
  • ARTICLE_EXCLUDES and PAGE_EXCLUDES prevent Pelican from trying to process the files as content
  • EXTRA_PATH_METADATA allows you to specify a custom output path for your HTML file

Step 4: Build Your Site

Now when you build your Pelican site, your custom HTML page will be copied to the output directory:

pelican content

Your page will be accessible at yourblog.com/custom-page/.

Why This Works

This approach works because:

  • Bypasses Content Processing: By excluding the static directory from content processing, Pelican won't try to parse your HTML file for metadata or apply templates to it.

  • Preserves Original HTML: Your HTML file is copied as-is to the output directory, preserving all styling, scripts, and functionality.

  • Custom URL Structure: Using EXTRA_PATH_METADATA allows you to place the file at any URL path you want, creating clean URLs without the .html extension.

Common Issues and Solutions

Issue: Pelican tries to process HTML as content
Solution: Make sure you've added the static directory to both ARTICLE_EXCLUDES and PAGE_EXCLUDES.

Issue: CSS or JavaScript paths are broken
Solution: If your HTML file references relative paths for CSS or JavaScript, you may need to adjust them to work with your site's URL structure.

Issue: HTML file not showing up in output
Solution: Verify that you've added the static directory to STATIC_PATHS and that the file exists in the correct location.

Advanced: Linking to Your Custom Page

To link to your custom page from your Pelican site's navigation menu, you'll need to modify your theme's templates. Most themes use a variable like MENUITEMS in the pelicanconf.py file:

MENUITEMS = [
    ('Home', '/'),
    ('Blog', '/blog/'),
    ('Custom Page', '/custom-page/'),
]

Integrating Custom Pages with Site Navigation

After adding your custom HTML page to your Pelican site, you'll likely want to make it accessible through your site's navigation menu. There are several ways to accomplish this, depending on your theme and navigation preferences.

Using MENUITEMS for Basic Navigation

The simplest approach is to use Pelican's built-in MENUITEMS configuration variable, which most themes support. In your pelicanconf.py file, add or modify the MENUITEMS list:

MENUITEMS = [
    ('Home', '/'),
    ('Blog', '/blog/'),
    ('Custom Page', '/custom-page/'),  # This links to your custom HTML page
]

Each tuple contains two elements: 1. The display name that will appear in your menu 2. The URL path to the page (which should match what you configured in EXTRA_PATH_METADATA)

If your theme automatically displays categories in the navigation menu, you'll need to consider how static menu items and dynamic category links will interact. Here are some common configurations:

Option 1: Disable Category Menu Items

If you prefer to manually control all menu items, you can disable automatic category links:

# Disable automatic category links in menu
DISPLAY_CATEGORIES_ON_MENU = False

# Define your custom menu structure
MENUITEMS = [
    ('Home', '/'),
    ('Blog', '/blog/'),
    ('Categories', '/categories/'),  # Link to category index if available
    ('Custom Page', '/custom-page/'),
]

Option 2: Keep Both Systems

Many themes will gracefully handle both static menu items and dynamic category links, placing MENUITEMS first, followed by category links:

# Keep automatic category links enabled (default behavior)
# DISPLAY_CATEGORIES_ON_MENU = True  # This is usually the default

# Define static menu items
MENUITEMS = [
    ('Home', '/'),
    ('Blog', '/blog/'),
    ('Custom Page', '/custom-page/'),
]

Theme-Specific Navigation

Some themes implement custom navigation systems that don't rely solely on MENUITEMS. In these cases, consult your theme's documentation or examine its template files to understand how to integrate custom pages.

For example, the popular theme "Flex" uses a variable called MAIN_MENU with a more complex structure:

MAIN_MENU = True
MENUITEMS = (
    ('Home', '/'),
    ('Custom Page', '/custom-page/'),
    ('Categories', (
        ('Category 1', '/category/category-1/'),
        ('Category 2', '/category/category-2/'),
    )),
)

Testing Your Navigation

Whenever you modify your menu configuration, test your site by regenerating it:

pelican content

Then check the navigation links in your local development server to ensure they work as expected.

Troubleshooting Common Issues

Issue: Menu items don't appear
Check if your theme supports MENUITEMS or requires a different variable. Some themes require MAIN_MENU = True to be set as well.

Issue: Links don't work correctly
Verify that your URL paths match the structure defined in EXTRA_PATH_METADATA. Remember that if you're using RELATIVE_URLS = True for development, your paths will be relative.

Issue: Unexpected menu order
If categories are appearing between your static menu items, you may need to override your theme's template files to control the precise ordering.

Conclusion

Using the static files approach is the most straightforward way to add custom HTML pages to your Pelican site. It preserves the original HTML without modification, allows for custom URL structures, and integrates seamlessly with the rest of your site.

This method is particularly useful for: - Interactive pages with complex JavaScript - HTML generated by other tools - Pages with custom styling that shouldn't be affected by your site's theme - Embedding third-party applications or widgets

By following these steps, you can extend your Pelican site beyond its standard blog functionality while maintaining full control over your custom HTML content.

corey@gallon.me:~$ tail -f /writing Attach to the stream. An email when I have something worth sending. Replies encouraged!
corey@gallon.me:~$ ls -lt /til ↑2025-03-18 Founders #383: Todd Graves' $10B Chicken Finger Dream
▸2025-02-27 How to Add Custom HTML Pages to a Pelican Site ⋅ you are here
↓2025-02-22 AI Engineer Summit 2025: Agents at Work