Javascript pentru a efectua procesarea după descărcarea unui fișier

Pagina actualizată :
Data creării paginii :

Mediul de verificare a funcționării

Visual Studio
  • Visual Studio 2022
ASP.NET Nucleul
  • 8.0 (Razpr Pagini, MVC)
Browsere web
  • Muchie 119

Mediu de operare

Visual Studio (dacă includeți și programe server)
  • Visual Studio 2022
ASP.NET Core (dacă include și programe server)
  • 8.0 (Razpr Pagini, MVC)
Browsere web
  • Margine
  • Google Chrome
  • Alte browsere (nu toate bifate)

(* Corpul principal al acestui sfat este procesul din partea clientului, astfel încât partea serverului poate fi orice)

La început

Principalul obiectiv al acestor sfaturi este programul client (Javascript), iar programul server este acolo doar pentru a descărca fișiere. Prin urmare, nu contează ce este programul serverului, atâta timp cât vă poate face să descărcați fișierul.

Solicitați utilizatorilor să descarce fișiere atunci când sunt accesate pe server

Mr./Ms. vă permite să descărcați fișiere atunci când primiți o solicitare. În acel moment, așteptăm în mod deliberat o anumită perioadă de timp pe server, astfel încât să fie ușor de înțeles începutul și sfârșitul descărcării.

Iată ce se întâmplă pe partea de server a Razor Pages și MVC: Îl puteți implementa în alte proiecte, cum ar fi Web API.

Pagini de ras : Pagini/Index.cshtml.cs

// 省略

namespace DownloadCompleteNotifyRazorPages.Pages
{
  public class IndexModel : PageModel
  {
    // 省略

    /// <summary>時間をかけてファイルをダウンロードします。</summary>
    public async Task<IActionResult> OnGetDownload()
    {
      // ダウンロード開始と完了を明確にする目的で待機を入れる
      await Task.Delay(5000);

      // 適当にファイルを作って返す
      var fileSize = 10_000_000;
      var sb = new System.Text.StringBuilder(fileSize);
      for (int i = 0; i < fileSize; i++) sb.Append('a');
      using var stream = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(sb.ToString()));
      return File(stream.ToArray(), "text/plain", $"ダウンロード.txt");
    }
  }
}

MVC : Coletolleri/HomeController.cs

// 省略

namespace DownloadCompleteNotifyMvc.Controllers
{
  public class HomeController : Controller
  {
    // 省略

    /// <summary>時間をかけてファイルをダウンロードします。</summary>
    public async Task<IActionResult> Download()
    {
      // ダウンロード開始と完了を明確にする目的で待機を入れる
      await Task.Delay(5000);

      // 適当にファイルを作って返す
      var fileSize = 10_000_000;
      var sb = new System.Text.StringBuilder(fileSize);
      for (int i = 0; i < fileSize; i++) sb.Append('a');
      using var stream = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(sb.ToString()));
      return File(stream.ToArray(), "text/plain", $"ダウンロード.txt");
    }
  }
}

Prelucrarea clientului

În mod normal, descărcați un fișier accesând o adresă URL specificată într-un browser web. Dacă doriți să faceți ceva după finalizarea descărcării, puteți rula descărcarea cu Javascript.

Există multe modalități de a face acest lucru, dar în acest caz, vom folosi , care este, de asemenea XMLHttpRequest , originea procesării asincrone. De asemenea, puteți utiliza funcțiile jQuery ajax sau API-ul Fetch.

ahref URL-ul de descărcare este scris în etichetă și id procesul este executat atunci când se face clic pe cel setatdownload.

$('#download').click(function (e) {
  console.log('ダウンロードを開始します。');
  e.preventDefault();  // href による画面遷移を抑止
  let url = $(e.target).attr('href');  // href からダウンロード URL 取得

  const xhr = new XMLHttpRequest();
  xhr.open('GET', url, true);   // ダウンロード先 URL 設定
  xhr.responseType = 'blob';   // バイナリデータ取得であることを指示

  // ダウンロード完了後の処理を設定。この時点ではデータは取得してクライアントにありますが保存はしていません。
  xhr.onload = function (oEvent) {
    if (xhr.status !== 200) {
      console.log(`データの取得に失敗しました。(status=${xhr.status})`);
    } else {
      // 取得したデータ
      let blob = xhr.response;

      // レスポンスヘッダーからサーバーから送られてきたファイル名を取得する
      let fileName = '';
      let disposition = xhr.getResponseHeader('Content-Disposition');
      if (disposition && disposition.indexOf('attachment') !== -1) {
        let filenameRegex = /filename[^;=\n]=((['"]).*?\2|[^;\n]*)/;
        let matches = filenameRegex.exec(disposition);
        if (matches != null && matches[1]) {
          // 「filename*=UTF-8''%E3%83%87%E3%83%BC%E3%82%BF.txt;」からファイル名を取得
          fileName = decodeURI(matches[1].replace(/['"]/g, '').replace('utf-8', '').replace('UTF-8', ''));
        }
      }
      if (fileName === '') {
        // ファイル名を取得できなかったら念のため URL をファイル名とする
        let fileName = url.match('.+/(.+?)([\?#;].*)?$')[1];
      }

      // Blob オブジェクトを指す URL オブジェクトを作る
      let objectURL = window.URL.createObjectURL(blob);
      // リンク(<a>要素)を生成し、JavaScript からクリックする
      let link = document.createElement('a');
      document.body.appendChild(link);
      link.href = objectURL;
      link.download = fileName;   // download を指定するとブラウザで開くことなくダウンロードになる
      link.click();
      document.body.removeChild(link);

      console.log('ダウンロードを完了しました。');
    }
  };

  // リクエスト開始
  xhr.send();
});

a În mod normal, dacă lăsați elementul pe care ați făcut clic, procesul implicit de descărcare se va muta, așa că e.preventDefault(); sunăm pentru a dezactiva procesul implicit.

href Obțineți URL-ul de descărcare de la și XMLHttpRequest GET setați-l pentru a-l obține de la .

XMLHttpRequest.responseTypeblob pentru a instrui datele binare care urmează să fie descărcate.

XMLHttpRequest.onload Deoarece procesul după finalizarea descărcării datelor poate fi descris în eveniment, procesul după finalizarea descărcării este scris aici. Deoarece datele au fost descărcate numai către client, fișierul nu este stocat local. Pentru a salva un fișier local, puteți să adăugați o etichetă care a conține pseudodate și să o faceți să se comporte ca și cum ați fi făcut clic pe un link și ați salvat fișierul. Datele din acel moment pot window.URL.createObjectURL fi convertite într-o adresă URL de către funcție, astfel încât href să le puteți seta și să le faceți să funcționeze.

Numele fișierului care trebuie salvat poate fi preluat din antetul răspunsului dacă este inclus în răspunsul de la Content-Disposition server. Deoarece este puțin complicat de achiziționat, cred că codul ar trebui folosit așa cum este. Dacă numele fișierului nu este specificat pe server, acesta nu poate fi ajutat, deci cred că va fi setat la numele de fișier implicit sau la numele fișierului la sfârșitul căii URL.

Deoarece de data aceasta îl afișez în consolă numai după salvarea fișierului, cred că operația dorită poate fi executată prin rescrierea acestei părți cu cod arbitrar.

Odată ce procesul de descărcare a datelor este descris, ultimul lucru pe care dorim să-l facem este XMLHttpRequest.send să apelăm o funcție pentru a începe efectiv solicitarea.

Descărcați linkul de rulare

Mr./Ms. Code oferă link-uri către modelul de descărcare directă a fișierului și modelul de descărcare a acestuia cu Javascript. a Puteți scrie adresa URL direct în href etichetă, dar dacă scrieți următoarele în ASP.NET Core, adresa URL se va extinde automat href la .

Razor Pages : Pagini/Index.cshtml

<ul>
  <li><a asp-page-handler="Download">ダウンロード (Javascript なし)</a></li>
  <li><a asp-page-handler="Download" id="download">ダウンロード (Javascript あり)</a></li>
</ul>

MVC : Vizualizări/Acasă/Index.cshtml

<ul>
  <li><a asp-controller="Home" asp-action="Download">ダウンロード (Javascript なし)</a></li>
  <li><a asp-controller="Home" asp-action="Download" id="download">ダウンロード (Javascript あり)</a></li>
</ul>