C# - Állomány feltöltése web oldalon keresztül

forráskód letöltése
Sok esetben szükségünk lehet olyan funkcióra web oldalunkon, hogy felhasználóink tetszőleges állományt tölthessenek fel webszerverünkre. Ekkor biztosítanunk kell egy olyan oldalt, melyen kiválaszthatják a helyi gépükön azokat az állományokat, melyeket fel kívánnak tölteni, majd meg kell oldanunk az ilyen jellegű adatok fogadását és tartalmuk állományba írását.
Mellékelt példa kipróbálásához szükséges egy HtmlUploadFile nevű virtuális könyvtár létrehozása, mely arra a könyvtárra mutat, amelybe másolta a példát. Ehhez legegyszerűbb út az adott mappa tulajdonság ablakában lévő Webmegosztás lapon található, ahol engedélyezzük a megosztást.
Példánkban két WebForm-ot hozunk létre: az egyiken elvégezhetjük a feltöltendő állományok kiválasztását és elindíthatjuk a feltöltés folyamatát. A másik oldalon fogadjuk az adatokat, állományba írjuk azokat, majd megjelenítünk egy statisztikát, hogy milyen típusú, mekkora állományokat fogadtunk.
A feltöltés elindításakor az állományok automatikusan kódolásra kerülnek és azokat megkapja web szerverünkön futó programunk. Az így kapott adatokat könnyedén állományba írhatjuk, így nekünk nem is kell foglalkoznunk azzal, hogy a felhasználó gépéről miként kerül az állomány tartalma hozzánk.
WebForm1.aspx
Állomány kiválasztáshoz egy speciális <INPUT> objektumra van szükség, melynél a típus type=file. Ennek hatására nem csak egy TextBox jelenik meg, hanem mellette egy gomb is, melyre kattintva megjelenik egy állomány dialóg ablak, melyben tetszés szerint kiválaszthatunk egy állományt. A választás után az állomány elérési útja, neve a TextBox-ba kerül.
      <INPUT id="File1" type="file" name="File1" Runat="Server">
Felteszünk ezt követően egy nyomógombot, melyre kattintva indítjuk a feltöltést. Ehhez első lépésként tároljuk a feltöltendő állományok listáját, melyet a Request objektum Files property-ben kapunk meg, egy HttpFileCollection osztály típusában. A tárolt adatokat utána a WebForm2.aspx lappal dolgoztatjuk fel. Ehhez a Server osztály Transfer függvényét hívjuk, mely képes a WebForm1-nek küldött adatokat továbbítani egy másik cím felé.
    private void Button1_Click(object sender, System.EventArgs e)
    {  
      hfc = Request.Files;
      Server.Transfer("WebForm2.aspx");
    }
A tárolt állományok listájához készítünk egy property-t, hogy majd elérhetővé váljanak az adatok a WebForm1-en kívülről is.
    private HttpFileCollection hfc;
    public HttpFileCollection Files
    {
      get
      {
        return hfc;
      }
    }
WebForm2.aspx
A WebForm2 Page osztály Load eseményénél fogadjuk a WebForm1 adatait. Itt lekérdezzük a WebForm1-ben eltárolt HttpFileCollection osztály adatait az általunk létrehozott Files property-n keresztül.
    private void Page_Load(object sender, System.EventArgs e)
    {
      WebForm1 wf = (WebForm1)Context.Handler;
      HttpFileCollection hfc = wf.Files;
Ezt követően végigmegyünk egy ciklussal az összes állományon, melyet a felhasználó feltöltött. A HttpFileCollection kollekció minden eleme egy-egy HttpPostedFile osztályt tartalmaz, mely egy adott állomány tulajdonságait foglalja össze, beleértve magát az állomány tartalmát is.
      for (int i=0; i<hfc.Count; i++)
      {
        HttpPostedFile hpf = hfc[i];
Ha az állomány hossza nem nulla, akkor írjuk ki annak adatait a WebForm2-re és ez esetben fogjuk az állományt is létrehozni a szerverünkön.
        if (hpf.ContentLength>0) 
        {
          Label1.Text += i.ToString() + "<br>";
A HttpPostedFile osztály FileName property-jéből tudjuk meg a feltöltött állomány nevét, a ContentType-ból a típusa derül ki, míg a ContentLength property-ből az állomány hossza bájtban.
          Label1.Text += "<b>FileName:</b> " + hpf.FileName + "<br>";
          Label1.Text += "<b>ContentType:</b> " + hpf.ContentType + "<br>";
          Label1.Text += "<b>ContentLength:</b> " + hpf.ContentLength.ToString() + "<br><br>";
Az állományt lementeni a SaveAs függvény hívásával tudjuk. Ekkor paraméterként a cél állomány nevét, elérési útját kell megadnunk. Ezt a mellékelt példa esetében az alkalmazásunk könyvtárában elhelyezett Save mappába tesszük meg.
          hpf.SaveAs(Server.MapPath("save") + "\\" + Path.GetFileName(hpf.FileName));
        }
      }
    }