George K.
George K.

Reputation: 3151

Create a tar.xz in one command

I am trying to create a .tar.xz compressed archive in one command. What is the specific syntax for that?

I have tried tar cf - file | xz file.tar.xz, but that does not work.

Upvotes: 250

Views: 260279

Answers (7)

Oshan Wisumperuma
Oshan Wisumperuma

Reputation: 1958

tar -I 'xz -9 -T0' -cf <archive.tar.xz> <files>

In this approach, you can pass arguments to xz as well. You may change the arguments as you wish. -9 is for the maximum compression level and setting -T to 0 lets xz use as many threads as it wishes (instead of the default limit of 1 prior to XZ Utils 5.4).

Also it works with other compression tools, for example zstd:

tar -I 'zstd -18 -T0' -cf <archive.tar.ztd> <files>

This switch only works with GNU tar (which comes with the majority of Linux distributions), version 1.27 (2013) or later. On macOS, you can install it, but the command will be gtar.

Upvotes: 4

codeling
codeling

Reputation: 11418

I can never remember which archive switch does what, so these days, I prefer tar's automatic detection, activated with the -a or --auto-compress switches. The command then simply looks like this:

tar caf file.tar.xz file

With that option, tar deduces the format to use automatically from the file extension used for the archive! It needs GNU tar 1.20 (2008) or above (or bsdtar from libarchive 3.1 (2013) and ulterior).

Upvotes: 16

Connor
Connor

Reputation: 4844

Quick Solution

tarxz() { tar cf - "$1" | xz -4e > "$1".tar.xz ; }
tarxz name_of_directory

(Notice, not name_of_directory/)


Using xz compression options

If you want to use compression options for xz, or if you are using tar on MacOS, you probably want to avoid the tar -cJf syntax.

According to man xz, the way to do this is:

tar cf - filename | xz -4e > filename.tar.xz

Because I liked Wojciech Adam Koszek's format, but not information:

  1. c creates a new archive for the specified files.
  2. f reads from a directory (best to put this second because -cf != -fc)
  3. - outputs to Standard Output
  4. | pipes output to the next command
  5. xz -4e calls xz with the -4e compression option. (equal to -4 --extreme)
  6. > filename.tar.xz directs the tarred and compressed file to filename.tar.xz

where -4e is, use your own compression options. I often use -k to --keep the original file and -9 for really heavy compression. -z to manually set xz to zip, though it defaults to zipping if not otherwise directed.

To uncompress and untar

To echo Rafael van Horn, to uncompress & untar (see note below):

xz -dc filename.tar.xz | tar x

Note: unlike Rafael's answer, use xz -dc instead of catxz. The docs recommend this in case you are using this for scripting. Best to have a habit of using -d or --decompress instead of unxz as well. However, if you must, using those commands from the command line is fine.

Upvotes: 18

Wojciech Adam Koszek
Wojciech Adam Koszek

Reputation: 1170

Switch -J only works on newer systems. The universal command is:

To make .tar.xz archive

tar cf - directory/ | xz -z - > directory.tar.xz

Explanation

  1. tar cf - directory reads directory/ and starts putting it to TAR format. The output of this operation is generated on the standard output.

  2. | pipes standard output to the input of another program...

  3. ... which happens to be xz -z -. XZ is configured to compress (-z) the archive from standard input (-).

  4. You redirect the output from xz to the tar.xz file.

Upvotes: 88

Jhim Preston
Jhim Preston

Reputation: 93

Try this: tar -cf file.tar file-to-compress ; xz -z file.tar

Note:

  1. tar.gz and tar.xz are not the same; xz provides better compression.
  2. Don't use pipe | because this runs commands simultaneously. Using ; or & executes commands one after another.

Upvotes: 4

user2062950
user2062950

Reputation:

Use the -J compression option for xz. And remember to man tar :)

tar cfJ <archive.tar.xz> <files>

Edit 2015-08-10:

If you're passing the arguments to tar with dashes (ex: tar -cf as opposed to tar cf), then the -f option must come last, since it specifies the filename (thanks to @A-B-B for pointing that out!). In that case, the command looks like:

tar -cJf <archive.tar.xz> <files>

Upvotes: 389

Rafael van Horn
Rafael van Horn

Reputation: 621

If you like the pipe mode, this is the most clean solution:

tar c some-dir | xz > some-dir.tar.xz

It's not necessary to put the f option in order to deal with files and then to use - to specify that the file is the standard input. It's also not necessary to specify the -z option for xz, because it's default.

It works with gzip and bzip2 too:

tar c some-dir | gzip > some-dir.tar.gz

or

tar c some-dir | bzip2 > some-dir.tar.bz2

Decompressing is also quite straightforward:

xzcat tarball.tar.xz | tar x
bzcat tarball.tar.bz2 | tar x
zcat tarball.tar.gz | tar x

If you have only tar archive, you can use cat:

cat archive.tar | tar x

If you need to list the files only, use tar t.

Upvotes: 48

Related Questions