1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

🏫10時限目「GET・POST・requestとは?」【🍞Bakery Hubで学ぶPython・Webアプリ開発】

1
Last updated at Posted at 2026-10-11

4056.png

📌 この記事を3行でまとめると

  • GETとPOSTの違いを、Bakery Hubの商品登録機能を使って学び直します。
  • request.method・request.form・request.args の役割を、実際のFlaskコードで確認します。
  • ブラウザで入力した商品情報がPythonに届き、検証されて保存されるまでの流れを整理します。

🥐 はじめに

こんにちは、tosane932です。

2026年5月からPythonの独学を始め、AIを活用しながらベーカリー向け売上管理アプリ「Bakery Hub」を開発しています。

今回で、Python基礎の学び直しシリーズも 第10時限目 になりました。

前回の第9時限目では、店舗メモツールを題材にCRUD(作成・取得・更新・削除)を学びました。

今回は、そこから少し戻って、Webアプリの基本的な仕組みを確認していきます。

例えば、Bakery Hubの商品登録画面。

商品名と売価を入力して、登録ボタンを押す。

普段は当たり前のように操作していますが、改めて考えると疑問があります。

ブラウザに入力した商品情報は、どうやってPythonに届いているんだろう?

🐹「商品名と値段を入力して、登録ボタンを押す……」

🐹「それだけでデータベースに保存されるけど、裏では何をしてるんだろう?」

今回はこの疑問を出発点に、GET・POST・request を学び直してみます。

🥪 今回の教材:Bakery Hub

Bakery Hubは、僕が開発しているベーカリー向け売上管理アプリです。

商品登録、日次売上入力、ダッシュボード、店舗メモなどの機能があります。

今回紹介するコードは、このアプリの実装から抜粋しています。


📖 第1章|GETとPOSTって何が違う?

Webアプリでは、ブラウザとサーバーが情報をやり取りしています。

ブラウザからサーバーへ送る依頼を、HTTPリクエスト と呼びます。

例えば、

  • 商品登録画面を表示してほしい
  • 入力した商品情報を登録してほしい

といった依頼です。

ここで登場するのが、GETとPOSTです。

GETとPOSTの基本

HTTPメソッド 主な役割 Bakery Hubでの例
GET 情報や画面を取得する 商品登録画面を開く
POST データを送信して処理を依頼する 商品の登録・更新を依頼する

🐹「GETは『画面を見せて!』で、POSTは『この商品を登録して!』ってこと?」

今回の商品登録機能では、そのイメージで理解できそうです。

ただし、POSTは必ずデータベースに保存するためのもの、というわけではありません。

送信された情報を使って計算したり、別の処理をしたりすることもあります。

流れを図にすると

【GET】

ブラウザ
   │
   │「商品登録画面を見せて」
   ▼
Flask / Python
   │
   │ HTMLを返す
   ▼
ブラウザに画面が表示される


【POST】

ブラウザ
   │
   │「この商品情報を処理して」
   ▼
Flask / Python
   │
   │ 入力された情報を確認
   ▼
データベースへ保存

💡 HTTPメソッドとは?

HTTPメソッドは、サーバーにどのような処理を依頼するかを表すものです。

GETとPOST以外にも、PUT・PATCH・DELETEなどがあります。

今回は商品登録で使っているGETとPOSTに絞って確認します。

参考:MDN|HTTPリクエストメソッド


📖 第2章|FlaskはGETとPOSTをどう受け取る?

ここからは、Bakery Hubの実コードを見てみます。

商品登録を担当する app.py には、次のコードがあります。

@app.route("/", methods=["GET", "POST"])
@admin_or_guest_required
def index():

出典:Bakery Hub|app.py

注目したいのは、

methods=["GET", "POST"]

です。

これは / というURLで、GETとPOSTの両方を受け付ける設定です。

コードを分解してみる

コード 役割
@app.route("/") URLとPythonの関数を結びつける
methods=["GET", "POST"] GETとPOSTを受け付ける
@admin_or_guest_required 管理者またはゲストの利用条件を確認する
def index(): 処理を担当する関数を定義する

🐹「あれ?GETもPOSTも、同じ index() 関数が担当するの?」

そうなんです。

同じURLでも、リクエストの種類によって処理を分けられます。

では、どうやって見分けるのでしょうか。

そこで登場するのが、次の if 文です。


📖 第3章|request.method と if 文

Bakery Hubの index() 関数には、次の条件分岐があります。

if request.method == "POST":

これは、今回のリクエストがPOSTかどうかを確認しています。

POSTなら、商品情報を受け取って登録・更新する処理へ進みます。

GETなら、この条件には入らず、後半の画面表示処理へ進みます。

🐹「……あれ?これって普通の if 文じゃない?」

そうです。

以前学んだPythonの条件分岐と同じ構造です。

if 条件:
    処理

さらに、

request.method == "POST"

は比較演算子 == を使っています。

POSTなら True、そうでなければ False と判定されるわけです。

request とは?

request は、Flaskが現在のHTTPリクエストの情報を扱うために用意しているオブジェクトです。

書き方 役割
request.method GET・POSTなどを確認する
request.form フォームの入力データを扱う
request.args URLのクエリパラメータを扱う

🐹「Web開発って難しい処理ばかりかと思ったけど、ちゃんとPythonの基本文法が使われてるんだね」

こういう発見があると、基礎を学び直している意味を感じます。

📚 Python基礎とのつながり

ここまでに登場したのは、

  • 比較演算子 ==
  • 真偽値 True / False
  • if 文による条件分岐
  • 関数の定義 def

などです。

Web開発でも、これまで学んだPythonの知識が土台になっています。

参考:Flask公式|Request Object


📖 第4章|HTMLからPythonへデータを送る

次は、ブラウザ側のコードです。

Bakery Hubの index.html には、次の記述があります。

<form method="POST">
    <input type="hidden" name="csrf_token" value="{{ csrf_token() }}">

出典:Bakery Hub|index.html

method="POST" と書いてあります。

この指定によって、フォームを送信するときにPOSTリクエストが使われます。

今回のフォームには action 属性が指定されていないため、基本的には現在のページのURLへ送信されます。

HTMLとPythonの役割分担

担当 役割
HTML 商品名・売価の入力欄を用意する
ブラウザ 入力された情報をHTTPで送る
Flask リクエストを受け取る
Python 入力値を確認して処理する

🐹「なるほど。HTMLで入力した情報をブラウザが送って、Flaskが受け取るんだ!」

ここで、ようやくHTMLとPythonのつながりが見えてきました。

csrf_token って何?

コードには、もう一つ気になるものがあります。

<input type="hidden" name="csrf_token" value="{{ csrf_token() }}">

これは、不正なフォーム送信を防ぐために使われる仕組みです。

今回はGET・POSTの理解が中心なので、詳しい説明は別の機会にしたいと思います。

⚠️ POSTを使えば安全、というわけではない

POSTはHTTPリクエストの種類を表すものであり、それだけで安全になるわけではありません。

通信の暗号化にはHTTPS、フォームの不正送信対策にはCSRFトークンなど、それぞれ別の仕組みが必要です。


📖 第5章|request.form で商品情報を受け取る

ここからが、今回特に理解したかった部分です。

Bakery Hubでは、フォームから送信された商品情報を次のように受け取っています。

product_names = request.form.getlist("prod_name")
product_prices = request.form.getlist("prod_price")
product_ids = request.form.getlist("product_id")

出典:Bakery Hub|app.py

なぜ getlist() を使う?

🐹「getlist()……名前からして、リストで取得するってこと?」

そうです。

Bakery Hubでは複数の商品をまとめて登録できるため、同じ名前で送信された値をリストで取得しています。

例えば、次の3商品を入力したとします。

商品名 売価
クロワッサン 280円
あんぱん 180円
食パン 350円

フォームから取得した情報は、次のようなイメージになります。

product_names = [
    "クロワッサン",
    "あんぱん",
    "食パン",
]

product_prices = [
    "280",
    "180",
    "350",
]

ここで一つ気になりました。

売価なのに、"280" とダブルクォーテーションで囲まれています。

フォームから受け取る数値は文字列

HTMLで数値を入力しても、request.form から取得する値は基本的に文字列です。

price = "280"

print(type(price))

実行結果:

<class 'str'>

🐹「えっ、280円って入力したのに、整数の280じゃないの?」

画面で数字に見えていても、Python側では文字列として受け取っているんですね。

そのため、必要に応じて整数へ変換したり、入力値が正しいか確認したりする処理が必要になります。

get() と getlist() の違い

メソッド 役割
request.form.get("name") 指定した名前の値を1つ取得する
request.form.getlist("name") 同じ名前の値をリストで取得する

💡 リストの学習がここで役立った

以前学んだリストは、複数の値をまとめて扱うためのデータ型でした。

Bakery Hubでも、複数の商品名や売価を扱うために使われています。

基本文法が実際のアプリで使われているところを見ると、理解しやすくなります。


📖 第6章|受け取ったデータをそのまま保存しない

🐹「よし!商品名と値段を受け取ったら、そのままデータベースに保存すればいいんだね!」

……と思ったのですが、実際にはその前に確認が必要です。

もし商品名が空っぽだったら?

もし売価がマイナスだったら?

もし想定外の数字が送られてきたら?

そうしたデータをそのまま保存しないために、入力値を検証しています。

商品名のチェック

Bakery Hubでは、次のコードで商品名を確認しています。

normalized_name = name.strip()

if not 1 <= len(normalized_name) <= PRODUCT_NAME_MAX_LENGTH:
    logger.warning("Rejected product update with invalid product name.")
    return "商品名は1文字以上100文字以内で入力してください。", 400

コードを分解する

コード 意味
name.strip() 前後の空白などを取り除く
len(normalized_name) 商品名の文字数を調べる
1 <= ... <= PRODUCT_NAME_MAX_LENGTH 許可された文字数か確認する
not 条件を満たしていない場合を判定する
return ..., 400 エラーを返して処理を終了する

現在のBakery Hubでは、商品名は 1〜100文字 に制限されています。

🐹「商品名が空白だけだったとしても、strip() したら空文字になるんだね」

ここにも、以前学んだ文字列処理や条件分岐が登場しています。

売価のチェック

売価にも条件があります。

price_value = _parse_bounded_nonnegative_integer(
    price,
    PRODUCT_PRICE_MAX,
)

if price_value is None or price_value % PRODUCT_PRICE_STEP != 0:
    logger.warning("Rejected product update with invalid price.")
    return "売価は0〜9,990円の10円単位で入力してください。", 400

現在のBakery Hubでは、売価は 0〜9,990円の10円単位 です。

入力値 判定
280円 OK
350円 OK
285円 NG
-100円 NG
10,000円 NG

🐹「285円も整数なのに、なぜ駄目なんだろう?」

10円単位という条件があるためです。

ここでは % という剰余演算子が使われています。

例えば、

print(280 % 10)  # 0
print(285 % 10)  # 5

10で割った余りが0なら、10円単位という条件を満たします。

📌 バリデーションとは?

入力された値が、アプリの決めた条件を満たしているか確認することです。

Bakery Hubでは、商品名・売価・年月などをサーバー側で検証しています。

HTMLの入力制限だけに頼らず、Python側でも確認することが大切です。


📖 第7章|データベースへの保存

入力値の確認が終わると、データベースへの保存処理に進みます。

新しい商品を追加する場合、Bakery Hubでは次のコードが使われています。

db.session.add(
    Product(
        dataset=current_dataset,
        year=year,
        month=month,
        name=prod["name"],
        price=prod["price"],
        image_key=prod["image_key"],
    )
)

そして、必要な処理をまとめたあとに、

db.session.commit()

が実行されます。

🐹「あっ!add() と commit() は前にも見たことがある!」

SQLAlchemyを使ったデータベース操作ですね。

処理 役割
db.session.add() 新しい商品を保存対象に追加する
db.session.commit() 変更を確定する
db.session.rollback() エラー時などに未確定の変更を取り消す

実際のBakery Hubでは、新規追加だけでなく、既存商品の更新や非表示処理も行っています。

今回は新規追加部分を中心に読みました。

🔗 関連ドキュメント

SQLAlchemy公式|Session Basics

add()、commit()、rollback() の役割を詳しく確認できます。


📖 第8章|GETでもデータを送れる?

ここまでPOSTを中心に見てきましたが、GETでも情報を渡すことがあります。

Bakery Hubには次のコードがあります。

month = request.args.get("month", type=int)

これは、URLのクエリパラメータから month を取得する処理です。

例えば、

/?month=10

というURLなら、10月を指定しているイメージです。

type=int が指定されているため、整数に変換できれば整数として取得します。

🐹「GETでも、表示したい月を伝えられるんだね!」

GETでは、検索条件や表示対象などをクエリパラメータで指定することがあります。

request の役割を整理

書き方 何を扱う?
request.method リクエストの種類
request.form フォームから送られたデータ
request.args URLのクエリパラメータ

似たような名前ですが、取得する情報が違います。

この3つは、今後も何度か読み直したいところです。


📖 第9章|商品登録の流れをまとめる

今回学んだ内容を、商品登録の流れに沿って整理してみます。

① ブラウザからGETでアクセス
          │
          ▼
② Flaskが商品登録画面を表示
          │
          ▼
③ 商品名と売価を入力
          │
          ▼
④ HTMLフォームからPOSTで送信
          │
          ▼
⑤ Flaskがrequest.formで受け取る
          │
          ▼
⑥ Pythonで入力値を検証
          │
          ▼
⑦ SQLAlchemyで商品を追加・更新
          │
          ▼
⑧ commit()で変更を確定
          │
          ▼
⑨ 登録完了画面を表示

🐹「登録ボタン一つで、こんなに処理が動いていたんだね」

今回登場したのは、

  • HTTPのGET・POST
  • Flaskのルーティング
  • request からのデータ取得
  • Pythonの条件分岐
  • リスト
  • 文字列処理
  • 入力値の検証
  • SQLAlchemyのデータベース操作

などです。

こうして並べると多く感じますが、すでに学んだPythonの基本文法も含まれています。

バラバラに覚えていたことが、一つの機能の中でつながっているのが面白いですね。


📝 第10時限目の理解度チェック

最後に、今回の内容を5問で復習してみます。

問題 内容
Q1 GETとPOSTの主な違いは?
Q2 request.method == "POST" は何を確認している?
Q3 request.form.getlist() を使う理由は?
Q4 なぜフォームから受け取った売価を検証する?
Q5 db.session.commit() は何をする?
✅ 解答例を見る

Q1. GETとPOSTの主な違いは?

GETは情報の取得、POSTはデータを送って処理を依頼するときなどに使います。

Q2. request.method == "POST" は何を確認している?

今回のHTTPリクエストがPOSTかどうかを確認しています。

Q3. request.form.getlist() を使う理由は?

同じ名前で送られた複数の値を、リストとして取得するためです。

Q4. なぜフォームから受け取った売価を検証する?

文字列として送られた値が、アプリの決めた形式や範囲に合っているか確認するためです。

Q5. db.session.commit() は何をする?

データベースへの変更を確定します。


🐹 おわりに

今回は、Bakery Hubの商品登録機能を使って、GET・POST・requestを学び直しました。

僕はAIを活用しながらWebアプリを開発していますが、開発を続けるにつれて、自分の理解が追いつかなくなってきた部分があります。

特にBakery Hubは、独学を始めた頃と比べて機能が増え、コードも大きくなりました。

だからこそ、今は新しい機能を追加するだけでなく、すでに動いているコードを読み返す時間を大切にしています。

今回の商品登録も、最初は単純な機能だと思っていました。

でも実際には、ブラウザとFlaskがHTTPでやり取りし、Pythonが入力値を確認し、SQLAlchemyがデータベースへの変更を担当していました。

それぞれの仕組みを一度に全部理解するのは難しいですが、以前学んだ if 文やリスト、文字列処理が実際に使われていると分かったのは嬉しい発見です。

🐹「第10時限目まで来たけど、まだまだ知らないことがいっぱいあるなぁ……」

🐹「でも、前に学んだことが実際のアプリで使われてると、ちょっと嬉しいね!」

今後も、コードを丸暗記するのではなく、なぜその処理が必要なのか、自分の言葉で説明できるようになりたいと思っています。

最後まで読んでいただき、ありがとうございました!


🔗 参考資料・関連リンク

公式ドキュメント

🐹 Python基礎シリーズ|これまでの学習記録

Bakery Hub(旧sales_data_app)の実コードを教材に、Pythonの基礎からWebアプリ開発の仕組みまで学び直しています。

時限 学習テーマ 記事
第1時限目 変数・データ型・比較演算子・if文 📖 読む
第2時限目 リスト・辞書・set・for文 📖 読む
第3時限目 関数・引数・return・関数の呼び出し・型ヒント 📖 読む
第4時限目 モジュール・import・例外・try・except 📖 読む
第5時限目 クラス・インスタンス・init・self・属性 📖 読む
第6時限目 f文字列・アンパック・リスト内包表記・join 📖 読む
第7時限目 strip・len・splitlines・スライス 📖 読む
第8時限目 None・is・is not・isinstance 📖 読む
第9時限目 CRUD・Create・Read・Update・Delete 📖 読む
第10時限目 GET・POST・request 📍 今回の記事

🥐 学習の進め方

各記事では、実際に開発したアプリのコードを読みながら、基本文法や処理の仕組みを一つずつ確認しています。

第1〜8時限目はPythonの基本文法を中心に、第9時限目からはFlaskやデータベースを含むWebアプリ開発の基礎にも範囲を広げています。

🥐 Bakery Hub

GitHub|Tosane Works

Bakery Hub|公開デモ

システム概要|実コードで学ぶページ

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?