Skip to content

Commit 5f5c55e

Browse files
authored
Use blog.python.org (#2949)
1 parent a59280c commit 5f5c55e

File tree

3 files changed

+72
-2
lines changed

3 files changed

+72
-2
lines changed
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
"""Rewrite legacy pythoninsider.blogspot.com URLs to blog.python.org.
2+
3+
Blogger's RSS feed historically served entry links under the old
4+
pythoninsider.blogspot.com domain. This one-time migration normalizes
5+
existing BlogEntry rows so that the parser's runtime normalization
6+
(added in the same changeset) doesn't create duplicates via
7+
update_or_create.
8+
"""
9+
10+
from django.db import migrations
11+
from django.db.models import Value
12+
from django.db.models.functions import Replace
13+
14+
15+
def normalize_blogentry_urls(apps, schema_editor):
16+
BlogEntry = apps.get_model("blogs", "BlogEntry")
17+
BlogEntry.objects.filter(url__contains="pythoninsider.blogspot.com").update(
18+
url=Replace("url", Value("pythoninsider.blogspot.com"), Value("blog.python.org")),
19+
)
20+
21+
22+
class Migration(migrations.Migration):
23+
dependencies = [
24+
("blogs", "0003_alter_relatedblog_creator_and_more"),
25+
]
26+
27+
operations = [
28+
migrations.RunPython(
29+
normalize_blogentry_urls,
30+
reverse_code=migrations.RunPython.noop,
31+
),
32+
]

apps/blogs/parser.py

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
"""RSS feed parsing and blog supernav rendering utilities."""
22

33
import datetime
4+
from urllib.parse import urlparse, urlunparse
45

56
import feedparser
67
from django.conf import settings
@@ -9,6 +10,19 @@
910
from apps.blogs.models import BlogEntry, Feed
1011
from apps.boxes.models import Box
1112

13+
# Blogger serves RSS entry links with this legacy domain instead of
14+
# the canonical blog.python.org hostname.
15+
_BLOGGER_LEGACY_HOST = "pythoninsider.blogspot.com"
16+
17+
18+
def _normalize_blog_url(url):
19+
"""Rewrite legacy Blogger URLs to the canonical blog.python.org domain."""
20+
parsed = urlparse(url)
21+
if parsed.hostname == _BLOGGER_LEGACY_HOST:
22+
canonical = urlparse(settings.PYTHON_BLOG_URL)
23+
return urlunparse(parsed._replace(scheme=canonical.scheme, netloc=canonical.netloc))
24+
return url
25+
1226

1327
def get_all_entries(feed_url):
1428
"""Retrieve all entries from a feed URL."""
@@ -22,7 +36,7 @@ def get_all_entries(feed_url):
2236
"title": e["title"],
2337
"summary": e.get("summary", ""),
2438
"pub_date": published,
25-
"url": e["link"],
39+
"url": _normalize_blog_url(e["link"]),
2640
}
2741

2842
entries.append(entry)

apps/blogs/tests/test_parser.py

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import datetime
22
import unittest
33

4-
from apps.blogs.parser import get_all_entries
4+
from apps.blogs.parser import _normalize_blog_url, get_all_entries
55
from apps.blogs.tests.utils import get_test_rss_path
66

77

@@ -24,3 +24,27 @@ def test_entries(self):
2424
self.entries[0]["url"],
2525
"http://feedproxy.google.com/~r/PythonInsider/~3/tGNCqyOiun4/introducing-electronic-contributor.html",
2626
)
27+
28+
29+
class NormalizeBlogUrlTest(unittest.TestCase):
30+
def test_rewrites_pythoninsider_blogspot(self):
31+
url = "https://pythoninsider.blogspot.com/2026/02/join-the-python-security-response-team.html"
32+
self.assertEqual(
33+
_normalize_blog_url(url),
34+
"https://blog.python.org/2026/02/join-the-python-security-response-team.html",
35+
)
36+
37+
def test_rewrites_http_to_canonical_scheme(self):
38+
url = "http://pythoninsider.blogspot.com/2026/01/some-post.html"
39+
self.assertEqual(
40+
_normalize_blog_url(url),
41+
"https://blog.python.org/2026/01/some-post.html",
42+
)
43+
44+
def test_preserves_non_blogspot_urls(self):
45+
url = "http://feedproxy.google.com/~r/PythonInsider/~3/abc/some-post.html"
46+
self.assertEqual(_normalize_blog_url(url), url)
47+
48+
def test_preserves_blog_python_org_urls(self):
49+
url = "https://blog.python.org/2026/02/some-post.html"
50+
self.assertEqual(_normalize_blog_url(url), url)

0 commit comments

Comments
 (0)