Extract files to same folder as archive using recursive to search all directories

僤鯓⒐⒋嵵緔 提交于 2020-01-03 05:19:07

问题


I'm working on an automation task in PowerShell that extracts the contents of several .tar archives to their respective subfolders using recursion and the 7z.exe utility.

Im running into an issue where the output dumps in my working directory instead of the subdirectory gci -r found the original tarball.

So far I have:

    $files=gci -r | where {$_.Extension -match "tar"}
        foreach ($files in $files) {
            c:\7z.exe e -y $file.FullName }

Advice on setting the working directory within the loop or 7z tips are appreciated.


回答1:


I am totally totally clueless when it comes to powershell, but after downloading an enormous torrent full of subdirectories ("publisher.title.author.year" essentially) each containing one or more zip files, which when unzipped each contained a part of a multi-file rar arhive, and FINALLY once assembled that contained a (uselessly named) pdf file...

so I came up with this rough and ready script to recurse into each subdirectory, unzip the zips into that directory, then assemble the rar files and extract the pdf into that directory, then rename the pdf with the directory name, and move it up a directory (so by the end I ended up with the base directory full of meaningfully named pdf files...

anyway - like I said I have literally no powershell knowledge so I'm mainly posting this because I wasted two hours writing it (I could have done it in 5-10 minutes in python or perl :P) and because if it's on the net I might actually find it again if I need to hehe

$subdirs = Get-ChildItem | ?{$_.Attributes -match 'Directory'}
foreach ($dir in $subdirs) {
    cd $dir
    $zip get-childitem | where {$_.Extension -match "zip"}
    C:\7z.exe x -y $zip.FullName
    $rar = get-childitem | where { $_.Extension -match "rar"}
    C:\7z.exe x -y $rar
    $pwd = get-item .   
    $newname = $pwd.basename+".pdf"
    get-childitem *.pdf | rename-item -newname $newname
    move-item $newname ..\
    cd ..
}



回答2:


Few points:

1) Use x flag instead of e to preserve paths.

2) Use -o to specify destination / output. I am taking the destination folder to be the name of the tar file ( without extension ) and the path to be the same as the tar file. You can remove the folder and just have the path.

3) You are just using gci -r - it will look for the files in the current directory. I have included $scriptDir below, which will under the directories the script's path. To search entire machine, do something like gci c:\ -r

This is how I will do it:

$scriptDir = Split-Path -Parent $MyInvocation.MyCommand.Path
$z ="7z.exe"

$files=gci $scriptDir -r | where {$_.Extension -match "tar"}
foreach ($file in $files) {
    $source = $file.FullName
    $destination = Join-Path (Split-Path -parent $file.FullName) $file.BaseName
    write-host -fore green $destination
    $destination = "-o" + $destination
    & ".\$z" x -y $source $destination
}



回答3:


I'm the OP (made a new acct). Thanks manojlds, I changed

$destination = Join-Path (Split-Path -parent $file.FullName) $file.BaseName

to

$destination = Join-Path (Split-Path -parent $file.FullName) $file.DirName

in order to output to the same directory as the archive and maintain the tree structure. I also tweaked

$z ="7z.exe"
...
& ".\$z" x -y $source $destination

to

$z="c:\7z.exe"
...
& "$z" x -y $source $destination

because it was throwing an error (7z issue?).

Thanks much.




回答4:


Give this a try. Performance tip, use the Filter parameter instead of where-object.

gci -r -filter *.tar | foreach { c:\7z.exe x -y $_.FullName $_.DirectoryName } 


来源:https://stackoverflow.com/questions/7265827/extract-files-to-same-folder-as-archive-using-recursive-to-search-all-directorie

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!