2008-09-16 12 views
34

Tôi đang sử dụng <input type="file" id="fileUpload" runat="server"> để tải lên tệp trong ứng dụng ASP.NET. Tôi muốn giới hạn loại tệp tải lên (ví dụ: giới hạn ở các phần mở rộng tệp .xls hoặc .xlsx).Làm cách nào để Xác thực Loại Tệp của Tệp Tải lên?

Cả xác thực của JavaScript hoặc phía máy chủ đều OK (miễn là xác thực phía máy chủ sẽ diễn ra trước khi tệp được tải lên - có thể có một số tệp rất lớn được tải lên, vì vậy mọi xác thực cần phải diễn ra trước khi thực tế tệp được tải lên).

Trả lời

29

Có vẻ như bạn sẽ có các tùy chọn hạn chế kể từ khi bạn muốn kiểm tra để xảy ra trước tải lên. Tôi nghĩ rằng tốt nhất bạn sẽ nhận được là sử dụng javascript để xác nhận phần mở rộng của tập tin. Bạn có thể xây dựng một băm các phần mở rộng hợp lệ và sau đó xem xét xem phần mở rộng của tệp đang được tải lên có tồn tại trong băm hay không.

HTML:

<input type="file" name="FILENAME" size="20" onchange="check_extension(this.value,"upload");"/> 
<input type="submit" id="upload" name="upload" value="Attach" disabled="disabled" /> 

Javascript:

var hash = { 
    'xls' : 1, 
    'xlsx' : 1, 
}; 

function check_extension(filename,submitId) { 
     var re = /\..+$/; 
     var ext = filename.match(re); 
     var submitEl = document.getElementById(submitId); 
     if (hash[ext]) { 
     submitEl.disabled = false; 
     return true; 
     } else { 
     alert("Invalid filename, please select another file"); 
     submitEl.disabled = true; 

     return false; 
     } 
} 
+11

đừng quên, đây chỉ là xác thực phía máy khách. Tôi vẫn có thể 'HTTP' thủ công tới url biểu mẫu để bỏ qua kiểm tra này - bạn cũng sẽ cần phải thực hiện kiểm tra xác thực phía máy chủ. –

+0

@jamie cách kiểm tra tài liệu từ '.doc' và' .docx' ... –

+0

Chỉ cần thêm phần mở rộng đó vào biến "băm". var hash = {'xls': 1, 'xlsx': 1, 'doc': 1, 'docx': 1}; – Jamie

1

Vâng - bạn sẽ không thể thực hiện phía máy chủ ở mặt sau khi tệp sẽ được gửi (đã tải lên) trong khi đăng lại.

Tôi nghĩ bạn có thể làm điều đó trên ứng dụng khách bằng JavaScript. Cá nhân, tôi sử dụng thành phần của bên thứ ba có tên là radUpload by Telerik. Nó có một API phía máy khách và phía máy chủ tốt, và nó cung cấp một thanh tiến trình cho các tệp tải lên lớn.

Tôi chắc chắn cũng có sẵn các giải pháp nguồn mở.

0

Tùy chọn duy nhất của bạn có vẻ là xác thực phía máy khách, vì phía máy chủ có nghĩa là tệp đã được tải lên. Ngoài ra, loại MIME thường được quyết định bởi phần mở rộng của tệp.

sử dụng một khung JavaScript như jQuery để quá tải sự kiện kích hoạt biểu mẫu. Sau đó kiểm tra phần mở rộng. Điều này sẽ hạn chế hầu hết các nỗ lực. Tuy nhiên, nếu một người thay đổi hình ảnh thành XLS mở rộng thì bạn sẽ gặp sự cố.

Tôi không biết đây có phải là tùy chọn cho bạn hay không, nhưng bạn có quyền kiểm soát nhiều ứng dụng khách hơn khi sử dụng thứ gì đó như Silverlight hoặc Flash để tải lên. Bạn có thể xem xét sử dụng một trong những công nghệ này cho quá trình tải lên của mình.

6

Từ javascript, bạn sẽ có thể lấy tên tệp trong trình xử lý onsubmit. Vì vậy, trong trường hợp của bạn, bạn nên làm một cái gì đó như:

<form onsubmit="if (document.getElementById('fileUpload').value.match(/xls$/) || document.getElementById('fileUpload').value.match(/xlsx$/)) { alert ('Bad file type') ; return false; } else { return true; }">...</form> 
3

Bạn có thể sử dụng một biểu validator thường xuyên trên kiểm soát tải lên:

<asp:RegularExpressionValidator id="FileUpLoadValidator" runat="server" ErrorMessage="Upload Excel files only." ValidationExpression="^(([a-zA-Z]:)|(\\{2}\w+)\$?)(\\(\w[\w].*))(.xls|.XLS|.xlsx|.XLSX)$" ControlToValidate="fileUpload"> </asp:RegularExpressionValidator> 

Ngoài ra còn có các chấp nhận thuộc tính của thẻ đầu vào:

<input type="file" accept="application/msexcel" id="fileUpload" runat="server"> 

nhưng tôi không có nhiều thành công khi tôi đã cố gắng này (với FF3 và IE7)

1

tôi nghĩ rằng có là những cách khác nhau để làm điều này. Vì im không quen thuộc với asp tôi chỉ có thể cung cấp cho bạn một số gợi ý để kiểm tra một loại tệp cụ thể:

1) cách an toàn: nhận thêm thông tin về tiêu đề của loại tệp bạn muốn chuyển. phân tích cú pháp tệp đã tải lên và so sánh các tiêu đề

2) cách nhanh: chia tên tệp thành hai phần -> tên tệp và phần cuối của tệp. kiểm tra kết thúc của tập tin và so sánh nó với filetype bạn muốn cho phép để được tải lên

hy vọng nó sẽ giúp :)

1

Tránh sự kiểm soát Asp.Net tiêu chuẩn và sử dụng thành phần NeadUpload từ phát triển Brettle: http://www.brettle.com/neatupload

nhanh hơn, dễ dàng hơn để sử dụng, không có lo lắng về tham số maxRequestLength trong các tập tin cấu hình và rất dễ tích hợp.

3

Như một số người đã đề cập, Javascript là con đường để đi. Ghi nhớ rằng "xác nhận" ở đây chỉ là bởi phần mở rộng tập tin, nó sẽ không xác nhận rằng tập tin là một bảng tính excel thực sự!

6

Tôi đồng ý với Chris, việc kiểm tra tiện ích không xác thực loại tệp bất kỳ cách nào bạn xem. Telerik's radUpload có lẽ là lựa chọn tốt nhất của bạn, nó cung cấp thuộc tính ContentType của tệp đang được tải lên, mà bạn có thể so sánh với các loại mime đã biết. Bạn nên kiểm tra cho:

application/vnd.ms-excel,

application/excel,

application/x-Msexcel

và cho định dạng 2k7 mới:

ứng dụng /vnd.openxmlformatsofficedocument.spreadsheetml.sheet

Telerik được sử dụng để bán radUpload dưới dạng một thành phần riêng lẻ, nhưng bây giờ nó được bao bọc thành thứ Bộ điều khiển điện tử, điều này làm cho nó đắt hơn một chút, nhưng đến nay, cách dễ nhất để kiểm tra loại đúng

+0

theo trang web, dịch vụ này chi phí tiền ... – Thundter

1

Đảm bảo rằng bạn luôn kiểm tra phần mở rộng tệp ở phía máy chủ để đảm bảo rằng không ai có thể tải lên tệp độc hại chẳng hạn như .aspx, .asp, v.v.

1

Là tùy chọn thay thế, bạn có thể sử dụng thuộc tính "chấp nhận" của đầu vào tệp HTML xác định loại MIME nào được chấp nhận.

Định nghĩa here

26

Nó khá đơn giản bằng cách sử dụng trình kiểm chứng biểu thức điều chỉnh.

<asp:RegularExpressionValidator 
id="RegularExpressionValidator1" 
runat="server" 
ErrorMessage="Only zip file is allowed!" 
ValidationExpression ="^.+(.zip|.ZIP)$" 
ControlToValidate="FileUpload1" 
> </asp:RegularExpressionValidator> 

Client-Side Validation of File Types Permissible to Upload

+1

Regex phân biệt chữ hoa chữ thường theo mặc định. Bạn có thể vô hiệu hóa việc đó bằng cách sử dụng (? I) cho một nhóm (như đã nêu ở đây -> http://www.exampledepot.com/egs/java.util.regex/Case.html). Nó sẽ không làm việc cho Javascript, mặc dù (như đã nêu ở đây http://stackoverflow.com/questions/2641236/make-regular-expression-case-insensitive và thử nghiệm cá nhân của tôi). – marquito

3

Dựa trên kd7 của reply cho thấy bạn kiểm tra các tập tin kiểu nội dung, đây là một phương pháp wrapper:

private bool FileIsValid(FileUpload fileUpload) 
{ 
    if (!fileUpload.HasFile) 
    { 
     return false; 
    } 
    if (fileUpload.PostedFile.ContentType == "application/vnd.ms-excel" || 
     fileUpload.PostedFile.ContentType == "application/excel" || 
     fileUpload.PostedFile.ContentType == "application/x-msexcel" || 
     fileUpload.PostedFile.ContentType == "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" //this is xlsx format 
     ) 
     return true; 

    return false; 
} 

trở về true nếu tập tin tải lên là .xls hoặc .xlsx

0

Như một lưu ý khác, loại tệp có thể bị giả mạo (ví dụ: .exe đổi tên .pdf), việc kiểm tra loại MIME sẽ không ngăn chặn (ví dụ: .exe w bệnh hiển thị MIME của "application/pdf" nếu đổi tên thành .pdf). Tôi tin rằng một kiểm tra của các loại tập tin thực sự chỉ có thể được thực hiện phía máy chủ; một cách dễ dàng để kiểm tra nó bằng System.IO.BinaryReader được mô tả ở đây:

http://forums.asp.net/post/2680667.aspx

và VB phiên bản ở đây:

http://forums.asp.net/post/2681036.aspx

Lưu ý rằng bạn sẽ cần phải biết 'mã' nhị phân cho các loại file (s), bạn' kiểm tra lại, nhưng bạn có thể lấy chúng bằng cách thực hiện giải pháp này và gỡ lỗi mã.