Ist POSIX wirklich ungeeignet für Objektspeicher? Eine datenbasierte Antwort

Der Autor dieses Beitrags stellt die in einem MinIO-Artikel dargestellte Perspektive in Frage, der zufolge POSIX nicht geeignet ist für Objektspeicher. Er führte umfangreiche Tests durch, die MinIO s3fs-fuse und JuiceFS umfassten. Die Ergebnisse zeigen, dass sowohl MinIO als auch JuiceFS hervorragende Leistungen liefern, während s3fs-fuse zurückbleibt. Bei Szenarien mit Überschreibung von kleinen Dateien übertrifft JuiceFS FUSE-POSIX andere Lösungen.

Kürzlich stieß ich auf einen Artikel auf dem MinIO-Blog mit dem Titel „Putting a Filesystem on Top of an Object Store is a Bad Idea. Here is why.“ Der Autor benutzte s3fs-fuse als Beispiel, um die Leistungsschwierigkeiten aufzuzeigen, die beim Zugriff auf MinIO-Daten mithilfe von Portable Operating System Interface (POSIX) Methoden auftreten, und betonte, dass die Leistung deutlich hinter dem direkten MinIO-Zugriff zurückbleibt. Der Autor führte diese Leistungsprobleme auf inhärente Mängel von POSIX zurück. Unsere Erfahrungen weichen jedoch etwas von dieser Schlussfolgerung ab.

POSIX ist eine nützliche und weit verbreitete Norm. Die Entwicklung von Software gemäß POSIX garantiert Kompatibilität und Portabilität über verschiedene Betriebssysteme hinweg. Die meisten Anwendungen in verschiedenen Branchen halten sich an die POSIX-Norm. Mit dem Fortschritt von Cloud Computing, Big Data und KI-Technologien sowie dem zunehmenden Datenvolumen, das gespeichert wird, besteht eine wachsende Nachfrage nach elastischen Speicherlösungen wie Objektspeichern. Obwohl Objektspeicher wie MinIO SDKs in mehreren Sprachen anbieten, haben viele traditionelle Anwendungen Schwierigkeiten, ihren Code an die Objektspeicher-APIs anzupassen. Dies hat dazu geführt, dass verschiedene Speicherprodukte POSIX-Schnittstellen auf Objektspeichern implementieren, um diese starre Nachfrage zu befriedigen.

Viele Produkte in der Branche, wie Ceph, JuiceFS und Weka, haben erfolgreich POSIX-Schnittstellen auf Objektspeichern implementiert. Diese Lösungen haben große Nutzerbasen und zahlreiche Erfolgsgeschichten und zeigen gute Leistungswerte.

Obwohl es zutrifft, dass POSIX eine beträchtliche Komplexität aufweist, sind die damit verbundenen Probleme nicht unüberwindbar. Aus Respekt und dem Wunsch, diese Behauptungen zu überprüfen, habe ich eine Testumgebung eingerichtet, die gleichen Beispieldaten und Testmethoden wie im MinIO-Artikel verwendet und eine Überprüfung durchgeführt.

Vergleich von Produkten und Testziele

Um eine umfassende Bewertung zu gewährleisten, habe ich JuiceFS in den Vergleich eingeführt.

JuiceFS ist eine quelloffene, cloud-native verteilte Dateisystem. Es nutzt Objektspeicher als Datenspeicherschicht und setzt auf eine separate Datenbank zur Speicherung von Metadaten. Es bietet verschiedene Zugriffsmethoden, einschließlich POSIX API, S3 API, CSI Driver, HDFS API und WebDAV, zusammen mit einzigartigen Daten-Chunking, Caching und parallelen Lese-/Schreibmechanismen. JuiceFS ist ein Dateisystem, grundlegend verschieden von Werkzeugen wie s3fs-fuse, die lediglich von Objektspeicher zu POSIX-Protokollen konvertieren.

Indem ich JuiceFS in die Bewertung einbrachte, wollte ich objektiv die Vor- und Nachteile der Implementierung von Protokollen wie POSIX auf Objektspeicher evaluieren.

I conducted the following two tests on MinIO, JuiceFS, and s3fs-fuse:

  • Schreiben einer 10 GB großen Datei
  • Überschreiben kleiner Dateien mit Pandas

Alle drei Lösungen nutzten eine MinIO-Instanz, die auf separaten Servern bereitgestellt wurde, als zugrundeliegenden Speicher. Für die Testbeispiele wurde eine 10 GB große Datei verwendet, die dieselbe CSV-Datei war, die im MinIO-Artikel erwähnt wurde.

Die Umgebungen, Software, Skripte und Beispieldaten in diesem Artikel kommen mit vollständigem Code und Anweisungen, um sicherzustellen, dass Sie die Umgebung und Testresultate reproduzieren können.

Server- und Testumgebungs-Setup

Zwei identisch konfigurierte Cloud-Server:

  • System: Ubuntu 22.04 x64
  • CPU: 8 Kerne
  • RAM: 16 GB
  • SSD: 500 GB
  • Netzwerk: VPC

Die Informationen für jeden Server:

Server IP Purpose
Server A 172.16.254.18 Deploying the MinIO instance
Server B 172.16.254.19 As the test environment

Server A Vorbereitung

1. Ich habe MinIO auf Server A mithilfe von Docker mit den folgenden Befehlen bereitgestellt:

# Erstelle ein dediziertes Verzeichnis und navigiere zu ihm.
mkdir minio && cd minio

# Erstelle eine Konfigurationsdatei.
mkdir config
touch config/minio

2. Ich habe die folgenden Informationen in die Datei config/minio geschrieben:

MINIO_ROOT_USER=admin
MINIO_ROOT_PASSWORD=abc123abc
MINIO_VOLUMES="/mnt/data"

3. Ich habe den MinIO-Container erstellt:

sudo docker run -d --name minio \
  -p 9000:9000 \
  -p 9090:9090 \
  -v /mnt/minio-data:/mnt/data \
  -v ./config/minio:/etc/config.env \
  -e "MINIO_CONFIG_ENV_FILE=/etc/config.env" \
  --restart unless-stopped \
  minio/minio server --console-address ":9090"

4. Im Web-Konsol von MinIO habe ich drei Buckets vorgefertigt:

Bucket name Purpose
test-minio For testing MinIO
test-juicefs For testing JuiceFS
test-s3fs For testing s3fs-fuse

Server B Vorbereitung

1. Ich habe die 10 GB Test-Beispieldatei heruntergeladen.

curl -LO https://data.cityofnewyork.us/api/views/t29m-gskq/rows.csv?accessType=DOWNLOAD

2. Ich habe den mc-Client installiert.

mc ist ein Kommandozeilen-Dateimanager, der vom MinIO-Projekt entwickelt wurde. Er ermöglicht Lese- und Schreiboperationen sowohl auf lokalem Speicher als auch auf S3-kompatiblem Objektspeicher in der Linux-Kommandozeile. Der mc cp-Befehl liefert Echtzeit-Fortschritt und Geschwindigkeitsupdates während des Datenkopierens, was die Beobachtung verschiedener Tests erleichtert.

Hinweis: Um die Testgerechtigkeit zu wahren, wurde mc für alle drei Ansätze zur Datei-Schreibtest verwendet.

# mc herunterladen.
wget https://dl.min.io/client/mc/release/linux-amd64/mc

# mc-Version überprüfen.
mc -v
mc version RELEASE.2023-09-20T15-22-31Z (commit-id=38b8665e9e8649f98e6162bdb5163172e6ecc187)
Runtime: go1.21.1 linux/amd64

# mc installieren.
sudo install mc /usr/bin

# Alias für MinIO setzen.
mc alias set my http://172.16.254.18:9000 admin abc123abc

3. Ich habe s3fs-fuse heruntergeladen.

sudo apt install s3fs

# Version überprüfen.
s3fs --version
Amazon Simple Storage Service File System V1.93 (commit:unknown) with OpenSSL

# Objektspeicher-Zugriffsschlüssel setzen.
echo admin:abc123abc >  ~/.passwd-s3fs

# Schlüsseldatei-Berechtigungen ändern.
chmod 600  ~/.passwd-s3fs

# Montageverzeichnis erstellen.
mkdir mnt-s3fs

# Objektspeicher montieren.
s3fs test-s3fs:/ /root/mnt-s3fs -o url=http://172.16.254.18:9000 -o use_path_request_style

4. Ich habe JuiceFS installiert.

I used the official script to install the latest JuiceFS Community Edition.

# Ein-Klick-Installationsskript
curl -sSL https://d.juicefs.com/install | sh -

# Version überprüfen.
juicefs version
juicefs version 1.1.0+2023-09-04.08c4ae6

5. Ich habe ein Dateisystem erstellt. JuiceFS ist ein Dateisystem, das vor der Verwendung erstellt werden muss. Neben dem Objektspeicher benötigt es eine Datenbank als Metadaten-Engine. Es unterstützt verschiedene Datenbanken. Hier habe ich die gebräuchliche Redis als Metadaten-Engine verwendet.

Hinweis: Ich habe Redis auf Server A installiert, erreichbar über 172.16.254.18:6379 ohne Passwort. Der Installationsprozess wird hier ausgelassen. Sie können die Redis-Dokumentation für Details heranziehen.

# Erstelle das Dateisystem.
juicefs format --storage minio \
--bucket http://172.16.254.18:9000/test-juicefs \
--access-key admin \
--secret-key abc123abc \
--trash-days 0 \
redis://172.16.254.18/1 \
myjfs

6. Ich habe JuiceFS mit den häufiger verwendeten POSIX- und S3-API-Methoden zugreifen und ihre Leistung getestet.

# Erstelle die Montageverzeichnisse.
mkdir ~/mnt-juicefs

# Befestige das Dateisystem im POSIX-Modus.
juicefs mount redis://172.16.254.18/1 /root/mnt-juicefs

# Greife auf das Dateisystem mit der S3-API-Methode zu.
export MINIO_ROOT_USER=admin
export MINIO_ROOT_PASSWORD=abc123abc
juicefs gateway redis://172.16.254.18/1 0.0.0.0:9000

# Setze einen Alias für die JuiceFS S3 API in mc.
mc alias set juicefs http://172.16.254.18:9000 admin abc123abc

Hinweis: Die JuiceFS-Gateway kann auch auf Server A oder auf jedem anderen internetzugänglichen Server bereitgestellt werden, da es eine netzwerkbasierte S3-API exponiert.

Tests und Ergebnisse

Hier ist eine kurze Zusammenfassung meiner Tests und Ergebnisse:

Test MinIO S3FS-FUSE JuiceFS
(FUSE)
JuiceFS
(S3 gateway)
Writing a 10 GB file 0m27.651s 3m6.380s 0m28.107s 0m28.091s
Overwriting small files with Pandas 0.83s 0.78s 0.46s 0.96s

Test 1: Schreiben einer 10 GB Datei

Dieser Test sollte die Leistung beim Schreiben großer Dateien evaluieren. Je kürzer die benötigte Zeit, desto besser die Leistung. Ich habe den time-Befehl verwendet, um die Dauer der Schreibvorgänge zu messen und biete drei Metriken:

  • real: Die tatsächliche Zeit vom Start bis zum Ende des Befehls. Sie umfasste alle Wartezeiten, wie zum Beispiel das Warten auf den Abschluss von E/A-Operationen, das Warten auf Prozesswechsel und Ressourcenwartezeit.
  • user: Die Zeit, die im Benutzermodus ausgeführt wurde, gibt die vom CPU verwendete Zeit für die Ausführung von Benutzercode an. Sie stellt typischerweise die Rechenlast des Befehls dar.
  • sys: Die Zeit, die im Kernel-Modus ausgeführt wurde, gibt die vom CPU verwendete Zeit für die Ausführung von Kernel-Code an. Sie stellt typischerweise die Last in Bezug auf Systemaufrufe dar, wie Datei-E/A und Prozessverwaltung.

MinIO

I ran the following command to perform a copy test:

time mc cp ./2018_Yellow_Taxi_Trip_Data.csv  my/test-minio/

Ergebnisse für das direkte Schreiben einer 10 GB Datei auf MinIO:

real    0m27.651s
user    0m10.767s
sys 0m5.439s

s3fs-fuse

I ran the following command to perform a copy test:

time mc cp ./2018_Yellow_Taxi_Trip_Data.csv /root/mnt-s3fs/

Ergebnisse für das direkte Schreiben einer 10 GB Datei auf s3fs-fuse:

real 3m6.380s
user 0m0.012s
sys 0m5.459s

Anmerkung: Obwohl die Schreibzeit für s3fs-fuse 3 Minuten und 6 Sekunden betrug, gab es keine Schreibfehler, wie in dem Artikel von MinIO beschrieben.

JuiceFS

I tested the performance of JuiceFS for large file writes using both the POSIX and S3 API methods:

# POSIX Schreibtest
time mc cp ./2018_Yellow_Taxi_Trip_Data.csv /root/mnt-juicefs/

# S3 API Schreibtest
time mc cp ./2018_Yellow_Taxi_Trip_Data.csv  juicefs/myjfs/

Ergebnisse für JuiceFS POSIX beim Schreiben einer 10 GB Datei:

real    0m28.107s
user    0m0.292s
sys 0m6.930s

Ergebnisse für JuiceFS S3 API beim Schreiben einer 10 GB Datei:

real    0m28.091s
user    0m13.643s
sys 0m4.142s

Zusammenfassung der Ergebnisse zum Schreiben großer Dateien

Die folgende Abbildung zeigt die Testresultate:

Large file write results (lower is better)

Die Testresultate zeigen, dass sowohl das direkte Schreiben auf MinIO als auch auf JuiceFS vergleichbare Leistungen erbrachten und die Aufgabe in etwa 30 Sekunden abschlossen. Im Gegensatz dazu benötigte s3fs-fuse über 3 Minuten, um eine 10 GB Datei zu schreiben, was ungefähr sechsmal langsamer als die beiden vorherigen ist.

Beim Schreiben großer Dateien nutzt mc die Multipart API, um Dateien in Teilen zur S3-Schnittstelle hochzuladen. Im Gegensatz dazu kann s3fs-fuse nur in einer einzigen Threads auf POSIX schreiben. JuiceFS teilt auch große Dateien automatisch in Teile auf und schreibt diese während der sequentiellen Schreibvorgänge parallel zu MinIO, was eine Leistung gewährleistet, die der direkten MinIO-Schreibweise entspricht. S3FS schreibt dagegen zunächst in einem einzigen Thread auf eine Cache-Festplatte und lädt die Datei anschließend in Teilen zu MinIO hoch, was zu längeren Schreibzeiten führt.

Basierend auf der Berechnung, dass das Schreiben einer 10 GB großen Datei 30 Sekunden gedauert hat, betrug die durchschnittliche Geschwindigkeit 333 MB/s. Dies war durch die Bandbreite von Cloud-Server-SSDs begrenzt. Diese Testresultate zeigten, dass sowohl MinIO als auch JuiceFS die Bandbreite der lokalen SSD voll ausschöpfen konnten, und ihre Leistung würde sich mit Verbesserungen an Server-Cloud-Festplatten und Netzwerkbandbreite verbessern.

Test 2: Überschreiben kleiner Dateien mit Pandas

Dieser Test bewertete die Leistung von Objektspeichersystemen in Szenarien des Überschreibens kleiner Dateien. Die Testskripte für jedes Softwarepaket waren leicht unterschiedlich. Sie können alle Skriptcode hier finden.

MinIO

I got the test script and ran the test:

# Holen Sie sich das Testskript.
curl -LO https://gist.githubusercontent.com/yuhr123/7acb7e6bb42fb0ff12f3ba64d2cdd7da/raw/30c748e20b56dec642a58f9cccd7ea6e213dab3c/pandas-minio.py

# Führen Sie den Test aus.
python3 pandas-minio.py

Das Ergebnis war wie folgt:

Execution time: 0.83 seconds

s3fs-fuse

I got the test script and ran the test:

# Holen Sie sich das Testskript.
curl -LO gist.githubusercontent.com/yuhr123/7acb7e6bb42fb0ff12f3ba64d2cdd7da/raw/30c748e20b56dec642a58f9cccd7ea6e213dab3c/pandas-s3fs.py

# Führen Sie den Test aus.
python3 pandas-s3fs.py

Das Testergebnis war wie folgt:

Execution time: 0.78 seconds

JuiceFS POSIX

I got the test script and ran the test:

# Holen Sie sich das Testskript.
curl -LO gist.githubusercontent.com/yuhr123/7acb7e6bb42fb0ff12f3ba64d2cdd7da/raw/30c748e20b56dec642a58f9cccd7ea6e213dab3c/pandas-juicefs-posix.py

# Führen Sie den Test aus.
python3 pandas-juicefs-posix.py

Das Testergebnis war wie folgt:

Execution time: 0.43 seconds

JuiceFS S3 API

I got the test script and ran the test:

# Holen Sie sich das Testskript.
curl -LO https://gist.githubusercontent.com/yuhr123/7acb7e6bb42fb0ff12f3ba64d2cdd7da/raw/30c748e20b56dec642a58f9cccd7ea6e213dab3c/pandas-juicefs-s3api.py

# Führen Sie den Test aus.
python3 pandas-juicefs-s3api.py

Das Testergebnis war wie folgt:

Execution time: 0.86 seconds

Zusammenfassung der Pandas-Überschreibungen von kleinen Dateien

Die folgende Abbildung zeigt die Testergebnisse:

Pandas overwrite results (lower is better)

In diesem Test zeigte JuiceFS FUSE-POSIX die schnellste Geschwindigkeit, fast doppelt so schnell wie die anderen Lösungen. MinIO, s3fs-fuse und JuiceFS S3 Gateway zeigen ähnliche Leistung. Aus der Sicht der Überschreibungen von kleinen Dateien hat die POSIX-Schnittstelle sich als effizienter erwiesen und eine bessere Leistung als Objektspeicher-Schnittstellen geliefert.

Probleme und Analyse

Problem 1: Warum war S3FS so langsam?

Analyse: Aus den Testdaten geht hervor, dass beim Schreiben der gleichen 10 GB Datei S3FS 3 Minuten benötigte, während MinIO und JuiceFS die Aufgabe in etwa 30 Sekunden erledigten. Dieser signifikante Leistungsabfall war hauptsächlich auf unterschiedliche technische Implementierungen zurückzuführen. Wenn s3fs-fuse eine Datei schreibt, schreibt es zuerst die Datei in eine lokale temporäre Datei und lädt sie dann in Teilen in den Objektspeicher hoch. Wenn es nicht genügend lokalen Festplattenspeicher gibt, lädt es synchron hoch. Es muss Daten zwischen der lokalen Festplatte und dem S3-Speicher kopieren. Daher führen große Dateien oder eine große Anzahl von Dateien zu einer Leistungsverschlechterung.

Darüber hinaus beruht S3FS auf den unterliegenden Metadaten-Management-Fähigkeiten des Objektspeichers. Bei der Handhabung einer großen Anzahl von Dateien hat die häufige Interaktion mit dem Objektspeicher zur Metadatenerfassung einen erheblichen Einfluss auf die Leistung. In einfachen Worten: Je größer die Dateigröße und die Gesamtzahl der auf S3FS geschriebenen Dateien, desto größer ist der proportionale Leistungsaufwand.

Problem 2: Warum war JuiceFS schneller?

Analyse: In dem Test nutzten sowohl JuiceFS als auch S3FS FUSE für Lese- und Schreibvorgänge. JuiceFS nutzte die Festplattenbandbreite voll aus, wie MinIO, aber es traten keine Leistungsprobleme auf, wie bei S3FS.

Der Schlüssel liegt in ihren jeweiligen technischen Architekturen. Während Daten beim Dateischreiben durch die FUSE-Schicht verarbeitet werden, setzt JuiceFS auf hohe Konkurrentenzahlen, Zwischenspeicherung und Datenaufteilung, um den Kommunikationsaufwand zwischen der FUSE-Schicht und dem zugrunde liegenden Objektspeicher zu reduzieren. Dies ermöglicht JuiceFS, gleichzeitig mehr Lese- und Schreibanfragen für Dateien zu bearbeiten, was Wartezeiten und Übertragungsverzögerungen verringert.

Zusätzlich verwendet JuiceFS eine dedizierte Datenbank (in diesem Fall Redis) zur Verwaltung von Metadaten. Bei der Handhabung einer besonders großen Anzahl von Dateien kann ein eigenständiger Metadatengenerator die Arbeitsbelastung effektiv verringern und die Dateisuche beschleunigen.

Schlussfolgerung

Die Tests oben zeigen, dass die Verwendung von Objektspeicher als Grundlage und die Implementierung einer POSIX-Schnittstelle darauf nicht unbedingt zu einer Leistungsverminderung führt. Egal ob große oder kleine Dateien geschrieben werden, zeigt JuiceFS Leistungen, die vergleichbar sind mit direkten MinIO-Schreibvorgängen, ohne dass es zu einer Verschlechterung der zugrunde liegenden Objektspeicherleistung aufgrund von POSIX-Zugriffen kommt. Darüber hinaus bleibt die Leistung von JuiceFS FUSE-POSIX bei Pandas-Tischüberschreibungen konstant und übertrifft sogar MinIO fast um das Doppelte.

Die Testresultate zeigen, dass einige Software, wie s3fs-fuse, möglicherweise eine Leistungsverschlechterung erleiden, wenn sie zwischen S3-API und POSIX-Schnittstellen konvertieren. Während es ein praktisches Werkzeug für die zeitweilige S3-Zugriffsmöglichkeit sein kann, sind für eine stabile und leistungsfähige langfristige Verwendung sorgfältige Forschung und Validierung erforderlich, um geeignetere Lösungen auszuwählen.

Für die einfache Archivierung von unstrukturierten Dateien ist die direkte Verwendung von MinIO oder Cloud-Objektspeicher eine gute Wahl. Für Szenarien, die jedoch eine große Datenspeicherung und -verarbeitung erfordern, wie z.B. die Trainings von AI-Modellen, die Analyse von Big Data, die Datenpersistenz von Kubernetes und andere häufige Lese- und Schreibvorgänge, bietet JuiceFS aufgrund seiner eigenständigen Metadatenverwaltung, seiner Fähigkeit zur gleichzeitigen Lese- und Schreibzugriff und seiner Pufferungsmechanismen überlegene Leistung. Es ist eine leistungsfähige Dateisystemlösung, die in Betracht gezogen werden sollte.

Source:
https://dzone.com/articles/is-posix-really-unsuitable-for-object-stores-a-dat