Eine neue Ära für Datei-Uploads in Discourse

Sie haben in den letzten Monaten vielleicht viele Commits im Zusammenhang mit Uploads in Discourse Core bemerkt. Dies war Teil einer umfassenden Anstrengung innerhalb von Core, die Verwendung von jQuery File Upload aus unserer Codebasis zu ersetzen, als Teil einer noch breiteren Gesamtanstrengung, die Verwendung von jQuery selbst aus unserer Codebasis zu ersetzen. jQuery File Uploader ist ein sehr altes Projekt und war seit fast Beginn Teil von Discourse Core. Ich glaube, ich habe es auch in anderen Projekten während meiner gesamten Karriere verwendet. Aber es ist Zeit, Ol’ Reliable in den Ruhestand zu versetzen:

Wir haben jQuery File Upload ersetzt (und werden bald auch eine weitere Bibliothek, resumable.js, ersetzen) durch eine Bibliothek namens Uppy. Dies ist eine viel modernere Upload-Bibliothek, die einfach mit Plugins erweitert werden kann und in der Lage ist, alle verschiedenen Workflows zu verarbeiten, die wir ihr aufbürden. Wichtig ist, dass dies uns ermöglicht, direkte Multipart-Uploads von S3 vom Discourse-Client aus durchzuführen, anstatt große Dateien über unsere API senden zu müssen.

Der Composer verwendet jetzt Uppy für alle Uploads, und viele andere Stellen in der App verwenden es (Avatar-Uploads, Hintergrund-Uploads von Profilen usw.). Die letzten verbleibenden Stellen werden in den nächsten Wochen verschwinden. Dies sollte für die meisten Benutzer eine weitgehend unsichtbare Änderung sein, aber Autoren von Plugins und Theme-Komponenten müssen einige Änderungen vornehmen.

Plugin-API

Vorverarbeiter

Alle Upload-Vorverarbeiter müssen jetzt als Uppy-Plugin geschrieben werden. Diese Plugins sind ziemlich einfach zu schreiben und verwenden einen einfachen Promise-basierten Workflow. Ein Upload-Vorverarbeiter kann eine Datei ändern oder Metadaten hinzufügen, bevor Uppy sie nach S3 oder an den Endpunkt /uploads.json hochlädt. Wir haben bereits mehrere Vorverarbeiter im Core, die Sie als Referenz für das Schreiben Ihrer eigenen verwenden können:

Upload-Vorverarbeiter für den Composer werden über api.addComposerUploadPreProcessor unter Verwendung der Plugin-API registriert:

Upload-Handler

Upload-Handler werden nicht als Uppy-Plugins geschrieben; sie funktionieren weiterhin wie immer mit einer kleinen Änderung. Wenn eine Datei mit einer Erweiterung übereinstimmt, die für einen Upload-Handler registriert ist, werden alle übereinstimmenden Dateien auf einmal gesendet. Zuvor wurde nur eine Datei nach der anderen an den Upload-Handler gesendet, und jetzt wird stattdessen ein Array gesendet:

Dateien, die von einem Upload-Handler verarbeitet werden, werden in der Uppy-Upload-Pipeline nicht weiter verarbeitet. Vorverarbeiter werden ausgeführt, bevor Upload-Handler aufgerufen werden.

S3 Multipart Direct Uploads

Vorhin erwähnte ich, dass unsere Verwendung von Uppy es uns auch ermöglicht, direkte Multipart-Uploads von S3 aus der Benutzeroberfläche durchzuführen. Um diese Funktion zu aktivieren, müssen Sie die Site-Einstellung enable_direct_s3_uploads auf true setzen.

Wenn Sie bei uns gehostet werden, sind die relevanten S3-Berechtigungen bereits für Ihren Bucket angewendet. Wenn Sie jedoch selbst hosten, müssen mehrere Berechtigungen und CORS-Regeln auf Ihrem Bucket eingerichtet werden, damit dies funktioniert.

Für die CORS-Regeln müssen Sie nur die Rake-Aufgabe s3:ensure_cors_rules mit rake s3:ensure_cors_rules ausführen. Sie fügt Ihrem Bucket die folgenden Regeln hinzu, solange Sie über S3:GetBucketCors- und S3:PutBucketCors-Berechtigungen für den von Ihnen eingerichteten Zugangs- und geheimen Schlüssel für Ihre S3-Anmeldeinformationen in Ihrer Discourse-Instanz verfügen.

{
  "AllowedHeaders": [
    "Authorization",
    "Content-Disposition",
    "Content-Type"
  ],
  "AllowedMethods": [
    "GET",
    "HEAD",
    "PUT"
  ],
  "AllowedOrigins": [
    "*"
  ],
  "ExposeHeaders": [
    "ETag"
  ],
  "MaxAgeSeconds": 3000
}

Für die Berechtigungen müssen Sie die folgenden Berechtigungen für den von Ihnen eingerichteten Zugangs- und geheimen Schlüssel für Ihre S3-Anmeldeinformationen in Ihrer Discourse-Instanz aktivieren.

{
    "Sid": "YourSid",
    "Effect": "Allow",
    "Action": [
        "s3:PutObjectVersionAcl",
        "s3:PutObjectAcl",
        "s3:PutObject",
        "s3:GetObjectAcl",
        "s3:GetObject",
        "s3:DeleteObject",
        "s3:CreateMultipartUpload",
        "s3:CompleteMultipartUpload",
        "s3:AbortMultipartUpload"
    ],
    "Resource": [
        "YOUR_RESOURCE"
    ]
}

Dies war ein Prozess, der mehrere lange Monate gedauert hat, und wir sind noch nicht fertig! Ich werde in diesem Thema posten, wenn wir jQuery File Uploader und resumable.js vollständig aus Discourse Core entfernen. Lassen Sie mich wissen, wenn Sie Fragen zu dem haben, was ich hier gepostet habe!

49 „Gefällt mir“

5 Beiträge wurden in ein neues Thema aufgeteilt: Uppy funktioniert nicht unter Firefox 68

itsgoneitsdone

Mit diesen beiden Commits sind jQuery File Uploader und resumable.js kein Teil von Discourse Core mehr:

Ich habe mein Bestes getan, um alle Referenzen darauf und auf unseren alten UploadMixin in allen uns bekannten Plugins zu entfernen, aber es kann sein, dass ich einige übersehen habe oder mir nicht bewusst bin. Keine Angst, der Migrationsprozess ist einfach. 99% der Anwendungsfälle können einfach unseren neuen UppyUploadMixin als Drop-in-Ersatz mit sehr geringen Änderungen verwenden. Ein Beispiel finden Sie hier:

Für die anderen 1% können Sie eine Instanz von Uppy erstellen und sich direkt in die Ereignisse einklinken. Ein Beispiel finden Sie hier:

Ich habe die Plugin-Änderungen auch im OP dieses Themas behandelt. Wir haben noch ein paar Wochen bis zu unserer nächsten Veröffentlichung, also wenn jemand Probleme hat, melden Sie diese bitte hier. Es war eine wilde Fahrt! :roller_coaster:

14 „Gefällt mir“

Nebenbei bemerkt, wurde die API-Dokumentation nun mit den neuen Upload-Endpunkten aktualisiert. Gehen Sie zu Discourse API Docs, um sie anzuzeigen.

(cc @mattdm, das könnte Sie interessieren)

6 „Gefällt mir“

Nachdem der direkte S3-Upload aktiviert wurde, erhalten wir Berichte von Benutzern in China, die keine Bilder hochladen können – der Upload bleibt bei 0 % hängen und schlägt mit einem Timeout fehl.

Der erste Gedanke könnte sein, dass S3 in China blockiert ist, aber wir wissen mit Sicherheit, dass dies nicht der Fall ist – zumindest nicht vollständig: Unsere Benutzer aus China können die in S3 gespeicherten Bilder problemlos sehen (in unserem Fall ein Bucket in der Region eu-central-1). Aber irgendwie scheint nur der Upload nicht zu funktionieren.

Dies ist schwer zu debuggen, wenn man nicht hinter der GFW ist, aber einige unserer Benutzer in China erwähnten, dass ein vielleicht relevanter Unterschied darin zu bestehen scheint, dass Bilder über den Dual-Stack-Endpunkt geladen werden, der Upload jedoch den regulären (nur IPv4) Endpunkt verwendet (bucket-name.s3.dualstack.eu-central-1.amazonaws.com vs. bucket-name.s3.eu-central-1.amazonaws.com). Aus einigen Tests geht hervor, dass dies tatsächlich der Fall zu sein scheint, aber ich bin mir nicht sicher, ob dies für den Upload beabsichtigt oder erforderlich ist.

Vielleicht aussagekräftiger ist, dass einige berichteten, dass durch das Hinzufügen einer IP, die vom Dualstack-Hostnamen aufgelöst wurde, zu ihrer Hosts-Datei (für den Nicht-Dualstack-Namen-Hostnamen) das Problem vollständig behoben wurde und sie mit dieser einzigen Änderung hochladen konnten.

Ich bin mir nicht sicher, ob das Discourse-Team jemanden in China hat, der bei der besseren Fehlersuche helfen kann?

4 „Gefällt mir“

Ein Beitrag wurde in ein neues Thema aufgeteilt: Error while configuring S3: actions do not exist