期末專案練習 ⏱ 2個鐘頭內完成 最低門檻:能跑就好

個人語言學習小卡
一步一步把想法變成手上的 App

這是一個極簡的期末專案練習。不需要整合學期所有技術,只需要讓自己體會「我有個想法 → 變成可以給朋友看的東西」的完整過程。重點請聚焦在「落地實踐」,不追求完整性。

專案要求:學期教了不少技術,在期末專案中,不是要大家全部都用上,而是讓你選一個你 連自己都真的想用 的小工具,把它做出來。寧可一個簡單的東西完整跑起來,也不需要以為一個複雜的功能卡在半路中間而氣餒。
階段一 · 必做
本機原型
時間估算:1-2 小時
一個 HTML 檔,瀏覽器打開就能用。完成這階段就基本上達標。你已有一個能跑的小工具。
產出:一個 index.html 檔,在自己電腦能跑
階段二 · 選做加分
部署到雲端
時間估算:1–2 小時
推上 GitHub + 一鍵部署到 Zeabur,得到一個全世界都能訪問的網址。朋友打開手機就能用你做的工具。
產出:一個公開網址 + GitHub repo

完成後它長這樣

📱 your-app.zeabur.app
日語學習小卡
情境:在咖啡廳點餐
いただきます
i-ta-da-ki-ma-su
用餐前說的「我要開動了」,含感謝之意
客:「コーヒーをお願いします。いただきます!」

基本功能(最小可行版本)

每次打開或點「下一張」,AI 會幫你生成一張新的學習卡片:

  • 一個你選定主題下的常用詞或片語
  • 發音標記(拼音/羅馬字/注音都可)
  • 中文意思 + 使用情境
  • 一句例句
  • 「念給我聽」按鈕(使用瀏覽器內建語音)

主題你自己決定:日語、西班牙語、文言文、學術詞彙、台灣俚語、流行用語……


階段一 · 本機原型

第一步:在自己電腦做出來

整個小卡 App 是一個檔案——index.html 裡面包含 HTML 結構、CSS 樣式、JavaScript 邏輯。你不需要 Flask、不需要 Python、不需要安裝任何東西,只需要:

完整範本:index.html(複製貼上即可用)

index.html約 70 行
<!DOCTYPE html> <html lang="zh-Hant"> <head> <meta charset="UTF-8"> <title>我的日語小卡</title> <style> body { font-family: sans-serif; background: #faf9f7; padding: 24px; max-width: 480px; margin: 0 auto; } .card { background: #fff; border-radius: 14px; padding: 20px; box-shadow: 0 1px 6px rgba(0,0,0,.06); margin-bottom: 16px; } .word { font-size: 26px; font-weight: 500; } .pinyin { color: #888; margin: 4px 0; font-size: 13px; } .meaning { background: #EEEDFE; padding: 8px 12px; border-radius: 8px; margin-top: 10px; font-size: 14px; } .example { color: #5c5c58; font-style: italic; margin-top: 8px; font-size: 13px; } button { background: #534AB7; color: #fff; border: none; padding: 10px 16px; border-radius: 20px; cursor: pointer; margin-right: 6px; font-size: 13px; } button.sec { background: #f0efe9; color: #1a1a18; } </style> </head> <body> <h2>日語學習小卡</h2> <div class="card" id="output"> 點下方按鈕,AI 幫你出一張新卡片... </div> <button onclick="makeCard()">下一張 →</button> <button class="sec" onclick="speak()">🔊 念給我聽</button> <script> // ── 三個你要修改的地方 ───────────── const API_KEY = "你的_API_KEY_貼在這裡"; // ① 貼你的 Gemini API key const LANGUAGE = "日語"; // ② 你想學的語言 const SPEECH_LANG = "ja-JP"; // ③ 發音語碼 // ───────────────────────────── let currentWord = ""; async function makeCard() { const prompt = `請幫我出一張${LANGUAGE}學習小卡,回應請用 JSON: { "word": "(一個常用詞或片語)", "pinyin": "(發音標記)", "meaning": "(中文意思,含使用情境,30字內)", "example": "(一句例句)" } 不要加 markdown 標記,直接給 JSON。`; const res = await fetch( `https://generativelanguage.googleapis.com/v1beta/models/gemini-2.5-flash:generateContent?key=${API_KEY}`, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ contents: [{ parts: [{ text: prompt }] }] }) } ); const data = await res.json(); const text = data.candidates[0].content.parts[0].text; const card = JSON.parse(text); currentWord = card.word; document.getElementById("output").innerHTML = ` <div class="word">${card.word}</div> <div class="pinyin">${card.pinyin}</div> <div class="meaning">${card.meaning}</div> <div class="example">${card.example}</div>`; } function speak() { if (!currentWord) return; const u = new SpeechSynthesisUtterance(currentWord); u.lang = SPEECH_LANG; speechSynthesis.speak(u); } </script> </body> </html>
三個你需要修改的地方:
① API_KEY:貼上你的 Gemini API key
② LANGUAGE:你想學的語言("日語"、"西班牙語"、"文言文"、"台語"……)
③ SPEECH_LANG:發音語碼(日語 ja-JP、西語 es-ES、英語 en-US、中文 zh-TW)

測試:用瀏覽器打開

達到這裡:階段一完成。你已經有了一個能用的個人小工具。如果你不想做階段二,這個就可以當作期末作業繳交了(誤)。
注意:這版本把 API key 寫在 HTML 裡,只能 自己用,不要分享這個檔案給別人,更不要推上 GitHub。
如果你想讓朋友也能用,請繼續做階段二(用後端代理 key,才能安全部署)。

階段二 · 選做加分

第二步:讓全世界都能用你做的工具

階段一的問題:API key 寫在 HTML 裡,所以這個檔案只能你自己用。如果想分享給朋友、想推到 GitHub,必須加一個極簡的後端來「代管」API key。程式碼只多 20 行。

如何用 Flask 做後端代理,可參考這篇急速入門文章。https://ithelp.ithome.com.tw/articles/10258223

新的檔案結構

my-flashcard/4 個檔案
my-flashcard/ ├── app.py ← 後端,代理 API 呼叫(30 行) ├── requirements.txt ← 套件清單(2 行) ├── .gitignore ← 告訴 git 不要追蹤敏感檔(3 行) └── templates/ └── index.html ← 階段一那個 HTML 移到這裡

app.py:後端代理(30 行)

app.py後端代理
from flask import Flask, render_template, request, jsonify import google.generativeai as genai import os genai.configure(api_key=os.environ["GEMINI_API_KEY"]) model = genai.GenerativeModel("gemini-2.5-flash") app = Flask(__name__) @app.route("/") def home(): return render_template("index.html") @app.route("/api/card", methods=["POST"]) def card(): language = request.json.get("language", "日語") prompt = f"""請幫我出一張{language}學習小卡,回應請用 JSON: {{"word": "...", "pinyin": "...", "meaning": "...", "example": "..."}} 不要加 markdown 標記,直接給 JSON。""" response = model.generate_content(prompt) return jsonify({"text": response.text}) if __name__ == "__main__": port = int(os.environ.get("PORT", 5000)) app.run(host="0.0.0.0", port=port)

修改 index.html:呼叫自己的後端

把階段一的 fetch(...) 那一段替換成:

index.html · script 段落(部分)
// 不再需要 API_KEY ── 改為呼叫自己的 /api/card const LANGUAGE = "日語"; const SPEECH_LANG = "ja-JP"; async function makeCard() { const res = await fetch("/api/card", { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ language: LANGUAGE }) }); const data = await res.json(); const card = JSON.parse(data.text); currentWord = card.word; document.getElementById("output").innerHTML = `...`; }

requirements.txt 與 .gitignore

requirements.txt
flask google-generativeai
.gitignore
.env __pycache__/ *.pyc venv/

本機測試(推上線前先確認能跑)

bash
$ cd my-flashcard $ pip install -r requirements.txt # 設定環境變數(不要寫死在程式碼) $ export GEMINI_API_KEY="你的 key" # Mac/Linux $ $env:GEMINI_API_KEY="你的 key" # Windows PowerShell $ python app.py * Running on http://0.0.0.0:5000 # 打開瀏覽器訪問 http://localhost:5000 → 跟階段一一樣可用

推到 GitHub 並一鍵部署

達到這裡:階段二完成。你有一個全世界都能訪問的個人小工具。這就是「idea 變成手上的 App」的完整經驗:從一個想法到一個可分享的網址。

不一定要做語言學習

同樣的架構,你可以做……

整個 App 的核心邏輯只有兩件事:給 AI 一個 prompt,把回應顯示成卡片。改改 prompt,主題就不同。以下都是相同骨架,只換內容:

📚
學術詞彙小卡
針對你的領域出 GRE / 學術詞彙
prompt 改成:「出一個語言學領域的學術詞彙」
🏛️
文言文翻譯練習
出一句現代中文,提供文言文版本
prompt 改成:「出一句現代中文+文言文對照」
🗣️
台語俚語
每天學一個有趣的台語表達
prompt 改成:「出一句日常的台語俚語+教華語對照」
🍃
每日詩詞
每次抽一首古典詩詞,附白話翻譯
prompt 改成:「抽一首唐宋詩+白話譯文+背景」
🧠
英文單字本
針對你的程度(JLPT 範圍、TOEFL 等)
prompt 改成:「出一個 GRE 高頻字+用法」
💭
每日哲學問題
每次給一個值得思考的哲學問題
prompt 改成:「出一個哲學思辨題+思考方向」
調整思路:不需要重新寫程式碼。只要改 prompt 那段字串,整個 App 就變成不同主題了。這就是 Gemini API 強大的地方:用「自然語言指令」就能定義應用功能。這也是我們一直強調的,想法更為重要!

繳交方式

怎麼交期末作業

繳交清單
必交 01
專案檔案 — 上傳 index.html(階段一)或整個資料夾 zip(階段二)
必交 02
運作截圖 — 至少 2 張,顯示 App 確實能運作(卡片內容、發音按鈕等)
必交 03
專案報告 — 你們做了什麼主題?為什麼選這個(動機)?實作過程涉及哪些技術?哪裡卡住(方法)?感想是什麼(反思與結論)?團隊分工表(如果有)
加分 01
GitHub repo 連結 階段二完成
加分 02
公開部署網址 階段二完成 例如 your-app.zeabur.app;your-app.github.io

最後的話

為什麼這個專案這樣設計

vibe coding 的核心精神不是「學會所有技術」,而是「我有一個想法,我能讓它變成現實」。這個模擬期末專案故意設計得很小,目的是讓大家能體驗到「想法到落地」的完整過程,而不是被技術細節壓垮。輝達(NVIDIA)執行長黃仁勳指出,未來全球程式設計師將由 3,000 萬人暴增至 10 億人。他認為程式設計的本質已變成「制定規格(Spec)」;只要能精確用自然語言告訴 AI 電腦要做什麼,任何人都能成為程式設計師,不需再拘泥於傳統程式語言。語言就是程式碼! AI 時代的溝通門檻降低,讓文科生、非傳統理工背景的人才,能在軟體與應用開發上發揮極大的創造力與優勢。未來的程式設計不僅限於複雜的底層架構建置,更偏向於應用程式的創意發想與邏輯定義,進而開啟大眾化的軟體開發新時代。

希望大家在實作期末專案時,能慢慢體會到這個意思。