I have an applescript that calls a shell script. Sometimes the shell script reaches its timeout period (and I don’t want to increase the timeout period). In this case, I want to kill the process that is still trying to run and then delete a file that is created. I think this has something to do with ‘try’ and ‘on error’, but when I tried to add it in it didn’t seem to work. Here’s what I have so far:
set myFolder to ((path to home folder as Unicode text) & "Pando:video:" as string) as alias
tell application "Finder"
set these_items to files of myFolder
repeat with i from 1 to the count of these_items
set this_item to item i of myFolder
set {name:Nm, name extension:Ex} to info for this_item as alias
set myFile to Nm & "." & Ex
set pPack to ((path to home folder as Unicode text) & "Test:pack:" & myFile & ".txt")
tell application "Finder"
if not (exists pPack) then
try
with timeout of 100 seconds
set theResponse to do shell script "/Applications/Utilities/pcl/pcl version"
end timeout
on error
--This is where I need to fill in
--IF variable theResponse does not come back with a value, I want to kill the process with the id of 23, as well as check to make sure the file pPack hasn't been created, but if it has to delete it.
end try
end if
end tell
end repeat
end tell
set myFolder to ((path to home folder as Unicode text) & "Pando:video:") as alias -- as string coercion is useless
tell application "Finder"
set these_items to files of myFolder
repeat with i from 1 to the count of these_items
set this_item to item i of myFolder
set {name:Nm, name extension:Ex} to info for this_item as alias
set myFile to Nm & "." & Ex
set pPack to ((path to home folder as Unicode text) & "Test:pack:" & myFile & ".txt")
tell application "Finder"
if not (exists pPack) then
try
with timeout of 100 seconds
set theResponse to do shell script "/Applications/Utilities/pcl/pcl version"
end timeout
on error
do shell script "kill 23"
try
do shell script "rm " & quoted form of POSIX path of pPack
end try
end try
end if
end tell
end repeat
end tell
For working reliably, I recommend to gather the UNIX process ID by this subroutine
get_UNIXid("Safari")
on get_UNIXid(proc)
try
tell application "System Events" to return unix id of process proc as Unicode text
on error
return false -- application is not running
end try
end get_UNIXid
Thanks for this info. You are obviously right that I need a better way of getting the process id because it changes. My application is not one that is understood by finder or anything, so the function you gave is not working. So then I tried this:
set the_pid to (do shell script "ps ax | grep \"pcl\" | grep -v grep | awk '{print $1}'")
do shell script ("kill -9 " & the_pid)
When I run that shell script in terminal, it returns the correct process id. But when I run it in applescript I get that the apple event timed out. Any suggestions?
I don’t use pcl, so I can’t test it.
Here is a different way to get the PID
getProcessPID("pcl")
on getProcessPID(proc)
try
return word 1 of (do shell script "/bin/ps -xco pid,command | /usr/bin/grep '[0-9] " & proc & "$' ")
on error
return false
end try
end getProcessPID
Arrrrr. This is driving me insane. For some reason, when I run this and it gets to the getProcessPID(“pcl”)
part, it is unable to kill the process and it freezes the script until I kill it manually. So once I start the script and it gets frozen, I can go to my shell and type in:
And it kills it just fine. But it will not work from within the script itself. It just hangs. In terms of the pcl application, it’s just a command line tool that lets me publish these video files to the application called Pando’s servers. And since I can kill it by typing the command directly in shell from my script, this makes me think it’s not something within the application itself, but some issue with my script. I’m including my script and my event log while it runs and where it stops (until I kill the process manually – then the script continues to run as soon as the process is killed).
Here is my full script:
set myFolder to ((path to home folder as Unicode text) & "Pando:video:" as string) as alias
tell application "Finder"
set these_items to files of myFolder
repeat with i from 1 to the count of these_items
set this_item to item i of myFolder
checkStableSize(this_item as alias) of me
set {name:Nm, name extension:Ex} to info for this_item as alias
if Ex is missing value then set Ex to ""
if Ex is not "" then set Nm to text 1 thru ((count Nm) - (count Ex) - 1) of Nm
set myFile to Nm & "." & Ex
set destinationFile to quoted form of POSIX path of (this_item as alias)
set pandoPackage to ((path to home folder as Unicode text) & "Pando:packages:" & myFile & ".pando")
tell application "Finder"
if not (exists pandoPackage) then
try
--Here we use Pando Command Line (PCL) to package up the file and then we return the URL to the script
with timeout of 10 seconds
--set thePackageUrl to do shell script "/Applications/Utilities/pcl/pcl version"
set thePackageUrl to do shell script "/Applications/Utilities/pcl/pcl publish --username=me --password=me --pandofile=\"/Users/vtaccess/Pando/packages/" & myFile & ".pando\" --sender=\"me\" --title=\"" & Nm & "\" --logdir=\"/Users/vtaccess/Pando/logs/\" --sessiondir=\"/Users/vtaccess/Pando/session/\" --certdir=\"/Users/vtaccess/Pando/cert/\" " & destinationFile & ""
--say Nm & space & "finished"
end timeout
on error
try
getProcessPID("pcl")
end try
try
do shell script "rm " & quoted form of POSIX path of pandoPackage
end try
end try
--Now we compose an email where the packageURL is key!
tell application "Mail"
set addrVar to "me@email.com"
set subjectvar to Nm & " has been uploaded to Pando"
set alert_message to Nm & " is up on the Pando server. The URL that you need to reference is " & return & my getTinyURL(thePackageUrl)
--name of (info for this_folder as alias)
set composeMessage to make new outgoing message with properties {subject:subjectvar}
tell composeMessage
make new to recipient at beginning of to recipients with properties {address:addrVar}
set the content to alert_message
end tell
send composeMessage
end tell
end if
end tell
end repeat
end tell
-- Handler to wait until a file is fully loaded.
on checkStableSize(theItem)
set F to quoted form of POSIX path of theItem
set sizeThen to first word of (do shell script "du -d 0 " & F) as integer --coercing to integer fixes the quote problem
repeat
try
delay 10 -- seconds (set to longer if needed)
set sizeNow to first word of (do shell script "du -d 0 " & F) as integer --coercing to integer fixes the quote problem
if sizeNow - sizeThen = 0 then exit repeat
set sizeThen to sizeNow
on error
exit repeat
end try
end repeat
end checkStableSize
on getTinyURL(U)
do shell script "curl --stderr /dev/null \"http://tinyurl.com/api-create.php?url=" & U & quote
end getTinyURL
on getProcessPID(proc)
try
return word 1 of (do shell script "/bin/ps -xco pid,command | /usr/bin/grep '[0-9] " & proc & "$' ")
on error
return false
end try
end getProcessPID
Here is what my event log spits out:
get item 3 of alias "Macintosh HD:Users:vtaccess:Pando:video:"
document file "CRV 2 Year Term.mp4" of folder "video" of folder "Pando" of folder "vtaccess" of folder "Users" of startup disk
get document file "CRV 2 Year Term.mp4" of folder "video" of folder "Pando" of folder "vtaccess" of folder "Users" of startup disk
alias "Macintosh HD:Users:vtaccess:Pando:video:CRV 2 Year Term.mp4"
end tell
tell current application
do shell script "du -d 0 '/Users/vtaccess/Pando/video/CRV 2 Year Term.mp4'"
"2614264 /Users/vtaccess/Pando/video/CRV 2 Year Term.mp4"
do shell script "du -d 0 '/Users/vtaccess/Pando/video/CRV 2 Year Term.mp4'"
"2614264 /Users/vtaccess/Pando/video/CRV 2 Year Term.mp4"
end tell
tell application "Finder"
get document file "CRV 2 Year Term.mp4" of folder "video" of folder "Pando" of folder "vtaccess" of folder "Users" of startup disk
alias "Macintosh HD:Users:vtaccess:Pando:video:CRV 2 Year Term.mp4"
info for alias "Macintosh HD:Users:vtaccess:Pando:video:CRV 2 Year Term.mp4" given «class Krtn»:{name:"nm", name extension:"ex"}
get document file "CRV 2 Year Term.mp4" of folder "video" of folder "Pando" of folder "vtaccess" of folder "Users" of startup disk
alias "Macintosh HD:Users:vtaccess:Pando:video:CRV 2 Year Term.mp4"
path to home folder as Unicode text
"Macintosh HD:Users:vtaccess:"
exists "Macintosh HD:Users:vtaccess:Pando:packages:CRV 2 Year Term.mp4.pando"
false
do shell script "/Applications/Utilities/pcl/pcl publish --username=vmx@vermontmediaexchange.net --password=letSshare! --pandofile=\"/Users/vtaccess/Pando/packages/CRV 2 Year Term.mp4.pando\" --sender=\"LPCTV\" --title=\"CRV 2 Year Term\" --logdir=\"/Users/vtaccess/Pando/logs/\" --sessiondir=\"/Users/vtaccess/Pando/session/\" --certdir=\"/Users/vtaccess/Pando/cert/\" '/Users/vtaccess/Pando/video/CRV 2 Year Term.mp4'"
current application
getProcessPID("pcl")
Great, that was mostly the issue. Thank you for the help! By changing that, and then combining what Stefan gave me and the piece I was trying to run before, I changed the function to this, and now it works properly:
on getProcessPID(proc)
try
set myKill to (do shell script "/bin/ps -xco pid,command | /usr/bin/grep '[0-9] " & proc & "$' ")
do shell script ("kill -9 " & myKill)
on error
return false
end try
end getProcessPID