Programming with AI
ENRU
6.5

Stating tasks in Python

what has to be specified here in particular

What it is

The four parts of a prompt from article 3.2 work everywhere. This article is about what to add specifically for Python, because without it the AI will supply its own.

The list is short. Five points, and all five are one or two lines in the prompt.

What to tell the AI

1. The Python version

Not only the libraries' (article 2.11) but the language's own. The syntax changes between versions:

WhatFrom which version
str | None instead of Optional[str]3.10
list[str] instead of List[str]3.9
match3.10
tomllib in the standard library3.11
Exception groups, except*3.11

Code with str | None on Python 3.9 fails with a TypeError at import. To find your version:

python3 --version

2. Synchronous or asynchronous

Decided once and expensive to change later: a synchronous function cannot be called from an asynchronous one without a wrapper, and vice versa.

Prompt
The project is asynchronous: aiogram 3, aiosqlite. Every
function that touches the network or the database is async.

3. What already exists in the project

The highest-value point of all (article 3.1, reason 2):

Prompt
The database connection goes through get_conn() from db.py.
Logging through log = logging.getLogger(__name__).
Don't invent your own versions.

4. The signature

For Python it works particularly well, because it sets both the types and the behaviour when there is no data:

Prompt
def find_city(name: str) -> str | None

One line says: it takes a string, it may find nothing, and the caller is obliged to check. In words the same would have taken a paragraph (article 6.3).

5. Style boundaries

Prompt
Keep it simple: plain loops rather than nested comprehensions,
no walrus operator. Types are mandatory, mypy --strict must
pass.

The ready-made template

Better
Context: Python 3.12, aiogram 3.13, aiosqlite.
The project is asynchronous. Database connection via get_conn()
from db.py, logging via logging.getLogger(__name__).

Task: a function in storage.py

    async def find_subs(user_id: int) -> list[str]

Returns the list of cities the user is subscribed to.
If there are no subscriptions, an empty list, not None.

Boundaries: only this function, don't touch anything else.
Don't add new dependencies.

Done when: mypy --strict passes, and a user with no
subscriptions gets [].

What to look for

The Python version not named. The cheapest line in a prompt and one of the most useful.

Synchronous and asynchronous mixed. The AI can hand you a synchronous function for an asynchronous project — and it will block the loop (article 6.4).

Its own database connection. A sign point 3 was skipped: the function has grown its own sqlite3.connect instead of get_conn().

A signature without | None. If a function may find nothing, that has to be in the type. Otherwise the check gets forgotten — by you and by the AI.

Cheat sheet

  • Five points: Python version · sync or async · what already exists · signature · style boundaries.

  • The language version matters as much as the libraries'.

  • A signature with | None replaces a paragraph of explanation.

  • "Connection via get_conn(), don't invent your own."

  • "Done when mypy --strict passes" is a checkable criterion.

  • Move the constant points into the project context file.