Como passar um argumento para uma tarefa agendada do Windows com espaços nele

13

Eu preciso configurar uma tarefa agendada do Windows. Aceita 1 parâmetro / argumento que é um caminho e pode conter espaços. Minha tarefa agendada não funciona - "quebra" o parâmetro no primeiro espaço.

Se eu executá-lo no Prompt de Comando, posso apenas encapsular o argumento em "" e ele funciona bem, no entanto, isso não funciona na IU da Tarefa Agendada.

por exemplo. C:\Program Files\xyz\FTP File Transfer\FTPFileTransferTask.exe "C:\Program Files\xyz\The Interface\Folder Path"

Eu tentei quebrar o argumento com "" '' [] () e tentei preencher os espaços com% 20, ~ 1 etc. sem sorte.

Eu sei de uma solução para criar um arquivo "bat" e usar o "" meu argumento, mas não quero adicionar mais complexidade.

Eu tentei no Windows 7 e no Windows 2008 Server e ambos falharam. Parece não haver discussões sobre isso?

    
por Rodney 14.04.2011 / 07:24

7 respostas

5

Eu trabalhei com tarefas agendadas e você geralmente coloca os argumentos em sua própria caixa de entrada de texto. Isso significa que você aponta a ação para o campo program / script aponta para o exe e o campo "Add Arguments" deve ter todos os parâmetros. ( fonte )

Euacreditoqueestecomportamentofoiadicionadoparaevitarespaçosnocaminhodoarquivoparaoexecausandoproblemas.

EufaçoissootempotodocomscriptsdoPowerShell.Aquiestáumexemplo:

  • Programa/script:powershell.exe
  • Adicionarargumentos:-command"& C: \ HSD - Copy \ logoffstudents.ps1 '" -NonInteractive
  • Iniciar em: em branco
por 19.05.2011 / 22:24
4
schtasks.exe /create /SC WEEKLY /D SUN /SD 11/12/2015 /ST 12:00:00 /TN "taskname" /TR "'c:\program files(x86)\task.exe' Arguments"

Observe o uso de ' no caminho de um arquivo a ser executado.

    
por 12.04.2016 / 07:46
2

Nesse caso, você poderia contornar o problema passando o parâmetro path no formato 8.3.

Você pode descobrir o formato 8.3 do seu caminho abrindo um prompt de comando e emitindo o comando dir /x na raiz da sua unidade.

Você deve ver uma entrada semelhante a

11/04/2011  12:10    <DIR>          PROGRA~1     Program Files

para o diretório de arquivos de programas.

Em seguida, altere o diretório para Arquivos de Programas com cd "Program Files "seguido por cd xyz e emita novamente dir /x para encontrar o nome do formato 8.3 para "A Interface" e assim por diante.

Seu caminho final para o exemplo que você deu seria algo como:

C:\PROGRA~1\XYZ\THEINT~1\FOLDER~1
    
por 14.04.2011 / 08:31
1

Eu tive um problema semelhante com o VLC, que eu estava usando no Windows XP. O truque é colocar o argumento do comando cmd entre aspas duplas.

Aqui está um exemplo do que eu usei (agendando uma gravação às 15:00):

at 15:00 cmd /c ""C:\Programmi\VideoLAN\VLC\vlc.exe dvb-t://frequency=698000000 :program=4006 :run-time=5 --sout "C:\Documents and Settings\UserName\Documents\Video\VLC\test.mpg"""

Observe o uso de aspas duplas logo após /c e no final do comando (após .mpg ). O argumento com espaços neste caso é "C:\Documents and Settings\..."

    
por 27.10.2013 / 23:45
1

Pode ajudar a entender o problema de uma perspectiva diferente. Digamos que você seja o programador encarregado de adicionar um agendador de tarefas ao Windows. Como você faria? Você tem vários problemas para enfrentar: Se a tarefa for executada como alguém que não seja o usuário logado, você deve irritar o usuário logado com algum erro de pop-up? E se não houver usuário logado no momento em que a tarefa é executada? E quanto à diferença entre um programa GUI e um programa de console? GUI não tem stdin, stdout e stderr; o conceito não tem sentido neles. E quanto aos programas internos ou externos ao COMMAND.COM/CMD.EXE? Ou outros mecanismos de script? E quanto aos caminhos com espaços no nome do comando? Ou nos parâmetros (opções / argumentos)? (Como você está tentando lidar agora ..)

Embora eu não esteja 100% certo sobre os internos ou detalhes técnicos completos neste caso, as respostas parecem ser ... As tarefas são executadas em uma sessão isolada, não interativa, que não pode interagir com o usuário atualmente conectado (caso existam); É executado esperando que não haja saída do console, já que não é interativo, não pode simplesmente interromper qualquer usuário logado para mostrar a saída, de qualquer forma (e se houver saída, stdin é o bitbucket / NULL, stdout e stderr são logados para a facilidade de registro do sistema); Espaços são manipulados contornando o problema: o nome do comando é EXATAMENTE como está, e os parâmetros são passados para o comando são especificados em outra caixa de entrada nas propriedades da Tarefa.

O que significa que sua tarefa deve ser executada como se fosse um daemon (no Un * x world). Tudo é estático e preciso. O nome do comando é o nome real do comando, sem nenhum parâmetro. Isso geralmente inclui interpretadores de comandos / scripts, como o CMD.EXE! Os parâmetros, se houver, são especificados em outro lugar e devem ser conhecidos quando você configura a tarefa (ou seja, não é possível alterar os parâmetros "on-the-fly"). E assim por diante.

Portanto, se você quiser incluir parâmetros, terá que usar a seção de parâmetros para especificar os parâmetros. O Agendador de Tarefas não tenta analisar o nome do comando para dividi-lo em "comando" e "args", como os programas de linha de comando. Apenas o trata como um nome de comando grande e completo. Da mesma forma, se você quiser parâmetros variáveis, como usar% 1 ..% n em arquivos BATCH, não poderá fazer isso no próprio Agendador de Tarefas; Você terá que encontrar outro caminho. (Observe que você também não pode usar variáveis de ambiente, pois o ambiente transmitido ao programa depende do ambiente em que a tarefa foi iniciada, NÃO do ambiente "atual".) Você pode usar um arquivo temporário para salvar os parâmetros, mas desde deve especificar um nome de arquivo estático nas propriedades da tarefa, o que acontece quando você está em uma rede com 5000 usuários e quatro deles tentam executar a mesma tarefa ao mesmo tempo? Eles vão todos se atrapalhar tentando escrever no mesmo arquivo temporário ao mesmo tempo, provavelmente não o que você queria. (Existem soluções para esse problema também, mas isso está indo longe demais do escopo desta pergunta e resposta ..)

Assim, a resposta final: No caso simples - o caminho que você deseja passar como um parâmetro é estático e não muda - você precisa especificar os parâmetros na propriedade Task apropriada (Argumentos) e não no Programa. / Caixa de script, ou use um arquivo em lotes. Em um caso mais complexo - você precisará fazer a pergunta certa ou pesquisar como os daemons funcionam e como usar travamentos / semáforos e outros para comunicação entre processos (IPC).

Boa sorte.

    
por 20.04.2015 / 21:48
1

Uma maneira de conseguir isso é usar o powershell na linha de comando.

Adicione este código a um arquivo chamado MyModule.psm1.

$TASK_STATE_UNKNOWN   = 0;
$TASK_STATE_DISABLED  = 1;
$TASK_STATE_QUEUED    = 2;
$TASK_STATE_READY     = 3;
$TASK_STATE_RUNNING   = 4;
Function Run-Task(
        [ValidateNotNullOrEmpty()][string]
        [Parameter(Mandatory=$true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)]
        $ComputerName, 
        [ValidateNotNullOrEmpty()][string]
        [Parameter(Mandatory=$true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)]
        $Foldername, 
        [ValidateNotNullOrEmpty()][string]
        [Parameter(Mandatory=$true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)]
        $Taskname, 
        [int] $maxwait = 0, 
        [string[]]
        [Parameter(Mandatory=$false, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)]
        $TaskParameters = $null
    ){
    $TaskScheduler = New-Object -ComObject Schedule.Service
    $TaskScheduler.Connect($ComputerName)
    $ScheduledTaskFolder = $TaskScheduler.GetFolder($Foldername)
    $ScheduledTask = $ScheduledTaskFolder.GetTask($TaskName)

    if(-not $ScheduledTask) {
        return $Null
    }

    $ScheduledTask.Enabled = $True
    $ScheduledTask.Run($TaskParameters)

    if($maxwait -gt 0){
        $seconds = 5
        $i = 0;
        Start-Sleep -Seconds $seconds
        while ($ScheduledTask.State -eq $TASK_STATE_RUNNING)
        {
            if(($i * $seconds) -gt $maxwait) { 
                break; 
            } 
            Start-Sleep -Seconds $seconds        
            $i++;
        }
    }
    return $ScheduledTask
}

Export-ModuleMember -Variable "TASK_STATE*"
Export-ModuleMember -Function "Run-*"

Em seguida, a partir da linha de comando OU de um arquivo ps1, você pode executar:

Import-Module $(Get-Item .\MyModule.psm1 | Resolve-Path -Relative) -DisableNameChecking -Force

$task = Run-Task -ComputerName "$env:COMPUTERNAME" -Taskname "Foo" -Foldername "\" -TaskParameters "test", "Tim C", $(Get-Date -format G)

Cada item respectivo na matriz taskparameters seria passado como $ (Arg0), $ (Arg1) e $ (Arg2).

    
por 15.02.2017 / 14:27
0

Defina sua tarefa agendada da seguinte forma

cmd / c C: \ Arquivos de programas \ xyz \ FTP Transferência de arquivos \ FTPFileTransferTask.exe "C: \ Arquivos de programas \ xyz \ A interface \ Caminho da pasta"

    
por 28.04.2014 / 15:52