I know there are some paid GUI tools that let you do this, but I'm not interested in those.

Currently, I'm doing this:

gzcat Contents/Archive.pax.gz | pax -r

However, there are some pkg files that are now xar archives and I need pkgutil to extract them. And there's probably other permutations of pkg spec that I'm not aware of.

Bottom line is that I can always find some way to manually get the stuff out of the pkg, but I'd like a one-shot solution that would do this automatically without worrying about the specific pkg implementation, say:

unpkg CrappyPackage.pkg

Does such a thing exist?

Perhaps the most foolproof way is to use the system installer itself but that seems to always need a full system drive as its target. Would be really useful if you could do something along the lines of:

installer -pkg CrappyPackage.pkg -target SomeEmptySandbox.dmg

I know there is this question: How can I open a .pkg file manually? However, all the offered solutions there are pretty manual and I'm doing those right now anyways.

  • 1
    What would you want to do if the file is an 'xar' archive? – TJ Luoma Dec 29 '11 at 18:56
  • pkgutil --expand thepackage.pkg destination – kLy Dec 29 '11 at 22:01
  • or xar -xf package.pkg – kLy Dec 29 '11 at 22:11

It's easy enough to create a shell script which checks for a few conditions and then takes the appropriate action.

I've put mine at http://dl.dropbox.com/u/18414/bin/unpkg.sh but will copy the initial version below:

#   Author:     Timothy J. Luoma
#   Email:      luomat at gmail dot com
#   Date:       2011-12-29
#   Purpose:    extract .pkg files, either xar archives or directory
#   URL:       http://dl.dropbox.com/u/18414/bin/unpkg.sh
#   See also:  http://apple.stackexchange.com/questions/34957/foolproof-way-of-extracting-pkg-files


    # Brief explanation of how program works
USAGE="$NAME is meant to extract package files. (Filenames must end in .pkg). Can handle both .pkg directories or xar archives.

Usage: $NAME /path/to/foo.pkg

    # in case of emergency, report error and exit
die ()
    echo "$NAME: $@"
    exit 1

    # if not given any input, explain how to use it
if [ "$#" = "0" ]
        die "$USAGE"    

    # put whatever we get as an argument into a variable

    # does the input actual refer to an existing file?
    # if not, exit
[[ -e "$INPUT" ]]       || die "$INPUT does not exist"

    # get the extension of the input. i.e. if we are
    # given "foo.pkg" this will just be "pkg"

    # check to make sure that the extension is 'pkg'
    # because that's what we're looking for
[[ "$EXT" = "pkg" ]]    || die "$INPUT is not a pkg"

TYPE=`file -b "$INPUT"`

case "$TYPE" in 
                gzcat "$INPUT/Contents/Archive.pax.gz" | pax -r


    "xar archive - version 1")
                # Put whatever commands you want here

            die "$USAGE"    


exit 0

zsh has been included in Mac OS X for several releases now. I prefer it over /bin/sh because… well, let's not get into a "my shell is better than your shell" war, because my shell would win :-)

In any event, zsh makes things a little easier and a little nicer, and it's included, so there's no reason not to use it, IMO. Especially for a OS X-specific script like this.

This was tested on 10.7.

  • Exactly the kind of thing we need :) Has there not been anything of the sort made yet on github? The only thing is that there might be other permutations of .pkg files that aren't covered in the examples above but it's a good start. Would need a few test cases of different .pkg types. – kLy Dec 29 '11 at 23:44
  • I keep making plans to learn git/github, but haven't really. Feel free to use this as a starting point if you want to put it up on Github or elsewhere. FWIW the only other 'file' types that I've run into are 'empty' (package receipts) and 'data'. But I think the vast majority of them are directories or 'xar' archives. – TJ Luoma Dec 30 '11 at 4:52

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .