FastAPIデスクトップツール-001
[質問]
FastAPIをバックエンドとして、ブラウザからアクセスするマイクロブログを作ってください。個人利用なのでユーザー登録は不要です。記事タイトルと本文が投稿できる形にしてください。
[回答] Gemini
FastAPIを使って、個人でサクッと使えるマイクロブログを作成しましょう。 シンプルさを重視し、FastAPI(バックエンド) + Jinja2(HTMLテンプレート) + SQLite(データベース) の構成で構築します。
1. 準備:ディレクトリ構造
まず、プロジェクトフォルダを作成し、以下の構成でファイルを配置します。
microblog/
├── main.py # FastAPIのメインロジック
├── database.py # DB設定
├── models.py # DBテーブル定義
├── templates/ # HTMLファイル
│ └── index.html
└── blog.db # 実行時に自動生成されるDB
2. 実装:コードの記述
database.py (データベース接続)
SQLiteを使用するための設定です。
from sqlalchemy import create_engine
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import sessionmaker
SQLALCHEMY_DATABASE_URL = "sqlite:///./blog.db"
engine = create_engine(SQLALCHEMY_DATABASE_URL, connect_args={"check_same_thread": False})
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
Base = declarative_base()
models.py (データ構造)
記事のタイトルと本文を保存するテーブルを定義します。
from sqlalchemy import Column, Integer, String, Text, DateTime
from datetime import datetime
from database import Base
class Post(Base):
__tablename__ = "posts"
id = Column(Integer, primary_key=True, index=True)
title = Column(String(100))
content = Column(Text)
created_at = Column(DateTime, default=datetime.now)
main.py (メインロジック)
投稿の表示と保存を行うAPIを記述します。
from fastapi import FastAPI, Request, Form, Depends, responses
from fastapi.templating import Jinja2Templates
from sqlalchemy.orm import Session
import models
from database import SessionLocal, engine
# DBテーブルの作成
models.Base.metadata.create_all(bind=engine)
app = FastAPI()
templates = Jinja2Templates(directory="templates")
# DBセッションの取得
def get_db():
db = SessionLocal()
try:
yield db
finally:
db.close()
@app.get("/")
def read_root(request: Request, db: Session = Depends(get_db)):
posts = db.query(models.Post).order_by(models.Post.created_at.desc()).all()
return templates.TemplateResponse("index.html", {"request": request, "posts": posts})
@app.post("/post")
def create_post(title: str = Form(...), content: str = Form(...), db: Session = Depends(get_db)):
new_post = models.Post(title=title, content=content)
db.add(new_post)
db.commit()
return responses.RedirectResponse(url="/", status_code=303)
3. UI:templates/index.html
見た目を整えるために、軽量なCSSフレームワーク「Pico.css」を利用します。
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>My Microblog</title>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@picocss/pico@1/css/pico.min.css">
</head>
<body class="container">
<nav>
<ul><li><strong>My Microblog</strong></li></ul>
</nav>
<main>
<section>
<form action="/post" method="post">
<input type="text" name="title" placeholder="タイトル" required>
<textarea name="content" placeholder="いまなにしてる?" required></textarea>
<button type="submit">投稿する</button>
</form>
</section>
<hr>
<section>
{% for post in posts %}
<article>
<header>
<strong>{{ post.title }}</strong>
<small style="float: right;">{{ post.created_at.strftime('%Y-%m-%d %H:%M') }}</small>
</header>
{{ post.content }}
</article>
{% endfor %}
</section>
</main>
</body>
</html>
4. 実行方法
-
ライブラリのインストール
-
サーバーの起動
-
ブラウザでアクセス
http://127.0.0.1:8000を開くと、投稿フォームと記事一覧が表示されます。
次のステップへの提案
このままでも十分使えますが、さらに便利にするために以下の機能を追加することも可能です。
- 削除機能: 投稿を消せるようにするボタンの追加。
- Markdown対応: 本文を装飾できるようにする。
- パスワード保護: 自分以外が投稿できないように簡易的な認証をつける。
まずはこのコードを動かしてみて、削除機能なども追加してみたいですか?