Advies nodig over Sqoop Incremental Imports.
Stel dat ik een klant heb met Beleid 1 op dag 1 en ik heb die records op dag 1 geïmporteerd in HDFS en ik zie ze in deelbestanden.
Op dag 2 voegt dezelfde klant Beleid 2 toe en krijgen we na de incrementele importprocedure alleen nieuwe records in de deelbestanden?
In dat geval, hoe krijg ik de oude en incrementele toegevoegde/laatst gewijzigde records met Sqoop?
Antwoord 1, autoriteit 100%
Beschouw een tabel met 3 records die u al in hdfs hebt geïmporteerd met behulp van sqoop
+------+------------+----------+------+------------+
| sid | city | state | rank | rDate |
+------+------------+----------+------+------------+
| 101 | Chicago | Illinois | 1 | 2014-01-25 |
| 101 | Schaumburg | Illinois | 3 | 2014-01-25 |
| 101 | Columbus | Ohio | 7 | 2014-01-25 |
+------+------------+----------+------+------------+
sqoop import --connect jdbc:mysql://localhost:3306/ydb --table yloc --username root -P
Je hebt nu extra records in de tabel, maar geen updates over bestaande records
+------+------------+----------+------+------------+
| sid | city | state | rank | rDate |
+------+------------+----------+------+------------+
| 101 | Chicago | Illinois | 1 | 2014-01-25 |
| 101 | Schaumburg | Illinois | 3 | 2014-01-25 |
| 101 | Columbus | Ohio | 7 | 2014-01-25 |
| 103 | Charlotte | NC | 9 | 2013-04-22 |
| 103 | Greenville | SC | 9 | 2013-05-12 |
| 103 | Atlanta | GA | 11 | 2013-08-21 |
+------+------------+----------+------+------------+
Hier moet u een --incremental append
gebruiken met --check-column
die de kolom specificeert die moet worden onderzocht bij het bepalen welke rijen moeten worden geïmporteerd.
sqoop import --connect jdbc:mysql://localhost:3306/ydb --table yloc --username root -P --check-column rank --incremental append --last-value 7
De bovenstaande code voegt alle nieuwe rijen in op basis van de laatste waarde.
Nu kunnen we een tweede geval bedenken waarbij er updates in rijen zijn
+------+------------+----------+------+------------+
| sid | city | state | rank | rDate |
+------+------------+----------+------+------------+
| 101 | Chicago | Illinois | 1 | 2015-01-01 |
| 101 | Schaumburg | Illinois | 3 | 2014-01-25 |
| 101 | Columbus | Ohio | 7 | 2014-01-25 |
| 103 | Charlotte | NC | 9 | 2013-04-22 |
| 103 | Greenville | SC | 9 | 2013-05-12 |
| 103 | Atlanta | GA | 11 | 2013-08-21 |
| 104 | Dallas | Texas | 4 | 2015-02-02 |
| 105 | Phoenix | Arzona | 17 | 2015-02-24 |
+------+------------+----------+------+------------+
Hier gebruiken we incrementeel lastmodified, waarbij we alle bijgewerkte rijen op basis van datum ophalen.
sqoop import --connect jdbc:mysql://localhost:3306/ydb --table yloc --username root -P --check-column rDate --incremental lastmodified --last-value 2014-01-25 --target-dir yloc/loc
Antwoord 2, autoriteit 13%
Als antwoord op uw eerste vraag hangt het ervan af hoe u het importstatement uitvoert. Als u de optie --incremental append
gebruikt, geeft u uw argumenten --check-column
en --last-value
op. Deze zullen precies bepalen welke records worden opgehaald en ze zullen eenvoudig aan uw tabel worden toegevoegd.
Bijvoorbeeld: u kunt een DATE
Type-kolom opgeven voor uw --check-column
Argument en een zeer vroege datum (zoals ‘1900-01-01’ of Day1 In uw zaak) voor --last-value
en dit zou gewoon alles in de bronstabel (het maken van dubbele rijen) naar uw bestemming blijven toevoegen. In dit geval houden de gemaakte nieuwe deelbestanden zowel nieuw als oud records. U kunt ook een toenemende ID-kolom gebruiken en de kleine ID binnen blijven en dat zou hetzelfde effect hebben. Indien --last-value
is dag2 , zijn er extra deelbestanden met alleen nieuwe records. Ik weet niet zeker of je je afvroeg of je de oude records zou verliezen (voor het geval je dat was) maar dat is niet het geval.
De last-modified
argument voor --incremental
zou alleen handig zijn als u in de toekomst teruggaat en een deel van de kenmerken van een bestaande rij bijwerkt. In dit geval vervangt het de oude gegevens in uw tabel (en voegt het de nieuwe dingen toe) met de bijgewerkte versie van de rij die nu in uw brontabel is. Ik hoop dat dit helpt!
Oh, dit alles is gebaseerd op de SQOOT-gebruikershandleiding 7.2.7 https://sqoop.apache.org/docs/1.4.2/sqoopeuserguide.html#_incremental_Imports
en hoofdstuk 3 van de Apache Sqoop-kookboek (dat hoofdstuk is eigenlijk fantastisch!)
Antwoord 3, Autoriteit 4%
Stap1: de gehele tabel is geïmporteerd. Dit is beschikbaar als Part-M-bestand in uw opgegeven HDFS-locatie (zeg / gebruiker / ABC / DEF / DEEL-M-00000)
Stap 2: Alleen de incrementele records worden geïmporteerd. Dit is beschikbaar op een andere locatie (zeg / gebruiker / ABC / DEF1 / DEEL-M-00000)
Nu beide gegevens beschikbaar zijn, kunt u de sqoop merge-optie gebruiken om beide te consolideren op basis van de sleutelkolom.
Raadpleeg het onderstaande document. voor meer details
https://sqoop.apache.org/docs/1.4 .3/SqoopUserGuide.html#_literal_sqoop_merge_literal
Antwoord 4, autoriteit 4%
laten we hier een voorbeeld nemen, u hebt een klantentabel met twee kolommen cust_id en policy, ook custid is uw primaire sleutel en u wilt alleen gegevens cust-id 100 en verder invoeren
scenario 1: – voeg nieuwe gegevens toe op basis van cust_id veld
fase1:-
onder 3 records zijn er die recentelijk zijn ingevoegd in de klantentabel die we willen importeren in HDFS
| custid | Policy |
| 101 | 1 |
| 102 | 2 |
| 103 | 3 |
hier is het sqoop-commando daarvoor
sqoop import \
--connect jdbc:mysql://localhost:3306/db \
--username root -P \
--table customer \
--target-dir /user/hive/warehouse/<your db>/<table> \
--append \
--check-column custid \
--incremental append \
--last-value 100
fase2:-
hieronder 4 records zijn er die recentelijk zijn ingevoegd in de klantentabel die we willen importeren in HDFS
| custid | Policy |
| 104 | 4 |
| 105 | 5 |
| 106 | 6 |
| 107 | 7 |
hier is het sqoop-commando daarvoor
sqoop import \
--connect jdbc:mysql://localhost:3306/db \
--username root -P \
--table customer \
--target-dir /user/hive/warehouse/<your db>/<table> \
--append \
--check-column custid \
--incremental append \
--last-value 103
dus deze vier eigenschappen zullen we moeten overwegen voor het invoegen van nieuwe records
--append \
--check-column <primary key> \
--incremental append \
--last-value <Last Value of primary key which sqoop job has inserted in last run>
scenario 2:- nieuwe gegevens toevoegen +bestaande gegevens bijwerken op basis van cust_id veld
hieronder 1 nieuw record met klant-ID 108 is ingevoegd en klant-ID 101 en 102 zijn recentelijk bijgewerkt in klantentabel die we willen importeren in HDFS
| custid | Policy |
| 108 | 8 |
| 101 | 11 |
| 102 | 12 |
sqoop import \
--connect jdbc:mysql://localhost:3306/db \
--username root -P \
--table customer \
--target-dir /user/hive/warehouse/<your db>/<table> \
--append \
--check-column custid \
--incremental lastmodified \
--last-value 107
dus deze vier eigenschappen zullen we moeten overwegen voor het invoegen/bijwerken van records in hetzelfde commando
--append \
--check-column <primary key> \
--incremental lastmodified \
--last-value <Last Value of primary key which sqoop job has inserted in last run>
Ik noem specifiek de primaire sleutel alsof de tabel geen primaire sleutel heeft, dan moeten er nog een paar eigenschappen worden overwogen, namelijk:-
meerdere mappers voeren standaard de sqoop-taak uit, dus mapper moet gegevens op basis van een sleutel splitsen, dus
ofwel we moeten specifiek –m 1 optie definiëren om te zeggen dat slechts één mapper deze bewerking zal uitvoeren
of we moeten een andere sleutel specificeren (met behulp van de eigenschap sqoop –split-by ) waarmee u de gegevens op unieke wijze kunt identificeren en vervolgens kunt gebruiken
Antwoord 5
U kunt ook een vrije-vorm-query proberen die zal worden gewijzigd op basis van een specifieke voorwaarde. Je zou een Java-code kunnen schrijven met Sqoop Client om hetzelfde te doen:
Hoe gebruik ik Sqoop in het Java-programma?
Antwoord 6
Hier is een stapsgewijze handleiding voor Sqoop incrementeel importeert.
Voor een overzicht gebruikt u de append-modus alleen als de rijen in uw brontabel niet worden bijgewerkt of als u niet geïnteresseerd bent in de updates, maar u gebruikt lastmodified als u ook de reeds geïmporteerde gegevens wilt bijwerken.
Antwoord 7
Zoek in dergelijke gevallen altijd naar velden die echt incrementeel van aard zijn voor incrementeel toevoegen.
en voor het laatst gewijzigde uiterlijk is het meest geschikte veld gewijzigd_datum of ook enkele velden voor degenen die zijn gewijzigd sinds u ze hebt gesjoemeld. alleen die en die rijen worden bijgewerkt, het toevoegen van nieuwere rijen op uw hdfs-locatie vereist een incrementele toevoeging.
Antwoord 8
Er zijn hier al geweldige reacties. Samen met deze kunt u ook Sqoop Query Approach proberen. U kunt uw query aanpassen op basis van de voorwaarde om de bijgewerkte records op te halen.
STAP 1: Nieuwe records importeren uit de databasetabel:
Voorbeeld 1:
$ sqoop import \
–query ‘SELECT a., b.FROM a JOIN b on (a.id == b.id) WHERE $CONDITIONS’\
–split-by a.id –target-dir /tmp/MyNewloc
Voorbeeld 2:
sqoop import --connect "jdbc:jtds:sqlserver://MYPD22:1333;databaseName=myDb" --target-dir /tmp/MyNewloc --fields-terminated-by \| --username xxx --password='xxx' --query "select * from Policy_Table where Policy_ID > 1 AND \$CONDITIONS" -m1
Vergeet niet $CONDITIONS op te geven in de Where-clausule.
Raadpleeg Sqoop Free Form Import
STAP 2: Part-m-bestanden van zowel de basistabel (originele gegevens) & amp; Nieuwe tabel (nieuwe records)
U kunt dit op twee manieren doen.
Methode 1– Sqoop Merge gebruiken
Methode 2– Kopiëren van nieuw gegenereerde part-m-bestanden naar de oorspronkelijke doelmap van de tabel. (Kopieer part-m bestanden van /tmp/MyNewloc naar /tmp/MyOriginalLoc/)
STAP 3: HIVE TABLE MAKEN
1) Krat nu een hive-tabel met behulp van Locatie als oorspronkelijke doelmap van de tabel die zowel originele part-m-bestanden als nieuwe records part-m-bestanden bevat.
CREATE EXTERNAL TABLE IF NOT EXISTS Policy_Table(
Policy_ID string,
Customer_Name string
)
ROW FORMAT DELIMITED FIELDS TERMINATED BY '|'
STORED AS TEXTFILE
LOCATION '/tmp/MyOriginalLoc/';