FileUpload 서버 컨트롤을 사용하지 않고 ASP.net에서 파일 업로드


99

ASP.net 웹 양식 (v3.5)을 사용하여 일반 오래된 파일을 사용하여 파일을 게시하려면 <input type="file" />어떻게해야합니까?

ASP.net FileUpload 서버 컨트롤 사용에 관심이 없습니다.

답변:


133

귀하의 aspx에서 :

<form id="form1" runat="server" enctype="multipart/form-data">
 <input type="file" id="myFile" name="myFile" />
 <asp:Button runat="server" ID="btnUpload" OnClick="btnUploadClick" Text="Upload" />
</form>

코드 뒤에 :

protected void btnUploadClick(object sender, EventArgs e)
{
    HttpPostedFile file = Request.Files["myFile"];

    //check file was submitted
    if (file != null && file.ContentLength > 0)
    {
        string fname = Path.GetFileName(file.FileName);
        file.SaveAs(Server.MapPath(Path.Combine("~/App_Data/", fname)));
    }
}

3
@mathieu, 당신 변종이 사용하는 유감입니다 runat="server". 그것은 ASP.NET의 서버 물건과 독립적이지 않습니다
Secret

2 개 이상의 입력이 있고 두 파일 세트 모두에 대해 별도의 기능을 수행하려면 어떻게해야합니까?
Neville Nazerane 2014-06-11

여러 파일을 업로드하는 데 사용하는 동안 모든 파일에 대해 동일한 파일 이름을 반환하므로 첫 번째 파일을 n 번 저장합니다. 그것을 극복하는 방법을 아십니까?
sohaiby

확인 @Martina 이 코드를 여러 개의 파일을 저장하기위한
sohaiby

1
@DanielJ. 나중에 파일을 사용하여 데이터베이스에 저장하는 경우 코드 숨김을 사용 하지 않는 방법은 없습니다 . 물론, 당신은 입력 및 파일을 잡기 위해 바로 자바 스크립트를 사용할 수 있습니다 : var fileUploaded = document.getElementById("myFile").files[0];당신은 심지어 사용하여 바이트 얻을 수 있습니다 readAsArrayBuffer: stackoverflow.com/questions/37134433/...를 -하지만 당신은 그 클라이언트 측 바이트 모두와 함께 할 건가요? OP는 서버 측 통신이 아닌 ASP .NET 제어를 완전히 피하려고합니다. -1.
vapcguy

40

다음은 OP가 질문에서 설명한 것처럼 서버 측 제어에 의존하지 않는 솔루션입니다.

클라이언트 측 HTML 코드 :

<form action="upload.aspx" method="post" enctype="multipart/form-data">
    <input type="file" name="UploadedFile" />
</form>

upload.aspx의 Page_Load 메서드 :

if(Request.Files["UploadedFile"] != null)
{
    HttpPostedFile MyFile = Request.Files["UploadedFile"];
    //Setting location to upload files
    string TargetLocation = Server.MapPath("~/Files/");
    try
    {
        if (MyFile.ContentLength > 0)
        {
            //Determining file name. You can format it as you wish.
            string FileName = MyFile.FileName;
            //Determining file size.
            int FileSize = MyFile.ContentLength;
            //Creating a byte array corresponding to file size.
            byte[] FileByteArray = new byte[FileSize];
            //Posted file is being pushed into byte array.
            MyFile.InputStream.Read(FileByteArray, 0, FileSize);
            //Uploading properly formatted file to server.
            MyFile.SaveAs(TargetLocation + FileName);
        }
    }
    catch(Exception BlueScreen)
    {
        //Handle errors
    }
}

MyFile.FileName에서 전체 파일 경로를 보내는 HTTPWebRequest 호출을주의하십시오. WebClient 호출은 파일 이름 만 보냅니다. HTTPWebRequest로 인해 MyFile.SaveAs가 실패합니다. 한 명의 고객이 일하고 다른 한 명의 고객을 쫓는 데 시간을 낭비했습니다.
Bob Clegg 2016

난 그냥 사용하는 Request.Files[0]대신에 Request.Files["UploadedFile"]사람이 MVC이를 사용하고자하는 경우와 영업 이익은 직선 ASP .NET이 아닌 MVC를 사용하는 동안, 당신은 필요 HttpPostedFileBase가 아닌 HttpPostedFile.
vapcguy

23

당신은 설정해야 enctype의 속성 form에를 multipart/form-data; 그런 다음 HttpRequest.Files컬렉션을 사용하여 업로드 된 파일에 액세스 할 수 있습니다 .


내 서버 양식은 마스터 페이지에 있었고 multipart / form-data를 추가 할 수 없었습니다 (그 이후에는 모든 페이지에있을 것입니다). 빠르고 간단한 해결 방법은 숨겨진 FileUpload 컨트롤을 페이지에 추가하는 것이 었습니다. 그런 다음 WebForms는 multipart / form-data를 자동으로 추가했습니다. Angular2에서 파일 입력을 사용하고 있고 구성 요소 템플릿에서 서버 컨트롤을 사용할 수 없기 때문에이 작업을 수행해야했습니다.
Jason

9

runat 서버 속성과 함께 HTML 컨트롤 사용

 <input id="FileInput" runat="server" type="file" />

그런 다음 asp.net Codebehind에서

 FileInput.PostedFile.SaveAs("DestinationPath");

당신이 intrested 경우 진행 상황을 보여주는 몇 가지 타사 옵션도 있습니다


3
다시 말하지만, 그것은 서버 컨트롤로 바뀝니다. ;)
ahwm 2013 년

@ahwm OP는 ASP .NET FileUpload 컨트롤 ( <asp:FileUpload ID="fileUpload1" runat="server"></asp:FileUpload>) 을 피하고 싶었습니다 . runat=server이것은 input필드 에 넣지 말라는 것과는 다릅니다 .
vapcguy

1
나는 그들이 ASP.NET 컨트롤을 사용하고 싶지 않다는 것을 의미합니다. HtmlInputFile컨트롤을 포함합니다 .
ahwm

8

예, ajax post 메소드로 이것을 얻을 수 있습니다. 서버 측에서는 httphandler를 사용할 수 있습니다. 따라서 귀하의 요구 사항에 따라 서버 컨트롤을 사용하지 않습니다.

ajax를 사용하면 업로드 진행률도 표시 할 수 있습니다.

파일을 입력 스트림으로 읽어야합니다.

using (FileStream fs = File.Create("D:\\_Workarea\\" + fileName))
    {
        Byte[] buffer = new Byte[32 * 1024];
        int read = context.Request.GetBufferlessInputStream().Read(buffer, 0, buffer.Length);
        while (read > 0)
        {
            fs.Write(buffer, 0, read);
            read = context.Request.GetBufferlessInputStream().Read(buffer, 0, buffer.Length);
        }
    } 

샘플 코드

function sendFile(file) {              
        debugger;
        $.ajax({
            url: 'handler/FileUploader.ashx?FileName=' + file.name, //server script to process data
            type: 'POST',
            xhr: function () {
                myXhr = $.ajaxSettings.xhr();
                if (myXhr.upload) {
                    myXhr.upload.addEventListener('progress', progressHandlingFunction, false);
                }
                return myXhr;
            },
            success: function (result) {                    
                //On success if you want to perform some tasks.
            },
            data: file,
            cache: false,
            contentType: false,
            processData: false
        });
        function progressHandlingFunction(e) {
            if (e.lengthComputable) {
                var s = parseInt((e.loaded / e.total) * 100);
                $("#progress" + currFile).text(s + "%");
                $("#progbarWidth" + currFile).width(s + "%");
                if (s == 100) {
                    triggerNextFileUpload();
                }
            }
        }
    }

2
fs.close()IIS 내에서 열려 있기 때문에 읽을 수없는 파일이 될 수 있는 다른 모든 것을 추가하는 힌트를 추가해야 할 수도 있습니다.
mistapink

@mistapink 실행이 using 블록을 벗어날 때 파일 스트림이 닫히지 않습니까?
Sebi

@Sebi 거의 3 년 전에는 그렇지 않은 것 같습니다. 오랫동안 시도하지 않았기 때문에 여기서 확실한 답을 드릴 수는 없습니다. 미안 해요.
mistapink

4

Request.Files 컬렉션에는 FileUpload 컨트롤에서 가져온 것이 든 수동으로 작성된 <input type="file">.

따라서 WebForm 중간에 평범한 이전 파일 입력 태그를 작성한 다음 Request.Files 컬렉션에서 업로드 된 파일을 읽을 수 있습니다.


4

다른 사람들이 대답했듯이 Request.Files는 게시 된 모든 파일을 포함하는 HttpFileCollection이므로 다음과 같이 해당 개체에 파일을 요청하기 만하면됩니다.

Request.Files["myFile"]

그러나 동일한 속성 이름을 가진 입력 마크 업이 두 개 이상있는 경우 어떻게됩니까?

Select file 1 <input type="file" name="myFiles" />
Select file 2 <input type="file" name="myFiles" />

서버 측에서 이전 코드 Request.Files [ "myFile"]은 두 파일 대신 하나의 HttpPostedFile 개체 만 반환합니다. .net 4.5에서 GetMultiple이라는 확장 메서드를 보았지만 기존 버전의 경우 존재하지 않습니다. 그 문제로 인해 확장 메서드를 다음과 같이 제안합니다.

public static IEnumerable<HttpPostedFile> GetMultiple(this HttpFileCollection pCollection, string pName)
{
        for (int i = 0; i < pCollection.Count; i++)
        {
            if (pCollection.GetKey(i).Equals(pName))
            {
                yield return pCollection.Get(i);
            }
        }
}

이 확장 메서드는있는 경우 HttpFileCollection에 "myFiles"라는 이름을 가진 모든 HttpPostedFile 개체를 반환합니다.


2

HtmlInputFile 컨트롤

나는 이것을 항상 사용했습니다.


2
runat="server"이를 위해서는 기본적으로 사용하고 싶지 않은 서버 컨트롤을 추가 해야합니다.
ahwm

@ahwm 아니요, OP는 특정 ASP .NET FileUpload 컨트롤을 사용하고 싶지 않았습니다. 일반적으로 서버 측 컨트롤을 사용하고 싶지 않다는 것과는 다릅니다.
vapcguy


0
//create a folder in server (~/Uploads)
 //to upload
 File.Copy(@"D:\CORREO.txt", Server.MapPath("~/Uploads/CORREO.txt"));

 //to download
             Response.ContentType = ContentType;
             Response.AppendHeader("Content-Disposition", "attachment;filename=" + Path.GetFileName("~/Uploads/CORREO.txt"));
             Response.WriteFile("~/Uploads/CORREO.txt");
             Response.End();
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.