1

My script exits when it hits a long path name (>= 260 characters). How could I change my snippet to capture long path names in my tif to pdf conversion. Or is it easier/better to simply dirlist all the files<260 characters and apply the script on them alone (I still wouldn't know how to tackle the remaining long name files)?

SNIPPET: (this works as long as the pathname is <260 characters)

$tool = 'C:\Program Files\ImageMagick-7.0.1-Q16\magick.exe'
$source = "\\my\path"

Get-ChildItem -Path $source -filter longnames*.tif | %{ & $tool convert "$($_.FullName -Replace ".tif+$", ".tif[0]")" "C:\Data\$($_.Name -Replace ".tif+$", ".pdf")" }

From reading this blog+posts, it seems I need to use the syntax

[Alphaleonis.Win32.Filesystem.File]::<some AlphaFS function here?>

but I need some further guidance or examples related to my application.

I'm on Windows Server 2012 R using Powershell v 4 and I've got the AlphaFS library installed. I am using imagemagick to convert the first page of a PDF to TIF.

val
  • 1,629
  • 1
  • 30
  • 56

1 Answers1

1

sorry, i have not used the AlphaFS dll file, and that may be easier to implement in the long run, but here is a possible workaround using a combination of robocopy to get long file names and subst to shorten the path temporarily

this makes use of the function here for robocopy https://github.com/gangstanthony/PowerShell/blob/master/Get-Files.ps1

! warning, not tested - use at your own risk

$tool = 'C:\Program Files\ImageMagick-7.0.1-Q16\magick.exe'

$source = "\\my\path"

# this will load the Get-Files function which uses robocopy
# feel free to check it out before running the script
try{ iex (iwr https://raw.githubusercontent.com/gangstanthony/PowerShell/master/Get-Files.ps1).rawcontent -ea 0 }catch{}

$files = (Get-Files -Path $source -Include longnames*.tif).fullname

# get available drives in case dealing with long file names
# we can map a drive to a long file path so it is short enough for powershell to handle
$drives = [io.driveinfo]::getdrives() | % {$_.name[0]}
$alpha = [char[]](65..90)
$avail = diff $drives $alpha | select -ExpandProperty inputobject
$drive = $avail[0] + ':'

# prepare for write-progress
$index = 0
$total = $files.Count
$starttime = $lasttime = Get-Date

$result = foreach ($file in $files) {
    # this is just the write-progress section
    $index++
    $currtime = (Get-Date) - $starttime
    $avg = $currtime.TotalSeconds / $index
    $last = ((Get-Date) - $lasttime).TotalSeconds
    $left = $total - $index
    $WrPrgParam = @{
        Activity = (
            "imagemagick.exe $(Get-Date -f s)",
            "Total: $($currtime -replace '\..*')",
            "Avg: $('{0:N2}' -f $avg)",
            "Last: $('{0:N2}' -f $last)",
            "ETA: $('{0:N2}' -f (($avg * $left) / 60))",
            "min ($([string](Get-Date).AddSeconds($avg*$left) -replace '^.* '))"
        ) -join ' '
        Status = "$index of $total ($left left) [$('{0:N2}' -f (($index/$total)*100))%]"
        CurrentOperation = "FILE: $file"
        PercentComplete = ($index/$total)*100
    }
    Write-Progress @WrPrgParam
    $lasttime = Get-Date

    # if filename is longer than 240 characters,
    # map a drive to the current path to shorten the filename
    $null = subst $drive /d
    $path, $newfile = ''
    if ($file.length -gt 240) {
        $path = Split-Path $file
        subst $drive $path
        $newfile = Join-Path $drive $(Split-Path $file -Leaf)
    }

    if ($newfile) {
        & $tool convert "$($newfile -Replace '.tif+$', '.tif[0]')" "C:\Data\$($(Split-Path $newfile -Leaf) -Replace '.tif+$', '.pdf')"
    } else {
        & $tool convert "$($file -Replace '.tif+$', '.tif[0]')" "C:\Data\$($(Split-Path $file -Leaf) -Replace '.tif+$', '.pdf')"
    }

    # un-map the drive (whether we mapped it or not, just to be sure)
    $null = subst $drive /d
}

$result
Community
  • 1
  • 1
Anthony Stringer
  • 1,981
  • 1
  • 10
  • 15
  • Thanks. Something doesn't seem right on my end - when I pipe Get-Files to a dirlist, like this: "(Get-Files -Path $source -Filter Elko*.tif).fullname | Export-Csv .\dirlist.csv -NoTypeInformation", I get a file with this: "Length" "103" "144" "161" "147" "154" "200" "149" "152" "163" "144" "149" "144" "151" "144" "143" – val May 04 '16 at 23:22
  • I tried to add your Get-Files function by turning it into a module using one of the answers here: http://stackoverflow.com/questions/6016436/in-powershell-how-do-i-define-a-function-in-a-file-and-call-it-from-the-powersh – val May 04 '16 at 23:24
  • If the function is not working, you may be able to look at its comments to see how it's using robocopy then just replace the get-files line with a robocopy command and some regex. *edit: try changing -filter to -include – Anthony Stringer May 04 '16 at 23:28