市面上有 Moodle、有 Teachable、有無數現成的學習管理系統。 我卻選擇從頭打造一個。 有人會問:你為什麼不直接用?
我的理由有三個。 第一,我想要透過從頭打造一個 LMS,來知道他是怎麼被造出來的。 第二,我在很多 LMS 上面曾經有著期待, 我想要試試看能不能自己找到期待。 第三,如果有些東西是大家都有的,很可能他不是一個太難的事情; 如果有些人沒有,我想弄清楚他到底是不被需要,還是做不出來。 換句話說:我們的想法是一個糟糕的想法,還是一個有意思的 idea?
這篇文章,是關於我從造輪子的過程中體會到的想法—— 也給正在猶豫要不要「從頭做」的人,開一條釐清的路。
▍教材上傳的「應該很簡單」
教材上傳,聽起來很簡單。 實際上呢?
檔案不知道存到哪裡—— 程式裡寫的路徑 backend/public/uploads 根本不存在。 中文檔名變成亂碼—— Windows 和程式的編碼方式不一致,上傳後變成亂碼。 下載的檔案打不開—— 點下載後,內容竟是網頁的錯誤頁面,而不是真正的教材。
還有:存檔的欄位長度不夠、變數名稱重複宣告、 檔名和檔案類型設定混亂、MIME type、路徑、權限、時區、編碼。 每一個「應該很簡單」的環節, 都藏著「理想解」的細節。
最後的解法是: 建立清楚的對照表、統一命名規則、 改用時間戳+隨機數+副檔名儲存、確保每個環節都驗證過。 簡單的是「概念」,複雜的是「邊界」。
▍迭代式 vs 現成邏輯
作業系統「不就是上傳+批改」? 我要的不一樣。
我要的是「迭代式」: 學員可以多次修改、重交, 老師每次都會針對最新版本評分。 批改後若學員再交,會建立新版本, 舊版本和舊評語都會保留。 這不是現成 LMS 的預設邏輯。
需要從頭設計: 個別指定作業、版本規則、assignment_designations、is_latest 的判斷。 還有:審核制註冊、填空題+檔案上傳兩種作業類型、 教材說明欄位、外部連結支援、YouTube 自動內嵌、 經驗值、等級、徽章、排行榜、優秀作品觀摩。 現成產品要嘛沒有,要嘛要大改。
▍先跑通,再求持久
為何不一開始就用 Google Drive? 理想解是階段性的。 先本機跑通,再考慮持久化; 先功能完成,再考慮上線。 不是一步到位,而是「這一階段要什麼」。
原本檔案存在主機的硬碟裡, 但免費主機 Render 重啟後,檔案會消失。 後來才接 Google Drive, 改用「共用雲端硬碟」Shared Drives, 需要 Google Workspace 帳號才能建立。 先求跑通,再求持久。
▍伴飛計畫的旅程意義
在造的過程中,哪個 moment 讓我突然清楚「我要的是這個」? 其實我腦袋中一直想的是: 在我接下來要辦的培訓, 我想要帶給學員怎麼樣的體驗。 也就驅動著我必須怎麼樣完成這件事情。 有時候創造的來源, 可能不是你真的要解決什麼事, 而是你想要找尋一個專屬於你的劇本。
若有人問「你為什麼不直接用 Moodle / Teachable」,我會怎麼回答? 教材與內容、硬體,該有的都有了。 但是我想透過包含激勵方式與事件紀錄的模組, 帶給參加伴飛計畫的學員多一點旅程上的意義。 徽章、經驗值、等級、排行榜、學習歷程—— 這些不是「功能清單」, 而是「學員在旅程中會被怎麼對待」。
造輪子的價值,在於把「我要什麼」從模糊變成具體。 那些「應該很簡單」的環節——中文檔名、時區、版本規則—— 恰恰是理想解與通用解的落差。 重複造輪子,不是為了證明自己很厲害, 而是在造的過程中,發現現成輪子裝不上的地方。
(人機協作三部曲之二,前見之一〈AI 是鏡子〉,續見之三〈當 C 型人遇上更 C 的機器〉)













