›_ ebskola.lv
← 10.4 10.6 →

10.5 Python ↔ PostgreSQL (psycopg2)

Stundas uzdevums: Savienot Python kodu ar PostgreSQL datubāzi un izpildīt drošus parametrizētus vaicājumus.

SR 2.4.11. Lieto standartizētas bibliotēkas un API SR 3.2.5. Drošības riski

70 min darba sadalījums: 1. uzdevums (~20 min) - atjauno teorijas piemēru vai minimālo prototipu; 2. uzdevums (~25 min) - pielieto to galvenajā uzdevumā; 3. uzdevums (~25 min) - pārbaudi rezultātu, izlabo kļūdas un tikai beigās pieraksti vienu secinājumu. Papildus/4. līmeņa uzdevums ir paredzēts tikai tad, ja pamatdarbs ir pabeigts.

Pirms sāc: izmanto iepriekš apgūto un šīs lapas teorijas/koda piemērus. Ja vajadzīga jauna komanda vai rīks, vispirms atrodi tās paraugu teorijas sadaļā.

Teorija: psycopg2 - Python ↔ PostgreSQL tilts

psycopg2 ir Python bibliotēka, kas savieno tavu kodu ar PostgreSQL datubāzi. Instalācija: pip install psycopg2-binary.

import psycopg2

conn = psycopg2.connect(
    host="localhost",
    database="spele",
    user="postgres",
    password="tavs_parole"
)
cur = conn.cursor()

# DROŠA parametrizēta vaicājuma forma - %s ir TIKAI vietturis
cur.execute("SELECT * FROM speletaji WHERE punkti > %s", (100,))
for rinda in cur.fetchall():
    print(rinda)

conn.commit()  # apstiprina izmaiņas
cur.close()
conn.close()

⚠ DROŠĪBA: NEKAD nelieto string formatēšanu (f"...{x}...") SQL vaicājumos - tas ir SQL injekcijas uzbrukums!

Praktiskie uzdevumi

1. uzdevums - Iesildies ar gatavu piemēru

Šis ir īss iesildīšanās uzdevums. Nokopē sagatavi, ielīmē to pareizajā koda vietā un palaid. Šeit pietiek droši izmēģināt tēmu 10.5 Python ↔ PostgreSQL (psycopg2); detalizētu izpratni veidosi nākamajos uzdevumos.

Kopējamais piemērs vai sagatave: izmanto šo bloku kā starta punktu, nevis kā gala risinājumu.

import psycopg2

conn = psycopg2.connect(
    host="localhost",
    database="spele",
    user="postgres",
    password="tavs_parole"
)
cur = conn.cursor()

# DROŠA parametrizēta vaicājuma forma - %s ir TIKAI vietturis
cur.execute("SELECT * FROM speletaji WHERE punkti > %s", (100,))
for rinda in cur.fetchall():
    print(rinda)

conn.commit()  # apstiprina izmaiņas
cur.close()
conn.close()
  1. Atver darba failu vai rīku. Python fragmentu ievieto main.py failā un palaid no termināļa.
  2. Nokopē visu piemēra bloku no šī uzdevuma un ielīmē to norādītajā vietā.
  3. Palaid kodu tieši tādu, kāds tas ir, un pārliecinies, ka parādās rezultāts, izvade vai vismaz nav kļūdas paziņojuma.
  4. Atrodi vienu drošu vietu, ko drīkst mainīt: tekstu, skaitli, krāsu, mainīgā vērtību vai testa ierakstu.
  5. Maini tikai šo vienu vērtību un palaid kodu vēlreiz.
  6. Salīdzini rezultātu pirms un pēc izmaiņas. Ja parādās kļūda, atcel pēdējo izmaiņu un palaid vēlreiz.
  7. Turpini pie 2. uzdevuma tikai tad, kad šis mazais piemērs darbojas.

2. uzdevums - Ievieto algoritmu projektā

Pievieno šīs stundas datu paņēmienu kā nelielu, strādājošu projekta daļu.

  1. Izvēlies vienu projekta vietu: rezultātu glabāšanu, spēlētāju sarakstu, statistiku, CRUD darbību vai atskaiti.
  2. Nosauc tabulas, kolonnas, funkcijas un mainīgos pēc to lomas, piemēram, speletaji, rezultati vai ielade_topu().
  3. Uzraksti SQL vaicājumu vai Python funkciju, kas nolasa, saglabā, atjaunina vai apkopo datus.
  4. Savieno vaicājumu ar projekta Python kodu vai rezultāta izvadi.
  5. Pievieno vienu īsu komentāru pie sarežģītākās datu apstrādes vietas.
  6. Pārbaudi, ka esošie dati netiek sabojāti un atkārtota palaišana dod saprotamu rezultātu.
  7. Salabo pirmo atrasto kļūdu pirms pievieno nākamo vaicājumu.
  8. Veic Git commit ar īsu ziņu par pievienoto datu funkcionalitāti.

3. uzdevums - Testē datus un izdari secinājumu

Pārbaudi, vai datu algoritms darbojas paredzami.

  1. Izveido trīs testa scenārijus: parasts ieraksts, robežgadījums un kļūdains vai tukšs ieraksts.
  2. Palaid parasto scenāriju un pārbaudi rezultātu terminālī vai datubāzē.
  3. Palaid robežgadījumu ar mazāko, lielāko vai tukšāko datu vērtību.
  4. Palaid kļūdaino scenāriju un pārbaudi, vai kods neizdzēš vai nesabojā vajadzīgos datus.
  5. Izlabo vienu konkrētu problēmu SQL vaicājumā, Python kodā vai datu validācijā.
  6. Pārbaudi labojumu vēlreiz ar visiem trim scenārijiem.
  7. Beigās pieraksti vienu secinājumu: kura tabula, vaicājums vai Python funkcija vislabāk palīdzēja saprast tēmu 10.5 Python ↔ PostgreSQL (psycopg2).

Papildu uzdevums - Pievieno mazu datu funkciju

Ja pamatdarbs ir pabeigts, paplašini projektu ar vienu nelielu datu uzlabojumu.

  1. Izvēlies vienu mazu papildinājumu, kas izmanto to pašu šīs stundas paņēmienu.
  2. Pievieno vienu jaunu kolonnu, filtru, kārtošanu, ievades pārbaudi vai atskaites izvadi.
  3. Savieno papildinājumu ar esošo projekta kodu.
  4. Pārbaudi, ka pamatvaicājumi un papildinājums darbojas kopā.
  5. Saglabā izmaiņas ar Git commit tikai pēc veiksmīgas pārbaudes.

Biežākās kļūdas

Koda piemērs

import psycopg2
from psycopg2.extras import RealDictCursor

with psycopg2.connect(
    host="localhost", database="spele",
    user="postgres", password="parole"
) as conn:
    with conn.cursor(cursor_factory=RealDictCursor) as cur:
        # DROŠA INSERT
        cur.execute(
            "INSERT INTO speletaji (vards) VALUES (%s) RETURNING id",
            ("Anna",)
        )
        jauns_id = cur.fetchone()["id"]
        print(f"Pievienots ar id = {jauns_id}")

        cur.execute("SELECT * FROM speletaji ORDER BY id DESC LIMIT 3")
        for r in cur.fetchall():
            print(r["vards"], r["punkti"])
Pievienots ar id = 12
Anna 0
Marta 200
Eva 145
⬅ Iepriekšējā stunda Nākamā stunda ➡