Skip to main content

Drop-in blog integration for Django & Flask — powered by EarlySEO. Articles are served from EarlySEO's CDN. Just add your site ID and go.

Project description

earlyseo-blog

Drop-in blog integration for Django and Flask — powered by EarlySEO. Articles are authored in the EarlySEO dashboard and rendered in your Python web app.

Quick Start (Recommended)

The fastest way to get started — run the CLI from your project root:

pip install earlyseo-blog
earlyseo-blog

The CLI automatically:

  1. Detects whether you're using Django or Flask
  2. Asks for your Site ID (from Dashboard → Integrations → SDK)
  3. Generates starter templates, URL config, and a .env file

Run your dev server and visit /blog — your articles are live.


Manual Setup

If you prefer to configure things yourself:

Django

pip install "earlyseo-blog[django]"

settings.py

INSTALLED_APPS = [
    # …
    "earlyseo_blog.django",
]

EARLYSEO_SITE_ID = "your-site-id"   # from Dashboard → Integrations → SDK

urls.py

from django.urls import include, path

urlpatterns = [
    path("blog/", include("earlyseo_blog.django.urls")),
]

Visit /blog to see your articles.

Template tags

Override the built-in HTML by creating your own templates:

<!-- templates/earlyseo/blog_list.html -->
{% extends "base.html" %}
{% load earlyseo %}

{% block extra_head %}{% earlyseo_styles %}{% endblock %}

{% block content %}
  {% for article in articles %}
    <h2><a href="{% url 'earlyseo_blog:blog_detail' slug=article.slug %}">{{ article.title }}</a></h2>
    <p>{{ article.meta_description }}</p>
  {% endfor %}
{% endblock %}

Available template tags: {% earlyseo_styles %}, {% earlyseo_article_css %}, {% earlyseo_article article %}.

Flask

pip install "earlyseo-blog[flask]"

app.py

from flask import Flask
from earlyseo_blog.flask.views import create_blog_blueprint

app = Flask(__name__)
app.config["EARLYSEO_SITE_ID"] = "your-site-id"

app.register_blueprint(create_blog_blueprint(), url_prefix="/blog")

Override the built-in HTML by placing templates/earlyseo/blog_list.html and templates/earlyseo/blog_detail.html in your templates folder.


Sitemap

Django

Plug into Django's built-in sitemaps framework:

# settings.py
INSTALLED_APPS = [
    # …
    "django.contrib.sitemaps",
    "earlyseo_blog.django",
]
# urls.py
from django.contrib.sitemaps.views import sitemap
from earlyseo_blog.django.sitemap import EarlySeoBlogSitemap

sitemaps = { "blog": EarlySeoBlogSitemap }

urlpatterns = [
    path("blog/", include("earlyseo_blog.django.urls")),
    path("sitemap.xml", sitemap, {"sitemaps": sitemaps}, name="sitemap"),
]

Flask

Register a /blog/sitemap.xml route automatically:

from earlyseo_blog.flask.sitemap import register_blog_sitemap

app.config["EARLYSEO_BASE_URL"] = "https://example.com"
register_blog_sitemap(app, url_prefix="/blog")

Or get entries for a custom sitemap:

from earlyseo_blog.flask.sitemap import create_blog_sitemap_entries

entries = create_blog_sitemap_entries(base_url="https://example.com")

Python Client

Use the client directly in any Python app:

from earlyseo_blog import EarlySeoClient

client = EarlySeoClient(site_id="your-site-id")

# List articles (page 1)
page = client.get_list_page(1)
for article in page.articles:
    print(article.title, article.slug)

# Get a single article
article = client.get_article("my-article-slug")
print(article.title)
print(article.content_html)

Async Client

from earlyseo_blog import AsyncEarlySeoClient

async def main():
    async with AsyncEarlySeoClient(site_id="your-site-id") as client:
        page = await client.get_list_page(1)
        article = await client.get_article("my-article-slug")

Install the async extra for HTTP/2 support:

pip install "earlyseo-blog[async]"

Models

All responses are validated with Pydantic v2:

Model Description
Manifest Site manifest with total pages/articles
ArticleListItem Summary for list views
ArticleListPage Paginated list of ArticleListItem
Article Full article with content_html
from earlyseo_blog.models import Article, Manifest

CSS

Built-in styles for article content and blog layout:

from earlyseo_blog.css import ARTICLE_CSS, BLOG_CSS

Include them in your <style> tag or template to get default styling.


Configuration

Setting Description Default
site_id Your EarlySEO site ID (required)

Django: Set EARLYSEO_SITE_ID in settings.py.

Flask: Set in app.config["EARLYSEO_SITE_ID"].


Requirements

  • Python ≥ 3.9
  • httpx ≥ 0.24
  • pydantic ≥ 2.0
  • Django ≥ 4.2 (for Django integration)
  • Flask ≥ 2.3 (for Flask integration)

License

Proprietary — see LICENSE for details.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

earlyseo_blog-1.0.4.tar.gz (16.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

earlyseo_blog-1.0.4-py3-none-any.whl (22.0 kB view details)

Uploaded Python 3

File details

Details for the file earlyseo_blog-1.0.4.tar.gz.

File metadata

  • Download URL: earlyseo_blog-1.0.4.tar.gz
  • Upload date:
  • Size: 16.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/3.8.0 pkginfo/1.12.1.2 readme-renderer/42.0 requests/2.33.1 requests-toolbelt/1.0.0 urllib3/2.6.3 tqdm/4.67.3 importlib-metadata/9.0.0 keyring/25.7.0 rfc3986/2.0.0 colorama/0.4.6 CPython/3.11.10

File hashes

Hashes for earlyseo_blog-1.0.4.tar.gz
Algorithm Hash digest
SHA256 d67fde0abe84fff28e2a63d128f1ffbb476e09aaf2a35bfd1f5b53c16760fd06
MD5 eff00d25f5612343aa56bc76b5a2a63f
BLAKE2b-256 2ca2f7fce0c1df67a60f01e641521e88e5bab2c5f13ebd00e9792cc4da60f3e6

See more details on using hashes here.

File details

Details for the file earlyseo_blog-1.0.4-py3-none-any.whl.

File metadata

  • Download URL: earlyseo_blog-1.0.4-py3-none-any.whl
  • Upload date:
  • Size: 22.0 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/3.8.0 pkginfo/1.12.1.2 readme-renderer/42.0 requests/2.33.1 requests-toolbelt/1.0.0 urllib3/2.6.3 tqdm/4.67.3 importlib-metadata/9.0.0 keyring/25.7.0 rfc3986/2.0.0 colorama/0.4.6 CPython/3.11.10

File hashes

Hashes for earlyseo_blog-1.0.4-py3-none-any.whl
Algorithm Hash digest
SHA256 a5540c0430905db90433d640ec8db96f7cbfb15b19f2147912f973ad77b98452
MD5 ece9f93c5a9fa908fd56e1b2d184c422
BLAKE2b-256 3de746308b62c8d66411a0ba5aaee153843c4ac812a2e61a77c19115bd8814d5

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page