zamsi7
Goto Top

Windows Explorer hängt sich bei Powershell Script auf

Hallo an alle,

hätte mal eine Frage zu Powershell.
Ich habe ein PS Script, welches ich letztendlich in eine .EXE verpackt habe. Dieses Script
blockiert anscheinend den Windows Explorer, wenn es ausgeführt wird. Es kommt bei diversen dingen die Meldung
"Keine Rückmeldung". Diese Meldung kennt man ja bestimmt face-smile Dies passiert nur wenn das Script (Das Programm) gerade ausgeführt wird.
Ich denke mal das Problem hängt mir der MessageBox zusammen.
Hätte hierzu jemand eine Idee was das sein kann? Bzw. hatte das schon jemand? Und kann man das umgehen?

Es handelt sich um einen UpTimeCheck. Also Es wird geprüft, wie lange der jeweilige Rechner bereits läuft und wenn dies (in diesem Fall) über einen Tag ist, bekommt der
Benutzer eine Meldung und wird gefragt ob er den Rechner jetzt neustarten möchte.


Script:


$ProcessActive = Get-Process UpTimeCheck -ErrorAction SilentlyContinue
if($ProcessActive -eq $null)

{
[System.Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms")

$os = Get-WmiObject -Class win32_operatingsystem
$os.ConvertToDateTime($os.LastBootUpTime)
$uptime = (Get-Date) - $os.ConvertToDateTime($os.LastBootUpTime)
$UT_Days = $uptime.Days
$UT_Hours = $uptime.Hours
$UT_Minutes = $uptime.Minutes


if($UT_Days -ge 1){

$UserResponse = [System.Windows.Forms.MessageBox]::Show("Ihr PC läuft seit $UT_Days Tagen und $UT_Hours Stunden. Damit Ihr Gerät optimal läuft empfehlen wird Ihnen einen Neustart durchzuführen.
Wollen Sie jetzt neustarten?
(Speichern Sie zuvor alle geöffneten Daten!!)", 'Uptime Warning', 'YesNo', 'Warning')
}
if ($UserResponse -eq "YES" )
{
Restart-Computer
}
else
{
[System.Windows.Forms.MessageBox]::Show("Starten Sie Ihren PC bitte bei der nächsten Gelegenheit neu.", "Uptime Warning", "0", "Warning")
}
}
else
{
}


Danke schon mal!

LG Simon

Content-ID: 317132

Url: https://administrator.de/contentid/317132

Ausgedruckt am: 22.11.2024 um 03:11 Uhr

Pjordorf
Pjordorf 07.10.2016 um 10:21:30 Uhr
Goto Top
Hallo,

Zitat von @zamsi7:
Ich habe ein PS Script, welches ich letztendlich in eine .EXE verpackt habe.
Wie, womit?

"Keine Rückmeldung".
Bedeutet das es keine Zeit hat sich selbst zu aktualisieren bzw. das es läuft....

Ich denke mal das Problem hängt mir der MessageBox zusammen.
Wird diese denn überhaupt dargestellt? Oder liegt die einfach hinter ein Fenster versteckt (ALT+TAB mal genutzt)?

wird gefragt ob er den Rechner jetzt neustarten möchte.
Warum darf ein Rechner nicht länger als ein Tag laufen? Diese angebliche Krankheit wurde mit Win 2000 ausgemerzt.

Gruß,
Peter
atze187
atze187 07.10.2016 um 10:31:03 Uhr
Goto Top
Läuft das Skript denn wie erwartet wenn es in seinem natürlichen Zustand als Skript ausgeführt wird?
Kraemer
Kraemer 07.10.2016 um 11:21:07 Uhr
Goto Top
Moin,
Zitat von @zamsi7:
Ich habe ein PS Script, welches ich letztendlich in eine .EXE verpackt habe.
Und warum hast du das gemacht?

Gruß Krämer
SaschaRD
SaschaRD 07.10.2016 aktualisiert um 15:08:09 Uhr
Goto Top
Hallo Simon,

ab Powershell 3.0 kannst du Get-CimInstance verwenden.
Hier ist ein Beispiel was ich kurz zusammen geklöppelt habe und mit dem PowerGUI Script Editor in eine .Exe Datei kompiliert habe; funktioniert 1A.
[System.Reflection.Assembly]::LoadWithPartialName('System.Windows.Forms') | Out-Null  

$systemUpTime = (Get-CimInstance -ClassName Win32_OperatingSystem).LastBootUpTime
$currentTime = date
$timeDifference = New-TimeSpan -Start $systemUpTime -End $currentTime
if($timeDifference.Days -ge "1"){  
$userResponse = [System.Windows.Forms.MessageBox]::Show("Ihr PC läuft seit $($timeDifference.Days) Tagen und $($timeDifference.Hours) Stunden.`nDamit Ihr Gerät optimal läuft empfehlen wird Ihnen einen Neustart durchzuführen.`nWollen Sie jetzt neustarten?`n(Speichern Sie zuvor alle geöffneten Daten!!)", 'Uptime Warning', 'YesNo', 'Warning')  
if($userResponse -eq "Yes"){  
    #Restart-Computer
  } else {
    [System.Windows.Forms.MessageBox]::Show("Starten Sie Ihren PC bitte bei der nächsten Gelegenheit neu.", "Uptime Warning", "0", "Info") | Out-Null  
  }
}

Schönes Wochenende und Gruß, Sascha
colinardo
colinardo 07.10.2016 aktualisiert um 18:27:37 Uhr
Goto Top
Hallo Simon,
Ich habe ein PS Script, welches ich letztendlich in eine .EXE verpackt habe.
ein vernünftiger Admin macht sowas wirklich nicht. Wenn dich nur das Powershell-Fenster stört, das lässt sich auch leicht aus einem Powershell-Skript heraus verstecken oder direkt beim Aufruf des Skripts.
Wenn man wirklich eine EXE haben möchte macht man das korrekterweise direkt als native App C#/VB.net (mehr Zeilen sind das dort auch nicht).
Dim dLastBootUp As DateTime = System.Management.ManagementDateTimeConverter.ToDateTime((New System.Management.ManagementObjectSearcher("Select LastBootUpTime from Win32_OperatingSystem")).Get()(0).Properties("LastBootUpTime").Value)  
Dim diff As TimeSpan = DateTime.Now - dLastBootUp
If diff.Days >= 2 Then
    If MsgBox("Ihr PC läuft seit " & diff.Days & " Tagen und " & diff.Hours & " Stunden. Damit Ihr Gerät optimal läuft empfehlen wird Ihnen einen Neustart durchzuführen. Wollen Sie jetzt neustarten?(Speichern Sie zuvor alle geöffneten Daten!!)", MsgBoxStyle.YesNo Or MsgBoxStyle.Information, "Uptime Warning") = MsgBoxResult.Yes Then  
        Process.Start("shutdown", "/s /t 0")  
    Else
        MsgBox("Starten Sie Ihren PC bitte bei der nächsten Gelegenheit neu.", MsgBoxStyle.Exclamation, "Uptime Warning")  
    End If
End if
Das wäre wesentlich zielgerichteter, denn solche Wrapper bringen nur Probleme auf der einen Seite wie du sie gerade erlebst und auf der anderen Seite finden Virenscanner solche Files gar nicht schön und blockieren gerne manche Funktionsaufrufe. Das Get-Process ist z.B. ein solcher Kandidat der dann gerne mal hängen bleibt.

Grüße Uwe


p.s. VB.Net oder C# Anwendungen kannst du auch direkt mit der Powershell zu einer nativen EXE kompilieren:
$code = @"  
Imports System
Imports System.Windows.Forms
Imports System.Management
Imports System.Diagnostics

Module CheckLastBootUp
    Sub Main()
        Dim dLastBootUp As DateTime 
        dim objCol as ManagementObjectCollection = (New ManagementObjectSearcher("Select LastBootUpTime from Win32_OperatingSystem")).Get()  
        for each obj as ManagementObject in objCol
            dLastBootUp = ManagementDateTimeConverter.ToDateTime(obj.Properties("LastBootUpTime").Value)  
        Next
        Dim diff As TimeSpan = DateTime.Now - dLastBootUp
        If diff.Days >= 2 Then
            If MessageBox.Show(CStr("Ihr PC läuft seit " & diff.Days & " Tagen und " & diff.Hours & " Stunden. Damit Ihr Gerät optimal läuft empfehlen wird Ihnen einen Neustart durchzuführen. Wollen Sie jetzt neustarten?(Speichern Sie zuvor alle geöffneten Daten!!)"), "Uptime Warning", MessageBoxButtons.YesNo, MessageBoxIcon.Information) = 6 Then  
                Process.Start("shutdown", "/s /t 0")  
            Else
                MessageBox.Show("Starten Sie Ihren PC bitte bei der nächsten Gelegenheit neu.", "Uptime Warning", MessageBoxButtons.OK, MessageBoxIcon.Exclamation)  
            End If
        End If
    End Sub
End Module
"@  

Add-Type -TypeDefinition $code -OutputAssembly "CheckLastBootUp.exe" -OutputType WindowsApplication -Language VisualBasic -ReferencedAssemblies 'System.Management','System.Windows.Forms'  

pps. Warum müsst Ihr neure PCs alle 2 Tage neu starten face-smile habt Ihr so unzuverlässige PCs?