42908
Goto Top

Prozentzahl aus Textdatei via Batch auslesen und verwenden

Hallo,

ich habe folgendes Problem:

Mit einer Batch und dem Tool PSInfo habe ich von verschiedenen Servern in unsrem Netzwerk jeweils die Daten über die Festplattenbelegung bezogen.
Dabei wird das Ergebnis in eine Textdatei geschrieben und danach noch mittels "findstr" nur die bestimmten Zeilen herausgefiltert und diese dann in eine weitere Textdatei geschrieben. Diese hat dann folgendes Schema:

---------------------------------------------------------------------------------------
Servername: xxxxxxx 
 
Volume Type       Format     Label                      Size       Free   Free
    C: Fixed      NTFS                               8.00 GB    3.86 GB  48.3%
    D: Fixed      NTFS       Volume1                41.01 GB   27.40 GB  66.8%


--> ist jetzt ein wenig verschoben (copy&paste)
[[[--Jetzt nicht mehr dank -Formatierung. Biber---]]
Aber auf jeden Fall ist die Prozentzahl mit dem freien Speicherplatz immer an der gleichen Stelle.

Ist es irgendwie möglich, dass ich diese Zahl nun auslese und mit einem if-Anweisung den Befehl zum senden einer E-Mail starte, wenn die Zahl kleiner als 10 wäre?

Mein Hauptproblem ist es eben an diese Zahl ran zu kommen und diese dann evtl als Variable zu setzen. (set)
Danach könnte ich ja einfach mit einer anderen IF-Anweisung checken, ob die Variable "variable1" kleiner als 10 ist und dem entsprechend weitere Befehle starten.

Vielen Dank für Euer bemühen!


Gruß,
Patrick

Content-Key: 71571

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

Ausgedruckt am: 29.03.2024 um 09:03 Uhr

Mitglied: Biber
Biber 22.10.2007 um 14:02:43 Uhr
Goto Top
Moin System#Schneider,

eigentlich kein großer Akt...aber....

Im Moment stehen die Prozentangaben zwar (absolut gezählt) an der gleichen Spaltenposition und wären mit der eingebauten CMD-Substring-Funktion dort rausfieselbar, aber..

Ich würde eher den Weg der Zeilen-Zerlegung über FOR /F-Anweisung und "tokens" vorziehen.
Dazu wäre allerdings VORHER nötig, dass die bislang namenlose Platte C: einen Namen bekommt ("Just4Biber" z.B.). Sonst haben nämlich die Zeilen unterschiedlichen Aufbau.

Wenn also alle Platten auch ein Volumelabel hätten, dann wäre der proof of concept diese Zeile am CMD-Prompt:
>for /f "tokens=1,11 delims=. " %a in ('findstr "%" daddeldu.log') do @echo a[%a] b[%b]  
a[C:] b[48]
a[D:] b[66]
---> bedeutet: mit dieser FOR /F-Anweisung bekommst Du die für Dich relevanten Infos (Welche Platte und Prozentzahl heraus.

Du könntest also eine ähnliche Zeile in einer Batchdatei verwenden und dort im Fall "Prozentwert kleiner 10%" eine Mail mit blat.exe losjagen
Skizze:
.....
FOR /F ....%%a in (....) DO Call :TestLowLimit %%a %%b
goto :eof

:TestLowLimit Parm1 ist Laufwerksbuchstabe Parm2 ist Prozentzzahl ganzzahlig.
Set /a perc=%2
If %perc% GEQ 10 goto :eof
....Andernfalls
machMir den Blat mit Betreff "%date% %time% Auf Lw %1 sind nur noch %2 Prozent frei.  

Grüße
Biber
Mitglied: 42908
42908 22.10.2007 um 14:14:58 Uhr
Goto Top
danke erst mal für die Formatierung face-wink

Also es sind mehrere Rechner aber das wird kein Problem sein, den Platten jeweils einen Namen zu geben. (Bin sowieso dabei das Netzwerk mal bisschen auf Vordermann zu bringen...)
Werde es mal so probieren wie du gesagt hast.
Sind dann a und b eigentlich Variablen, sodass ich dann eben die IF-Anweisung mit wenn b kleiner als....machen kann?


wie genau funktioniert der for befehl? komme noch nicht ganz klar damit!
Kann ich deinen Befehl 1zu1 übernehmen? ohne die zwei ausgaben natürlich...???

gruß,
patrick
Mitglied: Biber
Biber 22.10.2007 um 14:31:11 Uhr
Goto Top
Moin Patrick,

%%a und %%b sind in diesem Fall "dynamische Variablen", die nur existieren, solange die FOR/F-Anweisung ausgeführt wird.

Deshalb kopiere ich die Variale %%b um in eine "statische"/dauerhafte Variable namens %perc%.
Diese kann ich dann in der Tat auch numerisch (mit LEQ, EQU etc) mit einem Zahlenwert vergleichen.

Mit der dynamischen Variablen %%b könnte ich unter Umständen das Problem haben, dass deren Inhalt nicht zwingend als Zahl erkannt wird und dann "zeichenweise" verglichen wird.

Und da käme dann bei "IF %%b LEQ 10 " im Falle fünf Prozent "IF 5 LEQ 10.." bei einem ZEICHEN-Vergleich das Verkehrte heraus [weil das ZEICHEN "5" niemals kleiner ist als das Zeichen "1" (das erste Zeichen des Strings "10".

Deshalb diese Umkopiererei mit "Set /a perc=%2" in eine "numerische Variable.

Kann ich deinen [FOR /F]-Befehl 1zu1 übernehmen?
Ja, nur jeweils im Batch zwei Prozentzeichen statt einem vor dynamischen Variablen ( %%a statt %a..).


Grüße
Biber
Mitglied: 42908
42908 22.10.2007 um 14:35:24 Uhr
Goto Top
ok werde mir das mal noch angucken. Aber wieso kann ich den Befehl


   for /f "tokens=1,11 delims=. " %a in ('findstr "%" d:\bat\test.txt') do @echo a[%a] b[%b]  

nicht in einer Batch starten? Wenn ich ihn direkt über den cmd promt laufen lasse gehts. Bekomme folgende Meldung:

"" d:\bat\test.txt') do @echo a[b]" ist syntaktisch an dieser Stelle nicht verar  
beitbar.


Der ließt wohl nicht alles oder wie?

*edit* Wo genau muss ich zwei %-zeichen machen und wo eins? es müsste doch so aussehen oder nicht:

for /f "tokens=1,11 delims=. " %%a in ('findstr "%" d:\bat\test.txt') do @echo a[%a] b[%b]  
Mitglied: Biber
Biber 22.10.2007 um 15:10:46 Uhr
Goto Top
Moin Patrick,

skizziert würde es so aussehen:

....
:: ... in einem Batch...
for /f "tokens=1,11 delims=. " %%a in ('findstr "%" daddeldu.log') do call :TestLowLimit %%a %%b  
goto :eof

:TestLowLimit ...siehe oben
Set /a perc=%2      
::---- in der vorangegangenen Zeile wird der Prozentwert (einst %%b, jetzt %2) 
::---- in eine numerische Variable namens %perc% kopiert.
....

goto :eof

Grüße
Biber
Mitglied: 42908
42908 22.10.2007 um 15:42:19 Uhr
Goto Top
Ich glaube die Batch hat ein Problem, wenn sie nach dem %-Zeichen suchen soll:

wenn ich folgendes ausführe tut sich nämlich gar nichts.Das Fenster springt einfach wieder weg. Auch über Kommandozeile tut sich nichts.

for /f "tokens=1,11 delims=. " %%a in ('findstr "%" d:\bat\test.txt') pause do @echo %%a %%b  

habe es auch so versucht

for /f "tokens=1,11 delims=. " %%a in ('findstr "%" d:\bat\test.txt') pause do @echo %a %b  

kein erfolg...vielleicht kannt du mir mal genau erklären was der Befehl macht.

Vielen Dank,

Patrick
Mitglied: Biber
Biber 22.10.2007 um 16:56:05 Uhr
Goto Top
Moin Patrick,

zuerst: das "pause" ist an diese Stelle nicht aufführbar.
Ersatzlos streichen und dann nochmal testen.

Kurzer Versuch der Erklärung (unter "FOR /?" am CMD-Prompt besser erkärt):

Beispiel am CMD-Prompt
for /f "tokens=1,11 delims=. " %a in ('findstr "%" d:\bat\test.txt') do @echo %a %b  

FOR /F-Anweisungen immer von innen nach aussen lesen...
In der runden Klammer steht das, was als "Textdatei" zeilenweise gelesen wird.
In der Klammer steht:
findstr "%" d:\bat\test.txt
nur deshalb in einfachen Hochkomma, damit die CMD.exe "weiss", dass es eine ausführbare Anweisung ist.
Ergebnis davon sind alle Zeilen, die ein Zeichen "%" enthalten.

Diese Zeilen enthalten, wenn man/frau als Delimiter, als Trennzeichen den Punkt (".") und das Leerzeichen definiert, was ich mit der Anweisung "Delims=. " tue, Pi mal Auge so 13 "Tokens", also Einzelteile.

Token Nummer#1 ist die Laufwerksbezeichnung ("C:\" oder "D:\") , Token Nummer #11 ist der Ganzzahlanteil der Frei-Prozentangabe.

Mehr isses eigentlich nicht.

Grüße
Biber
Mitglied: 42908
42908 22.10.2007 um 18:07:08 Uhr
Goto Top
Hallo
sorry die Pause gehört da echt nicht hin....das weiß ich aber ausnahmsweiße auch mal face-wink
Hab nur falsch gepostet sorry. Es tut sich jedoch leider nix. Ich denke das könnte was mit dem findstr-Befehl zu tun haben, da wenn ich z.b. nach "free" suche mit dem Befehl sich etwas tut. Aber bei "%" tut sich einfach nichts....

gruß,
patrick
Mitglied: bastla
bastla 22.10.2007 um 19:03:28 Uhr
Goto Top
Hallo System#Schneider!

Aber bei "%" tut sich einfach nichts....
Das kann ich zwar nicht nachvollziehen (bei mir macht Biber's Oneliner - mit Deinem oben geposteten Beispiel - genau, was er soll - [Edit] allerdings auch nur von der Kommandozeile face-sad [/Edit]), aber Du könntest alternativ zB
for /f "tokens=1,11 delims=. " %a in ('findstr /c:" GB " d:\bat\test.txt') do @echo %a %b  
versuchen - der String " GB " (inklusive Leerzeichen) könnte ja auch eindeutig sein.

Bis alle Partitionen auch einen Namen haben, wäre noch folgende Vorgangsweise möglich:
@echo off & setlocal
for /f "delims=" %%a in ('findstr /c:" GB " d:\bat\test.txt') do call :ProcessLine "%%a"  
goto :eof

:ProcessLine
set "Line=%~1"  
set Drv=%Line:~4,2%
set /a Free=%Line:~-5,3%
echo %Drv% %Free%

[Edit]
Nachtrag: Die Position -5 (und nicht -6) resultiert daraus, dass bei der Übergabe an das Unterprogramm das %-Zeichen am Ende "geschluckt" wird. Richtiger wäre daher eigentlich:
@echo off & setlocal
for /f "delims=" %%a in ('findstr /c:" GB " d:\bat\test.txt') do set "Line=%%a" & call :ProcessLine  
goto :eof

:ProcessLine
set Drv=%Line:~4,2%
set /a Free=%Line:~-6,3%
echo %Drv% %Free%
[/Edit]

Grüße
bastla
Mitglied: 42908
42908 22.10.2007 um 19:46:47 Uhr
Goto Top
Ok danke. Werde es morgen ausprobieren.heute komme ich leider nicht mehr dazu. Aber schon mal vielen Dank.

Bis morgen
Mitglied: Biber
Biber 22.10.2007 um 19:59:25 Uhr
Goto Top
Moin,

Nachtrag zur Meldung "findstr "%" funktioniert nicht im Batch".

Stimmt.
Im Batch müssten es tatsächlich zwei %-Zeichen sein:
>type proz.bat
for /f "tokens=1,11 delims=. " %%a in ('findstr "%%" Disks.log') do @echo %%a %%b  

>proz

>for /F "tokens=1,11 delims=. " %a in ('findstr "%" Disks.log') do @echo %a %b  
C: 48
D: 66

Aber herleitbar ist das nicht - ich würde dann schon eher auf bastla's Alternative ausweichen.
[Also die Alternative mit dem genauen Suchen nach "GB" in der Hoffnung, dass nirgends nicht nur noch 20 MB oder 16 KB frei sind *gg]

Grüße
Biber
Mitglied: 42908
42908 22.10.2007 um 21:22:33 Uhr
Goto Top
:-P das hoffe ich auch nicht.

Werde mal nochmal die Log durch gucken evtl finde ich ja noch etwas wo es nur einmal in den bestimmten zeilen gibt.

Aber werde wie gesagt erst morgen eure Lösungsvorschläge probieren....wenn ich dazu komme da ich noch ein Azubi bin und in die Berufsschule muss und nicht arbeiten...

Bis dann und super vielen Dank
Mitglied: bastla
bastla 22.10.2007 um 21:39:11 Uhr
Goto Top
Hallo System#Schneider!

Einen hab ich noch:
psinfo -d | more +19 > Disks.log
Damit bleiben (zumindest bei mir) nur noch die gewünschten Zeilen über, sodass das Filtern überhaupt entfallen könnte.

Grüße
bastla
Mitglied: Biber
Biber 22.10.2007 um 21:51:14 Uhr
Goto Top
Hmm...dann noch einen drauf:
>psinfo -d 2>nul|more +19
...damit die Copyrightmeldung nicht mit ausgewertet wird.
Im ganzen Satz:
for /f "tokens=1,11 delims=. " %i in ('psinfo -d ^2^>nul^|more +19') do @echo %i %j  

Grüße
Biber
Mitglied: bastla
bastla 22.10.2007 um 22:10:32 Uhr
Goto Top
@Biber
Ist natürlich schöner so, obwohl die Copyrightmeldung (da auf STDERR) ohnehin nur angezeigt, aber nicht ausgewertet wird.

Grüße
bastla
Mitglied: Biber
Biber 22.10.2007 um 23:27:27 Uhr
Goto Top
@bastla

Stimmt schon, stimmt schon...

Aber wir sollten doch den hoffnungsvollen Azubis wenigstens einen Oneliner mit auf den Weg geben und nicht nur einen Halfliner...

Du weißt doch, wie sehr die bekannten Namen in der IT-Branche auf Quantität achten.... face-wink

War da nicht vorhin jemand mit "Wie kann ich die Dateigröße meiner gezippten Security-Patches in Excel anzeigen lassen?"
face-wink

Grüße
Biber
Mitglied: 42908
42908 25.10.2007 um 12:40:41 Uhr
Goto Top
Hallo,

also ich komme weiter....werde aber mein ergebnis erst posten, wenns auch funktioniert. Evtl auch heute schon.
Jetzt habe ich aber noch eine kleine Frage:

Kann man ein Ergebnis eines Befehls als Variable speichernß

so in etwa:
set variable=findstr "Servername" %server%  
Ich weiß, dass es so nicht geht. Da setzt er die Variable einfach als String wie ich ihn eingegeben habe.

Bei
set variable=%cd%
zum Beispiel setzt er die Variable auf das aktuelle Verzeichnis. Ist dies auch irgendwie mit dem findstr-Befehl möglich?

Gruß,
Patrick
Mitglied: bastla
bastla 25.10.2007 um 15:31:51 Uhr
Goto Top
Hallo System#Schneider!

Wenn es Dir genügt, die letzte Ergebniszeile (falls es mehrere geben sollte) zu speichern (und nachfolgend zu überprüfen), dann einfach:
set variable=
for /f "delims=" %%i in ('findstr "Servername" %server%') do set "variable=%%i"  
if defined variable echo Gefunden in Zeile: %variable%
Alternativ könntest Du mit
set variable=
for /f "delims=" %%i in ('findstr "Servername" %server%') do if not defined variable set "variable=%%i"  
if defined variable echo Gefunden in Zeile: %variable%
das erste Ergebnis in die Variable schreiben.

Grüße
bastla
Mitglied: 42908
42908 13.11.2007 um 08:37:00 Uhr
Goto Top
Hallo sorry dass ich mich erst jetzt wieder melde...habe mein Problem folgendermaßen gelöst:

Wie schon gesagt mittels findstr-Befehl eine solche Ausgabe von PSInfo erstellt:

---------------------------------------------------------------------------------------
Di 13.11.2007  7:00:05,86 
Servername: SENECA 
 
Volume Type       Format     Label                      Size       Free   Free
    C: Fixed      NTFS       System                  7.81 GB    1.26 GB  16.2%
    D: Fixed      NTFS       Volume1                25.39 GB    8.64 GB  34.0%
    E: Fixed      FAT32      IMAGE                   4.03 GB    1.83 GB  45.3%



Mit einer weiteren Batch habe ich nun dieses Txt-File ausgelesen:

for %%a in (%server5% %server4% %server3% %server2% %server1% %server0%) do set server=%%a & call :check

:check
for /f "tokens=1,11 delims=. " %%a in ('findstr " GB " %server%') do call :machschon %%a %%b  
goto :eof



:machschon
set drv=%1
set /a perc=%2

if %perc% GEQ 10 goto :eof

set servername=
for /f "delims=" %%i in ('findstr "Servername" %server%') do set "servername=%%i"  


echo %date% %time%>>%achtung%
echo Achtung auf %servername% sind auf Laufwerk %drv% nur noch %perc% Prozent Speicherplatz frei!>>%achtung%


blat -to [e-mail adresse] -f [sende email-Adresse] -subject "ACHTUNG!!! Auf einem Rechner im Netzwerk besteht zu wenig Speicherplatz" -body "Siehe Anhang fuer naehere Infos und um welchen Rechner es sich handelt!" -Server [Interner Mailserver] -attach achtung.txt  

goto :eof


Einzelheiten kann man natürlich noch ändern. Sobald neue Rechner/Server dazu kommen muss man in der 2.Batch eine neue Variable für diesen Server/Rechner erstellen und in der ersten for-Schleife hinzufügen. Die Variblen zeigen auf die einzelnen Log-Files, die die 1. Batch erstellt hat. (Für jeden Rechner/Server eine eigene Log)

Weiterhin habe ich auch noch eine weiterlaufende Log gemacht, in die die Daten vom vorherigen Tag eingetragen werden. So kann ich immer sehen, wann sich der freie Speicherplatz geändert hat.


Gruß,

Schneider