Friday, January 21, 2005

iPodder VBScript (Copy New PodCasts to My SD Card)

I have been an iPodder user for a while now. And like others I have been thinking about content management. When you are downloading large MP3 files it makes sense to find ways to try to manage these files. Because iPodder works with iTunes and because there is an API available for iTunes (on Windows) I have created some VBScript files to help me perform some common tasks.

First of all the way that I manage my files in iTunes is to display the “Last Played” column (if it is not visible in your iTunes just right click on the header and click “Last Played”). With the “Last Played” column I can quickly tell if I have listened to the PodCast or not.

The first thing that I wanted to manage was to be able to copy newly downloaded PodCasts to my Pocket PC (I have not broken down and bought and iPod yet). The script that I wrote will scan the files in iTunes looking for files that have been added in the last seven days (“Date Added” is within seven days), has not been listened to (“Last Played” is blank) and is in the iPodder download directory (this should be “My Documents\ My Received Files” directory). The files that are found will be copied to a directory that I pass into the script. I have also added a –U flag that will update the “Last Played” column to now (I assume that if I copy the files to my Pocket PC that I will listen to them on my Pocket PC).

Example:

I have a batch file with the following in it.
iNewPodCasts -U E:\Podcasts

Where iNewPodCasts is the VBScript file and –U is the flag to update the “Last Played” column and E:\Podcasts is the destination folder (my SD card that I will use in my Pocket PC). It should also be noted that the E:\Podcasts directory must exist.

Additionally I have also added a –L flag to the iNewPodCasts VBScript that will just list the new PodCast files. This is useful if you don’t want to copy the PodCast files but just see what the new PodCast are. If you use the –L flag the destination directory will be ignored.

Here is the code.
My apologies for the formatting. (Formatted)

001 '-----------------------------------------------------------------------------------
002 ' This will copy newly downloaded files from iPodder to a specified directory. Files
003 ' from the "My Documents\My Received Podcasts" directory that have not been played
004 ' and have been downloaded within the last seven days will be copied to the
005 ' destination folder. If the –U flag is in the command line argument then the
006 ' “Last Played” column will be set to now). If the –L flag is in the command line
007 ' then the files will only be listed and not copied.
008 '
009 ' By: Richard Todosichuk
010 ' rtodosic@hotmail.com
011 '-----------------------------------------------------------------------------------
012 Option Explicit
013
014 Dim fso ' Scripting.FileSystemObject object used to copy files.
015 Dim Shell ' WScript.Shell object used to access information about the windows shell.
016 Dim args ' The command line argurments.
017 Dim arg ' A command line argurment.
018 Dim iTunesApp ' iTunes.Application object used to access the iTunes application.
019 Dim mainLibrary ' The iTunes Library object.
020 Dim tracks ' The tracks collection object of the Library object.
021 Dim currTrack ' The current track object from the Library in iTunes.
022 Dim TestDate ' Now minus seven days.
023 Dim PodCastDir ' The iPodder root download directory.
024 Dim FileList ' The list of files that have been copied.
025 Dim DestFolder ' The destination folder.
026 Dim UpdateLastPlayed ' Flag to update Last Played column in iTunes.
027 Dim ListOnly ' Flag to display only a list of resent PodCasts.
028 Dim i ' A counter variable.
029 Dim Msg ' A string for a message.
030 Dim f ' A file object.
031
032 Set args = WScript.Arguments
033 Set fso = CreateObject("Scripting.FileSystemObject")
034
035 UpdateLastPlayed = False
036 ListOnly = False
037 DestFolder = ""
038
039 FileList = ""
040 TestDate = (Date - 7)
041
042 ' Scan command line arguments
043 For Each arg in args
044 ' Is it a flag.
045 If Instr(1, arg, "-", 1) = 1 or Instr(1, arg, "/", 1) = 1 Then
046 ' Check for list flag
047 If UCase(arg) = "-L" or UCase(arg) = "/L" then
048 ListOnly = True
049 End If
050
051 ' Check for update flag
052 If UCase(arg) = "-U" or UCase(arg) = "/U" Then
053 UpdateLastPlayed = True
054 End If
055 Else
056 ' Only grab the first none flag
057 If DestFolder = "" Then
058 DestFolder = arg
059 End If
060 End If
061 Next
062
063 If args.Count > 0 and (ListOnly or fso.FolderExists(DestFolder)) Then
064 If (not ListOnly) and (not fso.FolderExists(DestFolder)) Then
065 WScript.Echo "Folder " & chr(34) & DestFolder & chr(34) & " not found!"
066 Else
067 Set fso = CreateObject("Scripting.FileSystemObject")
068 Set Shell = CreateObject("WScript.Shell")
069 Set iTunesApp = CreateObject("iTunes.Application.1")
070 Set mainLibrary = iTunesApp.LibraryPlaylist
071 Set tracks = mainLibrary.Tracks
072
073 PodCastDir = Shell.SpecialFolders("MyDocuments") & "\My Received Podcasts\"
074
075 For i = 1 to tracks.Count
076 Set currTrack = tracks.Item(i)
077 IF currTrack.Kind = 1 And _
078 currTrack.DateAdded > TestDate And _
079 currTrack.PlayedDate = 0 AND _
080 currTrack.Location <> "" Then
081 If Instr(1, currTrack.Location, PodCastDir, 1) > 0 then
082 If (fso.FileExists(currTrack.Location)) Then
083 'Build msg of all files
084 If FileList <> "" Then
085 FileList = FileList & chr(13) & chr(10) & currTrack.Location
086 Else
087 FileList = currTrack.Location
088 End If
089
090 If not ListOnly Then
091 'Move the file
092 Set f = fso.GetFile(currTrack.Location)
093 f.Copy DestFolder & "\" & f.name
094 End If
095
096 If UpdateLastPlayed Then
097 'Set the lasted played to now.
098 currTrack.PlayedDate = Date
099 End If
100 End If
101 End If
102 End If
103 Next
104
105 If FileList = "" Then
106 WScript.Echo "No new files found!"
107 ElseIf ListOnly Then
108 WSCript.Echo "The following files are new PodCasts:" & _
109 chr(13) & chr(10) & chr(13) & chr(10) & FileList
110 Else
111 WSCript.Echo "The following files have been copied to " & chr(34) & DestFolder & chr(34) & ":" & _
112 chr(13) & chr(10) & chr(13) & chr(10) & FileList
113 End If
114 End If
115 Else
116 Msg = "Usage: iNewPodCasts [-L] [-U] [destFolder]"
117 Msg = Msg & chr(13) & chr(10) & chr(13) & chr(10) & _
118 "-L - Flag to only list new PodCasts. destFolder will be ignored if specified." & chr(13) & chr(10) & _
119 "-U - Flag to update the Last Played column in iTunes. destFolder must be specified." & chr(13) & chr(10) & _
120 "destFolder - The folder that new PodCasts will be copied too."
121 WScript.Echo Msg
122 End If

(download iNewPodCasts.vbs)
The code is a little long, but not that complicated. Lines 42 to 61 handle searching the command line arguments that were passed into the script. Line 63 checks to see if the arguments are valid and if not then lines 116 to 121 will display a message telling you how to call this script. If the command line arguments are valid then on line 69 the COM object that accesses iTunes is created and from that object the tracks collection of the LibraryPlayList are accessed. Then all tracks in the tracks collection are scanned and checks are performed at line the 77 to 82. Kind of 1 means that the track is a file. DateAdd must be less than the last seven days. PlayedDate is the same as the “Last Played” column and 0 means that it is blank. Location is the full file name of the track. I then check to see the location of the file is in the iPodder root directory and then I check to see that the file does in fact exist. (The file can be deleted or moved and iTunes may be out of date.) Lines 83 to 88 build a string that will be displayed at the end if the execution of the script. Line 93 does the actual copy. Line 98 updates the “Last Played” column to now. For the most part that is all there is to it.

I should also mention that if you are running McAfee or other virus scanners this script may not work.Virus scanner writers like to re-implement the windows system Scripting.FileSystemObject and WScript.Shell objects. You can re-register the original windows COM objects and this will work fine. However, you should be aware that these files have been re-implemented for a reason. I don’t mean to scare people away from doing this but I mention this for two reasons. First I spent hours trying to figure out why things would not work and I don’t what you to do the same. Furthermore, if you have other virus scanners and spyware installed, you may be in luck. Better (well more script friendly) virus scanners and spyware software will detect that you are trying to run these objects and will prompt you to make sure that you really want to run them. This is a good approach. This will allow you to run VBScript files in a secure way. So, you CAN have your scripts and execute them too.

3 comments:

Evil Homer said...

Excellent script Richard. I've been looking round for a good example of VB Script with iTunes because I want to write my own... After seeing yours I might have admit I'm clueless with these new fangled scripting languages and give up :)

How do you add your podcasts to iTunes? I've been searching for a script to do it. One of the references you can use is PlayFile:

Sub PlayFile(filePath As String)

Which will add the file to iTunes if it's not already in the library.

Eugene Haney said...
This comment has been removed by a blog administrator.
Eugene Haney said...

Using part of your script I was able to synthesize a simple one-line "add file to iTunes" command from a script I found on another website. Thanks for posting your VBScript.

rem This script will cause iTunes to addthe specified file.

rem Syntax:
rem AddFile "FullPath"
rem Example:
rem AddFile "C:\My Music\Devo\Freedom of Choice\Whip It.MP3"
rem Be sure to enclose the path in quotes if it includes spaces.


' Variables
dim iTunes, iTunesFile, FullPath, mainLibrary


' Get the full path of the file to play
if Wscript.Arguments.Count <> 1 then
' Error!
Wscript.Echo "Error! Please specify the full path (enclosed in

quotes) to the music file that you wish to play."
Wscript.Quit
end if

FullPath = Wscript.Arguments.Item(0 )


' Connect to iTunes app
set iTunes = CreateObject("iTunes.Application.1")
set mainLibrary = iTunes.LibraryPlaylist

' Add the file
mainLibrary.AddFile (FullPath)


' Done; release object
set iTunes = nothing


rem End of script.