3148 Stimmen

Wie kann ich Dateien mit jQuery asynchron hochladen?

Ich möchte eine Datei asynchron mit jQuery hochladen.

$(document).ready(function () {
    $("#uploadbutton").click(function () {
        var filename = $("#file").val();

        $.ajax({
            type: "POST",
            url: "addFile.do",
            enctype: 'multipart/form-data',
            data: {
                file: filename
            },
            success: function () {
                alert("Daten hochgeladen: ");
            }
        });
    });
});

Datei

Statt die Datei hochzuladen, erhalte ich nur den Dateinamen. Was kann ich tun, um dieses Problem zu beheben?

0 Stimmen

Es gibt verschiedene fertige Plugins zum Hochladen von Dateien für jQuery. Das Durchführen solcher Upload-Hacks ist keine angenehme Erfahrung, daher verwenden die Leute lieber fertige Lösungen. Hier sind einige: - JQuery File Uploader - Mehrere Datei-Upload-Plugin - Mini Mehrfachdatei-Upload - jQuery-Datei-Upload Sie können nach weiteren Projekten auf NPM (unter Verwendung des Schlüsselworts "jquery-plugin") oder auf Github suchen.

78 Stimmen

Du erhältst nur den Dateinamen, weil deine Variable Dateiname den Wert von $('#file') erhält, nicht die Datei, die im Eingabefeld liegt

0 Stimmen

Ich bin auf einige wirklich leistungsstarke jQuery-basierte Datei-Upload-Bibliotheken gestoßen. Schau sie dir an: 1. Plupload - Dokumentation: plupload.com/docs 2. jQuery File Upload - Dokumentation: github.com/blueimp/jQuery-File-Upload 3. FineUploader - Dokumentation: docs.fineuploader.com

2625voto

olanod Punkte 29710

Mit HTML5 können Sie Datei-Uploads mit Ajax und jQuery durchführen. Nicht nur das, Sie können Datei-Validierungen (Name, Größe und MIME-Typ) durchführen oder das Fortschrittsereignis mit dem HTML5-Fortschritts-Tag (oder einem div) behandeln. Kürzlich musste ich einen Datei-Uploader erstellen, aber ich wollte weder Flash noch Iframes oder Plugins verwenden und nach einigen Recherchen fand ich die Lösung.

Das HTML:

Zuerst können Sie bei Bedarf eine Validierung durchführen. Zum Beispiel im .on('change') Ereignis der Datei:

$(':file').on('change', function () {
  var file = this.files[0];

  if (file.size > 1024) {
    alert('maximale Upload-Größe beträgt 1k');
  }

  // Siehe auch .name, .type
});

Jetzt erfolgt der $.ajax() Absenden durch Klick auf die Schaltfläche:

$(':button').on('click', function () {
  $.ajax({
    // Ihr Server-Skript zum Verarbeiten des Uploads
    url: 'upload.php',
    type: 'POST',

    // Formulardaten
    data: new FormData($('form')[0]),

    // Sagen Sie jQuery, dass die Daten nicht verarbeitet werden sollen oder sich um den Inhaltstyp kümmern müssen
    // Diese Optionen müssen unbedingt enthalten sein!
    cache: false,
    contentType: false,
    processData: false,

    // Benutzerdefiniertes XMLHttpRequest
    xhr: function () {
      var myXhr = $.ajaxSettings.xhr();
      if (myXhr.upload) {
        // Zur Behandlung des Fortschritts des Uploads
        myXhr.upload.addEventListener('Fortschritt', function (e) {
          if (e.lengthComputable) {
            $('progress').attr({
              value: e.geladen,
              max: e.gesamt,
            });
          }
        }, false);
      }
      return myXhr;
    }
  });
});

Wie Sie sehen können, wird mit HTML5 (und etwas Recherche) der Datei-Upload nicht nur möglich, sondern auch super einfach. Probieren Sie es mit Google Chrome aus, da einige der HTML5-Komponenten der Beispiele nicht in jedem Browser verfügbar sind.

1 Stimmen

@Silver89, wenn du Daten vom Server-Skript zurückgeben möchtest, das du in den URL-Einstellungen festgelegt hast ('upload.php' in diesem Fall), wird die Antwort das sein, was du in diesem Skript druckst oder echo. Dann kannst du mit den Daten machen, was du willst. Überprüfe die ajaxComplete- und ähnliche Funktionen in den jQuery-Dokumenten.

4 Stimmen

Ich habe den Dateiteil zum Laufen gebracht ... aber können Sie auch Textfelder darin einschließen? Dies scheint nicht mit var formData = new FormData($('form')[0]); oder serialize() zu funktionieren?

0 Stimmen

Mit "new FormData($('form')[0]);" sollte es funktionieren, hat Ihr Textfeld einen Namen? Verwenden Sie print_r für $_POST, um sicherzustellen, dass die Daten vorhanden sind, überprüfen Sie die Antwort im Netzwerkmonitor (Chrome), um die Rohantwort zu sehen.

303voto

Oli Punkte 226885

2019 Update: Es hängt immer noch von den Browsern ab, die deine Zielgruppe verwendet.

Ein wichtiger Punkt, den man mit der "neuen" HTML5 file API verstehen sollte, ist, dass sie erst ab dem IE 10 unterstützt wird. Wenn der spezifische Markt, den du anvisierst, eine überdurchschnittliche Neigung zu älteren Windows-Versionen hat, hast du möglicherweise keinen Zugriff darauf.

Im Jahr 2017 waren etwa 5% aller Browser IE 6, 7, 8 oder 9. Wenn du in ein großes Unternehmen gehst (z.B., wenn es sich um ein B2B-Tool handelt oder um etwas, das du für Schulungen bereitstellst), kann diese Zahl stark ansteigen. 2016 hatte ich es mit einem Unternehmen zu tun, das IE8 auf über 60% ihrer Rechner verwendete.

Es ist 2019 seit dieser Bearbeitung, fast 11 Jahre nach meiner ursprünglichen Antwort. IE9 und älter liegen weltweit etwa bei 1%, aber es gibt immer noch Cluster mit höherer Nutzung.

Das wichtige Fazit daraus ist, überprüfe, welchen Browser deine Nutzer verwenden. Wenn du das nicht tust, wirst du eine schnelle und schmerzhafte Lektion darüber lernen, warum "funktioniert bei mir" nicht ausreicht, um an einen Kunden auszuliefern. caniuse ist ein nützliches Werkzeug, aber beachte, woher sie ihre demografischen Daten beziehen. Sie stimmen möglicherweise nicht mit deinen überein. Dies gilt insbesondere für Unternehmensumgebungen.

Meine Antwort aus dem Jahr 2008 folgt.


Es gibt jedoch lebensfähige nicht-JS-Methoden für Datei-Uploads. Du kannst auf der Seite ein iframe erstellen (das du mit CSS ausblendest) und dann dein Formular auf dieses iframe ausrichten lassen. Die Hauptseite muss sich nicht bewegen.

Es handelt sich um einen "echten" Post, daher ist er nicht vollständig interaktiv. Wenn du den Status benötigst, benötigst du etwas serverseitiges, um das zu verarbeiten. Dies variiert stark abhängig von deinem Server. ASP.NET hat schönere Mechanismen. PHP versagt hier, aber du kannst Perl oder Apache-Modifikationen verwenden, um das zu umgehen.

Wenn du mehrere Datei-Uploads benötigst, ist es am besten, jede Datei nacheinander hochzuladen (um maximale Datei-Upload-Limits zu überwinden). Sende das erste Formular an das iframe, überwache den Fortschritt mit dem oben genannten und wenn es abgeschlossen ist, sende das zweite Formular an das iframe usw.

Oder verwende eine Java/Flash-Lösung. Sie sind flexibler in dem, was sie mit ihren Posts tun können...

145 Stimmen

Zur Information, es ist jetzt möglich, reine AJAX-Dateiuploads durchzuführen, wenn der Browser die File API unterstützt - developer.mozilla.org/en/using_files_from_web_applications

0 Stimmen

Dies ist eine ziemlich alte Antwort, aber sie war ein wenig irreführend. IE unterstützte XHR nativ schon ab IE7 und unterstützte es durch ActiveX schon ab IE5. w3schools.com/ajax/ajax_xmlhttprequest_create.asp. Der praktische Weg, dies zu tun, war sicherlich das Targeting von Flash (Shockwave)-Komponenten oder das Bereitstellen einer Flash/ActiveX (Silverlight)-Steuerung. Wenn Sie eine Anfrage starten und die Antwort über JavaScript bearbeiten können, handelt es sich um Ajax. Obwohl gesagt wurde, dass Ajax mit XHR gleichbedeutend ist, beschreibt es selbst nicht den zugrunde liegenden Mechanismus/Komponenten, die die Nutzlast liefern/austauschen.

5 Stimmen

@BrettCaswell Ich habe nicht gesagt, dass AJAX/XHR nicht möglich sind, sondern nur, dass es auf alten - aber ewig lebenden - Versionen von IE nicht möglich war, eine Datei damit hochzuladen. Das war und bleibt vollkommen wahr.

121voto

Ich empfehle die Verwendung des Fine Uploader-Plugins für diesen Zweck. Ihr JavaScript-Code wäre:

$(document).ready(function() {
  $("#uploadbutton").jsupload({
    action: "addFile.do",
    onComplete: function(response){
      alert( "Serverantwort: " + response);
    }
  });
});

36 Stimmen

"Dieses Plugin ist unter der GNU GPL 2 oder einer späteren Version und der GNU LGPL 2 oder einer späteren Version Open Source. Solange Sie die Kopie oder eine modifizierte Version nicht weitergeben, müssen Sie Ihr Projekt nicht öffentlich machen."

2 Stimmen

Für den Fall, dass jemand diesen Weg gehen will, wurde FineUploader im Jahr 2018 eingestellt. github.com/FineUploader/fine-uploader/issues/2073

108voto

Mattias Punkte 5059

Hinweis: Diese Antwort ist veraltet, es ist jetzt möglich, Dateien mit XHR hochzuladen.


Sie können Dateien nicht mit XMLHttpRequest (Ajax) hochladen. Sie können den Effekt mit einem iframe oder Flash simulieren. Das ausgezeichnete jQuery Form Plugin, das Ihre Dateien durch ein iframe postet, um den Effekt zu erzielen.

18 Stimmen

Kleiner Hinweis: In den neuesten Versionen von Chrome und Firefox ist es möglich, stackoverflow.com/questions/4856917/…

107voto

404 Punkte 1332

Zum Schluss für zukünftige Leser.

Asynchrones Datei-Upload

Mit HTML5

Sie können Dateien mit jQuery verwenden, indem Sie die $.ajax()-Methode verwenden, wenn FormData und das File API unterstützt werden (beides HTML5-Funktionen).

Sie können Dateien auch ohne FormData senden, aber in jedem Fall muss das File API vorhanden sein, um Dateien so zu verarbeiten, dass sie mit XMLHttpRequest (Ajax) gesendet werden können.

$.ajax({
  url: 'file/destination.html', 
  type: 'POST',
  data: new FormData($('#formWithFiles')[0]), // Das Formular mit den Dateieingaben.
  processData: false,
  contentType: false                    // Bei Verwendung von FormData müssen Daten nicht verarbeitet werden.
}).done(function(){
  console.log("Erfolg: Dateien gesendet!");
}).fail(function(){
  console.log("Ein Fehler ist aufgetreten, die Dateien konnten nicht gesendet werden!");
});

Für ein schnelles, reines JavaScript (kein jQuery) Beispiel siehe "Senden von Dateien mithilfe eines FormData-Objekts".

Ausweichlösung

Wenn HTML5 nicht unterstützt wird (kein File API), ist die einzige andere reine JavaScript-Lösung (kein Flash oder kein anderes Browser-Plugin) die versteckte iframe-Technik, die es ermöglicht, eine asynchrone Anfrage zu emulieren, ohne das XMLHttpRequest-Objekt zu verwenden.

Sie besteht darin, einen iframe als Ziel des Formulars mit den Dateieingaben festzulegen. Wenn der Benutzer eine Anfrage sendet, werden die Dateien hochgeladen, aber die Antwort wird im iframe angezeigt, anstatt die Hauptseite neu zu rendern. Durch Ausblenden des iframes wird der gesamte Prozess für den Benutzer transparent gemacht und eine asynchrone Anfrage wird emuliert.

Wenn es ordnungsgemäß durchgeführt wird, sollte es praktisch auf jedem Browser funktionieren, hat aber einige Einschränkungen, wie das Abrufen der Antwort aus dem iframe.

In diesem Fall können Sie bevorzugen, einen Wrapper-Plugin wie Bifröst zu verwenden, der die iframe-Technik verwendet, aber auch einen jQuery Ajax-Transport bereitstellt, der es ermöglicht, Dateien nur mit der $.ajax()-Methode wie folgt zu senden:

$.ajax({
  url: 'file/destination.html', 
  type: 'POST',
  // Setzen Sie den Transport zum Verwenden (iframe bedeutet, Bifröst zu verwenden)
  // und den erwarteten Datentyp (hier json).
  dataType: 'iframe json',                                
  fileInputs: $('input[type="file"]'),  // Die Dateieingaben, die die zu sendenden Dateien enthalten.
  data: { msg: 'Einige zusätzliche Daten, die Sie vielleicht benötigen.'}
}).done(function(){
  console.log("Erfolg: Dateien gesendet!");
}).fail(function(){
  console.log("Ein Fehler ist aufgetreten, die Dateien konnten nicht gesendet werden!");
});

Plugins

Bifröst ist nur ein kleiner Wrapper, der die Ausweichunterstützung für die jQuery-Ajax-Methode hinzufügt, aber viele der bereits erwähnten Plugins wie jQuery Form Plugin oder jQuery File Upload enthalten den gesamten Stapel von HTML5 bis hin zu verschiedenen Ausweichlösungen und einige nützliche Funktionen, um den Prozess zu erleichtern. Je nach Bedarf und Anforderungen möchten Sie möglicherweise eine reine Implementierung oder eines dieser Plugins in Betracht ziehen.

0 Stimmen

Bifrost fügt noch nicht einmal die POST-Daten an... kann dieses, fragwürdige Plugin, Zeitverschwendung, überhaupt NICHT empfehlen.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X