简体   繁体   中英

run powershell as administrator from python

I have a PowerShell script which look like this:

# Define time for report (default is 1 day)
$startDate = (get-date).AddDays(-10)

# Store successful logon events from security logs with the specified dates and workstation/IP in an array
# foreach ($DC in $DCs){
# $slogonevents = Get-Eventlog -LogName Security -ComputerName $DC.Hostname -after $startDate | where {$_.eventID -eq 4624 }
# }

$slogonevents = Get-Eventlog -LogName Security -after $startDate | where {$_.eventID -eq 4624 }

# Crawl through events; print all logon history with type, date/time, status, account name, computer and IP address if user logged on remotely

  $(foreach ($e in $slogonevents){
    # Logon Successful Events
    # Local (Logon Type 2)
    if (($e.EventID -eq 4624 ) -and ($e.ReplacementStrings[8] -eq 2)){
      write-host "Type: Local Logon`tDate: "$e.TimeGenerated "`tStatus: Success`tUser: "$e.ReplacementStrings[5] "`tWorkstation: "$e.ReplacementStrings[11]
    }
    # Remote (Logon Type 10)
    if (($e.EventID -eq 4624 ) -and ($e.ReplacementStrings[8] -eq 10)){
      write-host "Type: Remote Logon`tDate: "$e.TimeGenerated "`tStatus: Success`tUser: "$e.ReplacementStrings[5] "`tWorkstation: "$e.ReplacementStrings[11] "`tIP Address: "$e.ReplacementStrings[18]
    }
}) *>&1 > D:\Cyber_security\Python\test.txt

I want to run this script from python. this script is saved in my D drive.My python script is:

import subprocess, sys

p = subprocess.Popen(["powershell.exe", 
              "D:\Cyber_security\Python\login.ps1"], 
              stdout=sys.stdout)
p.communicate()

but it doesn't work. I need to run powershell as administrator but I don't know how to do it.

You need to nest powershell.exe calls:

  • An outer call that calls PowerShell's Start-Process cmdlet with -Verb RunAs , which allows running any executable with elevation.

  • Since what you want to run with elevation is a .ps1 script, it must be called via powershell.exe , the Windows PowerShell CLI , as in your own attempt, except that you explicitly need to incorporate a Set-Location call to ensure that the script runs in the same working dir. as the caller ( C:\Windows\System32 is the default in Windows PowerShell when Start-Process -Verb RunAs is used).

    • If you don't need this, or if you're using pwsh.exe , the CLI of the cross-platform PowerShell (Core) 7+ edition (which now retains the working dir. by default), the inner call can be simplified to:
    • powershell.exe -Args '-noprofile -file D:\Cyber_security\Python\login.ps1'
p = subprocess.Popen(
  [
    "powershell.exe", 
    "-noprofile", "-c",
    r"""
    Start-Process -Verb RunAs -Wait powershell.exe -Args "
      -noprofile -c Set-Location \`"$PWD\`"; & D:\Cyber_security\Python\login.ps1
      "
    """
  ],
  stdout=sys.stdout
)
p.communicate()

Note:

  • Running a process with elevation:

    • involves an interactive UAC confirmation / credentials prompt that cannot be bypassed (unless UAC is turned off, which would be ill-advised)
    • invariably runs in a new window .
    • prevents direct capture of the elevated process' output streams; you'll have to redirect to (temporary) files instead, which you can do with Start-Process '
      -RedirectStandardOutput / -RedirectStandardError parameters.
  • CLI parameters -noprofile and -c were added: -noprofile suppresses loading of PowerShell's profiles , and -c ( -Command ) explicitly indicates that what follows are PowerShell commands to execute.

  • -Wait was added to the Start-Process call above so as to make the outer powershell.exe call wait for the elevated process to exit before continuing.

  • You don't strictly need powershell.exe + Start-Process -Verb RunAs for launching an elevated process, but it is the most convenient option.

    • A Python-based solution is possible, but involves fairly complex use of the WinAPI - see this blog post
    • Note that while you can technically use runas.exe /user:Administrator utility to create an elevated session, doing so (a) only works with precisely that account, ie the built-in account named Adminstrator , and that account is often disabled in practice (it is disabled by default).
  • An alternative approach would be to modify the .ps1 file to self-elevate on demand (or use a helper .ps1 file that does that) - see this answer

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM