#492: Codeberg Puts Head in Sand
Sponsored by Logfire from Pydantic pythonbytes.fm/logfire
This episode is brought to you by Pydantic Logfire. It's observability for AI apps from the team behind Pydantic - agents, LLMs, APIs, database, and infrastructure in a single trace, queried with Postgres-compatible SQL. Your coding agent can query it too, through their MCP server. I'll tell you more later.
Connect with the hosts
- Michael: Mastodon / BlueSky / X / LinkedIn
- Calvin: Mastodon / BlueSky / X / LinkedIn
- Show: Mastodon / BlueSky / X
- Join us on YouTube at pythonbytes.fm/live to be part of the audience. Usually Tuesday at 7am PT. Older video versions available there too.
Finally, if you want an artisanal, hand-crafted digest of every week of the show notes in email form? Add your name and email to our friends of the show list, we'll never share it.
Calvin #1: Python 3.12.14, 3.11.16, 3.10.21 - security releases
https://blog.python.org/2026/08/python-31214-31116-31021/
- Source-only security releases for the three branches now in security-fix-only mode; release team blamed the European solar eclipse for the timing.
tarfilehardening. Multiple path-traversal bypasses of thedatafilter closed, including a symlink escape that bypassed the CVE-2025-4330 fix;extract()now applies the filter to link targets too.- Four fresh CVEs: CVE-2026-2297 (
SourcelessFileLoadernot usingio.open_code()for.pyc), CVE-2026-4224 (expat crash on deeply nested content models), CVE-2026-3644 (control chars inhttp.cookies.Morsel), plus the completed CVE-2021-4189 fix inftplib.ftpcp. - Quadratic-complexity DoS cleanup across the stdlib:
HTMLParser,configparserregexes,unicodedata.normalize(),csv.Sniffer.sniff(), and ElementTree XPath index predicates. - Header/injection fixes: CR/LF rejected in
HTTPConnection.set_tunnel(), control chars blocked inwsgiref.handlersstatus, andwebbrowsernow rejects leading dashes (plus a%actionprefix bypass). http.clientnow caps chunked trailer lines and 1xx interim responses at 100 each - a hostile server could previously hang the client forever despite a socket timeout.- Memory-safety odds and ends: stale pointers in lzma/bz2/zlib decompressors after
MemoryError, a bz2 stack overflow on reuse-after-error, and bundled libexpat bumped to 2.8.3. If you're still on 3.10, 3.11, or 3.12 - and you extract tarballs from anywhere you don't fully control - this one's not optional.
Michael #2: Codeberg’s AI-code ban tests its role as a GitHub alternative
- Armin’s article “Codeberg Divides”
- Armin Ronacher argues that Codeberg’s new terms, which prohibit projects mostly written with generative AI, create a vague and difficult-to-enforce boundary. His larger concern is that a democratically governed host can still be unpredictable or ideologically narrow, weakening Codeberg’s potential as a broad European alternative to GitHub.
- The strongest question for Python developers is whether repository hosting should judge legal open source by how code was produced, or focus on behavior and resource abuse.
- “Mostly generated” is hard to measure in modern codebases where developers mix handwritten code, completions, agents, and generated refactors.
- Ronacher suggests clearer alternatives: ban all LLM involvement, or target autonomous repository spam, abusive resource use, and low-quality generated contributions directly.
- Codeberg is free to choose a values-driven community, but that may conflict with being predictable, neutral infrastructure and a serious GitHub competitor.
- Worth discussing: can open-source communities set meaningful AI boundaries without driving maintainers and projects into opposing camps?
- Very first search for these terms lands on this page.
- Codeberg looked like a viable alternative. … Unfortunately, the latest update to its terms of service seems to mark a first step in changing one part I moved there for, namely the “freedom” part.
Sponsor: Logfire from Pydantic
Your AI agent failed at 2am. Was it the model? A tool call? The database? Most observability tools can't tell you, because they only see part of your stack. Pydantic Logfire sees all of it. One trace across your agents, LLMs, APIs, and database. Down to the infrastructure: services, Kubernetes, and hosts. It's built on OpenTelemetry, with SDKs for Python, TypeScript, and Rust, and it works with any OTel-compatible language. Every prompt, token count, and cost, right next to your vector searches and API calls. You query everything with Postgres-compatible SQL. And so can your coding agent, through the Logfire MCP server. Stop guessing. Read the trace. Pydantic Logfire. AI, it's still just engineering. Visit pythonbytes.fm/logfire today and sign up today. Get 10M records free every month, no card required. You can even click “Onboard with your coding agent” to copy a prompt to have claude or codex integrate Logfire into your app. Thanks to Pydantic for supporting the show.
Calvin #3: Brett Cannon: what's missing for reproducible builds on PyPI
- Framing came out of his 2026 Python Packaging Council nomination - the secure-supply-chain gap he found is that Python has no defined way to do reproducible builds at all.
- Design goal is zero friction: producers uploading to PyPI shouldn't have to do anything. The work lands on build backends and installers.
- Gap #1: nothing records the source code a distribution came from.
direct_url.jsoncaptures it when you install from a repo or archive, so the fix is putting the same info in sdist/wheel metadata. - Gap #2: recording the build tools. Wheels can already do this via PEP 770 SBOMs in
.dist-info/sboms/- sdists can't, since they're a tarball plus a precalculatedPKG-INFOwith nowhere to hang extra metadata. Either "don't use sdists" or an sdist v2. - The replay mechanism already exists:
[build-system]inpyproject.tomlis a defined entry point, so if backends recorded their own environment, you could reinstall and re-run the build. - Payoff idea: trusted third parties report successful reproductions back to PyPI, which displays "independently reproduced by X" - surfaced in the index API so installers could prefer reproduced files.
- Explicitly framed as a perk, not a requirement - roughly SLSA build level 1, no shaming projects that don't opt in. Verbal kicker option: "And don't think pure-Python wheels are off the hook. Something built that wheel, and if that something was compromised, so is your wheel. SolarWinds was a build-process attack."
Michael #4: Extra extra extra, hear all about it
- Python 3.14.7
- Upgraded the MCP servers to 2026-07-28 v2 protocols (talk python, python bytes)
- Got agentsview running synced via postgres
- Talk Python courses, teams trial offering
- Talk Python courses, government procurement offering
- Lean TDD audio book is out
Extras
Calvin:
- uv now prefers post-quantum key exchange - https://github.com/astral-sh/uv/releases/tag/0.12.4
Joke: Beware of dog
Episode Transcript
Collapse transcript
00:00
00:05
00:12
00:13
00:19
00:25
00:29
00:31
00:33
00:34
00:39
00:40
00:44
00:47
00:48
00:49
00:50
00:52
00:52
00:55
00:55
01:01
01:10
01:15
01:21
01:26
01:33
01:39
01:44
01:50
01:57
02:02
02:05
02:10
02:16
02:22
02:27
02:32
02:38
02:45
02:52
03:00
03:08
03:14
03:18
03:21
03:23
03:25
03:25
03:28
03:30
03:34
03:37
03:40
03:49
03:54
03:56
03:59
04:03
04:08
04:09
04:15
04:17
04:19
04:23
04:28
04:34
04:38
04:40
04:41
04:42
04:43
04:45
04:48
04:49
04:51
04:53
04:55
05:00
05:03
05:04
05:10
05:21
05:25
05:33
05:37
05:42
05:44
05:45
05:48
05:50
05:52
05:53
05:53
05:58
05:59
06:00
06:03
06:04
06:05
06:05
06:07
06:08
06:10
06:12
06:15
06:16
06:19
06:20
06:22
06:23
06:24
06:25
06:30
06:32
06:33
06:34
06:38
06:39
06:42
06:43
06:46
06:47
06:48
06:50
06:51
06:57
06:59
07:03
07:04
07:05
07:07
07:15
07:20
07:26
07:28
07:29
07:32
07:35
07:35
07:38
07:46
07:50
07:55
08:00
08:01
08:04
08:08
08:12
08:16
08:17
08:19
08:21
08:22
08:25
08:25
08:28
08:31
08:32
08:33
08:38
08:39
08:42
08:44
08:46
08:51
08:55
08:59
09:00
09:01
09:03
09:05
09:06
09:08
09:11
09:12
09:16
09:18
09:23
09:26
09:34
09:41
09:45
09:46
09:47
09:48
09:49
09:55
09:59
10:01
10:03
10:06
10:07
10:09
10:10
10:11
10:15
10:19
10:22
10:23
10:30
10:31
10:35
10:36
10:38
10:40
10:42
10:44
10:48
10:51
10:53
10:55
10:59
11:00
11:05
11:09
11:11
11:13
11:36
11:43
11:47
11:49
11:55
12:00
12:01
12:03
12:06
12:08
12:12
12:13
12:15
12:16
12:17
12:21
12:24
12:27
12:29
12:34
12:35
12:39
12:45
12:47
12:52
12:54
12:56
12:58
13:01
13:04
13:10
13:11
13:11
13:11
13:16
13:19
13:22
13:23
13:26
13:30
13:34
13:39
13:45
13:50
13:56
14:00
14:02
14:03
14:08
14:12
14:15
14:19
14:21
14:24
14:28
14:31
14:33
14:40
14:42
14:46
14:46
14:55
15:01
15:03
15:05
15:10
15:14
15:16
15:18
15:21
15:24
15:27
15:29
15:31
15:35
15:38
15:41
15:43
15:44
15:49
15:51
15:53
15:54
15:57
15:59
16:09
16:17
16:19
16:22
16:24
16:25
16:31
16:35
16:37
16:38
16:48
16:51
16:54
16:55
16:56
16:58
17:01
17:03
17:07
17:07
17:09
17:15
17:22
17:34
17:35
17:38
17:38
17:41
17:46
17:48
17:52
17:55
18:00
18:03
18:08
18:13
18:18
18:21
18:24
18:28
18:32
18:35
18:39
18:39
18:48
18:54
18:56
19:00
19:07
19:11
19:14
19:19
19:22
19:23
19:24
19:27
19:29
19:32
19:34
19:35
19:36
19:36
19:38
19:43
19:50
19:53
19:56
19:57
20:00
20:01
20:02
20:03
20:04
20:06
20:12
20:13
20:14
20:23
20:33
20:40
20:41
20:48
20:52
20:54
20:56
21:02
21:09
21:16
21:22
21:27
21:32
21:37
21:44
21:48
21:52
21:58
22:04
22:08
22:14
22:22
22:27
22:32
22:37
22:44
22:54
22:58
23:00
23:04
23:06
23:09
23:11
23:15
23:20
23:28
23:33
23:38
23:43
23:48
23:55
23:58
24:04
24:09
24:14
24:19
24:23
24:26
24:28
24:35
24:36
24:41
24:42
24:47
24:50
24:53
25:00
25:01
25:02
25:04
25:11
25:13
25:18
25:20
25:25
25:28
25:30
25:35
25:36
25:38
25:40
25:41
25:51
25:56
26:04
26:08
26:14
26:15
26:16
26:18
26:18
26:21
26:26
26:28
26:34
26:35
26:37
26:39
26:46
26:48
26:53
27:00
27:09
27:14
27:19
27:23
27:24
27:30
27:32
27:37
27:37
27:41
27:45
27:48
27:51
27:52
27:52
27:56
28:02
28:05
28:08
28:10
28:13
28:20
28:21
28:24
28:25
28:29
28:33
28:37
28:43
28:50
28:52
28:53
28:54
28:54
28:56
28:57
29:04
29:06
29:07
29:08
29:09
29:12
29:16
29:22
29:27
29:31
29:32
29:37
29:39
29:41
29:42
29:45
29:46
29:48
29:50
29:50
29:56
30:00
30:08
30:11
30:17
30:22
30:25
30:26
30:26
30:28
30:30
30:32
30:38
30:39
30:42
30:45
30:47
30:48
30:48
30:50
30:51
31:04
31:10
31:15
31:20
31:23
31:23
31:26
31:30
31:32
31:34
31:41
31:47
31:49
31:54
31:55
31:59
32:06
32:06
32:10
32:14
32:18
32:22
32:26
32:26
32:32
32:34
32:36
32:40
32:41
32:45
32:46
32:47
32:48
32:49
32:49
32:50
32:54
32:55
32:56
32:57
33:03
33:05
33:08
33:09
33:10
33:12
33:17
33:18
33:19
33:21
33:22
33:23
33:25
33:27
33:28
33:35
33:38
33:41
33:41
33:44
33:50
33:53
33:55
34:02
34:03
34:06
34:10
34:13
34:18
34:22
34:28
34:37
34:39
34:43
34:47
34:52
34:53
34:56
34:58
35:00
35:02
35:04
35:05
35:05
35:08
35:12
35:24
35:25
35:27
35:30
35:30
35:33
35:33
35:37
35:38
35:44
35:45
35:46
35:51
35:55
35:59
36:00
36:04
36:06
36:11
36:13
36:16
36:19
36:19
36:20
36:20
36:20
36:21
36:23
36:24
36:26
36:32
36:36
36:38
36:42
36:45
36:52
36:53
36:54
36:55
36:56
36:57
36:58
37:00
37:03
37:09
37:14
37:19
37:25
37:30
37:33
37:34
37:36
37:38
37:40
37:40
37:42
37:45
37:48
37:49
37:50
37:51
37:55
38:00
38:01
38:03
38:06
38:09
38:13
38:15
38:15
38:16
38:20
38:24
38:26
38:35
38:44
38:49
38:54
38:58
38:58
39:03
39:05
39:06
39:07
39:09
39:13
39:14
39:15
39:16
39:16
39:16


