form.action และ Javascript

เคยพบปัญหา ไม่สามารถเปลี่ยน action ของฟอร์มด้วย Javascript กันบ้างมั้ยครับ ตอนที่ผมเจอปัญหานี้ครั้งแรก ผมงงไป 2 วันเลยทีเดียว กว่าจะคลำหาต้นตอเจอ

ปัญหานี้จะเกิดขึ้นกับบางบราวเซอร์เท่านั้นนะครับ เช่น IE (IE อีกแล้ว) สำหรับในบราวเซอร์อื่นๆไม่พบปัญหานี้ครับ ลองมาดูตัวอย่างโค้ดที่เป็นปัญหากัน
<form id="frm_test" method="get" action="index.php">
<input type="text" name="action" id="action" />
<input type="submit" id="submit" />
</form>
<script type="text/javascript">
function changeAction () {
  document.getElementById('frm_test').action = 'https://www.goragod.com';
  document.getElementById('submit').click();
}
</script>

<input type="button" onclick="changeAction()" value="Submit 2"  />

โค้ดตัวอย่างด้านบน ไม่มีอะไรมากครับแค่ต้องการเปลี่ยน action ของฟอร์มไปที่ URL อื่นหากกด Submit 2

ปัญหาที่ผมพบเมื่อใช้ IE ก็คือ เมื่อกด Submit 2 แล้วมันไม่ไปยัง URL ใหม่ที่กำหนดให้ (https://www.goragod.com) แต่มันยัง Submit ไปยัง URL เดิม หรือเรียกให้เข้าใจง่ายๆว่า action มันไม่เปลี่ยนนั่นเอง (ไม่ต้องแปลกใจถ้า Browser ที่คุณใช้ทดสอบสามารถใช้งานได้ตามที่คาดหวังนะครับ นั่นเป็นเพราะ Browser ของคุณทันสมัยแล้ว)

ลองวิเคราะห์ปัญหาที่เกิดขึ้นกัน เรื่องของเรื่องคือ เรามี input ที่ชื่อ action อยู่ด้วย ซึ่งนี่เองที่เป็นปัญหา Browser บางรุ่นจะไม่สามารถแยกระหว่าง form.action ว่าเป็น action ของฟอร์ม หรือเป็น input ที่ชื่อ action ของฟอร์มได้ และไม่ว่าจะด้วย วิธีไหน
form.action
form.setAttribute()
document.forms[0].action
document.getElementById('frm_id').action

ทั้งหมดไม่สามารถอ้างไปยัง property action ของฟอร์มได้ แต่คำสั่งดังกล่าวด้านบนจะไปอ้างถึง input ที่ชื่อ action ของ ฟอร์มแทน

เรื่องของเรื่องคือ

  • IE กำหนดให้ property action ของฟอร์มเป็น readonly ครับ ถ้ามี element ที่ชื่อ action ของฟอร์มอยู่ด้วย นั่นทำให้เราไม่สามารถกำหนดค่า action ได้
  • คำสั่ง setAttribute() ของฟอร์ม ก็ยังไปอ้างถึง input ที่ชื่อ action เช่นกัน ทำให้เราไม่สามารถกำหนด action ใหม่ให้กับฟอร์มได้
  • Browser อื่นๆ เป็นไปตามที่คาดหวัง ยกเว้น IE :28:

หนทางแก้ไข และเป็นข้อควรจำไว้เลย คือ เราไม่ควรสร้าง input หรือ tag ที่มีชื่อเดียวกันกับ property ใดๆ ซึ่งปกติก็เป็นชื่อสงวนอยู่แล้วเพื่อป้องกันปัญหาข้างต้น ซึ่ง action ก็คือ parameter หนึ่งซึ่งเรามักใช้ในฟอร์มเสมอด้วยความเคยชิน ผมก็แนะนำให้เปลี่ยนไปใช้ชื่ออื่น (ที่ไม่ซ้ำกับ property ใดๆ หรือไม่เป็นชื่อสงวน) เพื่อให้การทำงานราบรื่น
^