前幾天我們已經把 AI 助教的後端 API 和前端介面接起來,也陸續加上了一些防呆設計和載入動畫。
不過隨著功能慢慢增加,程式碼也開始變得越來越多。有時候不是功能做不出來,而是改了一個地方,結果又在另一個地方出現 Bug。對一個自己一個人開發的人來說,要一邊趕進度、一邊整理程式碼,其實滿花時間的。所以今天想來試試看 Google Antigravity CLI。
簡單來說,就是把 AI 直接放進終端機裡,我可以直接告訴它「幫我看看這個專案有沒有問題」,讓它先幫我找 Bug,再協助我修改程式碼。
今天主要想完成三件事情:
首先先把 Antigravity CLI 安裝好,確認在終端機輸入 agy 後可以正常使用。
這樣之後就可以直接在專案資料夾裡叫 AI 幫忙處理程式碼。

接著進到專案的根目錄,直接請 Antigravity CLI 幫我檢查整個專案
agy -p "請幫我掃描目前資料夾底下的程式碼,檢查有沒有任何潛在的 Bug 或可以優化的地方"
這一步有點像先請 AI 幫我做一次 Code Review,讓它自己去看程式碼,找出可能有問題的地方。
不過這不要特別注意可能跑出jetski: no output produced — a tool required the "read_file" permission that headless mode cannot prompt for...
這是因為 Antigravity CLI 在背景執行無頭模式(Headless Mode)時,預設沒有權限直接讀取本機檔案夾,所以當它嘗試去掃描程式碼就會就被系統安全機制擋下來了。
我們有兩種解法:
依照提示,你可以在設定檔中加入權限允許規則,或者直接使用最快的黑客模式來繞過權限詢問。
直接在指令後面加上 --dangerously-skip-permissions 參數,讓 AI 結對工程師可以直接讀取並幫你檢查程式碼:
agy -p "請幫我掃描目前資料夾底下的程式碼,檢查有沒有任何潛在的 Bug 或可以優化的地方" --dangerously-skip-permissions
這次主要發現了幾個問題,例如前端的對話紀錄沒有完整保留、後端遇到 429 時沒有自動重試,以及靜態資源路由可能有安全上的風險。



找到問題之後,就可以繼續把需求告訴它,讓它直接修改程式碼:
agy -p "請直接幫我修改目前專案的程式碼來解決以下三個最優先的問題:
1. 在 index.html 的 sendMessage 中加入對話歷史(chatHistory),解決 AI 助教失憶的問題。
2. 在 server.js 的 generateWithRetry 中加入 429 流量超限的指數退避重試機制。
3. 將 server.js 中的靜態資源路由修改為僅對外開放指定資料夾,避免洩漏後端原始碼。" --dangerously-skip-permissions
這裡我覺得滿方便的地方是,不需要自己一個一個檔案找,再慢慢修改。
我只要把「現在遇到什麼問題」講清楚,AI 就可以直接去找相關的程式碼並進行修改。
當然,AI 改完之後還是要自己測試,不能看到它說「完成」就直接當作沒問題。

這次比較重要的修改有兩個。
第一個是後端的 429 重試機制。
當 API 使用量太高時,伺服器可能會回傳 429 Too Many Requests。如果程式直接把錯誤丟回去,使用者就只能看到錯誤訊息。所以這次讓程式遇到 429 或 503 時,不要馬上放棄,而是先等一下再重新嘗試,而且每次等待的時間會越來越長,1 秒 → 2 秒 → 4 秒,這就是所謂的 Exponential Backoff(指數退避)。
async function generateWithRetry(aiClient, modelName, contents, config, retries = 3, delay = 1000){
for (let i = 0; i < retries; i++) {
try {
const response = await aiClient.models.generateContent({
model: modelName,
contents: contents,
config: config
});
return response;
} catch (error) {
const isRateLimit = error.status === 429 || error.status === 503 ||
(error.message && error.message.includes('429'));
if (isRateLimit && i < retries - 1) {
const waitTime = delay * Math.pow(2, i);
console.warn(
`⚠️ 遇到流量限制或伺服器忙碌,等待 ${waitTime}ms 後重新嘗試...`
);
await new Promise(resolve => setTimeout(resolve, waitTime));
continue;
}
throw error;
}
}
}
第二個是前端的 chatHistory。
原本每次送訊息時,AI 只會收到「這一次」的問題,所以聊久了之後,它其實不知道前面講過什麼。
現在則是把之前的對話一起送到後端:
const response = await fetch('/api/chat', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
message: message,
history: chatHistory
})
});
const data = await response.json();
chatHistory.push({
role: 'user',
parts: [{ text: message }]
});
chatHistory.push({
role: 'model',
parts: [{ text: data.reply }]
});
這樣 AI 就可以知道前面聊過的內容,對話也會比較連貫。
今天最大的感受是,AI CLI 跟一般的聊天型 AI 還是有點不一樣,以前遇到 Bug,我可能會把程式碼複製到 AI 裡面,問它「這裡為什麼會錯」。
現在則可以直接在專案裡讓 AI 幫我看整個程式,甚至直接修改檔案,對一個人開發的小型專案來說,這種方式真的可以省掉不少時間。不過這也不代表以後就可以完全不看程式碼,AI 幫忙改完之後,還是需要自己確認它到底改了什麼,以及測試修改後有沒有產生新的問題。
回到這次的 AI 助教專案,其實這些看起來比較偏後端或開發的問題,最後都會影響學生使用時的體驗, AI 如果一直忘記前面講過的內容,學生就會覺得這個助教很笨,要不斷在向助教解釋剛剛的問題,強調連貫性,如果 API 偶爾因為流量問題直接報錯,也會讓學習被迫中斷。
所以把這些底層問題處理好,其實也是在讓 AI 助教變得更好用。
這次用 Antigravity CLI 最大的幫助,就是讓我不用把大量時間花在找 Bug 和整理程式碼上,可以把更多時間留給真正的功能開發。
今天先讓 AI 幫忙找 Bug 和修改程式碼,明天則要繼續玩 Antigravity CLI,看看能不能讓它幫我們把 API 的程式碼模組化,整理得更乾淨。