How to Check for Script Updates from a Remote Server in Batch Script
In a professional environment, automation scripts are rarely "one-and-done." They evolve to fix bugs and support new operating system features. Instead of waiting for users to report errors caused by outdated code, you can build an "Update Checker" into your Batch scripts. By querying a central server at startup, the script can notify the user that a newer, better version is available.
This guide will explain three ways to check for updates: via Web Server, via Local Network Share, and via File Hash.
Method 1: The Web-Based Check (HTTP/HTTPS)
This is the standard method for scripts distributed across different locations. You host a tiny text file (e.g., version.txt) on a web server containing only the version number (e.g., 2.1).
@echo off
setlocal
set "LocalVersion=2.0"
set "VersionURL=https://updates.example.com/myapp/version.txt"
set "TempFile=%temp%\remote_ver_%~n0.tmp"
echo [UPDATE] Checking for updates (current: v%LocalVersion%^)...
:: Verify curl is available
where curl >nul 2>&1
if %errorlevel% neq 0 (
echo [INFO] curl not available. Skipping update check.
goto :MainLogic
)
:: Download the remote version string silently
:: -f = fail on HTTP errors, -s = silent, --connect-timeout = limit wait
curl -f -s --connect-timeout 5 -o "%TempFile%" "%VersionURL%" 2>nul
if %errorlevel% neq 0 (
echo [INFO] Could not reach update server. Continuing with current version.
del "%TempFile%" >nul 2>&1
goto :MainLogic
)
:: Read the remote version
set "RemoteVersion="
set /p "RemoteVersion=" < "%TempFile%"
del "%TempFile%" >nul 2>&1
if not defined RemoteVersion (
echo [INFO] Empty version response. Skipping update check.
goto :MainLogic
)
:: Compare versions
if "%LocalVersion%"=="%RemoteVersion%" (
echo [OK] You are running the latest version (v%LocalVersion%).
) else (
echo.
echo [ALERT] New version available: v%RemoteVersion% (you have v%LocalVersion%^)
echo Download from: https://updates.example.com/myapp/download
echo.
)
:MainLogic
:: === Your main script logic goes here ===
echo Running main tasks...
pause
endlocal
Method 2: The Network Share Check (UNC Paths)
If your scripts are used inside a company office, you don't need a web server. You can compare the local script against the server copy using file timestamps or direct content comparison.
Script: Comparing Timestamps
@echo off
setlocal
set "SharePath=\\SERVER\CompanyScripts\DailyBackup.bat"
:: Verify the network share is accessible
if not exist "%SharePath%" (
echo [INFO] Cannot reach server copy: %SharePath%
echo Continuing with local version.
goto :MainLogic
)
:: Get the date/time of the local file
for %%i in ("%~f0") do set "LocalDate=%%~ti"
:: Get the date/time of the server file
for %%i in ("%SharePath%") do set "RemoteDate=%%~ti"
if "%LocalDate%"=="%RemoteDate%" (
echo [OK] Script is synchronized with the server.
) else (
echo [INFO] Server has a different version.
echo Local: %LocalDate%
echo Server: %RemoteDate%
echo.
echo Consider updating from: %SharePath%
)
:MainLogic
:: === Your main script logic goes here ===
pause
endlocal
Timestamp Limitations.
The %~ti modifier returns the file's last-modified date and time. Timestamps can differ if the file was simply copied (which may update the timestamp) without actual content changes. For precise change detection, use Method 3 (hash comparison).
Method 3: The Hash-Based Check (Deep Inspection)
Sometimes the version number is the same, but the code has been "Hotfixed." To detect even a single character change, compare the SHA-256 Hash of the local file against a known-good hash stored on the server.
@echo off
setlocal enabledelayedexpansion
set "RemoteHashFile=\\SERVER\Updates\script.sha256"
:: Verify the hash file is accessible
if not exist "%RemoteHashFile%" (
echo [INFO] Cannot reach hash file: %RemoteHashFile%
echo Skipping integrity check.
goto :MainLogic
)
:: 1. Calculate local hash
set "LocalHash="
for /f "skip=1 tokens=*" %%a in ('certutil -hashfile "%~f0" SHA256') do (
if not defined LocalHash set "LocalHash=%%a"
)
set "LocalHash=!LocalHash: =!"
:: 2. Read the expected hash from the server
set "RemoteHash="
set /p "RemoteHash=" < "%RemoteHashFile%"
set "RemoteHash=!RemoteHash: =!"
:: 3. Compare (case-insensitive for hex values)
if not defined LocalHash (
echo [ERROR] Could not compute local hash.
goto :MainLogic
)
if not defined RemoteHash (
echo [ERROR] Remote hash file is empty.
goto :MainLogic
)
if /i "!LocalHash!"=="!RemoteHash!" (
echo [OK] Script integrity verified. Code matches server master.
) else (
echo [WARNING] Local script does not match the server master!
echo Local: !LocalHash!
echo Server: !RemoteHash!
echo.
echo The script may be outdated or modified.
)
:MainLogic
:: === Your main script logic goes here ===
pause
endlocal
How to Avoid Common Errors
Wrong Way: Hardcoding Version URLs in multiple places
If you have 50 scripts and your server address changes, you have to edit 50 files.
Best Practice: Use a configuration file (like global_settings.ini) that holds the URL for all your scripts to reference.
Problem: Firewall Blocks
Many corporate firewalls block curl or bitsadmin by default.
Solution: If you are in a high-security environment, the Network Share method (Method 2) is almost always more reliable because it uses standard Windows SMB traffic.
Problem: Update check crashing the script
If the update check itself fails (network timeout, missing tool, corrupt response), it should never prevent the main script from running.
Best Practice: Always use goto :MainLogic on any update-check failure so the script continues with its primary task.
Best Practices and Rules
1. Minimal Traffic
Only check for updates once per day or once per session. Don't run the update check inside a loop that executes every 5 minutes, or you may be flagged as suspicious by your IT department's monitoring tools.
2. Graceful Failure
If the server is down, the check should fail silently and proceed to the main logic rather than crashing the script (as demonstrated in all three methods).
3. User Choice
Unless the update is a "Critical Security Patch," always inform the user that an update is available rather than automatically applying it. Let them choose when to update.
Conclusions
Building a remote update check into your Batch script is a sign of high-quality engineering. It ensures that your users are using the most stable version of your code and gives you a way to push improvements without manual deployment. Whether you use a simple version string or a precise cryptographic hash, the ability to detect updates from a distance is a foundational skill for modern automation.