Kap 5.6 · Miniuppgift
Kombinera GUI, API och databas
Bygg ett skämtregister med tkinter, requests och SQLite.
Mål
Tre tekniker i ett program
tkinterskapar gränssnittet.requestshämtar data från ett API.sqlite3sparar data lokalt.- Funktioner kopplar ihop hela flödet.
Projektet
Skämtregister
- Hämta ett skämt från ett API.
- Visa skämtet i GUI:t.
- Spara skämtet i SQLite.
- Visa alla sparade skämt.
Helhetsbild
Så samarbetar delarna
Klick i tkinter
startar en Pythonfunktion
requests → API → JSON
hämtar ett nytt skämt
sqlite3 → skamt.db
sparar skämtet permanent
Förberedelse
Installera requests
python3 -m pip install requests
tkinter och sqlite3 ingår normalt i Python.
requests behöver vanligtvis installeras separat.
Hela programmet · del 1
Import och databas
import tkinter as tk
import requests
import sqlite3
conn = sqlite3.connect("skamt.db")
cursor = conn.cursor()
cursor.execute("""
CREATE TABLE IF NOT EXISTS skamt (
id INTEGER PRIMARY KEY AUTOINCREMENT,
setup TEXT,
punchline TEXT
)
""")
conn.commit()
senaste_skamt = None
Hela programmet · del 2
Programmets funktioner
def hamta_skamt():
global senaste_skamt
response = requests.get(
"https://official-joke-api.appspot.com/random_joke"
)
if response.status_code == 200:
data = response.json()
skamt_label.config(
text=f"{data['setup']} - {data['punchline']}"
)
senaste_skamt = (data["setup"], data["punchline"])
def spara_skamt():
if senaste_skamt:
cursor.execute(
"INSERT INTO skamt (setup, punchline) VALUES (?, ?)",
senaste_skamt
)
conn.commit()
skamt_label.config(text="Skämtet sparat!")
Hela programmet · del 3
Visa sparade skämt och skapa GUI
def visa_skamt():
cursor.execute("SELECT * FROM skamt")
rader = cursor.fetchall()
output = "\n".join(
[f"{rad[1]} - {rad[2]}" for rad in rader]
)
if len(output) > 300:
output = output[:300] + "..."
skamt_label.config(text=output)
root = tk.Tk()
root.title("Skämtregister")
tk.Button(root, text="Hämta skämt", command=hamta_skamt).pack()
tk.Button(root, text="Spara skämt", command=spara_skamt).pack()
tk.Button(root, text="Visa alla skämt", command=visa_skamt).pack()
skamt_label = tk.Label(root, text="", wraplength=300, justify="left")
skamt_label.pack()
root.mainloop()
Databas
Skapa fil och tabell
conn = sqlite3.connect("skamt.db")
cursor = conn.cursor()
connect() öppnar databasen eller skapar filen.
CREATE TABLE IF NOT EXISTS skamt (...)
Tabellen skapas bara om den inte redan finns.
Tillstånd
Kom ihåg det senast hämtade skämtet
senaste_skamt = None
None betyder att inget skämt har hämtats ännu.
senaste_skamt = (
data["setup"],
data["punchline"]
)
Efter API-anropet innehåller variabeln en tuple med två texter.
global
Funktionen ändrar den yttre variabeln
def hamta_skamt():
global senaste_skamt
global anger att funktionen ska ändra variabeln utanför funktionen.
Utan raden skulle en tilldelning skapa en lokal variabel med samma namn.
API
Hämta och tolka ett skämt
response = requests.get(url)
if response.status_code == 200:
data = response.json()
requests.get() skickar en GET-förfrågan.
200 betyder att anropet lyckades.
json() gör svaret till Pythondata.
Visa resultat
API-data blir text i GUI:t
skamt_label.config(
text=f"{data['setup']} - {data['punchline']}"
)
setup innehåller skämtets första del.
punchline innehåller poängen.
config() ändrar texten i etiketten.
Spara
Spara bara när ett skämt finns
if senaste_skamt:
cursor.execute(
"INSERT INTO skamt "
"(setup, punchline) VALUES (?, ?)",
senaste_skamt
)
conn.commit()
? är platshållare för värdena i tuplen.
commit() sparar ändringen permanent.
Läsa
Hämta alla databasrader
cursor.execute("SELECT * FROM skamt")
rader = cursor.fetchall()
fetchall() ger en lista med alla rader.
output = "\n".join(
[f"{rad[1]} - {rad[2]}" for rad in rader]
)
Varje rad görs om till en text på en egen rad.
GUI
Tre knappar, tre funktioner
tk.Button(
root,
text="Hämta skämt",
command=hamta_skamt
).pack()
Varje knapp får sin funktion via command.
hamta_skamtanvänder API:et.spara_skamtskriver till databasen.visa_skamtläser från databasen.
Prova själv
Interaktiv simulering: skämtregister
Vad händer i koden?
Hela flödet
Från klick till databas
- Användaren klickar på Hämta skämt.
- API-svaret visas och sparas i
senaste_skamt. - Användaren klickar på Spara skämt.
INSERTlägger in tuplen i databasen.commit()sparar ändringen.- Visa alla läser och visar raderna.
Testning
Kontrollera fler än normalfallet
- Klicka på Spara innan något har hämtats.
- Spara flera olika skämt.
- Spara samma skämt flera gånger.
- Starta om programmet och visa sparade skämt.
- Testa när API:et eller nätverket inte svarar.
Förbättring
API-anropet behöver felhantering
try:
response = requests.get(url, timeout=10)
response.raise_for_status()
data = response.json()
except requests.exceptions.RequestException:
skamt_label.config(
text="Kunde inte hämta ett skämt."
)
Grundkoden visar flödet. Den robustare versionen hanterar nätverks- och HTTP-fel.
Bygg vidare
Nästa steg
- lägg till ett sökfält
- ta bort valda skämt
- visa skämten i en lista
- förhindra dubbletter
- stäng databasanslutningen korrekt
- kontrollera tabellen med SQLite Viewer
Sammanfattning
Kom ihåg
- GUI:t startar funktioner genom knapptryck.
- API:et levererar data som JSON.
- En tuple håller det senast hämtade skämtet.
- SQLite sparar skämt mellan programkörningar.
- Funktionerna binder ihop GUI, API och databas.
- Testning och felhantering behövs för ett robust program.