Gibt es eine Möglichkeit, ein zipArchiv in ein tarArchiv zu konvertieren , ohne es zuerst in ein temporäres Verzeichnis zu extrahieren? (und ohne meine eigene Implementierung von taroder zu schreiben unzip)
Gibt es eine Möglichkeit, ein zipArchiv in ein tarArchiv zu konvertieren , ohne es zuerst in ein temporäres Verzeichnis zu extrahieren? (und ohne meine eigene Implementierung von taroder zu schreiben unzip)
Antworten:
Dies ist jetzt als installierbarer Befehl von PyPI verfügbar (siehe Ende dieses Beitrags).
Ich kenne kein "Standard" -Dienstprogramm, das dies tut, aber als ich diese Funktionalität benötigte, schrieb ich das folgende Python-Skript, um von ZIP zu Bzip2-komprimierten Tar-Archiven zu wechseln, ohne zuerst etwas auf die Festplatte zu extrahieren:
#! /usr/bin/env python
"""zip2tar """
import sys
import os
from zipfile import ZipFile
import tarfile
import time
def main(ifn, ofn):
with ZipFile(ifn) as zipf:
with tarfile.open(ofn, 'w:bz2') as tarf:
for zip_info in zipf.infolist():
#print zip_info.filename, zip_info.file_size
tar_info = tarfile.TarInfo(name=zip_info.filename)
tar_info.size = zip_info.file_size
tar_info.mtime = time.mktime(list(zip_info.date_time) +
[-1, -1, -1])
tarf.addfile(
tarinfo=tar_info,
fileobj=zipf.open(zip_info.filename)
)
input_file_name = sys.argv[1]
output_file_name = os.path.splitext(input_file_name)[0] + '.tar.bz2'
main(input_file_name, output_file_name)
Einfach speichern zip2tarund ausführbar machen oder speichern zip2tar.pyund ausführen python zip2tar.py. Geben Sie den ZIP-Dateinamen als Argument für das Skript an. Der Ausgabedateiname für xyz.ziplautet xyz.tar.bz2.
Die komprimierte Ausgabe von Bzip2 ist normalerweise viel kleiner als die ZIP-Datei, da letztere keine Komprimierungsmuster für mehrere Dateien verwendet, aber es besteht auch eine geringere Wahrscheinlichkeit, dass eine spätere Datei wiederhergestellt wird, wenn etwas in der Bzip2-Datei nicht stimmt.
Wenn Sie die Ausgabe nicht komprimieren möchten, entfernen Sie :bz2und .bz2aus dem Code.
Wenn Sie pipin einer python3-Umgebung installiert haben , können Sie Folgendes tun:
pip3 install ruamel.zip2tar
Um ein zip2tarKommandozeilen-Dienstprogramm zu erhalten, das die oben genannten Schritte ausführt (Haftungsausschluss: Ich bin der Autor dieses Pakets).
timefehlt ein import.
timeKommentar, ich aktualisiere die Antwort
Der tarBefehl behandelt Dateisysteme. Die Eingabe ist eine Liste von Dateien, die dann aus einem Dateisystem gelesen werden (einschließlich vieler Metadaten). Sie müssten die zip-Datei als Dateisystem präsentieren, damit der tarBefehl sie lesen kann.
Ein virtuelles Dateisystem - Mit AVFS kann jedes Programm über eine standardmäßige Dateisystemschnittstelle über FUSE in archivierte oder komprimierte Dateien schauen .
Es gibt einige detaillierte Informationen in der Readme-Datei von avfs-fuse und einige Distributionen haben Pakete dafür.
Wenn Sie AVFS installiert haben, können Sie
mountavfs
cd ~/.avfs/path/to/somefile.zip#
tar -cvf /path/whatever.tar .
AVFS fügt alle Informationen für das Dateisystem ein, die in der ZIP-Datei fehlen, wie z. B. der Dateibesitz, den tar abholt.
Hier ist ein kleiner Ausschnitt, der ein ZIP-Archiv in ein passendes TAR.GZ-Archiv OnTheFly konvertiert.
Konvertieren Sie ZIP-Archiv in TAR-Archiv im laufenden Betrieb
# File: zip2tar.py
#
# Convert ZIP archive to TAR.GZ archive.
#
# Written by Fredrik Lundh, March 2005.
# helpers (tweak as necessary)
def getuser():
# return user name and user id
return "anonymous", 1000
def getmode(name, data):
# return mode ("b" or "t") for the given file.
# you can do this either by inspecting the name, or
# the actual data (e.g. by looking for non-ascii, non-
# line-feed data).
return "t" # assume everything's text, for now
#
# main
import tarfile
import zipfile
import glob, os, StringIO, sys, time
now = time.time()
user = getuser()
def fixup(infile):
file, ext = os.path.splitext(infile)
outfile = file + ".tar.gz"
dirname = os.path.basename(file)
print outfile
zip = zipfile.ZipFile(infile, "r")
tar = tarfile.open(outfile, "w:gz")
tar.posix = 1
for name in zip.namelist():
if name.endswith("/"):
continue
data = zip.read(name)
if getmode(name, data) == "t":
data = data.replace("\r\n", "\n")
tarinfo = tarfile.TarInfo()
tarinfo.name = name
tarinfo.size = len(data)
tarinfo.mtime = now
tarinfo.uname = tarinfo.gname = user[0]
tarinfo.uid = tarinfo.gid = user[1]
tar.addfile(tarinfo, StringIO.StringIO(data))
tar.close()
zip.close()
# convert all ZIP files in the current directory
for file in glob.glob("*.zip"):
fixup(file)