I am writing a small applescript which retrieves all "unread" messages in the viewer and loops them.
I have two goals to complete:
I need to get the subject of each message and perform a regular expression to see if it's suitable for step 2 (ex: get emails with subject {.*})
I need to open each message on a separate window and after 4 seconds, I need to close that window and proceed with the next message
Do you know how to do these?
Thanks in advance.
The following applescript works for me, but I'm not sure how to do the regex matching. You can use the unix 'grep' function with applescript's 'do shell script' command, but I'm no expert in how to use grep properly. I'll leave that for someone else to answer.
on run
tell application "Mail"
set myInbox to mailbox "INBOX" of account 1
set myMessages to every message of myInbox
repeat with theMessage in myMessages
if read status of theMessage is false then
if my subjectIsInteresting(subject of theMessage) then
open theMessage
delay 4
close window 1
end if
end if
end repeat
end tell
end run
on subjectIsInteresting(subject)
-- do some regex magic here
return true -- for now
end subjectIsInteresting
For regexes -- If you're running the script on your own machine, or can distribute it bundled, you could use Satimage's Smile extension (http://www.satimage.fr/software/en/downloads/index.html) which adds regexes to Applescript.
I know you already have your answer but have you looked into Automator? For most standard scripts such as this, it can be less painful if you aren't too familiar with AppleScript. It's not very 'programmy' but it's quick and you'll spend less time debugging.
Related
I have this script that sends multiple text messages, but sometimes the script will send the first message to another number that I've recently messaged in Messages. I can't seem to find a pattern either, sometimes the bug happens and sometimes it sends all of the texts to the right number.
--usage: osascript sendMessage phone_number text_to_send amount_to_send
--Sends targetMessage to targetBuddyPhone repeatAmount times to targetMessage
on run {targetBuddyPhone, targetMessage, repeatAmount}
set counter to 0
repeat while counter < repeatAmount
tell application "Messages"
send targetMessage to buddy targetBuddyPhone of service "SMS"
set counter to counter + 1
end tell
end repeat
end run
How can I fix this?
Let's assume that in the following code
tell application "Mail"
tell first account
tell first mailbox
set myMessage to first message
set myAttachment to mail attachments of myMessage
end tell
end tell
end tell
the first message of the first mailbox of the first account actually has attachments. Let's further assume that the account in question is a GMail account (maybe that proves relevant) and that I am trying this on El Capitan.
On the "set myAttachments" line I always get the error "error in apple event routine, -10000" (losely translated from German). I have read in old threads that there was indeed a bug in the access to attachments. But I also saw a new thread that was talking specifics about how to best handle them (no mentioning of having no access at all).
What am I missing? Does it work? Maybe in general but not with GMail? Do I have to do something specific?
Thanks!
Sandro
The exact syntax for this is "mail attachement of myMessage" (without "s").
The script bellow is working perfectly on my side for selected emails:
tell application "Mail"
activate
set ListMessage to selection
repeat with aMessage in ListMessage
set AList to every mail attachment of aMessage
repeat with aFile in AList
if (downloaded of aFile) then
-- do something with aFile
end if
end repeat -- next file
end repeat -- next message
end tell
Are you sure the the message with attachement is in your first account/first mailbox?
I have an endless loop AppleScript application started at login. But there is a problem: I can not quit it unless im using SIGKILL. Is there any way to add some quit handler to it? Or there is better approach to make background process in AppleScript then "repeat - delay - end repeat"?
It doesn't sound like you're using an on idle handler, that's what you want to do.
on run
-- prep code goes here
end run
on idle
-- your code here
display dialog "TEST" giving up after 4
return 10
end idle
The above code will repeat itself every 10 seconds (based on the return value of 10, change as needed). The only other thing to keep in mind is this script needs to be saved as "Stay Open".
Hope this helps
While Manu G E asked a similar question twice, neither got an adequate answer, and I'm hoping I'll have better luck.
I'm writing an AppleScript to execute a handler when Messages.app receives a message. The script is being saved to ~/Library/Application\ Scripts/com.apple.iChat and is set in the Messages preferences to be the AppleScript handler.
When Messages is the frontmost application and a message is received, the active chat message received handler is fired twice. This doesn't seem to be a problem when Messages is in the background (received messages then fire message received, and that handler only once). I know which handler is fired because the portion that deals with the handlers looks like this:
using terms from application "Messages"
on message received _msg from _sender for _chat with _text_desc
if DEBUG then display dialog "message received"
message_received(_sender)
end message received
on chat room message received _msg from _sender for _chat with _text_desc
if DEBUG then display dialog "chat room message received"
message_received(_sender)
end chat room message received
on active chat message received _msg from _sender for _chat with _text_desc
if DEBUG then display dialog "active chat message received"
message_received(_sender)
end active chat message received
-- More handlers below, mostly like the above or empty
end using terms from
I set a DEBUG property to true and can see which handler gets fired.
I've tried working around this by writing a temporary file (using the UUID of the _sender). The message_received handler checks for the existence of the file and is supposed to do nothing if it's present. But this hasn't worked, even with random delays. I tried extending the length of the random delays, but this brings up errors about the AppleScript running for more than 10 seconds, even when enclosing the code within a with timeout of block.
Regardless of Apple's apparent support for executing AppleScripts in response to Messages events, perhaps I should look at some other mechanism to support this request from the client. I'm open to ideas.
Somehow I managed to find a simple but (very) dirty hack that seems to work for me, but I can't say if it will work on any machine. So "active chat message received" seems to be called twice at the same time, but I noticed something like do shell script "php -r 'echo microtime() >> file.txt'" sometimes reveals slightly different values.
I also use a property as a flag and try to take advantage of that shell execution tiny interval by writing to a file:
echo 0 > ~/Documents/flag.txt
then:
property flag : 0
using terms from application "Messages"
#...
on active chat message received theMessage from theBuddy
set response to false
set the_script to "cat ~/Documents/flag.txt"
set flag to do shell script the_script
do shell script "echo 1 > ~/Documents/flag.txt"
if flag is "0" then
set response to true
else
do shell script "echo 0 > ~/Documents/flag.txt"
end if
if response then
#this should be executed only once
end if
end active chat message received
#...
end using terms from
And voilĂ . Again I cannot say if that solution works everytime, and explaining why it actually works in my case is way beyond my capabilities right now. Still, I hope it will be useful. Cheers
I'm trying to write an Applescript that will make an outgoing Skype call at times scheduled by received invites from other parties.
I think I'm fine with the script to Skype's API to make the call, however I'm struggling with iCal with either method of
A) getting the script to run in the background and getting the time of all new events, or
B) getting the event alert to run a one-off script.
The issue with option B) is that although you can set events from within iCal so that the alert runs a script, I need to trigger this from events that have been received.
A typical example would be:
All scripts and iCal running on the Host
At 10am a User schedules an event (via google cal on portable device) for 3pm** and invites the the Host.
At 3pm the script on the Host uses Skype API to make a call to the User.
** this could just as equally be on a date in the future and the requirements still hold.
Many thanks for any advice!
Since iCal doesn't have any notifications (some applications do like iChat) you'll have to run a "stay open" applescript application. Something like this will do it for your "B" scenario. NOTE: you will have to add the path to your applescript file (the one that makes your Skype call) in the "applescriptPath" variable.
When launched it will get a listing of all the calendar events you have in iCal. It will then run itself every 5 minutes. When it runs it will check the current events against the list of events it originally made. If there are new events then your applescript will be added as an alarm to the new events. This way it keeps track of the current events between runs and only finds the new ones.
So this script should be a good starting point for you. Remember to save it as a stay-open applescript application. You probably will want to modify it. For example I have it checking every calendar for new events but you may have one particular calendar you want to target. Good luck.
property storedUIDs : {} -- we use this to check for new events, if an event is not in this list then it is new
global applescriptPath
on run
set applescriptPath to (path to desktop as text) & "myAlarm.scpt" -- the path to the applescript which is run as the alarm
end run
on idle
set newEvents to {}
tell application "iCal"
set theCals to calendars
set allUIDs to {}
repeat with aCal in theCals
tell aCal
set theseEvents to events
repeat with anEvent in theseEvents
set thisUID to uid of anEvent
set end of allUIDs to thisUID
if thisUID is not in storedUIDs then
set end of newEvents to contents of anEvent
end if
end repeat
end tell
end repeat
set storedUIDs to allUIDs
if (count of newEvents) is less than 5 then -- this will prevent the first run of the script from adding the alarm to every event
repeat with aNewEvent in newEvents
-- do something with this new events like add an alarm to run an applescript
set theAlarm to make new open file alarm at end of open file alarms of aNewEvent with properties {trigger interval:0, filepath:POSIX path of applescriptPath}
end repeat
end if
end tell
return (5 * 60) -- run every 5 minutes
end idle
on quit
set storedUIDs to {}
continue quit
end quit