HDFS vejledning: Archilære, læse og skrive Operation

⚡ Smart opsummering

HDFS er det distribuerede lagringslag i Hadoop, der opdeler meget store filer i replikerede blokke på tværs af almindelige maskiner, så en enkelt NameNode tracks-metadata, mens mange DataNodes håndterer læse- og skriveanmodninger pålideligt.

  • 🔘 Archilære: NameNode indeholder navneområdebilledet og redigeringsloggen, mens DataNodes gemmer de faktiske blokreplikaer.
  • ☑️ Blokstørrelse: Hadoop 1.x satte standardværdien på 64 MB blokke; Hadoop 2.x og 3.x satte standardværdien på 128 MB i stedet.
  • ✅ Replikation: Tre replikaer pr. blok er standardindstillingen, fordelt på tværs af racks, så hardwarefejl aldrig mister data.
  • 🧪 Læs sti: FSDataInputStream og DFSInputStream henter blokplaceringer fra NameNode og streamer derefter bytes direkte fra DataNodes.
  • 🛠️ Skriv sti: DFSOutputStream sætter pakker i kø, DataStreamer opbygger en DataNode-pipeline, og en Ack-kø beskytter mod pakketab.
  • 🧭 Adgangsmuligheder: Filen org.apache.hadoop.fs Java API'en og hdfs dfs-shellen dækker begge åbning, læsning, skrivning og lukning.

HDFS tutorial

Hvad er HDFS?

HDFS er et distribueret filsystem til lagring af meget store datafiler, der kører på klynger af almindelig hardware. Det er fejltolerant, skalerbart og ekstremt nemt at udvide. Hadoop leveres med HDFS (Hadoop Distributed File System).

Når data overstiger lagerkapaciteten på en enkelt fysisk maskine, bliver det vigtigt at opdele dem på en række separate maskiner. Et filsystem, der styrer lagringsspecifikke operationer på tværs af et netværk af maskiner, kaldes et distribueret filsystem. HDFS er en sådan software.

HDFS Architecture

En HDFS-klynge består primært af en NavnNode der administrerer filsystemets metadata og DataNoder der lagrer de faktiske data.

  • NavnNode: NameNode kan betragtes som systemets master. Den vedligeholder filsystemtræet og metadataene for alle filer og mapper, der findes i systemet. To filer, 'navnerumsbilledet' og 'redigeringsloggen', bruges til at gemme metadatainformation. NameNode har kendskab til alle de DataNodes, der indeholder datablokke for en given fil, men den gemmer ikke blokplaceringer permanent. Disse oplysninger rekonstrueres hver gang fra DataNodes, når systemet starter.
  • DataNode: DataNodes er slaver, der befinder sig på hver maskine i en klynge og leverer den faktiske lagring. De er ansvarlige for at håndtere læse- og skriveanmodninger fra klienterne.

Fordi en enkelt NameNode ville være et enkelt fejlpunkt, kører nuværende klynger en aktiv NameNode sammen med en standby NameNode, der deler redigeringsloggen gennem et quorum af JournalNodes med automatisk failover mellem de to.

Læse- og skriveoperationer i HDFS fungerer på blokniveau. Datafiler i HDFS er opdelt i blokstørrelsesstykker, der gemmes som uafhængige enheder. Standardblokstørrelsen er 64 MB i Hadoop 1.x. Fra Hadoop 2.x og fremefter er standard dfs.blokstørrelse er 128 MB.

HDFS fungerer ud fra et koncept med datareplikering, hvor flere replikaer af datablokke oprettes og distribueres på noder i en klynge for at muliggøre høj tilgængelighed af data i tilfælde af nodefejl. Standardreplikeringsfaktoren er tre (dfs.replikering), og når en DataNode holder op med at sende hjerteslag, replikerer NameNode automatisk sine blokke andre steder.

Kender du? En fil i HDFS, som er mindre end en enkelt blok, optager ikke en bloks fulde lagerplads.

Læs Operation i HDFS

En datalæsningsanmodning håndteres af HDFS, NameNode og DataNodes. Lad os kalde læseren en 'klient'. Diagrammet nedenfor viser fillæsningsoperationen i Hadoop.

HDFS læser operationsdataflow mellem klient, NameNode og DataNodes

  1. En klient initierer en læseanmodning ved at kalde 'open()'-metoden for FileSystem-objektet; det er et objekt af typen DistributedFileSystem.
  2. Dette objekt opretter forbindelse til NameNode ved hjælp af RPC og henter metadataoplysninger, såsom placeringen af ​​filens blokke. Bemærk venligst, at disse adresser er de første par blokke i en fil.
  3. Som svar på denne metadataanmodning returneres adresserne på de DataNodes, der har en kopi af den pågældende blok.
  4. Når adresserne på DataNodes er modtaget, returneres et objekt af typen FSDataInputStream til klienten. FSDataInputStream indeholder DFSInputStream, som tager sig af interaktioner med DataNode og NameNode. I trin 4, vist i ovenstående diagram, kalder en klient 'read()'-metoden, som får DFSInputStream til at etablere en forbindelse med den første DataNode, der indeholder den første blok af en fil.
  5. Data læses i form af strømme, hvor klienten gentagne gange kalder 'read()'-metoden. Denne proces med read()-operationen fortsætter, indtil den når slutningen af ​​blokken.
  6. Når slutningen af ​​en blok er nået, lukker DFSInputStream forbindelsen og går videre til at finde den næste DataNode for den næste blok.
  7. Når klienten er færdig med at læse, kalder den close()-metoden.

Skrive Operation i HDFS

I dette afsnit vil vi forstå, hvordan data skrives til HDFS via filer. Diagrammet nedenfor traces, der skriver sti.

HDFS-skriveoperationspipeline med DataQueue, DataStreamer og Ack Queue

  1. En klient starter en skriveoperation ved at kalde 'create()'-metoden for DistributedFileSystem-objektet, hvilket opretter en ny fil – trin nr. 1 i ovenstående diagram.
  2. DistributedFileSystem-objektet opretter forbindelse til NameNode ved hjælp af et RPC-kald og starter oprettelsen af ​​en ny fil. Denne filoprettelseshandling knytter dog ingen blokke til filen. Det er NameNodes ansvar at verificere, at filen (som oprettes) ikke allerede findes, og at klienten har de korrekte tilladelser til at oprette en ny fil. Hvis en fil allerede findes, eller klienten ikke har tilstrækkelige tilladelser til at oprette en ny fil, udløses en IOException til klienten. Ellers lykkes handlingen, og NameNode opretter en ny post for filen.
  3. Når en ny post i NameNode er oprettet, returneres et objekt af typen FSDataOutputStream til klienten. En klient bruger det til at skrive data til HDFS. Data write-metoden kaldes (trin 3 i diagrammet).
  4. FSDataOutputStream indeholder et DFSOutputStream-objekt, der tager sig af kommunikationen med DataNodes og NameNode. Mens klienten fortsætter med at skrive data, fortsætter DFSOutputStream med at oprette pakker med disse data. Disse pakker sættes i kø i en kø, der kaldes DataQueue.
  5. Der er endnu en komponent kaldet DataStreamer, som bruger denne DataQueue. DataStreamer beder også NameNode om allokering af nye blokke og vælger dermed ønskede DataNodes, der skal bruges til replikering.
  6. Nu starter replikeringsprocessen ved at oprette en pipeline ved hjælp af DataNodes. I vores tilfælde har vi valgt et replikeringsniveau på 3, og der er derfor 3 DataNoder i pipelinen.
  7. DataStreameren hælder pakker ind i den første DataNode i pipelinen.
  8. Hver DataNode i en pipeline lagrer den pakke, den modtager, og videresender den til den anden DataNode i pipelinen.
  9. En anden kø, 'Ack-køen', vedligeholdes af DFSOutputStream for at gemme pakker, der venter på bekræftelse fra DataNodes.
  10. Når bekræftelse for en pakke i køen er modtaget fra alle DataNodes i pipelinen, fjernes den fra 'Ack Queue'. I tilfælde af en DataNode-fejl, bruges pakker fra denne kø til at genstarte operationen.
  11. Når en klient er færdig med at skrive data, kalder den close()-metoden (trin 9 i diagrammet). Kaldet til close() resulterer i, at de resterende datapakker flyttes til pipelinen, efterfulgt af venten på bekræftelse.
  12. Når en endelig bekræftelse er modtaget, kontaktes NameNode for at fortælle den, at filskrivningen er fuldført.

Få adgang til HDFS ved hjælp af Java API

I dette afsnit forsøger vi at forstå Java grænseflade, der bruges til at få adgang til Hadoops filsystem.

For at kunne interagere programmatisk med Hadoops filsystem, tilbyder Hadoop flere Java klasser. Pakken med navnet org.apache.hadoop.fs indeholder klasser, der er nyttige til manipulation af en fil i Hadoops filsystem. Disse operationer omfatter åbning, læsning, skrivning og lukning. Hadoop-fil-API'en er generisk og kan udvides til at interagere med andre filsystemer end HDFS.

Læser en fil fra HDFS, programmatisk

Objekt java.net.URL bruges til at læse indholdet af en fil. Til at begynde med skal vi lave Java genkende Hadoops hdfs URL skema. Dette gøres ved at kalde sættetURLStreamHandlerFactory-metoden på URL objekt og videregive en instans af FsUrlStreamHandlerFactory til det. Denne metode skal kun udføres én gang pr. FMV, derfor er den indesluttet i en statisk blok.

Et eksempel på kode er-

public class URLCat {
    static {
        URL.setURLStreamHandlerFactory(new FsUrlStreamHandlerFactory());
    }
    public static void main(String[] args) throws Exception {
        InputStream in = null;
        try {
            in = new URL(args[0]).openStream();
            IOUtils.copyBytes(in, System.out, 4096, false);
        } finally {
            IOUtils.closeStream(in);
        }
    }
}

Denne kode åbner og læser indholdet af en fil. Stien til denne fil på HDFS sendes til programmet som et kommandolinjeargument.

Få adgang til HDFS ved hjælp af kommandolinjegrænsefladen

Dette er en af ​​de enkleste måder at interagere med HDFS på. Kommandolinjegrænsefladen understøtter filsystemhandlinger som at læse en fil, oprette mapper, flytte filer, slette data og vise mapper.

Vi kan løbe '$HADOOP_HOME/bin/hdfs dfs -help' for at få detaljeret hjælp til hver kommando. Her er 'dfs' en shell-kommando i HDFS, som understøtter flere underkommandoer. I nuværende Hadoop-udgivelser hdfs dfs er den foretrukne form, mens den ældre hadoop fs Kommandoen udfører det samme arbejde for ethvert understøttet filsystem.

Nogle af de udbredte kommandoer er anført nedenfor sammen med nogle detaljer om hver enkelt.

1. Kopier en fil fra det lokale filsystem til HDFS

$HADOOP_HOME/bin/hdfs dfs -copyFromLocal temp.txt /

Denne kommando kopierer filen temp.txt fra det lokale filsystem til HDFS, som outputtet nedenfor viser.

hdfs dfs -copyFromLocal kommando kopierer temp.txt til HDFS

2. Vi kan liste filer, der findes i en mappe, ved hjælp af -ls

$HADOOP_HOME/bin/hdfs dfs -ls /

I listen nedenfor kan vi se filen 'temp.txt' (kopieret tidligere) under mappen '/'.

hdfs dfs -ls output viser temp.txt i HDFS rodmappen

3. Kommando til at kopiere en fil til det lokale filsystem fra HDFS

$HADOOP_HOME/bin/hdfs dfs -copyToLocal /temp.txt

Denne kommando afspejler -get og accepterer en eksplicit lokal destinationssti som et andet argument. Outputtet nedenfor viser temp.txt kopieret til det lokale filsystem.

hdfs dfs -copyToLocal output viser temp.txt kopieret til det lokale filsystem

4. Kommando for at oprette en ny mappe

$HADOOP_HOME/bin/hdfs dfs -mkdir /mydirectory

Kommandoen fuldføres lydløst, som prompten nedenfor viser.

hdfs dfs -mkdir kommando opretter mappen /mydirectory i HDFS

Tjek om mappen er oprettet eller ej. Nu burde du vide hvordan man gør det 😉

Ofte Stillede Spørgsmål

Store blokke holder NameNode-metadataene små og lader en mapper læse en lang sekventiel række bytes, før den søger igen. Disksøgningstiden bliver derfor en lille brøkdel af overførselstiden, hvilket er det, der gør scanninger af fulde filer hurtige.

NameNode stopper med at modtage hjerteslag, markerer noden som død og planlægger genreplikering af hver blok, der faldt under dens replikeringsfaktor, til sunde DataNodes. Skrivninger under kørsel gendannes fra Ack-køen, så klienten ikke mister pakker.

Ikke i en korrekt konfigureret klynge. HDFS High Availability kører en aktiv og en standby NameNode, der deler redigeringer via JournalNodes, og ZooKeeper failover-controllere forfremmer automatisk standby, når den aktive node holder op med at svare.

Begge uploader data til HDFS. -copyFromLocal-indstillingen begrænser kilden til det lokale filsystem, hvorimod -put accepterer enhver understøttet kilde, inklusive en anden HDFS-sti eller stdin. Opførslen er ellers identisk, så -copyFromLocal dokumenterer blot intentionen.

Hver fil, mappe og blok optager hukommelse i NameNode, så millioner af små filer opbruger heapen længe før diskene fyldes. Ved at kombinere dem til sekvensfiler, Avro-, ORC-, Parquet- eller HAR-arkiver, holder metadataene håndterbare.

Replikering gemmer tre fulde kopier, hvilket koster 200 procent ekstra lagerplads. Sletningskodning, tilføjet i Hadoop 3, lagrer i stedet paritetsceller og opnår lignende holdbarhed ved cirka 50 procent overhead, hvor billigere lagerplads byttes ud med højere CPU- og netværksomkostninger under gendannelse.

Maskinlæringsmodeller trænet på NameNode-revisionslogfiler og DataNode-målinger kan forudsige kapacitetsudmattelse, markere hot blocks og registrere fejlende diske, før de falder ud. Anomalidetektion på adgangsmønstre afslører også løbende job tidligt.

Copilot fuldfører hurtigt den velkendte org.apache.hadoop.fs-standardtekst, såsom FileSystem.get, FSDataInputStream-løkker og IOUtils.copyBytes-kald. Verificér altid genereret kode i forhold til den anvendte Hadoop-version, da API-navne og forældede metoder adskiller sig markant mellem Hadoop 2.x og 3.x.

Opsummer dette indlæg med: