Global variable not so global

Hi,

I’m very new to AS but have been programming in Perl for a number of years.

I have a need for a script to extract the artist, album & URL from an email, download the track and then import it into iTunes.

This was working reasonably well until last night. Now - for some reason - my global variables that are declared at the top of the script do not seem to be in scope (that is they don’t exist with the repeat loop). Would some learned AS programmer please cast his/her eye the script and tell me where I’m going wrong.

I haven’t tackled functions/subroutines/methods in AS so it is all inline. Sorry!


set downloadLocation to "Macintosh HD:Users:davidg:Desktop:"
set iTunesBaseDir to "Macintosh HD:Users:davidg:Music:iTunes:iTunes Music:"

using terms from application "Mail"
	on perform mail action with messages theMessages
		repeat with thisMessage in theMessages
			
			-- extract required info
			set theContents to content of thisMessage
			set oldDelimiters to AppleScript's text item delimiters
			
			-- get artist and album details
			set AppleScript's text item delimiters to {" request for "}
			set parseString to text items of theContents
			set parseString to item 2 of parseString
			set AppleScript's text item delimiters to {", "}
			set theArtist to text item 1 of parseString
			set theAlbum to text item 2 of parseString
			
			-- extract theURL
			set AppleScript's text item delimiters to {" at "}
			set parseString to text item 2 of parseString
			set AppleScript's text item delimiters to {return}
			set theURL to text item 1 of parseString
			
			-- extract filename
			set AppleScript's text item delimiters to {"/"}
			set parseString to text items of theURL
			set parseString to item 5 of parseString
			set AppleScript's text item delimiters to {"
"}
			set theTrack to text item 1 of parseString
			set AppleScript's text item delimiters to oldDelimiters
			try
				set fullDestPath to iTunesBaseDir & theArtist & ":" & theAlbum & ":"
			on error theError
				display dialog theError
			end try
			set partDestPath to iTunesBaseDir & theArtist & ":"
			set fullSrcFile to downloadLocation & theTrack
			set fullDestFile to fullDestPath & theTrack
			
			display dialog fullDestFile
			display dialog fullSrcFile
			
			-- download track
			-- if not (fullSrcFile exists) or not (fullDestFile exists) then
			tell application "Safari"
				try
					open location theURL
					close window 2
				on error theError
					display dialog "Safari: " & theError
				end try
			end tell
			
			-- Check to see if artist/album dir already exists. if not then create it
			tell application "Finder"
				if not (the folder fullDestPath exists) then
					if not (the folder partDestPath exists) then
						make new folder at alias iTunesBaseDir with properties {name:theArtist}
					end if
					
					make new folder at alias partDestPath with properties {name:theAlbum}
				end if
				
				repeat until item fullSrcFile exists
					delay 5
				end repeat
				
				move item fullSrcFile to folder fullDestPath
			end tell
			
			-- delete messsage
			tell application "Mail"
				try
					set read status of thisMessage to true
					set deleted of thisMessage to true
				on error theError
					display dialog "Mail: " & theError
				end try
			end tell
			
			-- import track into iTunes
			tell application "iTunes"
				try
					add fullDestFile to playlist "Library"
				on error theError
					display dialog "iTunes: " & theError
				end try
			end tell
			
		end repeat
	end perform mail action with messages
end using terms from

display dialog "complete"

tia

internet_pixie

To make a variable a global, you explicitly have to declare it as such at the top of your script. Using properties alone will probably suffice for you, though:

Jon


[This script was automatically tagged for color coded syntax by Convert Script to Markup Code]

excellent. Thanks for that it worked a treat.

Cheers

internet_pixie

OK Now I’m confused. The iTunesBaseDir and downloadLocation variables are now null again.

Here’s the complete code:


global downloadLocation, iTunesBaseDir

property downloadLocation : ""
property iTunesBaseDir : ""

set downloadLocation to (path to desktop) as Unicode text
set iTunesBaseDir to (((path to music folder) as Unicode text) & "iTunes:iTunes Music") as Unicode text

using terms from application "Mail"
	on perform mail action with messages theMessages
		repeat with thisMessage in theMessages
			
			-- these variables are blank again!?!
			display dialog iTunesBaseDir
			display dialog downloadLocation
			
			-- extract required info
			set theContents to content of thisMessage
			set oldDelimiters to AppleScript's text item delimiters
			
			-- get artist and album details
			set AppleScript's text item delimiters to {" request for "}
			set parseString to text items of theContents
			set parseString to item 2 of parseString
			set AppleScript's text item delimiters to {", "}
			set theArtist to text item 1 of parseString
			set theAlbum to text item 2 of parseString
			
			-- extract theURL
			set AppleScript's text item delimiters to {" at "}
			set parseString to text item 2 of parseString
			set AppleScript's text item delimiters to {return}
			set theURL to text item 1 of parseString
			
			-- extract filename
			set AppleScript's text item delimiters to {"/"}
			set parseString to text items of theURL
			set parseString to item 5 of parseString
			set AppleScript's text item delimiters to {"
"}
			set theTrack to text item 1 of parseString
			set AppleScript's text item delimiters to oldDelimiters
			set fullDestPath to iTunesBaseDir & theArtist & ":" & theAlbum & ":" as Unicode text
			set partDestPath to iTunesBaseDir & theArtist & ":"
			set fullSrcFile to downloadLocation & theTrack
			set fullDestFile to fullDestPath & theTrack
			
			-- download track
			tell application "Safari"
				try
					open location theURL
				on error theError
					display dialog "Safari: " & theError
				end try
			end tell
			
			-- Check to see if artist/album dir already exists. if not then create it
			tell application "Finder"
				try
					if not (the folder fullDestPath exists) then
						if not (the folder partDestPath exists) then
							make new folder at alias iTunesBaseDir with properties {name:theArtist}
						end if
						
						make new folder at alias partDestPath with properties {name:theAlbum}
					end if
				on error theError
					display dialog "Finder" & theError -- I always get an error here
				end try
				
				try
					repeat
						if (file fullSrcFile exists) then
							exit repeat
						else
							delay 5
						end if
					end repeat
				on error theError
					display dialog theError
				end try
				
				move item fullSrcFile to folder fullDestPath
			end tell
			
			-- delete messsage
			tell application "Mail"
				try
					set read status of thisMessage to true
					set deleted of thisMessage to true
				on error theError
					display dialog "Mail: " & theError
				end try
			end tell
			
			-- import track into iTunes
			tell application "iTunes"
				try
					add fullDestFile to playlist "Library"
				on error theError
					display dialog "iTunes: " & theError
				end try
			end tell
			
		end repeat
	end perform mail action with messages
end using terms from

display dialog "complete"

So within the repeat block these vars are blank. I’ve tried setting these vars the “old” way, i.e. as a string. but that makes no difference.

Most odd as it did work for a little while…

Any ideas?

Aha! Fixed it. :smiley:

Turns out that the global variables weren’t so global after all - again!

By changing the code to:


global downloadLocation, iTunesBaseDir

property downloadLocation : ""
property iTunesBaseDir : ""

using terms from application "Mail"
	on perform mail action with messages theMessages
		set downloadLocation to (path to desktop) as Unicode text
		set iTunesBaseDir to (((path to music folder) as Unicode text) & "iTunes:iTunes Music") as Unicode text
		repeat with thisMessage in theMessages

I was able to fix the problem. :slight_smile:

From the AppleScript Language Guide:

"Script properties are labeled containers for values that you can use in much the same way you use variables. The value of a script property persists until you recompile the script that contains it, and you can easily set the property’s initial value without resetting it each time the script is run. You can accomplish the same thing with a global variable, but it is usually more convenient to use a property for this purpose. "

You can view/download it here:
http://developer.apple.com/documentation/AppleScript/Conceptual/AppleScriptLangGuide/index.html

Good luck!
Tom