วันจันทร์ที่ ๑๒ พฤศจิกายน พ.ศ. ๒๕๕๐

อัพโหลดไฟล์แบบ AJAX บน ASP.NET (ASP.NET AJAX FileUpload)

ในการทำระบบอัพโหลดไฟล์บน ASP.NET AJAX Extension โดยใช้ FileUpload Control นั้น ผมพบว่าไม่สามารถอัพโหลดได้ เมื่อลอง Debug ดู พบว่า property ชื่อ PostedFile ของอ็อบเจ็ค FileUpload มีค่าเป็น 'null' หรือ 'Nothing' ผมจึงได้พยายามหาคำตอบจึงพบว่า ในเว็บ http://www.asp.net/ajax/documentation/live/overview/UpdatePanelOverview.aspx (หัวข้อ Controls that Are Not Compatible with UpdatePanel Controls) ได้บอกเป็นทางการไว้แล้วว่า server control ใดบ้างที่ UpdatePanel Control ไม่ซัพพอร์ต ซึ่งหนึ่งในนั้นคือ FileUpload ที่มีการใช้งานแบบ asynchronous postback (เป็นการทำงานโดย default ของ UpdatePanel Control)

ด้วยปัญหาที่ได้เขียนมา ผมก็ต้องแก้ไขปัญหาโดยการค้นคว้าหาข้อมูลจากอินเตอร์เน็ต ซึ่งพบว่า มีคนแก้ปัญหานี่ไว้หลายวิธี เรียงตามความยุ่งยากในการ implement นะครับ ได้แก่

1. กำหนดให้ UpdatePanel Control ที่มี FileUpload Control ทำงานแบบ synchronous postback นั้นคือต้องไปกำหนด attribute ของ UpdatePanel เป็น UpdateMode="Conditional" แล้วเพิ่มแท็ก <Triggers> เข้าไปแท็กลูกของแท็ก UpdatePanel Control เช่น

<asp:UpdatePanel ID="UpdatePanel1" runat="server" UpdateMode="Conditional">
<Triggers>
<asp:PostBackTrigger ControlID="btnUpload" />
</Triggers>
<ContentTemplate>
<asp:FileUpload ID="FileUpload1" runat="server" Width="380px" />
....

* ข้อเสียของวิธีที่ 1 คือ ถ้าเราใช้ AJAX Control ที่ทำงานแบบ asynchronous postback เช่น UpdateProgress (ซึ่งถือเป็นเสน่ห์ของ web app. แบบ AJAX) จะไม่สามารถทำงานได้

2. เขียน JavaScript เพิ่ม เพื่อเสริมการทำงาน ซึ่งเท่าที่ผมค้นมาได้ก็เห็นอยู่ 3 คน คือ
1).ของ Dzianis ซึ่งเขียนโค้ดไว้ใน CodeProject.com โดย Dzianis ได้ใช้ AJAX ร่วมกับเว็บเซอร์วิสในการอัพโหลดไฟล์
2).ของ Vinayak Kumar Shrestha เป็นคนเนปาล เขียนรายละเอียดไว้ที่บล็อกตัวเอง 2 บทความ โดยบทความแรก (Uploading files using asp.net ajax extensions) เป็นการบอกปัญหาและทางแก้ไข บทความที่ 2 (ajax extensions file upload workaround) เป็นตัวอย่างจริงในการแก้ปัญหาซึ่งมีโค้ด VB.NET ให้ดาน์วโหลดด้วย (zip 4kB) ซึ่งผมลองนำมาใช้ดู พบว่ายังมีการมี postback หน้าเว็บอยู่ ทำให้มีไม่ความรู้สึกเป็น AJAX
3).ของ Kazi Manzur Rashid (Amit) ซึ่งเขียนวิธีของเค้าไว้ในบทความ Create An Ajax Style File Upload ที่บล็อกเค้า มีให้ดาน์วโหลดโค้ดด้วย

3. ใช้ Custom ASP.NET AJAX Server Control ที่มีผู้สร้างไว้ เท่าที่ผมหาเจอ คือของ Subgurim ที่ codeplex.com ตอนที่ผมเขียนเค้าทำถึงเวอร์ชั่น 1.2 ไฟล์ดาวน์โหลดเป็น .dll (ถ้าสนใจวิธีการสร้างหรือต้องการนำมา customize ต่อ ก็มี source code ให้โหลดครับ) ขั้นตอนการนำมาใช้ก็ง่ายๆ เพียงนำไฟล์ FUA.dll ไปวางไว้ในโฟลเดอร์ bin ของ web app. ของเรา แล้วเพิ่ม
<%@ Register Assembly="FUA" Namespace="Subgurim.Controles" TagPrefix="cc1" %>
ที่ไฟล์ .aspx และเอา
<cc1:FileUploaderAJAX ID="FileUploaderAJAX1" runat="server" />
ไปวางไว้ในส่วนที่ต้องการให้แสดงคอนโทรล ส่วนในหน้า code-behide (.cs หรือ .vb) ให้ประกาศเนมสเปชที่ด้านบนก่อน เช่น using Subgurim.Controles; หรือ Imports Subgurim.Controles แล้วเขียนคำสั่งใน Page_Load และ Method ดังนี้

//สำหรับ C#
protected void Page_Load(object sender, EventArgs e)
{
if (FileUploaderAJAX1.IsPosting)
this.managePost();
}

private void managePost()
{
HttpPostedFileAJAX pf = FileUploaderAJAX1.PostedFile;

//กรณีต้องการต้องสอบชนิดและขนาดไฟล์
if (pf.ContentType.Equals("image/gif") && pf.ContentLength <= 5 * 1024)
FileUploaderAJAX1.SaveAs("~/temp", pf.FileName);
}


4. สร้าง Custom ASP.NET AJAX Server Control ขึ้นใช้เอง ซึ่งผมน่าจะเขียนแยกไว้เป็นอีกบทความนึง ผู้สนใจลองดูวีดีโอนี้ไปก่อนครับ How Do I:Build a Custom ASP.NET AJAX Server Control? ความยาวประมาณ 20 นาที

แหล่งข้อมูล :
UpdatePanel Control Overview
ASP.NET AJAX Videos
fileuploadajax.subgurim.net
Simple AJAX File Upload

Related Post