Finding Address Book entries with no group

I have a 2,500+ entry address book, much of which is sorted into groups. However, I know some cards have no group, and I can’t for the life of me figure out how to identify them. SmartGroups seem to be no help.

My AppleScript skills are minimal, but I’m trying to adapt chunks of existing Address Book scripts I’ve found online. I’m using 10.4.11 on an iBook G4; Address Book 4.0.6; and Script Editor 2.1.1

I figure the simplest way to do this is to put all cards in a new group (“NoGroup”), then cycle through each existing group, removing any matches. At the end, all that’s left should be contacts without a group.

I’ve gotten as far as creating the new group and dumping all existing contacts into it. I then tried to set it up to identify and remove cards that belong to a single group (hard-coded as my Friends/Family group, for simplicity); I figured once I got this down, I could figure out how to cycle through all the groups in turn.

However, now it’s choking on my if statement, even though it’s nearly identical to an if statement I found in a (working) script I found on the Web. Any suggestions? And any suggestions for accomplishing the end goal? I’d love to learn how to do it myself, but that doesn’t seem to be working…

Here’s what I’ve got:


tell application "Address Book"
	
	activate
	
	set NoGroup to "NoGroup"
	set theUnGroupByID to make new group with properties {name:NoGroup}
	
	add every person to theUnGroupByID
	
	save addressbook
	
	try
		set nameOfEveryGroup to name of every group
		
	end try
	
	set theGroupByID to group named "Friends/Family"
	set allCards to every person of theGroupByID
	
	repeat with i from 1 to number of people
		set thisPerson to person i as list
		if thisPerson is in allCards then remove person i from theUnGroupByID
		
	end repeat
	
end tell


Thanks in advance!

Model: iBook G4 1.07 GHz 768 MB RAM
Browser: Firefox 2.0.0.14
Operating System: Mac OS X (10.5)

OK, well, I poked around some more, and thought I (almost) had it. See below.

It seemed to cycle through the groups OK, and identify the members of the groups (that’s what the dialog displays are about – giving me some feedback about what it’s doing). But in fact, it doesn’t actually remove anything from the NoGroup group… (I also realize that if it did work, it would leave NoGroup empty; I’ll have to figure out some way of telling the script not to delete all NoGroup from NoGroup…)

Anyway, all suggestions welcome. And maybe there’s a simpler way of doing this.

tell application "Address Book"
	
	activate
	
	set NoGroup to "NoGroup"
	set theUnGroupByID to make new group with properties {name:NoGroup}
	
	add every person to theUnGroupByID
	
	save addressbook
	
	try
		set nameOfEveryGroup to name of every group
		
	end try
	
	repeat with i from 1 to number of groups
		set thisGroupName to item i of nameOfEveryGroup
		
		display dialog thisGroupName
		
		set thisGroup to group thisGroupName
		set peopleOfThisGroup to name of every person of thisGroup
		
		set theResult to choose from list peopleOfThisGroup with prompt "These are the members of the group."
		
		set thisGroupsCards to every person of thisGroup
		repeat with j from 1 to number of people
			set thisPerson to person j as list
			
			if thisPerson is in thisGroupsCards then remove thisPerson from group "NoGroup"
			
		end repeat
		
	end repeat
	
end tell

Model: iBook G4 1.07 GHz 768 MB RAM
Browser: Firefox 2.0.0.14
Operating System: Mac OS X (10.5)

Hi,

adding all people to new group and removing one by one is wasted time :wink:
This might be the fastest way, it puts once the IDs of the people of all groups in a flattened list
and checks, if the given ID is in the list.
The group “NoGroup” will be deleted and recreated if the group already exists
and smart groups won’t be considered


property NoGroup : "NoGroup"

tell application "Address Book"
	set {ASTID, AppleScript's text item delimiters} to {AppleScript's text item delimiters, return}
	set GroupIDs to id of every person of (groups whose id does not end with "ABSmartGroup") as text
	set AppleScript's text item delimiters to ASTID
	if exists group NoGroup then delete group NoGroup
	set theUnGroupByID to make new group with properties {name:NoGroup}
	tell people to set {allPeople, allID, cnt} to {it, its id, count it}
	repeat with onePerson from 1 to cnt
		if GroupIDs does not contain item onePerson of allID then
			add item onePerson of allPeople to theUnGroupByID
		end if
	end repeat
end tell

Another way to check for people in no group would be:

people whose groups is equal to {} -- "{}" indicates an empty list.

So something like the following should work. It doesn’t delete the group if it’s already there.

set NoGroup to "NoGroup" -- Name of group to use.
tell application "Address Book"
	-- If the group is not there make it.
	if (name of groups) does not contain NoGroup then
		make new group with properties {name:NoGroup}
	end if
	-- Get all people who have no group set and add them to this group.
	add (people whose groups is equal to {}) to group NoGroup
	-- To update the UI.
	save addressbook
end tell

I’m not sure about speed comparisons though.

best wishes

John Maisey
www.nhoj.co.uk

EDIT: added “save addressbook” to the script.

Good catch, John, thanks :slight_smile:
I’ve looked for a group property and lost sight of the group element

Wonderful – thanks to both of you! Both are much more elegant solutions, from what I can read of them.

Just for the record, Mike, yours took 7.6 seconds; Stefan, yours seemed like it would take a little longer, but then choked on this line at one point (well into running):
add item onePerson of allPeople to theUnGroupByID

Sadly, the script is beyond me, so I can’t really guess what might have happened…

Many thanks!

tf