غير قادر على حذف دليل به أقواس مربعة في الاسم باستخدام WinSCP وPowerShell

StackOverflow https://stackoverflow.com//questions/22032008

  •  21-12-2019
  •  | 
  •  

سؤال

أحاول كتابة برنامج PowerShell النصي الذي يحذف تلقائيًا الدلائل الفارغة على خادم FTP الخاص بنا.ليس لدي أي وصول مباشر إلى الخادم الذي توجد عليه الدلائل - لا يمكنني الوصول إليها إلا عبر FTP.لهذا السبب، قمت بكتابة برنامج PowerShell النصي الذي يستخدم مجموعة WinSCP .NET لـ (محاولة) حذف الدلائل الفارغة.ومع ذلك، لدي مشكلة، حيث أن العديد من الدلائل الموجودة على الخادم تحتوي على أقواس مربعة في اسم الدليل.

على سبيل المثال، يمكن استدعاء اسم الدليل: [a]153432

هناك الكثير من هذه الأدلة، ومن هنا رغبتي في كتابة برنامج نصي لحذفها.يحدث هذا لأنه تم إنشاؤها بواسطة برنامج يستخدم رقمًا لإنشاء الدلائل التي يتطلبها.من أجل العمل على هذا البرنامج، قمت بإنشاء دليل فارغ

/latest/[b]test

برنامجي يذهب مثل هذا:

# program to test deletion of directories with square-brackets in the name.

$HOSTNAME="myftpservername"
$USERNAME="myftpusername"
$PASSWORD="myftppassword"
$DLL_LOCATION="C:\Program Files (x86)\WinSCP\WinSCPnet.dll"
$LOCAL_DIRECTORY="C:\testdir\extended\baseroot"

# Load WinSCP .NET assembly
[Reflection.Assembly]::LoadFrom($DLL_LOCATION) | Out-Null

# Session.FileTransferred event handler

try
{
    $sessionOptions = New-Object WinSCP.SessionOptions
    $sessionOptions.Protocol = [WinSCP.Protocol]::ftp
    $sessionOptions.HostName = $HOSTNAME
    $sessionOptions.UserName = $USERNAME
    $sessionOptions.Password = $PASSWORD

    $session = New-Object WinSCP.Session
    try
    {
        # Connect
        $session.Open($sessionOptions)

        $remoteFileWithUnixPath = "/latest/[b]test"

        $removalResult = $session.RemoveFiles($remoteFileWithUnixPath)
        if ($removalResult.IsSuccess)
        {
            Write-Host ("Removal of remote file {0} succeeded" -f $remoteFileWithUnixPath)
        }
        else
        {
            Write-Host ("Removal of remote file {0} failed" -f $remoteFileWithUnixPath)
        }
    }
    finally
    {
        # Disconnect, clean up
        $session.Dispose()
    }
    exit 0
}
catch [Exception]
{
    Write-Host $_.Exception.Message
    exit 1
}

وعندما أقوم بتشغيله تظهر الرسالة التالية:

PS C:\Users\dbuddrige\Documents\dps> .\delete-squarebracket-dir.ps1
Removal of remote file /latest/[b]test succeeded

ومع ذلك، لا يتم حذف الدليل.

لقد حاولت أيضًا تحديد اسم الدليل بمحددات مثل:

$remoteFileWithUnixPath = "/latest/\[b\]test"

لكن هذا فشل أيضًا (لكنه على الأقل يقول ذلك):

PS C:\Users\dbuddrige\Documents\dps> .\delete-squarebracket-dir.ps1
Removal of remote file /latest/\[b\]test failed

ولكن، إذا قمت بتغيير اسم الدليل [والمتغير $remoteFileWithUnixPath] إلى شيء من هذا القبيل

/latest/foo

ومن ثم إعادة تشغيل البرنامج، فإنه يحذف الدليل /latest/foo بخير.

هل لدى أي شخص أي أفكار عما يجب علي فعله حتى ينجح هذا؟


تمت الإشارة إلى الإجابة على هذا السؤال بواسطة مارتن بريكريل [شكرًا!]

رمز العمل الكامل يلي:

# program to test deletion of directories with square-brackets in the name.

$HOSTNAME="myftpservername"
$USERNAME="myftpusername"
$PASSWORD="myftppassword"
$DLL_LOCATION="C:\Program Files (x86)\WinSCP\WinSCPnet.dll"
$LOCAL_DIRECTORY="C:\testdir\extended\baseroot"

# Load WinSCP .NET assembly
[Reflection.Assembly]::LoadFrom($DLL_LOCATION) | Out-Null

# Session.FileTransferred event handler

try
{
    $sessionOptions = New-Object WinSCP.SessionOptions
    $sessionOptions.Protocol = [WinSCP.Protocol]::ftp
    $sessionOptions.HostName = $HOSTNAME
    $sessionOptions.UserName = $USERNAME
    $sessionOptions.Password = $PASSWORD

    $session = New-Object WinSCP.Session
    try
    {
        # Connect
        $session.Open($sessionOptions)

        $remoteFileWithUnixPath = "/latest/[b]test"

        $removalResult = 
            $session.RemoveFiles($session.EscapeFileMask($remoteFileWithUnixPath))
        if ($removalResult.IsSuccess)
        {
            Write-Host ("Removal of remote file {0} succeeded" -f $remoteFileWithUnixPath)
        }
        else
        {
            Write-Host ("Removal of remote file {0} failed" -f $remoteFileWithUnixPath)
        }
    }
    finally
    {
        # Disconnect, clean up
        $session.Dispose()
    }
    exit 0
}
catch [Exception]
{
    Write-Host $_.Exception.Message
    exit 1
}
هل كانت مفيدة؟

المحلول

بعض أساليب تجميع WinSCP .NET، بما في ذلك Session.RemoveFiles, ، اقبل قناع ملف، وليس مسارًا بسيطًا.

الأقواس المربعة لها معنى خاص في قناع الملف.

يجب عليك دائمًا استخدام RemotePath.EscapeFileMask طريقة على مسارات الملفات، قبل تمريرها إلى أساليب التجميع.

نصائح أخرى

سأستخدم تسلسل الهروب في سطر الأوامر:

Remove-Item 'C:\Scripts\Test`[1`].txt'

أو استخدم -LiteralPath معامل.

Remove-Item -LiteralPath C:\scripts\test[1].txt

لا تحاول المعلمة -LiteralPath تحويل السلسلة.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top