Mnohdy se může stát, že máte více souborů, které je třeba sloučit do jednoho souboru. Může se stát, že jste dříve rozdělili jeden soubor na více souborů a chcete je prostě sloučit zpět nebo máte několik souborů protokolu, které chcete sloučit do jednoho. Ať už je důvod jakýkoli, sloučení více textových souborů do jednoho souboru je v Linuxu velmi snadné.
Příkaz v Linuxu pro spojování nebo slučování více souborů do jednoho se nazývá cat. Příkaz cat ve výchozím nastavení spojí a vypíše více souborů na standardní výstup. Standardní výstup můžete přesměrovat do souboru pomocí operátoru ‚>‘ a uložit výstup na disk nebo do souborového systému.
Další užitečný nástroj pro slučování souborů se nazývá join, který dokáže spojit řádky dvou souborů na základě společných polí. Umí však pracovat pouze se dvěma soubory najednou a jeho použití se mi zdálo poměrně těžkopádné. V tomto příspěvku se budeme zabývat především příkazem cat.
Sloučení více souborů do jednoho v pořadí
Příkaz cat přijímá jako argument seznam názvů souborů. Pořadí, v jakém jsou názvy souborů uvedeny v příkazovém řádku, určuje pořadí, v jakém budou soubory sloučeny nebo spojeny. Pokud tedy máte několik souborů s názvy file1.txt, file2.txt, file3.txt atd…
bash$ cat file1.txt file2.txt file3.txt file4.txt > ./mergedfile.txt
Výše uvedený příkaz připojí obsah souboru2.txt na konec souboru1.txt. Obsah souboru3.txt se připojí na konec sloučeného obsahu souboru1.txt a souboru2.txt atd… a celý sloučený soubor se uloží pod názvem sloučenýsoubor.txt do aktuálního pracovního adresáře.
Mnohdy se může stát, že máte nepřiměřeně velký počet souborů, což znesnadňuje zadávání názvů všech souborů. Příkaz cat přijímá jako vstupní názvy souborů regulární výrazy, což znamená, že s jejich pomocí můžete snížit počet argumentů.
bash$ cat file*.txt my*.txt > mergedfile.txt
Tento příkaz sloučí všechny soubory v aktuálním adresáři, které začínají názvem soubor a mají příponu txt, za nimiž následují soubory začínající na my a mají příponu txt. Pokud chcete zachovat pořadí souborů, musíte být opatrní při používání regulárních výrazů. Pokud regulární výraz použijete špatně, ovlivní to přesné pořadí, v jakém budou soubory sloučeny.
Rychlý a snadný způsob, jak zajistit, aby byly soubory sloučeny přesně v požadovaném pořadí, je použít výstup jiného programu pro výpis souborů, například ls nebo find, a připojit jej do příkazu cat. Nejprve spusťte příkaz find s regulárním výrazem a ověřte pořadí souborů…
bash$ find . -name "file*.txt" -o -name "my*.txt"
Tento příkaz vypíše soubory v takovém pořadí, abyste mohli ověřit, že je správné, nebo jej upravit tak, aby odpovídalo tomu, co chcete. Tento výstup pak můžete vložit do roury příkazem cat.
bash$ find . -name "file*.txt" -o -name "my*.txt" | xargs cat > ./mergedfile.txt
Při slučování více souborů do jednoho souboru pomocí regulárních výrazů pro jejich porovnání, zejména pokud se jedná o slučování do roury a pokud výstupní soubor není příliš zřejmý, dbejte na to, aby se regulární výraz neshodoval s názvem slučovaného souboru. V případě, že se shoduje, je obvykle příkaz cat docela dobrý v chybovém hlášení „vstupní soubor je výstupní soubor“. Pro začátek ale pomůže být opatrný.
Sloučení dvou souborů na libovolném místě
Někdy můžete chtít sloučit dva soubory, ale na určitém místě v obsahu souboru. Jedná se spíše o proces vložení obsahu jednoho souboru do druhého na určité místo v souboru.
Pokud je velikost souborů malá a zvládnutelná, pak je vi skvělým editačním nástrojem k tomuto účelu. V opačném případě je možné soubor nejprve rozdělit a pak výsledné soubory v pořadí sloučit. Nejjednodušší způsob rozdělení souboru je na základě čísel řádků, přesně v místě, kam chcete vložit druhý soubor.
bash$ split -l 1234 file1.txt
Soubor můžete rozdělit na libovolný počet výstupních souborů v závislosti na vašich požadavcích. Výše uvedený příklad rozdělí soubor file1.txt na části po 1234 řádcích. Je docela dobře možné, že vám nakonec vznikne více než dva soubory s názvy xaa, xab, xac atd… Všechny je můžete sloučit zpět pomocí stejného příkazu cat, jaký byl zmíněn dříve.
bash$ cat xaa file2.txt xa{b..z}
Výše uvedený příkaz sloučí soubory v pořadí, přičemž obsah souboru2.txt bude vložen mezi obsah souborů xaa a xab.
Dalším případem použití je situace, kdy potřebujete sloučit pouze určité části určitých souborů v závislosti na nějaké podmínce. To se mi hodí zejména tehdy, když musím analyzovat několik velkých souborů protokolu, ale zajímají mě jen určité zprávy nebo řádky. Budu tedy potřebovat vyjmout důležité zprávy protokolu na základě nějakých kritérií z několika souborů protokolu a uložit je do jiného souboru a zároveň zachovat nebo zachovat pořadí zpráv.
Ačkoli to můžete udělat pomocí příkazů cat a grep, můžete to udělat také jen pomocí příkazu grep.
bash$ grep -h "" logfile*.log > onlyerrors.log
Výše uvedené vyčlení všechny řádky, které odpovídají vzoru, a uloží je do jiného souboru. Při použití regulárního výrazu pro porovnání souborů protokolu se musíte ujistit, že jsou soubory v pořádku, jak bylo zmíněno dříve v příspěvku.