跳至內容
Astera Technology

FormData 收了哪些欄位?停用和未剔選要分清

核對初始表單項目,分清重複名稱與略過欄位。

下載完整個案資料及參考答案 ↓

先看這個固定例子

固定表單只建立 FormData,不會送出。程式只印一次初始項目;名稱與備註是只讀示範文字,剔選值固定為 html、css、js。之後改剔選,不會重跑這份初始記錄。

完整頁面內容與固定程式
<style>html{font-size:16px}body{margin:12px;font:1rem/1.5 system-ui,sans-serif;color:#17332d;background:#fff}p{overflow-wrap:anywhere}output{display:block;margin-block:12px;overflow-wrap:anywhere;white-space:pre-wrap}button,input{font:inherit;max-width:100%;box-sizing:border-box}button{margin:4px;padding:8px}label{display:block;margin-block:8px}button:focus-visible,input:focus-visible{outline:3px solid #23715d;outline-offset:2px}ul{padding-inline-start:24px}li{overflow-wrap:anywhere}.highlight{border:2px solid green}</style>
<form id="sample"><label>名稱 <input name="name" value="Ada" readonly></label><label>只讀備註 <input id="note" name="note" value="本地" readonly></label><label>停用備註 <input name="disabled" value="略過" disabled></label><label><input type="checkbox" name="tag" value="html" checked>結構</label><label><input type="checkbox" name="tag" value="css" checked>版面</label><label><input type="checkbox" name="other" value="js">程式</label></form><output id="result"></output>
<script>const result=[...new FormData(document.querySelector('#sample'))];
document.querySelector('#result').textContent=JSON.stringify(result);
console.log(JSON.stringify(result));
</script>
確實的 console 輸出
[["name","Ada"],["note","本地"],["tag","html"],["tag","css"]]
輸入與原生結果
核對項目所給輸入或動作結果
name / note有名稱的只讀文字兩項都加入
disabled / other停用/未剔選兩項都略過
taghtml、css 已剔選getAll: ["html","css"]

原生機制怎樣處理

有 name 的只讀文字欄會加入項目;停用欄及未剔選的 checkbox 會略過。同名已剔選控制項按欄位次序保留多組。建立 FormData 不等於送出,也不代表操作已獲授權。

比較另一寫法

Object.fromEntries 遇同名,只保留後一個值;兩個剔選欄都合資格,html 卻在轉換時失去。

另開的反例原始碼
<style>html{font-size:16px}body{margin:12px;font:1rem/1.5 system-ui,sans-serif;color:#17332d;background:#fff}p{overflow-wrap:anywhere}output{display:block;margin-block:12px;overflow-wrap:anywhere;white-space:pre-wrap}button,input{font:inherit;max-width:100%;box-sizing:border-box}button{margin:4px;padding:8px}label{display:block;margin-block:8px}button:focus-visible,input:focus-visible{outline:3px solid #23715d;outline-offset:2px}ul{padding-inline-start:24px}li{overflow-wrap:anywhere}.highlight{border:2px solid green}</style>
<form id="sample"><label>名稱 <input name="name" value="Ada" readonly></label><label>只讀備註 <input id="note" name="note" value="本地" readonly></label><label>停用備註 <input name="disabled" value="略過" disabled></label><label><input type="checkbox" name="tag" value="html" checked>結構</label><label><input type="checkbox" name="tag" value="css" checked>版面</label><label><input type="checkbox" name="other" value="js">程式</label></form><output id="result"></output>
<script>const entries=[...new FormData(document.querySelector('#sample'))];const result={tag:Object.fromEntries(entries).tag,allTags:new FormData(document.querySelector('#sample')).getAll('tag')};
document.querySelector('#result').textContent=JSON.stringify(result);
console.log(JSON.stringify(result));
</script>
反例輸出
{"tag":"css","allTags":["html","css"]}

試清邊界

只讀備註再設 disabled,建立 FormData 時會怎樣?

查看參考答案

備註會略過;readonly 不會抵消 disabled 的排除。名稱和兩個已剔選 tag 仍保留。

另開的邊界原始碼
<style>html{font-size:16px}body{margin:12px;font:1rem/1.5 system-ui,sans-serif;color:#17332d;background:#fff}p{overflow-wrap:anywhere}output{display:block;margin-block:12px;overflow-wrap:anywhere;white-space:pre-wrap}button,input{font:inherit;max-width:100%;box-sizing:border-box}button{margin:4px;padding:8px}label{display:block;margin-block:8px}button:focus-visible,input:focus-visible{outline:3px solid #23715d;outline-offset:2px}ul{padding-inline-start:24px}li{overflow-wrap:anywhere}.highlight{border:2px solid green}</style>
<form id="sample"><label>名稱 <input name="name" value="Ada" readonly></label><label>只讀備註 <input id="note" name="note" value="本地" readonly></label><label>停用備註 <input name="disabled" value="略過" disabled></label><label><input type="checkbox" name="tag" value="html" checked>結構</label><label><input type="checkbox" name="tag" value="css" checked>版面</label><label><input type="checkbox" name="other" value="js">程式</label></form><output id="result"></output>
<script>document.querySelector('#note').disabled=true;const data=new FormData(document.querySelector('#sample'));const result={entries:[...data],hasNote:data.has('note'),tags:data.getAll('tag')};
document.querySelector('#result').textContent=JSON.stringify(result);
console.log(JSON.stringify(result));
</script>
邊界輸出
{"entries":[["name","Ada"],["tag","html"],["tag","css"]],"hasNote":false,"tags":["html","css"]}

原始例子檔案