How to update one file in a zip archive

BashShellZip

Bash Problem Overview


Is it possible to replace a file in a zip file without unzipping deleting the old file adding the new file and rezipping it back?

Reason is I have a zip file which is really big there is one xml inside the zip file that I have to update sometimes. Unzipping the zip and rezipping it takes a long time. So I'd like to just be able to replace the one xml inside the zip through a script. I already have that checks for updates on the xml I have.

So is it possible to just replace the one xml without unzipping and rezipping ?

Sorry i would use the zip command to do things like that but problem is the script is actually for an android phone and zip is not a command i can use unfortunately sorry i left that out. I would have used zip definately if i could but i only have unzip for droid and then there is tar in busybox but tar doesn't do what i need

Bash Solutions


Solution 1 - Bash

I've found the Linux zip file to be cumbersome for replacing a single file in a zip. The jar utility from the Java Development Kit may be easier. Consider the common task of updating WEB/web.xml in a JAR file (which is just a zip file):

jar -uf path/to/myapp.jar -C path/to/dir WEB-INF/web.xml

Here, path/to/dir is the path to a directory containing the WEB-INF directory (which in turn contains web.xml).

Solution 2 - Bash

Try the following:

zip [zipfile] [file to update] 

An example:

$ zip test.zip test/test.txt
updating: test/test.txt (stored 0%)

Solution 3 - Bash

From zip(1):

>When given the name of an existing zip archive, zip will replace identically named entries in the zip archive or add entries for new names.

So just use the zip command as you normally would to create a new .zip file containing only that one file, except the .zip filename you specify will be the existing archive.

Solution 4 - Bash

Use the update flag: -u

Example: > zip -ur existing.zip myFolder

This command will compress and add myFolder (and it's contents) to the existing.zip.


Advanced Usage:

The update flag actually compares the incoming files against the existing ones and will either add new files, or update existing ones.

Therefore, if you want to add/update a specific subdirectory within the zip file, just update the source as desired, and then re-zip the entire source with the -u flag. Only the changed files will be zipped.

If you don't have access to the source files, you can unzip the zip file, then update the desired files, and then re-zip with the -u flag. Again, only the changed files will be zipped.

Example:

Original Source Structure


ParentDir
├── file1.txt
├── file2.txt
├── ChildDir
│   ├── file3.txt
│   ├── Logs
│   │   ├── logs1.txt
│   │   ├── logs2.txt
│   │   ├── logs3.txt

Updated Source Structure


ParentDir
├── file1.txt
├── file2.txt
├── ChildDir
│   ├── file3.txt
│   ├── Logs
│   │   ├── logs1.txt
│   │   ├── logs2.txt
│   │   ├── logs3.txt
│   │   ├── logs4.txt <-- NEW FILE 

Usage

$ zip -ur existing.zip ParentDir 
> updating: ParentDir/ChildDir/Logs (stored 0%)
>   adding: ParentDir/ChildDir/Logs/logs4.txt (stored 96%)

Solution 5 - Bash

I know this is old question, but I wanted to do the same. Update a file in zip archive. And none of the above answers really helped me.

Here is what I did. Created temp directory abc. Copied file.zip to abc and extracted the file in that directory. I edited the file I wanted to edit. Then while being in abc, ran the following command

user@host ~/temp/abc $ zip -u file.zip
updating: content/js/ (stored 0%)
updating: content/js/moduleConfig.js (deflated 69%)

-u switch will look for changed/new files and will add to the zip archive.

Solution 6 - Bash

You can use: zip -u file.zip path/file_to_update

Solution 7 - Bash

There is also the -f option that will freshen the zip file. It can be used to update ALL files which have been updated since the zip was generated (assuming they are in the same place within the tree structure within the zip file).

If your file is named /myfiles/myzip.zip all you have to do is

zip -f /myfiles/myzip.zip

Solution 8 - Bash

From the side of ZIP archive structure - you can update zip file without recompressing it, you will just need to skip all files which are prior of the file you need to replace, then put your updated file, and then the rest of the files. And finally you'll need to put the updated centeral directory structure. However, I doubt that most common tools would allow you to make this.

Solution 9 - Bash

7zip (7za) can be used for adding/updating files/directories nicely:

Example: Replacing (regardless of file date) the MANIFEST.MF file in a JAR file. The /source/META-INF directory contains the MANIFEST.MF file that you want to put into the jar (zip):

7za a /tmp/file.jar /source/META-INF/

Only update (does not replace the target if the source is older)

7za u /tmp/file.jar /source/META-INF/

Solution 10 - Bash

yes its possible.

on linux based systems just install zip and you can call it in the command line. have a look at the manpage: http://linux.die.net/man/1/zip

but in my personal experience, if possible and compression is not so important, this works better with plain tar files and tar.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
Questionuser577732View Question on Stackoverflow
Solution 1 - BashcayhorstmannView Answer on Stackoverflow
Solution 2 - BashWizardsOfWorView Answer on Stackoverflow
Solution 3 - BashPleaseStandView Answer on Stackoverflow
Solution 4 - BashEthan StriderView Answer on Stackoverflow
Solution 5 - BashtraditionalView Answer on Stackoverflow
Solution 6 - BashRenato Luiz RamosView Answer on Stackoverflow
Solution 7 - BashW7GVRView Answer on Stackoverflow
Solution 8 - BashNickolay OlshevskyView Answer on Stackoverflow
Solution 9 - BashmzsoltView Answer on Stackoverflow
Solution 10 - BashThe SurricanView Answer on Stackoverflow