Mein Gedanke ist, eine Warteschlange durch Erstellen einer Sperrdatei pro neuer Instanz Ihres Skripts einzurichten. Bei der Ausführung des Skripts wird ein Verzeichnis überprüft, das der Verfolgung der Warteschlange auf vorhandene Instanzen des Skripts dient. Wenn es keine gibt, fügt sich das Skript in die Warteschlange ein, führt eine Aktion aus (führt Ihren Code aus) und bereinigt dann seine Sperre. Wenn Sperren vorhanden sind, wird am Ende der Warteschlange eine neue hinzugefügt, und die Instanz prüft endlos, bis sie sich am Anfang der Warteschlange befindet.
Auf diese Weise können Sie dasselbe Skript mehrmals ausführen, wobei sich alle einzeln durch Überprüfen der extern verfügbaren Warteschlange verhalten.
Die Sperrdateien sind wie folgt aufgebaut: Index, Trennzeichen ("_"), Prozess-ID.
Clear-Host
function New-Lock ([int] $index) {
$newLock = "$index" + "_" + $pid + ".lck"
New-Item $queue$newLock | Out-Null
}
$queue = "C:\locks\"
# find the end of the stack
$locks = gci $queue *.lck | sort | select -expandproperty name
# if locks exist, find the end of the stack by selecting the index of the last lock
if($locks) {
# gets the last lock file, selects the index by splitting on the delimiter
[int]$last = [convert]::ToInt32(($locks | select -last 1).Split("_")[0],10)
# add the lock to the end of the stack
New-Lock ($last + 1)
}
# if no locks exist, create one at the top of the stack
else {
New-Lock 0
}
# check if we're at the top of the stack
do {
$locks = gci $queue *.lck | sort | select -expandproperty name
# this is the PID on the top of the stack
[int]$top = [convert]::ToInt32(($locks | select -first 1).Split("_")[1].Split(".")[0],10)
write-verbose "not at the top..."
sleep 1
} until ($pid -eq $top)
# if we're here, we've been to the top. it's our turn to do something
Write-Verbose "we've reached the top!"
# <do something. put your code here>
# might be good to add some Start-Sleep here
# </do something put your code here>
# now that we're done, let's delete our lock
gci $queue | select -first 1 | Remove-Item
Unten sehen Sie ein fiktives Timeline-Beispiel, in dem Sie drei Dateien heruntergeladen haben (ich habe zufällige PIDs ausgewählt).
- Datei 1 wird heruntergeladen und startet das Skript. Es sind keine Sperren vorhanden. Erstellen Sie die Sperre "0_19831". Wir sind an der Spitze des Stapels, sodass Ihr Code ausgeführt wird. Dies ist ein großes E-Book, daher dauert die Ausführung Ihres Dateiübertragungscodes eine volle Minute.
- Datei 2 wird heruntergeladen und startet das Skript. Sperre (n) vorhanden Erstellen Sie die Sperre "1_332". Wir sind nicht an der Spitze des Stapels, also werden wir warten
do/until
und weiter nachsehen, bis wir an erster Stelle stehen.
- Datei 1 wurde kopiert. Sperre "0_19831" löschen.
- Datei 3 wird heruntergeladen und startet das Skript. Sperre (n) vorhanden Erstellen Sie die Sperre "2_7582". Wir sind nicht an der Spitze des Stapels, warten Sie, bis wir es sind.
- Datei 2 wurde kopiert. Sperre "1_332" löschen.
- Datei 3 wurde kopiert. Sperre "2_7582" löschen.
Diese Lösung ist nicht kugelsicher, funktioniert jedoch je nach Maßstab.