[unix] Concatenate multiple files but include filename as section headers

I would like to concatenate a number of text files into one large file in terminal. I know I can do this using the cat command. However, I would like the filename of each file to precede the "data dump" for that file. Anyone know how to do this?

what I currently have:

file1.txt = bluemoongoodbeer

file2.txt = awesomepossum

file3.txt = hownowbrowncow

cat file1.txt file2.txt file3.txt

desired output:

file1

bluemoongoodbeer

file2

awesomepossum

file3

hownowbrowncow

This question is related to unix header terminal concatenation cat

The answer is


If the files all have the same name or can be matched by find, you can do (e.g.):

find . -name create.sh | xargs tail -n +1

to find, show the path of and cat each file.


Was looking for the same thing, and found this to suggest:

tail -n +1 file1.txt file2.txt file3.txt

Output:

==> file1.txt <==
<contents of file1.txt>

==> file2.txt <==
<contents of file2.txt>

==> file3.txt <==
<contents of file3.txt>

If there is only a single file then the header will not be printed. If using GNU utils, you can use -v to always print a header.


This should do the trick as well:

find . -type f -print -exec cat {} \;

Means:

find    = linux `find` command finds filenames, see `man find` for more info
.       = in current directory
-type f = only files, not directories
-print  = show found file
-exec   = additionally execute another linux command
cat     = linux `cat` command, see `man cat`, displays file contents
{}      = placeholder for the currently found filename
\;      = tell `find` command that it ends now here

You further can combine searches trough boolean operators like -and or -or. find -ls is nice, too.


For solving this tasks I usually use the following command:

$ cat file{1..3}.txt >> result.txt

It's a very convenient way to concatenate files if the number of files is quite large.


If you want to replace those ugly ==> <== with something else

tail -n +1 *.txt | sed -e 's/==>/\n###/g' -e 's/<==/###/g' >> "files.txt"

explanation:

tail -n +1 *.txt - output all files in folder with header

sed -e 's/==>/\n###/g' -e 's/<==/###/g' - replace ==> with new line + ### and <== with just ###

>> "files.txt" - output all to a file


This should do the trick:

for filename in file1.txt file2.txt file3.txt; do
    echo "$filename"
    cat "$filename"
done > output.txt

or to do this for all text files recursively:

find . -type f -name '*.txt' -print | while read filename; do
    echo "$filename"
    cat "$filename"
done > output.txt

Here is a really simple way. You said you want to cat, which implies you want to view the entire file. But you also need the filename printed.

Try this

head -n99999999 * or head -n99999999 file1.txt file2.txt file3.txt

Hope that helps


find . -type f -print0 | xargs -0 -I % sh -c 'echo %; cat %'

This will print the full filename (including path), then the contents of the file. It is also very flexible, as you can use -name "expr" for the find command, and run as many commands as you like on the files.


This is how I normally handle formatting like that:

for i in *; do echo "$i"; echo ; cat "$i"; echo ; done ;

I generally pipe the cat into a grep for specific information.


And the missing awk solution is:

$ awk '(FNR==1){print ">> " FILENAME " <<"}1' *

I used grep for something similar:

grep "" *.txt

It does not give you a 'header', but prefixes every line with the filename.


When there is more than one input file, the more command concatenates them and also includes each filename as a header.

To concatenate to a file:

more *.txt > out.txt

To concatenate to the terminal:

more *.txt | cat

Example output:

::::::::::::::
file1.txt
::::::::::::::
This is
my first file.
::::::::::::::
file2.txt
::::::::::::::
And this is my
second file.

If you like colors, try this:

for i in *; do echo; echo $'\e[33;1m'$i$'\e[0m'; cat $i; done | less -R

or:

tail -n +1 * | grep -e $ -e '==.*'

or: (with package 'multitail' installed)

multitail *

If you want the result in the same format as your desired output you can try:

for file in `ls file{1..3}.txt`; \
do echo $file | cut -d '.' -f 1; \ 
cat $file  ; done;

Result:

file1
bluemoongoodbeer
file2
awesomepossum
file3
hownowbrowncow

You can put echo -e before and after the cut so you have the spacing between the lines as well:

$ for file in `ls file{1..3}.txt`; do echo $file | cut -d '.' -f 1; echo -e; cat $file; echo -e  ; done;

Result:

file1

bluemoongoodbeer

file2

awesomepossum

file3

hownowbrowncow

I like this option

for x in $(ls ./*.php); do echo $x; cat $x | grep -i 'menuItem'; done

Output looks like this:

./debug-things.php
./Facebook.Pixel.Code.php
./footer.trusted.seller.items.php
./GoogleAnalytics.php
./JivositeCode.php
./Live-Messenger.php
./mPopex.php
./NOTIFICATIONS-box.php
./reviewPopUp_Frame.php
            $('#top-nav-scroller-pos-<?=$active**MenuItem**;?>').addClass('active');
            gotTo**MenuItem**();
./Reviews-Frames-PopUps.php
./social.media.login.btns.php
./social-side-bar.php
./staticWalletsAlerst.php
./tmp-fix.php
./top-nav-scroller.php
$active**MenuItem** = '0';
        $active**MenuItem** = '1';
        $active**MenuItem** = '2';
        $active**MenuItem** = '3';
./Waiting-Overlay.php
./Yandex.Metrika.php

First I created each file: echo 'information' > file1.txt for each file[123].txt.

Then I printed each file to makes sure information was correct: tail file?.txt

Then I did this: tail file?.txt >> Mainfile.txt. This created the Mainfile.txt to store the information in each file into a main file.

cat Mainfile.txt confirmed it was okay.

==> file1.txt <== bluemoongoodbeer

==> file2.txt <== awesomepossum

==> file3.txt <== hownowbrowncow


  • AIX 7.1 ksh

... glomming onto those who've already mentioned head works for some of us:

$ r head
head file*.txt
==> file1.txt <==
xxx
111

==> file2.txt <==
yyy
222
nyuk nyuk nyuk

==> file3.txt <==
zzz
$

My need is to read the first line; as noted, if you want more than 10 lines, you'll have to add options (head -9999, etc).

Sorry for posting a derivative comment; I don't have sufficient street cred to comment/add to someone's comment.


you can use this simple command instead of using a for loop,

ls -ltr | awk '{print $9}' | xargs head

This method will print filename and then file contents:

tail -f file1.txt file2.txt

Output:

==> file1.txt <==
contents of file1.txt ...
contents of file1.txt ...

==> file2.txt <==
contents of file2.txt ...
contents of file2.txt ...

find . -type f -exec cat {} \; -print

Examples related to unix

Docker CE on RHEL - Requires: container-selinux >= 2.9 What does `set -x` do? How to find files modified in last x minutes (find -mmin does not work as expected) sudo: npm: command not found How to sort a file in-place How to read a .properties file which contains keys that have a period character using Shell script gpg decryption fails with no secret key error Loop through a comma-separated shell variable Best way to find os name and version in Unix/Linux platform Resource u'tokenizers/punkt/english.pickle' not found No 'Access-Control-Allow-Origin' header in Angular 2 app How to add header row to a pandas DataFrame How can I make sticky headers in RecyclerView? (Without external lib) Adding header to all request with Retrofit 2 Python Pandas Replacing Header with Top Row Request header field Access-Control-Allow-Headers is not allowed by Access-Control-Allow-Headers Pythonically add header to a csv file fatal error C1010 - "stdafx.h" in Visual Studio how can this be corrected? correct PHP headers for pdf file download How to fix a header on scroll

Examples related to terminal

Git is not working after macOS Update (xcrun: error: invalid active developer path (/Library/Developer/CommandLineTools) Can't compile C program on a Mac after upgrade to Mojave Flutter command not found VSCode Change Default Terminal How to switch Python versions in Terminal? How to open the terminal in Atom? Color theme for VS Code integrated terminal How to edit a text file in my terminal How to open google chrome from terminal? Switch between python 2.7 and python 3.5 on Mac OS X

Examples related to concatenation

Pandas Merging 101 What does ${} (dollar sign and curly braces) mean in a string in Javascript? Concatenate two NumPy arrays vertically Import multiple csv files into pandas and concatenate into one DataFrame How to concatenate columns in a Postgres SELECT? Concatenate string with field value in MySQL Most efficient way to concatenate strings in JavaScript? How to force a line break on a Javascript concatenated string? How to concatenate two IEnumerable<T> into a new IEnumerable<T>? How to concat two ArrayLists?

Examples related to cat

Can linux cat command be used for writing text to file? Concatenating Files And Insert New Line In Between Files How do I read the first line of a file using cat? Concatenate multiple files but include filename as section headers