STUDENT HTML DOCUMENT

延伸:把 Mock Sender 換成真實 GAS Web App

這是第 27 次的延伸,不是標準驗收前置。沒有 Google 帳號、Workspace 權限受限或課堂網路不穩時,維持 mock 模式即可完成本堂核心能力。

官方依據:Apps Script Web App 以 doPost(e) 接收 POST,部署後使用 /exec URL;/dev 測試網址只開放有專案編輯權限的人。Web Apps 官方說明Content Service 官方說明

1. 準備專用測試 Sheet

  1. 建立一份不含個資的 Google Sheet。
  2. 第一列建立 createdAtidtypetext 四個欄位。
  3. 由「擴充功能 → Apps Script」開啟綁定專案。

2. 建立 doPost

將下列程式貼入 Apps Script。它會檢查必要欄位,再把一筆變更寫入目前試算表。

function jsonResponse(payload) {
  return ContentService.createTextOutput(JSON.stringify(payload))
    .setMimeType(ContentService.MimeType.JSON);
}

function doPost(e) {
  try {
    const change = JSON.parse(e.postData.contents);
    if (!change.id || !change.type || typeof change.text !== "string") {
      throw new Error("缺少 id、type 或 text");
    }

    const sheet = SpreadsheetApp.getActiveSpreadsheet().getSheets()[0];
    sheet.appendRow([new Date(), change.id, change.type, change.text]);
    return jsonResponse({ ok: true, id: change.id });
  } catch (error) {
    return jsonResponse({ ok: false, error: String(error.message) });
  }
}

3. 部署 Web App

  1. 選「部署 → 新增部署作業」。
  2. 類型選 Web app。
  3. 依課堂帳號政策選擇最小必要存取範圍;不要用含個資的正式 Sheet 測試。
  4. 完成授權後複製結尾為 /exec 的 URL。
  5. 程式更新後要建立新版本或更新部署,不能只儲存程式碼。

禁止把 OAuth token、帳號密碼或敏感試算表內容放進前端。Web App 若以部署者身分執行,就會使用部署者權限寫入資料,必須更審慎限制用途。

4. 建立 gasSend

在自己的延伸分支保留 mockSend(),另外加入以下函數;不要把真實 URL commit 到公開教材範例。

const GAS_URL = "貼上你自己的 /exec URL";

async function gasSend(change) {
  const response = await fetch(GAS_URL, {
    method: "POST",
    headers: { "Content-Type": "text/plain;charset=utf-8" },
    body: JSON.stringify(change),
  });
  const result = await response.json();
  if (!result.ok) throw new Error(result.error || "GAS 寫入失敗");
  return result;
}

syncQueue() 中的 mockSend(change) 暫時換成 gasSend(change)。若真實服務失敗,失敗項仍必須留在 queue,不能因為換了 sender 就改變復原規則。

5. 驗收證據

  1. Network 面板可看到對 /exec 的 POST。
  2. 回應 JSON 為 { "ok": true, "id": "..." }
  3. Sheet 新增一列,id 與送出資料一致。
  4. 故意填錯 URL 時,queue 仍保留失敗項。
  5. 修回 URL 後重試,成功項才從 queue 移除。

只截 Sheet 畫面不足以證明前端同步流程;必須同時具備 Network 回應、queue 狀態與 Sheet 新列三項證據。