Solved Move files using BATCH script only if another file exists

May 23, 2013 at 23:02:32
Specs: Windows 7
I am trying to do something similar to this guy:

I want to copy my .wtv & .xml files to a new directory (network location eventually) but I only want to move them if the .xml file exists.

I could not modify the code above and make it work. My %%a has the extension on the end. This is what I used for my code:
::@echo off & setLocal enableDELAYedeXpansioN
pushd "C:\Recorded TV"
for /f "tokens=* delims= " %%a in ('dir/b') do (
pushd "%%a"
if exist %%a.xml echo MOVE /-Y "C:\Recorded TV\%%a.wtv" "C:\Analyzed"
goto :eof

I know that the "dir/b" portion of my code is different, but if I used "dir/b/s/ad" the script would not run. I know the the /s is for and I don't need it but I could not find what the /ad is. I'm new to all of this so thanks for your help in advance.

I am running this on a Windows 7 x64 machine. If you need any more info let me know what you need and I'll provide.

See More: Move files using BATCH script only if another file exists

May 24, 2013 at 00:06:37
M2's answer was designed to recurse, which you apparently don't need, so that changes things. I don't know if you want "any" xml (*.xml) or a specific name, but I'll try to guess: "for all .xml file, move the same-name .wtv file to dir 'analyzed'
::==== begin batchscript
pushd "C:\Recorded TV"
for /f "tokens=* delims= " %%a in ('dir/b *.xml') do (
:: SAFETY ON. remove the echo from foll line to arm weapon
echo MOVE /-Y "%%~na.wtv" "C:\Analyzed"
::===== end
I left it "safetied", since i didn't test. remove "echo" from line 4 to lock-and-load.

Report •

May 24, 2013 at 13:53:38
✔ Best Answer
THANKS nbrane!!!!!

That worked (any you guessed right all xml file, move the same-name wtv file), but this shows how little I really know about this stuff...

What I really need it to do is look for a .xml file in one directory, check the time and if it's older than "x" seconds then move the .wtv file (which is in another directory) to the "analyzed" directory. I'm not too sure if this is too much for a batch file or not but it seems like you guys know your stuff!

Thanks again. Do you know of some tutorials/book that could help me learn the syntax?

Report •

May 24, 2013 at 19:57:44
"Do you know of some tutorials/book that could help me learn the syntax?"

Not really, I learned what little I know from this forum and from using the /?
(FOR /?, SET /?, IF /?, SETLOCAL /? etc.) And use Google.

"What I really need it to do is look for a .xml file in one directory, check the time and if it's older than "x" seconds then move the .wtv file (which is in another directory) to the "analyzed" directory. I'm not too sure if this is too much for a batch file..."

The time math (getting the difference between one time and another time) is messy in batch. Being lazy, I just use vbscript for those jobs:
wscript.echo datediff("s",wscript.arguments(0),wscript.arguments(1))

save that line (as simple text) with a .vbs extension. To use in batch:
:: sample batch snippet
set tlimit=60
for %%a in (*.xml) do (
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do
echo file: %%a, age in seconds: %%z
if %%z gtr %tlimit% move "c:\xx\yy\%%~nxa" "nn\analyzed" & move "%%a" "\wherever"
::======== end
Note that I moved the xml files "somewhere else" to keep from repeating over ones that had already been processed. You could also rename then to flag them out.

Report •

Related Solutions

May 24, 2013 at 22:56:02
THANKS again nbrane!

I must be missing something because I cannot get this to work.
I created a file named td.vbs
this is exactly what's in the file:
wscript.echo datediff("s",wscript.arguments(0),wscript.arguments(1))

I then have a bat file that looks like this:
:: I set the limit to 1 for testing only...
set tlimit=1
::I added this line because I figured I need to point the bat to the location???
pushd "C:\Recorded TV"
for %%a in (*.xml) do (
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do
echo file: %%a, age in seconds: %%z
if %%z gtr %tlimit% move "C:\Recorded TV\%%~nxa" "C:\Analyzed" & move "%%a" "C:\Analyzed\XML"

If I run the .vbs file separately I get a runtime error, but that is to be expected because I'm not "feeding" it any values. I tried to remove "echo" and other stuff, but the bottom line I cannot figure out for the life of me what I'm doing wrong.

Thanks for your help!

Report •

May 24, 2013 at 23:55:22
You're doing good work, you narrow things down!
this is what I see, and it's totally "my bad":
::= bad
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do
::== fix?
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do (

in other words, one "(" might be the bitch, and that's my fault.
The vbs takes in two date/times and spits out the difference in seconds. You can always test it like this:
cscript td.vbs "date1 time1" "date2 time2"
like: cscript td.vbs "4/30/13 14:23" "5-23-2013 2:22 pm"
(you need the quotes to allow spaces inside the arguments)
as you can see, it really does the heavy lifting on date/time formats and calculations. That's why I use it.
Let me know if you encounter further difficulties.

Report •

May 26, 2013 at 20:12:00
No worries, I actually caught that but I had changed enough stuff that once I had put in the "(" it would not execute... so it's my bad too.

...Ok sorry for bugging you some more, but I have spent more time than I would like to admit on trying to figure this out but I'm having no luck...

This is the exact code that I'm running:
set tlimit=900
pushd "E:\Recorded TV"
for %%a in (*.xml) do (
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do (
::for /f "tokens=*" %%z in ('cscript datedifftest.vbs "%%~ta" "%date:~4% %time:~0,8%"') do (
echo file: %%a, age in seconds: %%z
if %%z gtr %tlimit% del "E:\Recorded TV\%%~na.log" & del "E:\Recorded TV\%%~na.txt" & move "E:\Recorded TV\%%~na.wtv" "E:\Recorded TV\Analyzed" & move "E:\Recorded TV\%%~na.edl" "E:\Recorded TV\Analyzed" & move "E:\Recorded TV\%%a" "C:\Users\Public\DvrmsToolbox\CommercialsXml"

wscript.echo datediff("s",wscript.arguments(0),wscript.arguments(1))

wscript.echo datediff("s",wscript.arguments(0).DateLastModified,Now)

Everything is working except for the if statement. It will execute but it will do it no matter what the time difference is. For example if there is an XML that is 1 sec old it will still move the file even though it is not greater than 900 sec. (I actually changed this to be much greater for testing)??? I'm a little confused here, but playing around with the script (because what I really need it to do is run everything in the IF statement once the XML is done being modified, not from its creation date) it seems like my VBS script needs to be in the original XML file location (E:\Recorded TV\ in my case) not the location of the BAT file (assuming my BAT file is not in my Recorded TV directory). Is this correct? Also how are arguments(0) & arguments(1) getting populated? I'm at a loss here and that is why I cannot get my datedifftest.vbs to work (I think). I was able to see that your orignal tb.vbs script was giving me a time in seconds (why the IF statement would still execute if it were not true is beyond me though).

Thanks again for your help, and sorry for bugging you.

Report •

May 26, 2013 at 22:14:48
Aagh! ya got me, again. Sorry. The IF comparison is always as a string (left-justified). F/e: 6 is always greater than 1 even if the six is "6" and the one is "123456"
(they needed to put an "IF /A" option, but they never will at this point). First, I had to fix the vbscript. I couldn't use "0" for padding due to "octal" BS, and I couldn't use spaces due to argument parsing. So, I just used underscores:
wscript.echo "________________________"&datediff("s",wscript.arguments(0),wscript.arguments(1))

It doesn't matter how many underscores you put, just put a whole bunch. the batch will clip off ever how many it needs.

Here's the modified batch (using the modified vbs):

@echo off & setlocal enabledelayedexpansion
set tlimit=__________4500
::pushd "E:\Recorded TV"
for %%a in (*.xml) do (
for /f "tokens=*" %%z in ('cscript td.vbs "%%~ta" "%date:~4% %time:~0,8%"') do (
rem echo file: %%a, age in seconds: [%%z]
set f=%%z
:: just using 14 for now.
set f=!f:~-14!
echo file: %%a age in seconds: [!f!]
if "!f!" lss "%tlimit%" (
echo **** [%%z] [%tlimit%] %%a to be processed...
echo del "E:\Recorded TV\%%~na.log"
echo del "E:\Recorded TV\%%~na.txt"
echo move "E:\Recorded TV\%%~na.wtv" "E:\Recorded TV\Analyzed"
echo move "E:\Recorded TV\%%~na.edl" "E:\Recorded TV\Analyzed" 
echo move "E:\Recorded TV\%%a" "C:\Users\Public\DvrmsToolbox\CommercialsXml"
::===== end

hope this helps. I left everything "safetied" with "echo", I didn't run a full trial.

edited to fix mistake etc.

Report •

May 27, 2013 at 07:09:51
nbrane, I'm at a loss. I'm not sure what is really going on here... It is still executing no matter the limit.
1.) Should i comment out line "set f=!f:~-14!" ? I don't know what's going on here (I've ran it with and without)
2.) Is the vb script finding the difference between the current time and the last modified time?
3.) Is there a way for me to print f to the screen so I can check the time in seconds?
4.) The file names are generally long does that mean I need to add lots of "_"?
5.) Thanks for your help!

Report •

May 27, 2013 at 09:12:41
I suspect there's more to the story than what's being told. For instance, why wait for the XML fies to reach a specific age before acting on the corresponding video file? Wouldn't it be easier and quicker to either add this to your commercial detection workflow? Couldn't you have this script check to see if the XML generation program is not running, and forget the date/time math?

How To Ask Questions The Smart Way

Report •

May 27, 2013 at 12:41:58
To see the times, just enable this line:
rem echo f: [!f!]
might add %%a to see the filename as well: echo file: %%a age: !f!
"Should i comment out line "set f=!f:~-14!" ? "
no, that makes it the correct size.
The length of the filenames has no effect on the length of the time-string.
I cut/pasted from my post above, and ran it on my system and it worked ok (after I added the third closing parenthese that I managed to lose in transit - I guess you caught that or you would not be getting any output whatsoever). Make sure that whatever the total length of the tlimit is the same as the length in f:~-14
Also, it's painfully slow, even though it worked, so you might want to consider other approaches, as Razor mentioned. If you want a vbscripted version, I can probably do that, but I haven't learned enough powershell to do one in that. Pmail me with an exact copy of your scripts (vb and batch) and I'll test-run them on my end.

Report •

Ask Question