aivilon
Goto Top

Die gerade verwendete Zeile löschen

Hallo zusammen

Zu meinem Problem

Ich habe ein Script, welches in einem CSV nach dem Servernamen sucht. Dies wird mittels For Schleife gemacht. Diese geht ja bekanntlicherweise von unten nach oben um einen String zu suchen.
Nachdem der Servername gefunden wurde, werden die einzelnen angaben "eingelesen".
Da das Script nun einen Loop machen muss (bis der Servername nicht mehr vorhanden ist) muss ich jetzt diese Zeile, die ich gerade auch verwendet habe, löschen. NUR diese.
Wie mach ich das nun am Besten?


Der Aufbau des CSVs sieht wie folgt aus:

Server1;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server1;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2
Server1;21.12.2012;12:00;Programm3;\\Server\Software$\Software\Source1
Server2;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server2;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2


Grüsse
Aivilon

Content-ID: 186084

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

Ausgedruckt am: 18.11.2024 um 03:11 Uhr

bastla
bastla 07.06.2012 aktualisiert um 11:10:12 Uhr
Goto Top
Hallo aivilon!
Ich habe ein Script, welches in einem CSV nach dem Servernamen sucht. Dies wird mittels For Schleife gemacht.
Warum nicht per "findstr" (damit ließe sich auch das Löschen erledigen)?
Diese geht ja bekanntlicherweise von unten nach oben um einen String zu suchen.
???
Magst Du nicht einfach kurz beschreiben, was der Batch tatsächlich leisten soll?

Grüße
bastla
aivilon
aivilon 07.06.2012 aktualisiert um 11:16:44 Uhr
Goto Top
Hallo Bastla

Jap, sorry, zu wenig geschrieben. Den findstr hab ich drin:
for /f "tokens=1-5 delims=%Delim%" %%a in ('findstr /b /i /c:"%Host%%Delim%" "%srvList%"') do (  
	set "srvName=%%a"  
	set "srvDate=%%b"  
	set "srvTime=%%c  
	set "srvSoft=%%d"  
	set "srvPath=%%e"  
)

Aber eben. Der Teil des Scripts funktioniert. Jetzt zum Aber, respektive zu dem, was das Script noch leisten soll:
Der obige Code sucht als erstes in einem CSV nach dem Inhalt der Variablen. Danach werden einige Sachen ausgeführt (spielen in meinem Problem keine Rolle). Nun soll die Zeile, welche gerade verwendet wurde, gelöscht werden.

Also von so:
Server1;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server1;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2
Server1;21.12.2012;12:00;Programm3;\\Server\Software$\Software\Source1
Server2;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server2;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2

Nach so:
Server1;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server1;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2
Server2;21.12.2012;12:00;Programm1;\\Server\Software$\Software\Source
Server2;21.12.2012;12:00;Programm2;\\Server\Software$\Software\Source2

(dritte Zeile wurde hier jetzt gelöscht. Die erste, welche auf dem Server1 ausgeführt wurde)
bastla
bastla 07.06.2012 aktualisiert um 14:40:47 Uhr
Goto Top
Hallo aivilon!

Wozu löschen bzw wozu einzelne Zeilen löschen? Wenn schon sollte es doch genügen, alle Zeilen für einen bestimmten Server am Stück zu löschen, also etwa:
move "%srvList%" "%temp%\srvList"  
findstr /vbic:"%Host%%Delim%" "%temp%\srvList">"%srvList%"  
Falls aber wirklich jede einzelne Zeile weg soll, könntest Du vorweg die gesamte Zeile einlesen, dann erst zerlegen und dann die Zeile als Suchbegriff verwenden - ungetestet:
for /f "delims=" %%i in ('findstr /bic:"%Host%%Delim%" "%srvList%"') do (  
    for /f "tokens=1-5 delims=%Delim%" %%a in ("%%i") do (  
        set "srvName=%%a"  
        set "srvDate=%%b"  
        set "srvTime=%%c  
        set "srvSoft=%%d"  
        set "srvPath=%%e"  
    )
    REM Verarbeitung
    REM
    REM Verarbeitung Ende
    move "%srvList%" "%temp%\srvList"  
    findstr /vxc:"%%i" "%temp%\srvList">"%srvList%"  
)
BTW: Wozu werden eigentlich die "Tokens" Variablen zugewiesen?

Grüße
bastla
aivilon
aivilon 07.06.2012 um 15:06:55 Uhr
Goto Top
Zitat von @bastla:
Hallo aivilon!

Wozu löschen bzw wozu einzelne Zeilen löschen? Wenn schon sollte es doch genügen, alle Zeilen für einen
bestimmten Server am Stück zu löschen, also etwa:

Wie erwähnt. Dazwischen findet noch was statt (siehe code am ende des Posts)

Falls aber wirklich jede einzelne Zeile weg soll, könntest Du vorweg die gesamte Zeile einlesen, dann erst zerlegen und dann
die Zeile als Suchbegriff verwenden - ungetestet:

Hmm...versucht, geht ned. Habs jetzt auf nem anderen weg versucht, aber ich glaub das ist so nicht möglich (siehe code am Ende des Posts)

BTW: Wozu werden eigentlich die "Tokens" Variablen zugewiesen?

Das ist ein alter Codeschnippsel von mir. Den hatte ich damals von irgend ner Seite...eigentlich total unnötig ich weiss.

Ich hab mal versucht, alles in die For Schleife zu nehmen...
Code:
@echo off & setlocal
set "DeployPath=\\[SERVER]\Software$\"  
set "SoftCSV=  

set "srvList=%DeployPath%\Software\installsoft.csv"  
set "Delim=;"  
set "Host=%computername%"  

echo . >> %DeployPath%\Log\Log.log

:loop

set srvName=
for /f "tokens=1-5 delims=%Delim%" %%a in ('findstr /b /i /c:"%Host%%Delim%" "%srvList%"') do (  
	set "srvName=%%a"  
	set "srvDate=%%b"  
	set "srvTime=%%c"  
	set "srvSoft=%%d"  
	set "srvPath=%%e"  




	echo 1. %srvName%  2. %Host%
	If ."%srvName%"==."%Host%" goto maketask  
	if not ."%srvName%"==."%Host%" goto Endofdeploy  
	
	:maketask
	REM echo 1.) %srvDate%  2.) %srvTime%
	if %srvDate%==0 set srvDate=%date%
	if %srvTime%==0 set srvTime=%time%
	REM echo 1.) %srvDate%  2.) %srvTime%
	for /f "tokens=1-4 delims=:., " %%a in ("%srvTime%") do set srvTime=%%a:%%b:00  
	
	for /F "tokens=1,2,3 delims=., " %%A in ("%srvDate%") do (  
		Set Month=%%A
		Set Day=%%B
		Set Year=%%C
		SET srvDate=%%B/%%A/%%C
	)
	REM echo 1.) %Month%  2.) %Day%
	if %Month%==0* do (
		set Month=%Month:~1,1%
	)
	if %Day%==0* do (
		set Day=%Day:~1,1%
	)
	REM echo 1.) %Month%  2.) %Day%
	REM echo .%srvSoft%.
	REM echo .%srvDate%.
	REM echo .%srvTime%.
	
	schtasks /create /TN "SoftwareUpdate\%srvSoft%" /tr %srvPath%\%srvSoft%.msi /SC ONCE /ST %srvTime% /sd %srvDate%  


	ECHO. >> %DeployPath%\Log\Log.log
	ECHO Task wurde erstellt: >> %DeployPath%\Log\Log.log
	ECHO schtasks /create /TN "SoftwareUpdate\%srvSoft%" /tr %srvPath%\%srvSoft%.msi /SC ONCE /ST %srvTime% /sd %srvDate% >> %DeployPath%\Log\Log.log  
	ECHO Programm: %srvSoft% >> %DeployPath%\Log\Log.log
	ECHO Datum und Zeit: %srvDate%, %srvTime% >> %DeployPath%\Log\Log.log
	ECHO Task ist unter: SoftwareUpdate\%srvSoft% zu finden >> %DeployPath%\Log\Log.log
	
		findstr /v /b /i /c:"%%a" "%srvList%" > %srvList%  
)	
Goto Loop


ECHO Log vom: %Date% um %time% >> %DeployPath%\Log\Log.log
ECHO ######################### >> %DeployPath%\Log\Log.log
ECHO. >> %DeployPath%\Log\Log.log

Exit


:Endofdeploy
ECHO Log vom: %Date% um %time% >>  %DeployPath%\Log\Log.log
ECHO Es gibt keine/keine weitere zu installierende Software für %Host% >> %DeployPath%\Log\Log.log
ECHO ######################### >>  %DeployPath%\Log\Log.log
ECHO. >> %DeployPath%\Log\Log.log

Exit


Grüsse
aivilon
bastla
bastla 07.06.2012 aktualisiert um 15:36:08 Uhr
Goto Top
Hallo aivilon!

Würde ich eher so versuchen (ungetestet):
@echo off & setlocal enabledelayedexpansion
set "DeployPath=\\[SERVER]\Software$\"  
set "SoftCSV=  

set "srvList=%DeployPath%\Software\installsoft.csv"  
set "Delim=;"  
set "Host=%computername%"  
set "Log=%DeployPath%\Log\Log.log"  

>>"%Log%" echo.  
for /f "tokens=1-5 delims=%Delim%" %%a in ('findstr /b /i /c:"%Host%%Delim%" "%srvList%"') do (  

	set "srvName=%%a"  
	set "srvDate=%%b"  
	set "srvTime=%%c"  
	set "srvSoft=%%d"  
	set "srvPath=%%e"  

	echo 1. !srvName!  2. %Host%
	REM echo 1.) !srvDate!  2.) !srvTime!
	if !srvDate!==0 set "srvDate=!date!"  
	if !srvTime!==0 set "srvTime=!time!"  
	REM echo 1.) !srvDate!  2.) !srvTime!
	for /f "tokens=1-4 delims=:., " %%i in ("!srvTime!") do set srvTime=%%i:%%j:00  
	for /F "tokens=1,2,3 delims=., " %%i in ("!srvDate!") do (  
		Set "Month=%%i"  
		Set "Day=%%j"  
		Set "Year=%%k"  
		SET "srvDate=%%j/%%i/%%k"  
	)
	REM echo 1.) %Month%  2.) %Day%
	if !Month:~,1!==0 set "Month=!Month:~1,1!"  
	if !Day:~,1!==0 set "Day=!Day:~1,1!"  
	REM echo 1.) %Month%  2.) %Day%
	REM echo .!srvSoft!.
	REM echo .!srvDate!.
	REM echo .!srvTime!.
	
	schtasks /create /TN "SoftwareUpdate\!srvSoft!" /tr !srvPath!\!srvSoft!.msi /SC ONCE /ST !srvTime! /sd !srvDate!  

	>>"%Log%" ECHO.  
	>>"%Log%" ECHO Task wurde erstellt:  
	>>"%Log%" ECHO schtasks /create /TN "SoftwareUpdate\!srvSoft!" /tr !srvPath!\!srvSoft!.msi /SC ONCE /ST !srvTime! /sd !srvDate!  
	>>"%Log%" ECHO Programm: !srvSoft!  
	>>"%Log%" ECHO Datum und Zeit: !srvDate!, !srvTime!  
	>>"%Log%" ECHO Task ist unter: SoftwareUpdate\!srvSoft! zu finden  

)

move "%srvList%" "%temp%\srvList"  
findstr /vbic:"%Host%%Delim%" "%temp%\srvList"">"%srvList%"  

>>"%Log%" ECHO Log vom: %Date% um %time%  
>>"%Log%" ECHO #########################  
>>"%Log%" ECHO.  
Exit
Falls Dir der Eintrag
Es gibt keine zu installierende Software für %Host%
wichtig sein sollte, kannst Du vor Zeile 11 einfügen:
findstr /bic:"%Host%%Delim%" "%srvList%">nul||>>"%Log%" ECHO Es gibt keine zu installierende Software für %Host%
Grüße
bastla
aivilon
aivilon 07.06.2012 aktualisiert um 16:47:56 Uhr
Goto Top
EDIT####
Code zum Löschen der Zeilen nochmals angepasst. Jetzt funktionierts wirklich!


Hallo Bastla

Vielen Dank, aber hab auch gerade was gefunden. Glaube mein Code ist fast noch angenehmer. Ich wechsle bei jedem Durchlauf in der For-Schleife in den Prozess. Nach dem Prozess wechsle ich mittels goto :EOF wieder in die For-Schleife und der nächste durchlauf wird ausgeführt. Bis alle durch sind.
Am Ende wird das CSV gesäubert. Mittels deinem Script-Schnipsel von weiter oben.

Code:
@echo off & setlocal
set "DeployPath=\\[SERVER]\Software$\"  
set "SoftCSV=  

set "srvList=%DeployPath%\Software\installsoft.csv"  
set "Delim=;"  
set "Host=%computername%"  

echo . >> %DeployPath%\Log\Log.log


set srvName=
for /f "tokens=1-5 delims=%Delim%" %%a in ('findstr /b /i /c:"%Host%%Delim%" "%srvList%"') do (  
	set "srvName=%%a"  
	set "srvDate=%%b"  
	set "srvTime=%%c"  
	set "srvSoft=%%d"  
	set "srvPath=%%e"  
	call :prozess
)

goto Endofdeploy


:prozess
	echo 1. %srvName%  2. %Host%
	If ."%srvName%"==."%Host%" goto maketask  
	if not ."%srvName%"==."%Host%" goto Endofdeploy  
	
	:maketask
	REM echo 1.) %srvDate%  2.) %srvTime%
	if %srvDate%==0 set srvDate=%date%
	if %srvTime%==0 set srvTime=%time%
	REM echo 1.) %srvDate%  2.) %srvTime%
	for /f "tokens=1-4 delims=:., " %%a in ("%srvTime%") do set srvTime=%%a:%%b:00  
	
	for /F "tokens=1,2,3 delims=., " %%A in ("%srvDate%") do (  
		Set Month=%%A
		Set Day=%%B
		Set Year=%%C
		SET srvDate=%%B/%%A/%%C
	)
	REM echo 1.) %Month%  2.) %Day%
	if %Month%==0* do (
		set Month=%Month:~1,1%
	)
	if %Day%==0* do (
		set Day=%Day:~1,1%
	)
	REM echo 1.) %Month%  2.) %Day%
	REM echo .%srvSoft%.
	REM echo .%srvDate%.
	REM echo .%srvTime%.
	
	schtasks /create /TN "SoftwareUpdate\%srvSoft%" /tr %srvPath%\%srvSoft%.msi /SC ONCE /ST %srvTime% /sd %srvDate%  


	ECHO. >> %DeployPath%\Log\Log.log
	ECHO Task wurde erstellt: >> %DeployPath%\Log\Log.log
	ECHO schtasks /create /TN "SoftwareUpdate\%srvSoft%" /tr %srvPath%\%srvSoft%.msi /SC ONCE /ST %srvTime% /sd %srvDate% >> %DeployPath%\Log\Log.log  
	ECHO Programm: %srvSoft% >> %DeployPath%\Log\Log.log
	ECHO Datum und Zeit: %srvDate%, %srvTime% >> %DeployPath%\Log\Log.log
	ECHO Task ist unter: SoftwareUpdate\%srvSoft% zu finden >> %DeployPath%\Log\Log.log
	
	copy "%DeployPath%\Software\%srvList%" "%Temp%\installsoft.csv"  
	findstr /vbic:"%Host%" "%srvList%" > "%temp%\installsoft.csv"  
	move "%Temp%\installsoft.csv" "%srvList%"  

GOTO:EOF


:Endofdeploy
ECHO Log vom: %Date% um %time% >>  %DeployPath%\Log\Log.log
ECHO Es gibt keine/keine weitere zu installierende Software für %Host% >> %DeployPath%\Log\Log.log
ECHO ######################### >>  %DeployPath%\Log\Log.log
ECHO. >> %DeployPath%\Log\Log.log

Exit


OK. Das Löschen funktioniert doch noch nicht ganz wie gewünscht. hatte ein fehler drinn darum hatte es so ausgesehen als hätte es gestummen.
bastla
bastla 07.06.2012 aktualisiert um 16:34:00 Uhr
Goto Top
Hallo aivilon!

Ist natürlich auch eine Möglichkeit ...

Die Zeile 67 ist übrigens nicht nur überflüssig, sondern kontraproduktiv.

BTW: Die Zeilen 44 und 47 haben bisher auch nur darum zu keinem Fehler (wegen des enthaltenen "do") geführt, weil die Abfragen ohnehin nicht so funktioniert, wie Du es vermutlich vorhattest, und die Zeile 28 dürfte eigentlich nur dann zu einem Sprung führen, wenn aufgrund von Unterschieden durch Groß-/Kleinschreibung die Abfrage in der Zeile 27 nicht funktioniert (ansonsten muss immer %srvName% mit "%host% übereinstimmen, da ansonsten die Zeile gar nicht erst gefunden/die Schleife nicht durchlaufen worden wäre ...

Grüße
bastla
aivilon
aivilon 07.06.2012 um 16:53:06 Uhr
Goto Top
Zitat von @bastla:
Hallo aivilon!

Ist natürlich auch eine Möglichkeit ...

Die Zeile 67 ist übrigens nicht nur überflüssig, sondern kontraproduktiv.

Habs jetzt nochmals geändert. Nun gehts. Vorhin hats mich getäuscht, da es immer das alte file aus dem Temp kopiert hat. Und da ich nur einen Server im csv hatte sah ich den fehler nicht


BTW: Die Zeilen 44 und 47 haben bisher auch nur darum zu keinem Fehler (wegen des enthaltenen "do") geführt,
weil die Abfragen ohnehin nicht so funktioniert, wie Du es vermutlich vorhattest, und die Zeile 28 dürfte eigentlich nur dann

if %Day%==0* set Day=%Day:~1,1%

das wäre glaub richtig oder? Dasselbe mit Time

zu einem Sprung führen, wenn aufgrund von Unterschieden durch Groß-/Kleinschreibung die Abfrage in der Zeile 27 nicht
funktioniert (ansonsten muss immer %srvName% mit "%host% übereinstimmen, da ansonsten die Zeile gar nicht erst
gefunden/die Schleife nicht durchlaufen worden wäre ...

Jop, das mit der Gross klein schreibung muss ich noch machen. aber es geht in meiner arbeit momentan nur um das grundkonzept dafür. muss noch nicht perfekt sein ;)


Grüße
bastla

Nochmal herzlichen Dank für deine Unterstützung! =)
Grüsse
aivilon
bastla
bastla 07.06.2012 aktualisiert um 17:04:10 Uhr
Goto Top
Hallo aivilon!
if %Day%==0* set Day=%Day:~1,1%
Soferne Du damit, wie ich vermute, erreichen willst, dass eine führende Null entfernt wird, schau Dir meinen Ansatz dazu an (Zeile 33) - Deine Abfrage kann so nicht funktionieren, da Wildcards beim Vergleich mit "==" nicht unterstützt werden ...
Jop, das mit der Gross klein schreibung muss ich noch machen.
Das ist zwar nur ein "/i", aber eigentlich sind beide Abfragen unnötig, da ja aufgrund des "findstr" die Schleife ohnehin nur für jene Zeilen durchlaufen wird, an deren Anfang der Inhalt von "%host%" steht (sodass es niemals einen Sprung zu ":Endofdeploy" geben dürfte) ...

Grüße
bastla
aivilon
aivilon 08.06.2012 um 07:30:15 Uhr
Goto Top
Zitat von @bastla:
Hallo aivilon!
> if %Day%==0* set Day=%Day:~1,1%
Soferne Du damit, wie ich vermute, erreichen willst, dass eine führende Null entfernt wird, schau Dir meinen Ansatz dazu an
(Zeile 33) - Deine Abfrage kann so nicht funktionieren, da Wildcards beim Vergleich mit "==" nicht unterstützt
werden ...

Ja, das hatte ich vor. Ist mir nicht aufgefallen, dass das nicht funktioniert face-confused. Habs angepasst.

----
> Jop, das mit der Gross klein schreibung muss ich noch machen.
Das ist zwar nur ein "/i", aber eigentlich sind beide Abfragen unnötig, da ja aufgrund des
"findstr" die Schleife ohnehin nur für jene Zeilen durchlaufen wird, an deren Anfang der Inhalt von
"%host%" steht (sodass es niemals einen Sprung zu ":Endofdeploy" geben dürfte) ...

Ja das schon. Aber nach dem alle Zeilen mit %host% durch sind, müsste er die Schlaufe ja normal verlassen (respektive wird %srvName% leer sein, sodass unter :prozess der Vergleich von if not ."%srvName%*==."%Host%" goto :EOF positiv ausfällt und der :EOF die Schlaufe verlässt. Und danach kommt es zum goto Endofdeploy.

Oder versteh ich da was falsch?

Grüße
bastla

Noch kurz zum Schtasks:
Wie kann ich den Task so setzten, dass der Task mit "Run Wheter User is logged in or not" konfiguriert ist?

Grüsse
aivilon
bastla
bastla 08.06.2012 um 12:24:55 Uhr
Goto Top
Hallo aivilon!
Und danach kommt es zum goto Endofdeploy.
Das ist richtig, aber diesen Sprung hatte ich auch nicht gemeint, sondern nur jenen in Zeile 28 ...
Wie kann ich den Task so setzten, dass der Task mit "Run Wheter User is logged in or not" konfiguriert ist?
Indem Du ihn über das Systemkonto (mit dem Schalter "/RU") ausführen lässt?

Grüße
bastla
aivilon
aivilon 08.06.2012 aktualisiert um 12:57:35 Uhr
Goto Top
Zitat von @bastla:
Hallo aivilon!
Und danach kommt es zum goto Endofdeploy.
Das ist richtig, aber diesen Sprung hatte ich auch nicht gemeint, sondern nur jenen in Zeile 28 ...

Jep hab ich auch bemerkt. Da haben wir wohl im Endeffekt das selbe gedacht =)


Wie kann ich den Task so setzten, dass der Task mit "Run Wheter User is logged in or not" konfiguriert ist?
Indem Du ihn über das Systemkonto (mit dem Schalter "/RU") ausführen lässt?

Dankschön hat funktioniert =)

Grüße
bastla

Grüsse, Aivilon