Thursday, April 21, 2016

Generate filename-friendly datetime in Windows shell script

Summary: Windows batch script to generate timestamp for a filename.
People who write Windows Shell (AKA batch or .BAT) scripts for living sometimes need to create file (or directory) names using timestamp values based on local current date and time. This is not as trivial as it may sound. First, there is no shell command that would return a timestamp in a custom format, and the standard command may return a value containing illegal (for filenames) characters, such as colons.

There are articles that address this issue, but many proposed solutions do not accommodate region specifics, so they may work for an OS configured for one region, but fail for another.

The following script will generate a filename-friendly local timestamp for any region:
@echo off
rem -----------------------------------------------------------------
rem MAIN routine
setlocal & pushd

set timestamp=%ret%

echo %timestamp%

rem End of the main routine.
popd & endlocal 
goto :EOF

rem -----------------------------------------------------------------
rem Generate current timestamp in the format:
rem YYYYMMDDhhmmss (as shown here), or
rem YYYYMMDD_hhmmss (commented out), or
rem YYYMMDDhhmmssmmm (commented out), or
rem YYYMMDD_hhmmss_mmm (commented out)
rem Uncomment the block that generates the desired format and comment
rem out the alternate implementations.
rem Returns %ret%.

for /f "usebackq tokens=1,2 delims==" %%i in (`wmic os get LocalDateTime /value 2^>NUL`) do (
if '.%%i.'=='.LocalDateTime.' set ldt=%%j
rem Without milliseconds, without underscore: 20160421140125
set timestamp=%ldt:~0,4%%ldt:~4,2%%ldt:~6,2%%ldt:~8,2%%ldt:~10,2%%ldt:~12,2%
rem echo %timestamp%

rem Without milliseconds, with underscore: 20160421_140125
rem timestamp=%ldt:~0,4%%ldt:~4,2%%ldt:~6,2%_%ldt:~8,2%%ldt:~10,2%%ldt:~12,2%
rem echo %timestamp%

rem With milliseconds, without underscores: 20160421140125202
rem set timestamp=%ldt:~0,4%%ldt:~4,2%%ldt:~6,2%%ldt:~8,2%%ldt:~10,2%%ldt:~12,2%%ldt:~15,3%
rem echo %timestamp%

rem With milliseconds, with underscores: 20160421_140125_202
rem set timestamp=%ldt:~0,4%%ldt:~4,2%%ldt:~6,2%_%ldt:~8,2%%ldt:~10,2%%ldt:~12,2%_%ldt:~15,3%
rem echo %timestamp%

endlocal&set ret=%timestamp%
goto :EOF

See also:
How to get current datetime on Windows command line, in a suitable format for using in a filename?

No comments: