Powershell:从任务计划程序运行脚本时 Get-StoredCredential 不起作用

Powershell:从任务计划程序运行脚本时 Get-StoredCredential 不起作用

我正在编写一个 powershell 脚本,该脚本将定期运行以备份远程文件夹的内容。该远程文件夹作为 WebDav 共享映射到我的 Windows 驱动器 G:\。

这个帖子这个

  • 映射驱动器无法直接访问,并且
  • 应该通过 UNC 来访问它们。

通过 UNC 访问远程文件夹需要我提供凭证。我不希望它们以纯文本形式存在,因此我尝试访问它们通过凭证管理器.我已这样做了安装模块 CredentialManager,现在获取凭据并挂载远程文件夹

  • 如果我手动运行脚本(从 MS Code 内部)就可以正常工作
    • 我的 powershell 版本是 7.3.6
  • 如果脚本是从任务计划程序运行的,则会失败

为什么会这样?我该怎么做才能从计划脚本访问远程文件夹?

脚本access.ps1:

# MAIN ########################################################################
$debuglog = $PSScriptRoot + "\" + "debuglog.txt"
#$debuglog = $null
$PSDefaultParameterValues = @{'Out-File:Encoding' = 'utf8'}   # https://stackoverflow.com/questions/64757125/how-to-specify-file-format-for-powershell-tee-command
                                                              # https://stackoverflow.com/questions/40098771/changing-powershells-default-output-encoding-to-utf-8
                                                              # https://stackoverflow.com/questions/30606929/tee-with-utf-8-encoding

# Info:
echo "$(get-date -format 'yyMMdd-HHmmss') ##################################################" >> $debuglog 
echo "Which domain/account?: <$(whoami)>"   >> $debuglog
echo "Available drives:"     $(get-psdrive) >> $debuglog

# OK, when drive does not show up when script is run from task scheduler, then let's map it:
$credential = Get-StoredCredential -Target "webdav.mc.gmx.net"
echo "Credential: _$credential_" >> $debuglog
if ($credential) {
  echo "Credentials found." >> $debuglog  
  $username = $credential.UserName
  $password = $credential.GetNetworkCredential().Password
    
  $driveLetter = "Y"
  $networkPath = "\\webdav.mc.gmx.net@SSL\DavWWWRoot\myData\"
  remove-psdrive       $driveLetter
  New-PSDrive    -Name $driveLetter -PSProvider FileSystem -Root $networkPath -Credential $credential
}
else {
  echo "Accessing credentials failed." >> $debuglog  
}
echo "psdrives:" $(get-psdrive) >> $debuglog
echo "Dir:     " $(dir y:\) >> $debuglog
remove-psdrive       $driveLetter

echo "Exit."                >> $debuglog
exit 

脚本的输出:

  • 左:当“手动”运行时,即从 MS Code 运行
  • 右图:通过任务调度程序运行时
    • 用户名相同
    • 驱动器 G:\ 不可用
    • 访问凭证失败

在此处输入图片描述

调度程序的 XML:

<?xml version="1.0" encoding="UTF-16"?>
<Task version="1.4" xmlns="http://schemas.microsoft.com/windows/2004/02/mit/task">
  <RegistrationInfo>
    <Date>2023-07-31T23:41:50.6178473</Date>
    <Author>DELFIN7\Martin</Author>
    <URI>\Access2</URI>
  </RegistrationInfo>
  <Triggers>
    <CalendarTrigger>
      <StartBoundary>2023-07-31T23:40:09</StartBoundary>
      <Enabled>true</Enabled>
      <ScheduleByMonth>
        <DaysOfMonth>
          <Day>13</Day>
        </DaysOfMonth>
        <Months>
          <January />
          <February />
          <March />
          <April />
          <May />
          <June />
          <July />
          <August />
          <September />
          <October />
          <November />
          <December />
        </Months>
      </ScheduleByMonth>
    </CalendarTrigger>
  </Triggers>
  <Principals>
    <Principal id="Author">
      <UserId>S-1-5-21-48XXXXX20-12XXXXXX13-21XXXXXX82-1001</UserId>
      <LogonType>Password</LogonType>
      <RunLevel>LeastPrivilege</RunLevel>
    </Principal>
  </Principals>
  <Settings>
    <MultipleInstancesPolicy>Parallel</MultipleInstancesPolicy>
    <DisallowStartIfOnBatteries>false</DisallowStartIfOnBatteries>
    <StopIfGoingOnBatteries>false</StopIfGoingOnBatteries>
    <AllowHardTerminate>true</AllowHardTerminate>
    <StartWhenAvailable>true</StartWhenAvailable>
    <RunOnlyIfNetworkAvailable>false</RunOnlyIfNetworkAvailable>
    <IdleSettings>
      <StopOnIdleEnd>true</StopOnIdleEnd>
      <RestartOnIdle>false</RestartOnIdle>
    </IdleSettings>
    <AllowStartOnDemand>true</AllowStartOnDemand>
    <Enabled>true</Enabled>
    <Hidden>false</Hidden>
    <RunOnlyIfIdle>false</RunOnlyIfIdle>
    <DisallowStartOnRemoteAppSession>false</DisallowStartOnRemoteAppSession>
    <UseUnifiedSchedulingEngine>true</UseUnifiedSchedulingEngine>
    <WakeToRun>false</WakeToRun>
    <ExecutionTimeLimit>PT0S</ExecutionTimeLimit>
    <Priority>7</Priority>
    <RestartOnFailure>
      <Interval>PT2H</Interval>
      <Count>120</Count>
    </RestartOnFailure>
  </Settings>
  <Actions Context="Author">
    <Exec>
      <Command>C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe</Command>
      <Arguments>"D:\Datenbanken\Datensicherung\myRoboBak\Executables\access.ps1"</Arguments>
      <WorkingDirectory>D:\Datenbanken\Datensicherung\myRoboBak\Executables\</WorkingDirectory>
    </Exec>
  </Actions>
</Task>

答案1

您需要将凭据添加到凭据管理器作为用于运行计划任务的帐户,然后它就可以正常运行。

将其添加到脚本顶部:

Import-Module CredentialManager

New-StoredCredential -Target "webdav.mc.gmx.net" -Username "Username" -Password "Password" -Persist LocalMachine

保存并运行该脚本一次作为计划任务。如果成功,您可以删除存储的 New-StoredCredential 行,然后它应该可以正常工作。

相关内容