Quit script from Dock

I have script running in Dock but cannot quit it using Docks Contectual Menu and when Mac is shutting down, it halts shutting down process. Only Force Quit works. How i need to modify script?

We’ll have to take a look under the hood. I bet you have some repeat loop going that has no exit. But that’s just a hunch till you show it to us.
SC

As sitcom says, it’s very difficult to say - without knowing more about the script and what it does.

It’s not, by any chance, a stay-open application with a quit handler - but no ‘continue quit’ statement - is it?

I tried to save it as stay-open and also dont stay-open, but it dont work. How can i exit repeat loop?

Now when list1 changes, i force quit script and manually edit list1. How can i save list1 to preference file on quit and read it to list1 when script runs? How can i add dialog asking “do you want to APPEND (item numb in list2) to list1?”?

Thanks


--if script founds new string in list2, it should add it to list1

set list1 to {"lij", "234", "wert", "yiuo"}

repeat with count1 from 1 to 2000 --i want this to be infinite, but 2000 is enough too
	set list2 to {"abc", "fghj", "wert", "dt342"} --this list changes over time, this list is just example
	
	repeat with numb from 1 to the (count of the list2)
		if list1 does not contain item numb in list2 then
			say "nope" & numb
		else
			say numb
		end if
	end repeat
	
	delay 10
end repeat

on quit
	display dialog ¬
		"Really quit?" buttons {"No", "Quit"} default button "Quit"
	if the button returned of the result is "Quit" then
		continue quit
	end if
end quit

Your script doesn’t really help to know what you’re trying to accomplish. Your “on quit” routine works, but that’s about all I can make out of it. Can you tell us in detail what it is your tring to do with these lists?
SC

List2 is actually:


tell application "Finder" to set list2 to name of every process

My script alerts if there is new process running so i can check it out what it is.

BTW, is there any way to get more complete list of running processes than “name of every process”? I think this dont list all processes running in system? I need only names of processes in list.


repeat
	
	tell application "System Events" to set visible of every process to true
	tell application "System Events" to get name of every process
	set ProcessList1 to result as list
	
	delay 1
	
	tell application "System Events" to set visible of every process to true
	tell application "System Events" to get name of every process
	set ProcessList2 to result as list
	
	if ProcessList1 is not ProcessList2 then
		
		tell application "System Events" to set frontmost of process "ProcessCheck" to true--I saved as an application named "ProcessCheck"; this line brings the alert to the front
		display dialog "There there has been a change in the processes active in the system"
	end if
	
	
end repeat

You can see what it does. It checks the process list, waits a second, and then checks again. If the list changes, you get an alert. It’s an infinite repeat loop, but when the alert comes up, clicking “Cancel” quits the app.
The process list is very limited, definitely not “all” the processes. This script seems pretty useless but I figured you would like to see the proper code for what you were doing. I think there are scripts for Terminal (shell scripts, as they are called) that would return a more complete list.
SC

Hi,

I’ve never experienced this, but a short while ago someone said a process wasn’t showing using the System Events. Instead the person used the unix ps command I think. Here’s what I came up with to get a list of processes:

set process_list to (rest of paragraphs of (do shell script “ps -xco command”))

I’m using Jaguar 10.2.8 and the quit handler has a bug. If an error occurs, then the script doesn’t continue. On the other hand, ‘continue quit’ works. So if they fixed it in Panther or Tiger, then you can use the quit handler with an idle handler instead of a repeat loop. If they didn’t fix it, then I’d stay away from the quit handler.

I just tested out this stay open script with the quit handler and it now works. If the user presses cancel in the dialog, then the idle handle continues to fire. Apple must have fixed it in some update (Yeah Apple!).

global p_list

on run
set p_list to (rest of paragraphs of (do shell script “ps -xco command”))
end run

on idle
set cur_list to (rest of paragraphs of (do shell script “ps -xco command”))
repeat with this_p in cur_list
set p to (contents of this_p) as string
if p is not in p_list then
set end of p_list to p
say "nope " & p
quit
else
say p
end if
end repeat
return 10
end idle

on quit
activate
display dialog “Really quit?”
continue quit
end quit

I don’t know about writing the list to preference file, but I do know how to write a list using the standard additions read/write commands.

gl,

I switched around the conditional taking out the ‘not’.

global p_list

on run
set p_list to (rest of paragraphs of (do shell script “ps -xco command”))
end run

on idle
set cur_list to (rest of paragraphs of (do shell script “ps -xco command”))
repeat with this_p in cur_list
set p to (contents of this_p) as string
if p is in p_list then
say p
else
set end of p_list to p
say "nope " & p
quit
end if
end repeat
return 10
end idle

on quit
activate
display dialog “Really quit?”
continue quit
end quit

gl,

If all you want is to have the script remember variable values (text, numbers, lists, etc.), then there’s really no need to write to/read from a preferences file. You can use properties instead - since their values are persistent from one run to the next. (See the example below.)

As already mentioned, running a shell ‘ps’ command will give you a bit more info than System Events or Finder - although I can’t help wondering just how useful the extra bits (e.g: “ATSServer”, “Window Manager”, “pbs”, “AppleSpell”, “tcsh”, “man”, “sh”, “sh”, “less”, etc.) will be to you - since they’re generally considered to be system components anyway. However, I’ll leave that up to you… (It may also be worth noting that ‘ps’ normally truncates long process names to the first 16 characters only.) :slight_smile:

I’m currently running 10.2.8 too, kel - and, as far as I’m aware, this issue has ever been thus. A quit handler isn’t an essential requirement for a stay-open script application. However, if one is included, then it should contain a ‘continue quit’ statement. A problem may arise if an error occurs within the quit handler before the ‘continue quit’ statement is reached - thus preventing the application from quitting (and necessitating - as a last resort - a force-quit). To avoid this type of situation, it’s important to trap any potential errors within the quit handler, so that the ‘continue quit’ statement can be executed successfully.

Incidentally, I see that kel opted for an idle handler rather than using ‘delay’. It’s worth noting that, if a script/application is required to run for lengthy periods to carry out periodical operations, an idle handler is well worth considering - since it drains fewer cpu cycles than ‘delay’.

I confess that I’m still not entirely sure what you’re ultimately trying to achieve here, cirno (but then, I’ve always been a bit slow on the uptake). :wink:

Nevertheless, I’m including an example that may help to demonstrate some possible techniques - some of which have already been suggested.

When the script is first run, it checks for processes that are already running. You should then be asked to select those that you wish to add to the list (‘storedProcessList’) - which will then be ignored on all future runs. Items not selected will also be ignored - but only for the rest of the session. In other words, the next time you launch the script application, you will be asked again to consider any items not contained by ‘storedProcessList’. (All this will probably make more sense if you just try running the script as a stay-open application - and watch what happens…) :slight_smile:

(* save this script as a stay-open application *)

property storedProcessList : {}

global previousProcessList

on everyItem from currProcessList apart from mainProcessList
	set newList to {}
	repeat with currProcess in currProcessList
		tell currProcess to if it is not in mainProcessList then set newList's end to it
	end repeat
	newList's contents
end everyItem

on processesToAdd from currProcessList
	tell application (path to frontmost application as Unicode text) to set chosenProcesses to choose from list currProcessList with prompt ¬
		"Please select any process(es) you wish to add to the process list:" OK button name "Add" cancel button name "Ignore All" with multiple selections allowed
	if chosenProcesses is false then return {}
	chosenProcesses
end processesToAdd

on idle
	tell application "System Events" to set currProcessList to name of processes
	if currProcessList is not previousProcessList then
		set newProcessList to everyItem from currProcessList apart from storedProcessList & previousProcessList
		if (count newProcessList) > 0 then set storedProcessList to storedProcessList & (processesToAdd from newProcessList)
		set previousProcessList to currProcessList
	end if
	10 (* seconds to next check *)
end idle

on run
	set previousProcessList to {}
end run

Hi Kai,

The poster I wrote about was using an application whose process didn’t show up using the Finder. It wawn’t a system application. Using the unix ps solved it for that person.

It’s been a while since I tested the issue with the quit and idle handlers and I spoke too soon. Three ways I can think of to quit the script app is through the menu (or command + Q), the ‘quit’ command within the script, and the dock quit. If you run the following script one of two things happens on my computer depending on which way the quit was sent.

global c

on run
set c to 0
end run

on idle
beep 2
set c to c + 1
if c mod 3 = 0 then quit
return 2
end idle

on quit
display dialog “Quit?”
continue quit
end quit

If I quit it through the menu, then the script just sits there after hitting the Cancel button. If the quit command or the dock quit is used and I press Cancel, then it jumps back to the idle handler. One solution I can think of is to set a flag when the condition c mod 3 = 0 is true. Only then will the user have a choice of quitting or not quitting.

gl,

Right enough, Kel - I see what you mean. That sure looks like buggy behaviour to me. Damned if you don’t learn something new every day… :slight_smile:

I notice that, if the script does become ‘jammed’ from this type of quit/cancel, it can be reactivated by clicking on its icon in the dock. It then appears to revert to its normal idle actions. However, I can’t see any obvious way to simulate this reactivation from within the script itself (and it’s way past my bedtime, anyway - so I really must stop tinkering with it). :wink:

Hi Kai,

Yeah it’s an interesting feature and is the only good way I know of to restart the idle handler firing from the quit handler. error number -128 doesn’t produce an error alert. The user can save whatever and restart it.

goodnight,

Hi

My scripts purpose is to keep list of trusted processes and when new unknown processes runs, script speaks those processes names and shows list, then i add to the trusted list or not.

There is 86 processes in Activity Monitor and this script lists 42. Activity Monitor shows all Dashboard Widgets in their own names, but script lists “DashboardClient” 11 times. I really would like to get all those 42 and all Widgets in their own names. It seems that script below lists only my own processes. Activity Monitor list also processes owned by root, nobody, postfix, window…

Quitting from Dock works now. From now on, i save preferences to properties.

I learned alot from these examples. Especially the one below rocks.

Thanks!