:Title:			TclAB_QuickStart
:DestFolder:    ../../Help
:Project:		addressbook extension for Tcl
:Author:		Bernard Desgraupes <bdesgraupes@users.sourceforge.net>
:Homepage:		<http://sourceforge.net/projects/tcladdressbook>
:Created: 		2003-12-14 18:26:47
:Modified:	 	2009-03-13 09:54:16
:Keywords:		Address book, data base


((if $aida_params(target) eq "Html"
!! logo
((im ../Images/TclAB_logo.gif 
TclAB Logo im))
((nl ((lk TclAB.html ))Home Page lk)) | ((lk http://sourceforge.net/projects/tcladdressbook )) Project Page at SourceForge lk))
if))


((/
This file is a tutorial that demonstrates the [addressbook] command 
defined by the Tcladdressbook extension for Tcl. It documents 
version ((s [package require addressbook] s)). All the Tcl instructions in the sections 
below are very short one-line commands which you can try in any Tcl shell, 
like tclsh for instance.
((nl For a detailed and complete description of the syntax of each subcommand, 
refer to the ((lk TclAddressBookHelp.html ))help file lk)).
The home page for Tcladdressbook is 
((lk http://tcladdressbook.sourceforge.net/ )) on the SourceForge site lk)).
/))
((toc


First load the extension like this
((|
    package require addressbook
|))

((s1 Using the commands
((s2 The [groups] subcommand
List all the groups (ID and name)
((|
    addressbook groups
|))
List all the groups (only ID)
((|
    addressbook groups -ids
|))
List the subgroups of a specific group (ID and name)
((|
    set groupid [lindex [addressbook groups -ids] 0]
    addressbook groups -ingroup $groupid
|))
List the subgroups of a specific group (only ID)
((|
    addressbook groups -ids -ingroup $groupid
|))


((s2 The [persons] subcommand
List all the persons records (ID and name)
((|
    addressbook persons
|))
List all the persons records (only ID)
((|
    addressbook persons -ids
|))


((s2 The [count] subcommand
Count the existing groups and persons records
((|
    addressbook count -groups
    addressbook count -persons
    addressbook count -persons -ingroup [lindex [addressbook groups -ids] 0]
|))


((s2 The [getme] subcommand
Store the info about "me" in the variable ((i myrecord i)). 
((|
    set myrecord [addressbook getme]
|))
The value of ((i myrecord i)) is a keyed list. One can use the usual Tcl list 
commands to parse this value or special commands defined in the TclX 
extension (see section ((rf ukl ))Using keyed lists rf)) below).
((nl The ((i getme i)) command can also be used with an ((i -id i)) option. 
In that case the unique ID of the "Me" record is returned:
((|
    set myID [addressbook getme -id]
|))


((s2 The [setme] subcommand
Set the record that will represent in the database the logged-in user.
((|
    set theid [lindex [addressbook persons -ids] 2]
    addressbook setme $theid
    addressbook save
|))


((s2 The [record] subcommand
Store the ID of the first record in the variable ((i theid i))
((|
    set theid [lindex [addressbook persons -ids] 0]
|))
Store the info about this record in the variable ((i person i)). The 
returned value has the same keyed list format as with the [getme] subcommand.
((|
    set person [addressbook record $theid]
|))

Similarly with a group: store the ID of the first group in the variable ((i theid i))
((|
    set theid [lindex [addressbook groups -ids] 0]
|))
Store the info about this group in the variable ((i grp i))
((|
    set grp [addressbook record $theid]
|))


((s2 The [type] subcommand
Find the type (((i ABPerson i)) or ((i ABGroup i))) of the object corresponding 
to the ID ((i $theid i))
((|
    addressbook type $theid
|))


((s2 The [create] subcommand
One can create either a group's or a person's record.  The  third  argument
will be the "name" of the new record, that is to say the name  of  the  new
group or the last name of the new person respectively. The command  returns
the unique ID of the created record. For instance:
((|
    addressbook create group WorkingCommittee
    addressbook create person Beethoven
|))
One can make them subgroups or members of an already existing group using 
the ((i -ingroup i)) option:
((|
    set grpid [lindex [addressbook groups -ids] 0]	
    set subgrpid [addressbook create group Composers -ingroup $grpid]
    addressbook create person Beethoven -ingroup $subgrpid
|))


((s2 The [delete] subcommand
Remove from the database the record corresponding to the ID ((i $theid i))
((|
    addressbook delete $theid
|))
Check that there were changes (1 if yes, 0 if no)
((|
    addressbook changed
|))
Save the changes to make them permanent
((|
    addressbook save
|))


((s2 The [add] subcommand
Add to a specific group the record corresponding to the ID ((i $theid i)): 
this can be a person as well as a group (which would then become a 
subgroup of the group to which it is added).
((|
    set groupid [lindex [addressbook groups -ids] 0]
    set theid [lindex [addressbook persons -ids] 0]
    addressbook add $groupid $theid
|))
One can add several items at a time with this command:
((|
    addressbook add $groupid $theid1 $theid2 $theid3
|))


((s2 The [remove] subcommand
Remove from a specific group the record corresponding to the ID ((i $theid i)): 
this can be a person as well as a group.
((|
    set groupid [lindex [addressbook groups -ids] 0]
    set theid [lindex [addressbook persons -ids] 0]
    addressbook remove $groupid $theid
|))
One can remove several items at a time with this command:
((|
    addressbook remove $groupid $theid1 $theid2 $theid3
|))


((s2 The [parents] subcommand
List the parents of a person record (the various groups it belongs to). 
((|
    set theid [lindex [addressbook persons -ids] 0]
    addressbook parents $theid
|))
List the parents of a person record (only ID)
((|
    addressbook parents -ids $theid
|))

One can also find the parents of a group using this command.


((s2 The [label] subcommand
Let's find the label of the first phone number for a record:
((|
    set theid [addressbook getme -id]
    addressbook label $theid Phone 0
|))
The returned string could be ((i Home i)) for instance. Let's change it to 
((i Personal i)):
((|
    addressbook label $theid Phone 0 Personal
    addressbook save
|))


((s2 The [set] subcommand
This command lets you get or set the value of a particular field. For 
instance, to get the first name, dates and address fields of the first record:
((|
    set theid [lindex [addressbook persons -ids] 0]
    addressbook set $theid First
    addressbook set $theid ABDate
    addressbook set $theid Address
|))
To change the first name of the first record:
((|
    addressbook set $theid First Georgios
    addressbook changed
    addressbook save
|))
Note that the ((b addressbook save b)) command must be invoked to make the changes 
permanent. 
((nl When setting the value of a field it is important that the new value 
be formatted correctly with respect to the type of the property, as explained 
in the ((lk TclAddressBookHelp.html ))help file lk)). Here are a few 
examples corresponding to various property types:
((lu
((li Multi string value
((|
    addressbook set $theid Email {{Work BWV@harpsichord.com} {Concerts opus@sonatas.org}}
|))
 
((li  Date value
((|
    addressbook set $theid Birthday [clock scan "1 Apr 1985"]
|))

((li  Multi date value
((|
    addressbook set $theid ABDate [list [list "birthday Franny" 621597600] [list "birthday Zooey" 816692400]]
|))

((li  Multi dictionary value
((|
    addressbook set $theid Address [list [list Home [list {CountryCode fr} {City Paris} {Country France} {ZIP 75001} {Street "1, avenue de l'Opéra"}]]]
|))
lu))

See also the examples in the section ((rf ukl ))Using keyed lists rf)) 
below: the ((b [keylget] b)) and ((b [keylset] b)) commands defined 
in the TclX extension can be very useful to format multivalues correctly.

((s2 The [search] subcommand
This command can be used to report the IDs of the records corresponding to 
a single criterion. The criterion is expressed by a three elements list: 
the first element is the name of a property, the second is a comparison operator and 
the third is the value to search for. Refer to the help file for a complete 
description of the possible comparison operators. A few options are available 
(-persons, -ids and -nocase). Here are a few simple examples:

((|
    addressbook search Last == "Bach"
    addressbook search -persons -ids -nocase Last > "Ba"
    addressbook search -persons Modification >= 1070199949
    addressbook search -persons Modification < 1070199949
|))

((nl When searching on a particular property, it is important that the 
searched value be formatted correctly with respect to the type of the property, 
as explained in the ((lk TclAddressBookHelp.html ))help file lk)). Specify 
an empty label or an empty key to search on all possible labels or keys 
respectively. Here are a few examples corresponding to various property types:
((lu
((li  Multi string value. This instruction searches one value at a time.
((|
    addressbook search -persons Phone == {Work "01 02 03 04 05"}
|))
((li  Empty label to search on all phone numbers
((|
    addressbook search -persons Phone > {"" "01 02 03 04 05"}
|))
((li  Multi dictionary value. This instruction searches one key 
in one dictionary at a time.
((|
    addressbook search -persons -nocase Address == {Home {ZIP 98765}}
    addressbook search -persons -nocase Address > {Home {ZIP 98}}
|))
((li  Empty label to search on all labels
((|
    addressbook search -persons -nocase Address > {"" {City Paris}}
|))
((li  Empty key to search on all keys
((|
    addressbook search -persons -nocase Address > {home {"" abc}}
|))
((li  Empty label and key to search on all labels and keys
((|
    addressbook search -persons -nocase Address > {"" {"" abc}}
|))
((li  Prefix matching
((|
    addressbook search -persons Address ^= {Home {City "Par"}}
|))
((li  Suffix matching
((|
    addressbook search -persons Email =$ {Home ".com"}
|))
((li  Value ((i not i)) containing a given substring
((|
    addressbook search -persons Email !> {Home "xyz"}
|))
lu))


((s2 The [property] subcommand
This command accepts four subcommands: names, type, add, and remove.

((s3 The [property names] subcommand
Get the list of all existing properties for groups or for persons
((|
    addressbook property names -groups
    addressbook property names -persons
|))


((s3 The [property type] subcommand
Get the type of a particular property
((|
    addressbook property type -groups UID
    addressbook property type -persons Address
|))
For the two examples above, the result is respectively 
((i String i)) and ((i MultiDictionary i)).


((s3 The [property add] subcommand
Add a new person's property called ((i Instrument i)) with type ((i String i))
((|
    addressbook property add -persons Instrument String
|))

Add a new group's property called ((i Meeting i)) with type ((i Date i))
((|
    addressbook property add -groups Meeting Date
|))


((s3 The [property remove] subcommand
The third argument of this command can be either a record ID or the
-persons and -groups keywords. If it is the former, the property is removed
from the specified record, otherwise it is removed from all the records of
this type and the return value is now the number of properties successfully
removed.
((|
    set theid [addressbook getme -id]
    addressbook set $theid MaidenName Violet
    addressbook save
    addressbook property remove $theid MaidenName
|))

Remove the properties created above:
((|
    addressbook property remove -persons Instrument
    addressbook property remove -groups Meeting
|))


((s2 The [identifier] subcommand
This command is useful to manage distribution lists, groups used 
as a mailing list for instance. It has several subcommands (count, 
get, index, primary, and set).

((s3 The [identifier count] subcommand
((nl Suppose ((i theid i)) is the record ID of a person in the 
group ((i groupid i)):
((|
    set groupid [lindex [addressbook groups -ids] 0]
    set theid [lindex [addressbook persons -ids -ingroup $groupid] 0]
|))
((nl Count the identifiers of the Phone property:
((|
    addressbook identifier count $theid Phone
|))

((s3 The [identifier get] subcommand
((nl Get some identifiers by index (suppose here that there are at least
two of them). Indices start at 0:
((|
    set ident1 [addressbook identifier get $theid Phone 0]
    set ident2 [addressbook identifier get $theid Phone 1]
|))

((s3 The [identifier primary] subcommand
((nl Get the primary identifier (the one which is chosen by default if 
none has been specified otherwise):
((|
    addressbook identifier primary $theid Phone
|))

((s3 The [identifier set] subcommand
((nl Get the current distribution identifier:
((|
    addressbook identifier set $groupid $theid Phone
|))
((nl Set the distribution identifier to ((i ident2 i)):
((|
    addressbook identifier set $groupid $theid Phone $ident2
|))

((s3 The [identifier index] subcommand
((nl The reverse operation of the ((b addressbook identifier get b)) command 
is the ((b addressbook identifier index b)) command which returns the 
index corresponding to a given identifier. For instance, the following 
instruction will return the index 1:
((|
    addressbook identifier index $theid Phone $ident2
|))


((s2 The [export] subcommand
Create a VCard corresponding to a particular record:
((|
    set theid [lindex [addressbook persons -ids] 0]
    set vcardData [addressbook export $theid]
|))
The data returned is binary. You can store it in a file for instance.


((s2 The [import] subcommand
Import in the database some information stored in a .vcf file. A new 
record containing this info, is created in the database:
((|
    set fname [file join /Users bernardo someVcard.vcf]
    set fid [open $fname r]
    set vcard [read $fid]
    close $fid
    addressbook import $vcard
|))


((s2 The [image] subcommand
Get the custom image corresponding to a particular record:
((|
    set theid [lindex [addressbook persons -ids] 0]
    set img [addressbook image $theid]
|))
The data returned is binary. You can store it in a file for instance.
An error is raised if there is no custom image for this record.


((a ukl)) a))
((s1 Using keyed lists
Keyed lists can be easily manipulated using the ((b  keylget  b))  and  
((b keylset b)) commands defined by the TclX extension. For instance, if  a
record has been stored in some variable ((i myrecord i)), one  can  extract
various fields like this:
((|
    package require Tclx
    keylkeys myrecord
    keylget myrecord Email.work
    keylget myrecord Address.home.ZIP
    clock format [keylget myrecord Birthday]
|))
Similarly, with a group, one can invoke:
((|
    set theid [lindex [addressbook groups -ids] 0]
    set grp [addressbook record $theid]
    keylkeys grp
    keylget grp GroupName
    clock format [keylget grp Modification]
|))

To set a particular value, use the keylset command. For instance:
((|
    set personID [addressbook create person someName]
    keylset homeAddr City Paris Zip 75000 CountryCode fr
    set homeDict [list Home $homeAddr]
    addressbook set $personID Address [list $homeDict]
    
    set homeEmail "someName@home.org"
    set workEmail "someName@work.org"
    keylset emailsList Home $homeEmail Work $workEmail
    addressbook set $personID Email $emailsList
|))



((-
((nl Last updated ((s [ISOTime::ISODateAndTimeRelaxed] s))


