Stanislav Kamaletdin (twitter) today asked on #sqlhelp how to backup all user databases with TDP for SQL Server:

My first thought was to use the “*” wildcard, but this actually means all databases, not just user databases.
I ended up adapting a small batch file I’ve been using for a long time to take backups of all user databases with full recovery model:
@ECHO OFF
SQLCMD -E -Q "SET NOCOUNT ON; SELECT name FROM sys.databases WHERE name NOT IN ('master','model','msdb','tempdb')" -h -1 -o tdpsql_input.txt
FOR /F %%A IN (tdpsql_input.txt) DO CALL :perform %%A
GOTO end_batch
:perform
tdpsqlc backup %1 full /configfile=tdpsql.cfg /tsmoptfile=dsm.opt /sqlserver=servername /logfile=tdpsqlc.log
:end_batch
Most of the “trick” is in the SQLCMD line:
- -Q "query" executes the query and returns. I added "SET NOCOUNT ON;" to eliminate the row count from the output.
- -h -1 suppresses the column headers
- -o tdpsql_input.txt redirects the output to a text file
With that syntax I create a text file that contains a database name for each line, that I can use in a FOR loop.
FOR /F %%A IN (tdpsql_input.txt) DO CALL :perform %%Ameans: "For each token found in the file tdpsql_input.txt, assign the token to variable %%A and pass it to the function named 'perform'".
The function "perform" simply invokes tdpsqlc using the parameter %1.
I know that PowerShell would have been a better choice, but I coded this script a long time ago, when PS was not an option for me.
After all, the old DOS batch language still does the trick.
Archived WordPress comments (16)
Historical comments from the original site; this archive is read-only.
Do you know where I can find initial CMD files of recommended CDM files for TDP?
I tried to workaround this by adding " marks to SQL clause e.g. select ('"' + name + "'") from sys.databases which works fine from SQL Server Management Studio, but in SQLCMD it doesn't seem to work correctly and the whole command crashes.
del sqlinput.sql
echo SET NOCOUNT ON; SELECT '"'+name+'"' FROM sys.databases WHERE name NOT IN ('master','model','msdb','tempdb') and is_read_only = 0 and state = 0 and recovery_model = 1 > sqlinput.sql
SQLCMD -S . -i sqlinput.sql -h -1 -o tdpsql_input.txt
FOR /F %%A IN (tdpsql_input.txt) DO CALL :perform %%A
GOTO end_batch
I suppose that square brackets would work as well. You could obtain the same effect using QUOTENAME on the database name.
Of course, normally you don't need to modify this script, but I ran into some Sharepoint databases which were named as "User Database Something Important Next Line". That's the real reason for modifying this.
Sharepoint is a pain in many ways. Or maybe I should say "sharepain" :-)
This is what I have, but when I added these new lines, I broke the lopp... It backs up the first db only and exits.
@ECHO OFF
cd "C:\Program Files\Tivoli\tsm\TDPSql"
SQLCMD -E -Q "SET NOCOUNT ON; SELECT name FROM sys.dm_hadr_availability_replica_states ars INNER JOIN sys.databases dbs ON ars.replica_id = dbs.replica_id WHERE name NOT IN ('master','model','msdb','tempdb') and role_desc='PRIMARY'" -h -1 -o tdpsql_input.txt
FOR /F %%A IN (tdpsql_input.txt) DO CALL :perform %%A
GOTO end_batch
:perform
tdpsqlc backup %1 full /BackupMethod=Legacy /BackupDestination=TSM /SqlServer=COSQL3SP /SQLAUTHentication=INTegrated /Stripes=8 /Logfile=full_backup_defaultlog
:end_batch
findstr "error" full_backup_defaultlog
set rc=%errorlevel%
if %rc% eq 0 start powershell Send-MailMessage -To "l.peoples@juiceplus.com" -Subject 'COSQL3SP Backup Failed' -From "Sql@COSQL3SP.nsanet.local" -Body 'COSQL3SP FULL Backup Failed' -smtpServer relay.nsanet.local
However, tomorrow I will take a look from my computer.