Dateien nach und nach verschieben
Hallo zusammen,
ich hoffe, es kann mir jemand helfen.
Ich finde einfach die Lösung nicht.
Ich muss aus einem Quellordner knapp 6000 Dateien nach und nach, max. 50 Dateien alle 10 Minuten, in ein Zielordner verschieben.
In dem Zielordner werden die Dateien abgeholt und verarbeitet.
Meine Idee wäre es den Task Scheduler zu nutzen und alle 10 Minuten ein PowerShell Script oder eine Batchdatei zu starten, die dann jeweils 50 Dateien vom Quell- zum Zielordner verschiebt.
Hat jemand eine Idee wie das Script oder die Batchdatei aussehen könnte?
ich hoffe, es kann mir jemand helfen.
Ich finde einfach die Lösung nicht.
Ich muss aus einem Quellordner knapp 6000 Dateien nach und nach, max. 50 Dateien alle 10 Minuten, in ein Zielordner verschieben.
In dem Zielordner werden die Dateien abgeholt und verarbeitet.
Meine Idee wäre es den Task Scheduler zu nutzen und alle 10 Minuten ein PowerShell Script oder eine Batchdatei zu starten, die dann jeweils 50 Dateien vom Quell- zum Zielordner verschiebt.
Hat jemand eine Idee wie das Script oder die Batchdatei aussehen könnte?
Bitte markiere auch die Kommentare, die zur Lösung des Beitrags beigetragen haben
Content-ID: 82440337378
Url: https://administrator.de/contentid/82440337378
Ausgedruckt am: 21.11.2024 um 12:11 Uhr
14 Kommentare
Neuester Kommentar
Moin,
das wird mit allergrößter Wahrscheinlichkeit nicht so funktionieren, wie du dir das vorstellst.
Da muss man sich ein bischen mehr Mühe geben und das Ganze in ein Skript packen, welches dafür sorgt, das es zu keinem Fehler kommt.
Andersherum ist das Ganze auch per Hand in gerade einmal 2,5 Tagen erledigt.
Gruß
das wird mit allergrößter Wahrscheinlichkeit nicht so funktionieren, wie du dir das vorstellst.
Da muss man sich ein bischen mehr Mühe geben und das Ganze in ein Skript packen, welches dafür sorgt, das es zu keinem Fehler kommt.
Andersherum ist das Ganze auch per Hand in gerade einmal 2,5 Tagen erledigt.
Gruß
Moin,
das wäre schnell hingeschrieben mein Ansatz. Keine Garantie und nicht getestet:
hth
Erik
das wäre schnell hingeschrieben mein Ansatz. Keine Garantie und nicht getestet:
$quellordner = x:\quelle
$zielordner = x:\ziel
do {
$files = Get-ChildItem -path $quellordner-file | select -First 50
foreach($file in $files) {
try {
move-item -Path $file.fullname -Destination $zielordner\$file.name
}
catch {
#Fehlerbehandlung, wenn das schief geht
}
}
Start-Sleep -Seconds 600
} while($(get-childitem -Path $quellordner -file))
hth
Erik
Hallo Pit-80,
das ist gar nicht so schwer.
Du gehst in einer Schleife über alle Dateien und fügst nach dem kopieren einer Datei zu Sicherheit 13 sek Pause ein,
bevor die nächste Datei kopiert wird.
Das wäre wahrscheinlich der einfachste Weg.
10 min = 600 sek 600/50 = 12 sek um das Limit von 50 nicht zu überschreiten.
Deshalb habe ich 13 sek vorgeschlagen.
Das Ergebnis sieht dann so aus:
Das ist jetzt nicht schön oder elegant, sollte aber funktionieren.
Grüße vom it-frosch
das ist gar nicht so schwer.
Du gehst in einer Schleife über alle Dateien und fügst nach dem kopieren einer Datei zu Sicherheit 13 sek Pause ein,
bevor die nächste Datei kopiert wird.
Das wäre wahrscheinlich der einfachste Weg.
10 min = 600 sek 600/50 = 12 sek um das Limit von 50 nicht zu überschreiten.
Deshalb habe ich 13 sek vorgeschlagen.
$QUELLE = "C:\TMP\"
$ZIEL = "C:\TMP_ZIEL\"
$Abstand_in_sek = 13
$count = 0
$Dateien = Get-ChildItem -Path $QUELLE | %{$_.Name}
foreach ($datei in $Dateien) {
# eine Datei kopieren
Copy-Item -Path "$($QUELLE)$datei" -Destination "$($ZIEL)"
$datei
# Pause einbauen
Start-Sleep -Seconds $Abstand_in_sek
# Zeit anzeigen
Get-Date
# Zähler hochzählen
$count=$count+1
}
Write-host "$($count) Dateien kopiert"
Das Ergebnis sieht dann so aus:
datei1
Dienstag, 23. Juli 2024 17:19:45
datei2
Dienstag, 23. Juli 2024 17:19:58
datei3
Dienstag, 23. Juli 2024 17:20:11
datei4
Dienstag, 23. Juli 2024 17:20:24
4 Dateien kopiert
Das ist jetzt nicht schön oder elegant, sollte aber funktionieren.
Grüße vom it-frosch
Hallo,
wir haben so was Ähnliches am Laufen, nur nicht als Script. ERP System erzeugt Textdatei für einen Auftrag, Anderes System verschiebt und liest diese für eine halbautomatische Fertigungssteuerung. Aber das nur am Rande.
Worauf ich hinaus will ist eine Erfahrung die wir gemacht haben:
Hin und wieder wurde die Datei bereits gefunden, da sie vom ERP angelegt war, hatte aber noch keinen Inhalt. Heißt es wurde eine Null-Byte-Datei verschoben. Das ERP hat sie brav wieder angelegt und geschrieben. Der erneute Versuch sie zu verschieben ist dann aber auf Fehler gelaufen, da sie im Ziel schon existierte. Genauso gut könnte das aber auch mitten im Schreiben der Datei passieren, wenn sie in dem Moment nicht gelockt sein sollte. Typischer Fall von Race Condition zwischen zwei konkurrierend laufenden Prozessen.
Quick and dirty Lösung: In so einer Polling Schleife ist sowieso irgendeine Form von Sleep eingebaut. Wo, ist grundsätzlich erst mal egal. Im Script von @erikro haben wir das am Ende der do-while Schleife, könnte man aber ebenso zwischen der Definition der $files Variable und der foreach Schleife einbauen. Das eliminiert zwar nicht die Race Condition, aber die Wahrscheinlichkeit dass es jemals crasht tendiert gegen Null.
Ablauf wäre also
Steffen
wir haben so was Ähnliches am Laufen, nur nicht als Script. ERP System erzeugt Textdatei für einen Auftrag, Anderes System verschiebt und liest diese für eine halbautomatische Fertigungssteuerung. Aber das nur am Rande.
Worauf ich hinaus will ist eine Erfahrung die wir gemacht haben:
Hin und wieder wurde die Datei bereits gefunden, da sie vom ERP angelegt war, hatte aber noch keinen Inhalt. Heißt es wurde eine Null-Byte-Datei verschoben. Das ERP hat sie brav wieder angelegt und geschrieben. Der erneute Versuch sie zu verschieben ist dann aber auf Fehler gelaufen, da sie im Ziel schon existierte. Genauso gut könnte das aber auch mitten im Schreiben der Datei passieren, wenn sie in dem Moment nicht gelockt sein sollte. Typischer Fall von Race Condition zwischen zwei konkurrierend laufenden Prozessen.
Quick and dirty Lösung: In so einer Polling Schleife ist sowieso irgendeine Form von Sleep eingebaut. Wo, ist grundsätzlich erst mal egal. Im Script von @erikro haben wir das am Ende der do-while Schleife, könnte man aber ebenso zwischen der Definition der $files Variable und der foreach Schleife einbauen. Das eliminiert zwar nicht die Race Condition, aber die Wahrscheinlichkeit dass es jemals crasht tendiert gegen Null.
Ablauf wäre also
- Dateinamen die zu finden sind in ein Cache.
- Warten bis die Wahrscheinlichkeit hoch genug ist dass sie fertig geschrieben sind.
- Nur die Dateien verschieben die im Cache sind (keine eventuell bereits neu hinzugekommenen).
Steffen
Hi.
... knapp 6000 Dateien zu
... max 50 Dateien
... innerhalb 10 Minuten
Offen ist,
...ob das eine einmalige Aktion ist, oder
...ob kontinuierlich - und
...wie viele in welchem Zeitraum
hinzukommen.
Außerdem ist die Position bon Quell- und Zielordner - derselbe Rechner pder Netzwerk - ggf. interessant ...
... weil: in einem lange zurückliegenden ähnlichem Projekt habe ich den "Quellordner" als Verknüpfung zum Zielordner angelegt, wodurch die Dateien direkt dort abgelegt wurden ...
Ansonsten bedarf es so oder so ja schon benannter Prüfung, ob die Datei final geschrieben ist ...
... knapp 6000 Dateien zu
... max 50 Dateien
... innerhalb 10 Minuten
Offen ist,
...ob das eine einmalige Aktion ist, oder
...ob kontinuierlich - und
...wie viele in welchem Zeitraum
hinzukommen.
Außerdem ist die Position bon Quell- und Zielordner - derselbe Rechner pder Netzwerk - ggf. interessant ...
... weil: in einem lange zurückliegenden ähnlichem Projekt habe ich den "Quellordner" als Verknüpfung zum Zielordner angelegt, wodurch die Dateien direkt dort abgelegt wurden ...
Ansonsten bedarf es so oder so ja schon benannter Prüfung, ob die Datei final geschrieben ist ...
... bleibt die Frage, ob auf demselben Rechner - und demselben Datenträger - oder via Netzwerk verschoben soll ...
... weil: auf demselben Datenträger eine Datei nicht wirklich verschoben, sondern nur die Startadresse geändert wird ...
... beim verschieben auf andere Datenträger und insbesondere via Netzwerk ist die verfügbare Bandbreite und Dateigröße relevant ...
... ggf. kann man die genutzte Bandbreite [im Netzwerk] begrenzen ...
... weil: auf demselben Datenträger eine Datei nicht wirklich verschoben, sondern nur die Startadresse geändert wird ...
... beim verschieben auf andere Datenträger und insbesondere via Netzwerk ist die verfügbare Bandbreite und Dateigröße relevant ...
... ggf. kann man die genutzte Bandbreite [im Netzwerk] begrenzen ...
Der Quell- und der Zielordner sind auf dem gleichen Server, gleicher Datenträger.
Ich habe jetztmal gegoogelt um die Grundlagen von Kopieren vs. Verschieben und Selbes Laufwerk vs. anderem Laufwerk zu vermitteln ...
Zu meinen Schulungszeiten gehörte das noch zum Standard, aber ich habe auf die schnelle keine brauchbare Quelle gefunden ...
Was wir gelernt haben:
Beim Versvhieben einer Datei auf demselben Laufwerk - c:\Quelle -> C:\Ziel - etc..
... verbleibt die Datei physisch an ihrem Ort und nur die Zuweisung/Adresse im Verzeichnisbaum wird angepasst ...
... sonut sollte das verschieben in deibem Fall (selber Datenträger, selbes Laufwerk) auch für 6000 Dateien nur Sekunden dauern ...
... bei unterschiedlichen Laufwerken Quelle C: zu Ziel D: wird glaube ich "kopiert und gelöscht"
Die Lernressourcen betrafen damals das physische Verschieben und Kopieren in Zusammenhang mit der Behandlung der NTFS-Rechte
Nachtrag: Die Verständnis von [physischen] Datenträgern, [physischen] Partitionen [auch ohne LW-Buchstaben/Links] und [logischen] Laufwerken hat sich mit den steigenden Größen seit den 90ern der Platten ja geändert ...
Moin,
Da hast Du natürlich völlig recht. Also erst einmal ein Lock auf die Datei:
Wieder schnell hingeschrieben ohne Test.
Liebe Grüße
Erik
Zitat von @rubberman:
Quick and dirty Lösung: In so einer Polling Schleife ist sowieso irgendeine Form von Sleep eingebaut. Wo, ist grundsätzlich erst mal egal. Im Script von @erikro haben wir das am Ende der do-while Schleife, könnte man aber ebenso zwischen der Definition der $files Variable und der foreach Schleife einbauen. Das eliminiert zwar nicht die Race Condition, aber die Wahrscheinlichkeit dass es jemals crasht tendiert gegen Null.
Quick and dirty Lösung: In so einer Polling Schleife ist sowieso irgendeine Form von Sleep eingebaut. Wo, ist grundsätzlich erst mal egal. Im Script von @erikro haben wir das am Ende der do-while Schleife, könnte man aber ebenso zwischen der Definition der $files Variable und der foreach Schleife einbauen. Das eliminiert zwar nicht die Race Condition, aber die Wahrscheinlichkeit dass es jemals crasht tendiert gegen Null.
Da hast Du natürlich völlig recht. Also erst einmal ein Lock auf die Datei:
$quellordner = x:\quelle
$zielordner = x:\ziel
do {
$files = Get-ChildItem -path $quellordner-file | select -First 50
foreach($file in $files) {
$FileStream=""
do {
try {
$FileStream = [System.IO.File]::Open($file.fullname,'Open','Write')
move-item -Path $file.fullname -Destination $zielordner\$file.name
$FileStream.close()
}
catch {
Start-Sleep -s 5
$FileStream.close()
}
} while($FileStream.CanWrite -eq $false)
}
Start-Sleep -Seconds 600
} while($(get-childitem -Path $quellordner -file))
Wieder schnell hingeschrieben ohne Test.
Liebe Grüße
Erik