Batch File Variable überschreiben
Hallo zusammen,
in meinem Batch File ist eine Problem was ich nicht verstehe.
Vor ab, ich komme aus der C/C++/C# Welt.
Mein Batch File soll sequenziell nacheinander mehrere Dateien aus verschiedenen Verzeichnissen kopieren.
Vor jeder Kopieranweisung stelle ich dem User die Frage ob er den Kopiervorgang starten will oder nicht.
Betätigt der User die Enter-Taste ohne zuvor eine Eingabe gemacht zu haben, bleibt der Wert der Variablen "JESNO" erhalten.
Wie mache ich das, dass die Variable "JESNO" bei keiner Eingabe keinen Inhalt hat bzw. den Inhalt löscht?
Oder wie kann ich den vorhandenen Text zuvor entfernen.
set JESNO= funktioniert auch nicht.
set JESNO="" ist doch falsch, oder?
Die betroffenen Stellen sind rot gekennzeichnet.
Hier der gesamte Inhalt des Batch Files
@echo off
color 1F
title CheckOut
echo Dies Anwendung erstellt selektierte Kopien der lokalen Arbeitsumgebung auf das benutzerbezogene Konto
:PASSWORD
set /p PWD=Bitte Passwort eingeben:
if [%PWD%] == echo Es konnte keine Eingabe erkannt werden && goto PASSWORD
echo.
echo Danke %PWD%
if not %PWD% == Super echo Keine Berechtigung fuer einen CheckOut && goto END
echo.
set nameFolder=Arbeitshilfen
set nameFolder[1]=Intern
set nameFolder[2]=Projekte
set nameFolder[3]=Control
set pathRootLocal=C:\Users\schwer-robert\AppData\Local\Workspace
set pathRootRemote=H:\Vertraulich\Workspace
:WORKHELP
echo WORKHELP
set pathSource=%pathRootLocal%\%nameFolder%
set pathTarget=%pathRootRemote%\%nameFolder%
echo Sollen die Inhalte von "%nameFolder%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto WORKHELP
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto INTERNAL
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
:INTERNAL
echo INTERNAL
set pathSource=%pathRootLocal%\%nameFolder[1]%
set pathTarget=%pathRootRemote%\%nameFolder[1]%
echo Sollen die Inhalte von "%nameFolder[1]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto INTERNAL
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto PROJECTS
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
:PROJECTS
echo PROJECTS
set pathSource=%pathRootLocal%\%nameFolder[2]%
set pathTarget=%pathRootRemote%\%nameFolder[2]%
echo Sollen die Inhalte von "%nameFolder[2]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto PROJECTS
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto CONTROL
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
pause >NUL
:CONTROL
echo CONTROL
set pathSource=%pathRootLocal%\%nameFolder[3]%
set pathTarget=%pathRootRemote%\%nameFolder[3]%
echo Sollen die Inhalte von "%nameFolder[3]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto CONTROL
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto END
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
pause >NUL
:END
echo END
echo Sollen die Anwenung beendet werden?
set /p EXIT=Mit der Eingabe von "Exit" wird die Anwendung beendet:
echo.
if %EXIT% == Exit goto EXIT
if %EXIT% == Ja goto EXIT
if %EXIT% == Ende goto EXIT
pause >NUL
cls && goto PASSWORD
:EXIT
echo Die Anwendung wird beendet
ping localhost -n 2 > NUL
pause
Vielen Dank.
Vielen Grüße von CopWorker
in meinem Batch File ist eine Problem was ich nicht verstehe.
Vor ab, ich komme aus der C/C++/C# Welt.
Mein Batch File soll sequenziell nacheinander mehrere Dateien aus verschiedenen Verzeichnissen kopieren.
Vor jeder Kopieranweisung stelle ich dem User die Frage ob er den Kopiervorgang starten will oder nicht.
Betätigt der User die Enter-Taste ohne zuvor eine Eingabe gemacht zu haben, bleibt der Wert der Variablen "JESNO" erhalten.
Wie mache ich das, dass die Variable "JESNO" bei keiner Eingabe keinen Inhalt hat bzw. den Inhalt löscht?
Oder wie kann ich den vorhandenen Text zuvor entfernen.
set JESNO= funktioniert auch nicht.
set JESNO="" ist doch falsch, oder?
Die betroffenen Stellen sind rot gekennzeichnet.
Hier der gesamte Inhalt des Batch Files
@echo off
color 1F
title CheckOut
echo Dies Anwendung erstellt selektierte Kopien der lokalen Arbeitsumgebung auf das benutzerbezogene Konto
:PASSWORD
set /p PWD=Bitte Passwort eingeben:
if [%PWD%] == echo Es konnte keine Eingabe erkannt werden && goto PASSWORD
echo.
echo Danke %PWD%
if not %PWD% == Super echo Keine Berechtigung fuer einen CheckOut && goto END
echo.
set nameFolder=Arbeitshilfen
set nameFolder[1]=Intern
set nameFolder[2]=Projekte
set nameFolder[3]=Control
set pathRootLocal=C:\Users\schwer-robert\AppData\Local\Workspace
set pathRootRemote=H:\Vertraulich\Workspace
:WORKHELP
echo WORKHELP
set pathSource=%pathRootLocal%\%nameFolder%
set pathTarget=%pathRootRemote%\%nameFolder%
echo Sollen die Inhalte von "%nameFolder%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto WORKHELP
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto INTERNAL
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
:INTERNAL
echo INTERNAL
set pathSource=%pathRootLocal%\%nameFolder[1]%
set pathTarget=%pathRootRemote%\%nameFolder[1]%
echo Sollen die Inhalte von "%nameFolder[1]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto INTERNAL
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto PROJECTS
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
:PROJECTS
echo PROJECTS
set pathSource=%pathRootLocal%\%nameFolder[2]%
set pathTarget=%pathRootRemote%\%nameFolder[2]%
echo Sollen die Inhalte von "%nameFolder[2]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto PROJECTS
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto CONTROL
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
pause >NUL
:CONTROL
echo CONTROL
set pathSource=%pathRootLocal%\%nameFolder[3]%
set pathTarget=%pathRootRemote%\%nameFolder[3]%
echo Sollen die Inhalte von "%nameFolder[3]%" auf persoenliches Laufwerk kopiert werden?
set /p JESNO=Auswahl (Ja/Nein/Exit) Eingabe hier:
echo.
if [%JESNO%] == echo Es konnte keine Eingabe erkannt werden && goto CONTROL
if %JESNO% == Exit goto EXIT
if not %JESNO% == Ja goto END
echo Mit "Enter" werden die Dateien kopiert.
echo Quelle: %pathSource%
echo Ziel: %pathTarget%
pause >NUL
copy %pathSource%\*.* %pathTarget%
pause >NUL
:END
echo END
echo Sollen die Anwenung beendet werden?
set /p EXIT=Mit der Eingabe von "Exit" wird die Anwendung beendet:
echo.
if %EXIT% == Exit goto EXIT
if %EXIT% == Ja goto EXIT
if %EXIT% == Ende goto EXIT
pause >NUL
cls && goto PASSWORD
:EXIT
echo Die Anwendung wird beendet
ping localhost -n 2 > NUL
pause
Vielen Dank.
Vielen Grüße von CopWorker
Bitte markiere auch die Kommentare, die zur Lösung des Beitrags beigetragen haben
Content-ID: 597462
Url: https://administrator.de/contentid/597462
Ausgedruckt am: 22.11.2024 um 22:11 Uhr
10 Kommentare
Neuester Kommentar
Moin,
Warum tust du dir dann Batch an, statt zeitgemäß auf Powershell zu setzen?
Sei's drum. Für dein Vorhaben ist choice eigentlich die bessere Wahl. Zum einen kann der Benutzer dann keine leere Eingabe mehr tätigen, da nur noch die Tasten "J" & "N" zulässig sind, zum anderen ist so auch keine falsche Eingabe mehr möglich.
Gruß Thomas
Warum tust du dir dann Batch an, statt zeitgemäß auf Powershell zu setzen?
Sei's drum. Für dein Vorhaben ist choice eigentlich die bessere Wahl. Zum einen kann der Benutzer dann keine leere Eingabe mehr tätigen, da nur noch die Tasten "J" & "N" zulässig sind, zum anderen ist so auch keine falsche Eingabe mehr möglich.
echo.Moechten Sie fortfahren?
choice
if "%errorlevel%" equ "1" echo.Benutzer hat Ja gewaehlt
if "%errorlevel%" equ "2" echo.Benutzer hat Nein gewaehlt
Gruß Thomas
Nein dann hat die Variable den Wert "", also 2 Anführungszeichen als Text.
:CONTROL
REM nach dieser Anweisung ist die Umgebungsvariable nicht definiert.
set "JESNO="
...
set /p ...
REM Hier wird geprüft ob die Variable noch immer nicht definiert ist, also der User ohne weitere Eingabe Enter gedrückt hat.
if not defined YESNO goto CONTROL
Alles immer noch komplett inkonsistenter Mist in Batch. Um das narrensicher zu machen ist viel mehr notwendig. Sollte der User ein einzelnes Anführungszeichen eingeben geht das trotzdem krachen.
Steffen
Moin,
Ohja. Wenn ich dieses ganze if-goto angucke, wird mir ganz schwindelig.
So sähe das in etwa in der PS aus. (Nicht getestet.)
Und was mich wirklich interessieren würde: Was soll dass denn?
Super Passwortabfrage. Tolles Passwort. Richtig schick ist aber, dass Du das dann auch noch im Klartext ausgibst.
Und noch eine Frage: Was machen solche Daten überhaupt im Userprofil. Sowas gehört auf den Server. Außerdem lässt man solche Kopien nicht die User machen, sondern das passiert automatisiert auf extra Datenträgern. Auch bekannt unter Backup.
Liebe Grüße
Erik
Ohja. Wenn ich dieses ganze if-goto angucke, wird mir ganz schwindelig.
$dirs = @("Arbeitshilfen","Intern","Projekte","Projekte","Control")
$path_local = "$env:USERPROFILE\AppData\Local\Workspace"
$path_remote = "H:\Vertraulich\$env:username"
foreach ($dir in $dirs) {
copy-item -Path "$path_local\$dir" -Destination "$path_remote\$dir" -Recurse -Force -Confirm
}
So sähe das in etwa in der PS aus. (Nicht getestet.)
Und was mich wirklich interessieren würde: Was soll dass denn?
:PASSWORD
set /p PWD=Bitte Passwort eingeben:
if [%PWD%] == echo Es konnte keine Eingabe erkannt werden && goto PASSWORD
echo.
echo Danke %PWD%
if not %PWD% == Super echo Keine Berechtigung fuer einen CheckOut && goto END
echo.
Super Passwortabfrage. Tolles Passwort. Richtig schick ist aber, dass Du das dann auch noch im Klartext ausgibst.
Und noch eine Frage: Was machen solche Daten überhaupt im Userprofil. Sowas gehört auf den Server. Außerdem lässt man solche Kopien nicht die User machen, sondern das passiert automatisiert auf extra Datenträgern. Auch bekannt unter Backup.
Liebe Grüße
Erik
Zitat von @CopWorker:
Doch leider muss es auch möglich sein mit der Eingabe von Exit
ganz aus dem Vorgang auszusteigen um das Ganze zu beenden.
Auch das wäre kein Problem. Man kann bei Choice ja mit Schalter /c beliebig viele Optionen angeben.Doch leider muss es auch möglich sein mit der Eingabe von Exit
ganz aus dem Vorgang auszusteigen um das Ganze zu beenden.
echo.Moechten Sie fortfahren? [J]a / [N]ein / [E]xit
choice /c jne
if "%errorlevel%" equ "1" echo.Benutzer hat Ja gewaehlt
if "%errorlevel%" equ "2" echo.Benutzer hat Nein gewaehlt
if "%errorlevel%" equ "3" goto :EoF
Moin,
So sind wir.
Dann lerne Powershell und lass das mit den Batches. Batch-Programmierung war schon immer gruselig. Du siehst ja an meinem Beispiel, mit wie wenigen Zeilen und schön übersichtlich das in der PS aussieht. Und wenn Du von C kommst, wird Dir die PS auch gut gefallen.
AFAIK in Batches gar nicht. Ich würde das mit dem PW eh lassen. Leg das Skript irgendwo ab, wo nur User darauf Zugriff haben, die das sowieso dürfen.
Noch ein Hinweis: PS-Skripts sind im Standard verboten. Stichwort: set-executionpolicy. Ich würde es für User nur mit signierten Skripts freigeben.
Liebe Grüße
Erik
So sind wir.
Dann lerne Powershell und lass das mit den Batches. Batch-Programmierung war schon immer gruselig. Du siehst ja an meinem Beispiel, mit wie wenigen Zeilen und schön übersichtlich das in der PS aussieht. Und wenn Du von C kommst, wird Dir die PS auch gut gefallen.
Das mit dem Passwort weiß ich noch nicht wie man einzelne Zeichen durch '*' ersetzt bevor man diese auf der Konsole ausgibt.
Wenn du´s mir verrätst, das wäre fein.
Wenn du´s mir verrätst, das wäre fein.
AFAIK in Batches gar nicht. Ich würde das mit dem PW eh lassen. Leg das Skript irgendwo ab, wo nur User darauf Zugriff haben, die das sowieso dürfen.
Noch ein Hinweis: PS-Skripts sind im Standard verboten. Stichwort: set-executionpolicy. Ich würde es für User nur mit signierten Skripts freigeben.
Liebe Grüße
Erik
Wenn man die PS auch wieder zur Hilfe nimmt dann geht auch das wenn man unbedingt will
@echo off
for /f "delims=" %%a in ('powershell -EP Bypass -C "[System.Runtime.InteropServices.Marshal]::PtrToStringAuto([System.Runtime.InteropServices.Marshal]::SecureStringToBSTR((Read-host 'Passwort eingeben' -AsSecureString)))"') do set "pass=%%a"
echo %pass%
Ich würde das mit dem PW eh lassen. Leg das Skript irgendwo ab, wo nur User darauf Zugriff haben, die das sowieso dürfen.
Bin ich auch der Meinung, denn auch so steht das Passwort schon unverschlüsselt im RAM. Oder wenn Passwörter warum auch immer dann diese schon im Windows-Tresor ablegen (cmdkey) dann reicht der Windows Logon.
Doch. Aber man muss schon masochistisch veranlagt sein oder ausreichend Spieltrieb haben ...
Source: https://www.dostips.com/forum/viewtopic.php?f=3&t=6382
Amen.
Steffen
@echo off &setlocal
<nul set /p "=Enter your password: "
call :HInput pw
echo Input length is %errorlevel%
setlocal EnableDelayedExpansion
echo Your password is !pw!
pause
goto :eof
:HInput [ByRef_VarName]
:: inspired by Carlos
if "%__HI__%" neq "__HI__" (
setlocal DisableDelayedExpansion EnableExtensions
set "CR=" &set "S=" &set "N=0" &set "__HI__=__HI__"
for /f "skip=1" %%i in ('echo(^|replace ? . /u /w') do if not defined CR set "CR=%%i"
for /f %%i in ('"prompt $H &for %%b in (1) do rem"') do set "BS=%%i"
)
set "C="
for /f skip^=1^ delims^=^ eol^= %%i in ('replace ? . /u /w') do if not defined C set "C=%%i"
setlocal EnableDelayedExpansion EnableExtensions
if "!CR!"=="!C!" (
echo(
if "%~1"=="" (
echo(!S!
endlocal &endlocal &exit /b %N%
) else (
if defined S (
for /f delims^=^ eol^= %%i in ("!S!") do endlocal &endlocal &set "%~1=%%i" &exit /b %N%
) else endlocal &endlocal &set "%~1=" &exit /b 0
)
)
if "!BS!"=="!C!" (
set "C="
if defined S set /a "N -= 1" &set "S=!S:~,-1!" &<nul set /p "=%BS% %BS%"
) else set /a "N += 1" &<nul set /p "=*"
if not defined S (
endlocal &set "N=%N%" &set "S=%C%"
) else for /f delims^=^ eol^= %%i in ("!S!") do endlocal &set "N=%N%" &set "S=%%i%C%"
goto HInput
Amen.
Steffen