imip-agent

Annotated docs/wiki/Resources

1053:068aa85f0c45
2016-02-08 Paul Boddie Made the retraction operation a complete transaction. Tidied up the locking and unlocking function application.
paul@1032 1
= Resources =
paul@1032 2
paul@1032 3
In imip-agent, resources are a special kind of user that act upon requests
paul@1032 4
to schedule events and that perform such scheduling autonomously, meaning
paul@1032 5
that no human intervention is necessary when such resources receive messages
paul@1032 6
containing invitations.
paul@1032 7
paul@1032 8
By default, the [[../AgentPrograms|agent program]] responsible for resources
paul@1032 9
merely attempts to fit a received event into the resource's schedule. However,
paul@1032 10
in some organisations and environments, it is likely to be the case that other
paul@1032 11
policies are needed to ensure that a resource is not misused, overused or made
paul@1032 12
unnecessarily unavailable.
paul@1032 13
paul@1032 14
The [[../Preferences|preferences]] provide a way of controlling the behaviour
paul@1032 15
of resources, just as with any other kind of user, but certain preferences
paul@1032 16
are central to the configuration of resources.
paul@1032 17
paul@1032 18
<<TableOfContents(2,4)>>
paul@1032 19
paul@1039 20
== Confirmation and Retraction Functions ==
paul@1039 21
paul@1039 22
Confirmation and retraction functions are used to update other resources and
paul@1039 23
systems with the details of scheduled events. When an event is successfully
paul@1039 24
scheduled (according to the scheduling functions), all registered confirmation
paul@1039 25
functions are invoked to perform such notifications. Similarly, when an event
paul@1039 26
is cancelled, all registered retraction functions are invoked to inform other
paul@1039 27
components of the removal of the event from schedules.
paul@1039 28
paul@1039 29
The [[../Preferences#confirmation_function|confirmation_function]] and
paul@1039 30
[[../Preferences#retraction_function|retraction_function]] settings indicate
paul@1039 31
the behaviour of a resource when such circumstances arise. By themselves,
paul@1039 32
these settings do no more than keep a kind of journal of scheduling events,
paul@1039 33
but certain scheduling functions may build upon such journals to make
paul@1039 34
scheduling decisions. For example:
paul@1039 35
paul@1039 36
{{{{#!table
paul@1039 37
'''All Functions''' || '''Decision Process'''
paul@1039 38
==
paul@1039 39
<style="vertical-align: top;">
paul@1039 40
paul@1039 41
Scheduling functions:
paul@1039 42
paul@1039 43
{{{
paul@1039 44
check_quota
paul@1039 45
}}}
paul@1039 46
paul@1039 47
Confirmation functions:
paul@1039 48
paul@1039 49
{{{
paul@1039 50
add_to_quota
paul@1039 51
}}}
paul@1039 52
paul@1039 53
Retraction functions:
paul@1039 54
paul@1039 55
{{{
paul@1039 56
remove_from_quota
paul@1039 57
}}}
paul@1039 58
paul@1039 59
||
paul@1039 60
paul@1039 61
{{{#!graphviz
paul@1039 62
//format=svg
paul@1039 63
//transform=notugly
paul@1039 64
digraph scheduling_decisions {
paul@1039 65
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1039 66
  edge [tooltip="Scheduling decisions"];
paul@1039 67
paul@1039 68
  subgraph {
paul@1039 69
    rank=same;
paul@1039 70
    mail [label="Incoming mail\nfrom vincent.vole@example.com",shape=folder,style=filled,fillcolor=cyan];
paul@1039 71
    cancel [label="Incoming cancellation",shape=folder,style=filled,fillcolor=cyan];
paul@1039 72
  }
paul@1039 73
paul@1039 74
  subgraph {
paul@1039 75
    rank=same;
paul@1039 76
    check_quota [label="Is allowed by quota?",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 77
    quota [label="Quota for resource",shape=folder];
paul@1039 78
    quota_for_vole [label="...applying to\nvincent.vole@example.com",shape=folder]; 
paul@1039 79
  }
paul@1039 80
paul@1039 81
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 82
paul@1039 83
  subgraph {
paul@1039 84
    rank=same;
paul@1039 85
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 86
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 87
  }
paul@1039 88
paul@1039 89
  add_to_quota [label="Add to quota",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 90
  remove_from_quota [label="Remove from quota",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 91
paul@1039 92
  mail -> check_quota -> schedule -> accept;
paul@1039 93
  check_quota -> decline [style=dashed];
paul@1039 94
  schedule -> add_to_quota -> quota;
paul@1039 95
  quota -> quota_for_vole -> check_quota;
paul@1039 96
paul@1039 97
  cancel -> remove_from_quota -> quota;
paul@1039 98
}
paul@1039 99
}}}
paul@1039 100
paul@1039 101
}}}}
paul@1039 102
paul@1039 103
See the [[#Quota_Controls|quota controls]] documentation for more information
paul@1039 104
about applying quotas to resources.
paul@1039 105
paul@1032 106
== Scheduling Functions ==
paul@1032 107
paul@1032 108
The [[../Preferences#scheduling_function|scheduling_function]] setting
paul@1032 109
indicates the behaviour of a resource when a valid request to schedule an
paul@1032 110
event has been received. By default, a value equivalent to the following is
paul@1032 111
employed:
paul@1032 112
paul@1037 113
{{{{#!table
paul@1037 114
'''Scheduling Functions''' || '''Decision Process'''
paul@1037 115
==
paul@1037 116
<style="vertical-align: top;">
paul@1037 117
paul@1032 118
{{{
paul@1032 119
schedule_in_freebusy
paul@1032 120
}}}
paul@1032 121
paul@1037 122
||
paul@1037 123
paul@1037 124
{{{#!graphviz
paul@1037 125
//format=svg
paul@1037 126
//transform=notugly
paul@1037 127
digraph scheduling_decisions {
paul@1037 128
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1037 129
  edge [tooltip="Scheduling decisions"];
paul@1037 130
paul@1037 131
  mail [label="Incoming mail",shape=folder,style=filled,fillcolor=cyan];
paul@1037 132
paul@1037 133
  subgraph {
paul@1037 134
    rank=same;
paul@1037 135
    schedule_in_freebusy [label="Can schedule in free/busy?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 136
    freebusy [label="Free/busy",shape=folder];
paul@1037 137
  }
paul@1037 138
paul@1037 139
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 140
paul@1039 141
  subgraph {
paul@1039 142
    rank=same;
paul@1039 143
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 144
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 145
  }
paul@1037 146
paul@1037 147
  mail -> schedule_in_freebusy -> schedule -> accept;
paul@1037 148
  schedule_in_freebusy -> decline [style=dashed];
paul@1037 149
  freebusy -> schedule_in_freebusy;
paul@1037 150
}
paul@1037 151
}}}
paul@1037 152
paul@1037 153
}}}}
paul@1037 154
paul@1032 155
As described above, this merely attempts to schedule an event in the free
paul@1032 156
periods of the resource's schedule. However, no attempt is made to reject the
paul@1032 157
booking of the resource according to the identity of the organiser.
paul@1032 158
paul@1032 159
=== Identity Controls ===
paul@1032 160
paul@1032 161
Although identity controls may be implemented in the e-mail system,
paul@1032 162
effectively preventing the messages from addresses other than those within
paul@1032 163
an organisation (for example) from being delivered to the resource, it is
paul@1032 164
possible to use scheduling functions to implement such controls instead.
paul@1032 165
paul@1032 166
==== Same Domain Membership ====
paul@1032 167
paul@1032 168
For instance, the following combines the default free/busy check with a
paul@1032 169
test that the organiser belongs to the same Internet mail domain (by using
paul@1032 170
the organiser's address):
paul@1032 171
paul@1037 172
{{{{#!table
paul@1037 173
'''Scheduling Functions''' || '''Decision Process'''
paul@1037 174
==
paul@1037 175
<style="vertical-align: top;">
paul@1037 176
paul@1032 177
{{{
paul@1032 178
schedule_in_freebusy
paul@1032 179
same_domain_only
paul@1032 180
}}}
paul@1032 181
paul@1037 182
||
paul@1037 183
paul@1037 184
{{{#!graphviz
paul@1037 185
//format=svg
paul@1037 186
//transform=notugly
paul@1037 187
digraph scheduling_decisions {
paul@1037 188
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1037 189
  edge [tooltip="Scheduling decisions"];
paul@1037 190
paul@1037 191
  mail [label="Incoming mail",shape=folder,style=filled,fillcolor=cyan];
paul@1037 192
paul@1037 193
  subgraph {
paul@1037 194
    rank=same;
paul@1037 195
    schedule_in_freebusy [label="Can schedule in free/busy?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 196
    freebusy [label="Free/busy",shape=folder];
paul@1037 197
  }
paul@1037 198
paul@1037 199
  same_domain_only [label="Organiser has resource domain?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 200
paul@1037 201
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 202
paul@1039 203
  subgraph {
paul@1039 204
    rank=same;
paul@1039 205
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 206
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 207
  }
paul@1037 208
paul@1037 209
  mail -> schedule_in_freebusy -> same_domain_only -> schedule -> accept;
paul@1037 210
  schedule_in_freebusy -> decline [style=dashed];
paul@1037 211
  same_domain_only -> decline [style=dashed];
paul@1037 212
  freebusy -> schedule_in_freebusy;
paul@1037 213
}
paul@1037 214
}}}
paul@1037 215
paul@1037 216
}}}}
paul@1037 217
paul@1032 218
Note that if the first function is omitted, no check against the resource's
paul@1032 219
schedule will occur, so it is necessary to mention any such function in the
paul@1032 220
list.
paul@1032 221
paul@1032 222
==== Access Control Lists ====
paul@1032 223
paul@1032 224
A simple domain-related test may not be sufficient to control access to a
paul@1032 225
resource. Thus, another function is provided to exercise a finer degree of
paul@1032 226
control over event participants. For example:
paul@1032 227
paul@1037 228
{{{{#!table
paul@1037 229
'''Scheduling Functions and Data''' || '''Decision Process'''
paul@1037 230
==
paul@1037 231
<style="vertical-align: top;">
paul@1037 232
paul@1032 233
{{{
paul@1032 234
schedule_in_freebusy
paul@1032 235
access_control_list
paul@1032 236
}}}
paul@1032 237
paul@1037 238
Access control list:
paul@1037 239
paul@1037 240
{{{
paul@1037 241
accept
paul@1037 242
}}}
paul@1037 243
paul@1037 244
||
paul@1037 245
paul@1037 246
{{{#!graphviz
paul@1037 247
//format=svg
paul@1037 248
//transform=notugly
paul@1037 249
digraph scheduling_decisions {
paul@1037 250
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1037 251
  edge [tooltip="Scheduling decisions"];
paul@1037 252
paul@1037 253
  mail [label="Incoming mail",shape=folder,style=filled,fillcolor=cyan];
paul@1037 254
paul@1037 255
  subgraph {
paul@1037 256
    rank=same;
paul@1037 257
    schedule_in_freebusy [label="Can schedule in free/busy?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 258
    freebusy [label="Free/busy",shape=folder];
paul@1037 259
  }
paul@1037 260
paul@1037 261
  subgraph {
paul@1037 262
    rank=same;
paul@1037 263
    access_control_list [label="Access control list permits booking?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 264
    acl [label="acl setting",shape=folder];
paul@1037 265
  }
paul@1037 266
paul@1037 267
  accept_default [label="Accept invitation by default",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 268
  end_acl [label="end",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 269
paul@1037 270
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 271
paul@1039 272
  subgraph {
paul@1039 273
    rank=same;
paul@1039 274
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 275
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 276
  }
paul@1037 277
paul@1037 278
  mail -> schedule_in_freebusy -> access_control_list -> accept_default -> end_acl -> schedule -> accept;
paul@1037 279
  end_acl -> decline [style=dashed];
paul@1037 280
  schedule_in_freebusy -> decline [style=dashed];
paul@1037 281
  freebusy -> schedule_in_freebusy;
paul@1037 282
  acl -> access_control_list;
paul@1037 283
}
paul@1037 284
}}}
paul@1037 285
paul@1037 286
}}}}
paul@1037 287
paul@1037 288
To accompany the scheduling functions, the [[../Preferences#acl|acl]] setting
paul@1037 289
in the resource's preferences must be set, or if a separate file is more
paul@1037 290
appropriate, its full path may be given as an argument to `access_control_list`:
paul@1032 291
paul@1032 292
{{{
paul@1032 293
schedule_in_freebusy
paul@1032 294
access_control_list /etc/imip-agent/resources.acl
paul@1032 295
}}}
paul@1032 296
paul@1032 297
Within the file provided by the setting or separate file, a list of rules
paul@1037 298
must describe the handling procedure for an event. For example, the following
paul@1037 299
was given in the above example:
paul@1032 300
paul@1032 301
{{{
paul@1032 302
accept
paul@1032 303
}}}
paul@1032 304
paul@1032 305
This will merely accept all invitations, anyway. However, it may be
paul@1032 306
appropriate to prevent certain users from using resources. For example:
paul@1032 307
paul@1037 308
{{{{#!table
paul@1037 309
'''Scheduling Functions and Data''' || '''Decision Process'''
paul@1037 310
==
paul@1037 311
<style="vertical-align: top;">
paul@1037 312
paul@1037 313
{{{
paul@1037 314
schedule_in_freebusy
paul@1037 315
access_control_list
paul@1037 316
}}}
paul@1037 317
paul@1037 318
Access control list:
paul@1037 319
paul@1032 320
{{{
paul@1032 321
accept
paul@1032 322
decline attendee simon.skunk@example.com
paul@1032 323
}}}
paul@1032 324
paul@1037 325
||
paul@1037 326
paul@1037 327
{{{#!graphviz
paul@1037 328
//format=svg
paul@1037 329
//transform=notugly
paul@1037 330
digraph scheduling_decisions {
paul@1037 331
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1037 332
  edge [tooltip="Scheduling decisions"];
paul@1037 333
paul@1037 334
  mail [label="Incoming mail",shape=folder,style=filled,fillcolor=cyan];
paul@1037 335
paul@1037 336
  subgraph {
paul@1037 337
    rank=same;
paul@1037 338
    schedule_in_freebusy [label="Can schedule in free/busy?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 339
    freebusy [label="Free/busy",shape=folder];
paul@1037 340
  }
paul@1037 341
paul@1037 342
  subgraph {
paul@1037 343
    rank=same;
paul@1037 344
    access_control_list [label="Access control list permits booking?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 345
    acl [label="acl setting",shape=folder];
paul@1037 346
  }
paul@1037 347
paul@1037 348
  accept_default [label="Accept invitation by default",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 349
  decline_attendee [label="Is attendee simon.skunk@example.com?",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 350
  end_acl [label="end",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 351
paul@1037 352
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 353
paul@1039 354
  subgraph {
paul@1039 355
    rank=same;
paul@1039 356
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 357
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 358
  }
paul@1037 359
paul@1037 360
  mail -> schedule_in_freebusy -> access_control_list -> accept_default -> decline_attendee -> end_acl -> schedule -> accept;
paul@1037 361
  end_acl -> decline [style=dashed];
paul@1037 362
  schedule_in_freebusy -> decline [style=dashed];
paul@1037 363
  freebusy -> schedule_in_freebusy;
paul@1037 364
  acl -> access_control_list;
paul@1037 365
}
paul@1037 366
}}}
paul@1037 367
paul@1037 368
}}}}
paul@1037 369
paul@1032 370
This example indicates that by default, invitations will be accepted, but if
paul@1032 371
one of the attendees of an event is `simon.skunk@example.com`, the invitation
paul@1032 372
will be declined. However, it may be the case that this rule should be
paul@1032 373
overridden under certain circumstances. For example:
paul@1032 374
paul@1037 375
{{{{#!table
paul@1037 376
'''Scheduling Functions and Data''' || '''Decision Process'''
paul@1037 377
==
paul@1037 378
<style="vertical-align: top;">
paul@1037 379
paul@1037 380
{{{
paul@1037 381
schedule_in_freebusy
paul@1037 382
access_control_list
paul@1037 383
}}}
paul@1037 384
paul@1037 385
Access control list:
paul@1037 386
paul@1032 387
{{{
paul@1032 388
accept
paul@1032 389
decline attendee simon.skunk@example.com
paul@1032 390
accept organiser paul.boddie@example.com
paul@1032 391
}}}
paul@1032 392
paul@1037 393
||
paul@1037 394
paul@1037 395
{{{#!graphviz
paul@1037 396
//format=svg
paul@1037 397
//transform=notugly
paul@1037 398
digraph scheduling_decisions {
paul@1037 399
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1037 400
  edge [tooltip="Scheduling decisions"];
paul@1037 401
paul@1037 402
  mail [label="Incoming mail",shape=folder,style=filled,fillcolor=cyan];
paul@1037 403
paul@1037 404
  subgraph {
paul@1037 405
    rank=same;
paul@1037 406
    schedule_in_freebusy [label="Can schedule in free/busy?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 407
    freebusy [label="Free/busy",shape=folder];
paul@1037 408
  }
paul@1037 409
paul@1037 410
  subgraph {
paul@1037 411
    rank=same;
paul@1037 412
    access_control_list [label="Access control list permits booking?",shape=ellipse,style=filled,fillcolor=gold];
paul@1037 413
    acl [label="acl setting",shape=folder];
paul@1037 414
  }
paul@1037 415
paul@1037 416
  accept_default [label="Accept invitation by default",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 417
  decline_attendee [label="Is attendee simon.skunk@example.com?",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 418
  accept_organiser [label="Is organiser paul.boddie@example.com?",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 419
  end_acl [label="end",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1037 420
paul@1037 421
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 422
paul@1039 423
  subgraph {
paul@1039 424
    rank=same;
paul@1039 425
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 426
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 427
  }
paul@1037 428
paul@1037 429
  mail -> schedule_in_freebusy -> access_control_list -> accept_default -> decline_attendee -> accept_organiser -> end_acl -> schedule -> accept;
paul@1037 430
  end_acl -> decline [style=dashed];
paul@1037 431
  schedule_in_freebusy -> decline [style=dashed];
paul@1037 432
  freebusy -> schedule_in_freebusy;
paul@1037 433
  acl -> access_control_list;
paul@1037 434
}
paul@1037 435
}}}
paul@1037 436
paul@1037 437
}}}}
paul@1037 438
paul@1032 439
Here, the stated organiser may still arrange a booking of the resource where
paul@1032 440
the previously-mentioned attendee is involved.
paul@1039 441
paul@1039 442
=== Quota Controls ===
paul@1039 443
paul@1039 444
The [[#Confirmation_and_Retraction_Functions|confirmation and retraction functions]]
paul@1039 445
section provides an example of applying quotas to event participants. However,
paul@1039 446
this section describes the operation of the quota system in more detail.
paul@1039 447
paul@1039 448
In contrast to each user's stored information which consolidates information
paul@1039 449
related to that user's own schedule, the quota system consolidates information
paul@1039 450
related to the schedules of one or more resources, thus enabling observations
paul@1039 451
to be made about their collective usage.
paul@1039 452
paul@1039 453
First, consider a resource such as a car where an organiser of an event may be
paul@1039 454
booking the car for travel purposes. A quota prevents the organiser from
paul@1039 455
booking the resource too much and denying other users access to it.
paul@1039 456
paul@1039 457
Now consider a number of separate car resources. An organiser might attempt to
paul@1039 458
get around any individual resource quota by booking a number of different cars.
paul@1039 459
By grouping the resources together, the organiser will exhaust a quota set on
paul@1039 460
the group of resources as reservations are made for the different members of
paul@1039 461
the group.
paul@1039 462
paul@1039 463
==== Initialising Quotas ====
paul@1039 464
paul@1039 465
Within the journal storage area (described in the [[../FilesystemUsage|filesystem guide]]),
paul@1039 466
a quota group directory must be initialised with a `limits` file indicating
paul@1039 467
the amount of time that can be occupied by the cumulative total of all events
paul@1039 468
scheduled by an individual user or a group of which they are a member. For
paul@1039 469
example:
paul@1039 470
paul@1039 471
{{{
paul@1039 472
mailto:vincent.vole@example.com PT10H
paul@1039 473
}}}
paul@1039 474
paul@1039 475
This indicates that the given user may only reserve 10 hours of events or less.
paul@1039 476
Attempts to schedule more time will be declined.
paul@1039 477
paul@1039 478
To impose a general quota, the special `*` identity can be used:
paul@1039 479
paul@1039 480
{{{
paul@1039 481
* PT10H
paul@1039 482
}}}
paul@1039 483
paul@1039 484
When a user identity is not listed and no general quota is defined, that
paul@1039 485
particular user will be unable to reserve the resource unless defined as a
paul@1039 486
member of a group listed in the `limits` file, as described below.
paul@1039 487
paul@1039 488
==== Sharing Quotas Across Users ====
paul@1039 489
paul@1039 490
When the use of resources is to be shared between users in such a way that
paul@1039 491
groups of users will be sharing a single quota, the `groups` file in the
paul@1039 492
quota directory must be defined, mapping each user identity to the group to
paul@1039 493
which they will belong. For example:
paul@1039 494
paul@1039 495
{{{
paul@1039 496
mailto:vincent.vole@example.com developers
paul@1039 497
mailto:harvey.horse@example.com developers
paul@1039 498
mailto:paul.boddie@example.com developers
paul@1039 499
mailto:simon.skunk@example.com testers
paul@1039 500
}}}
paul@1039 501
paul@1039 502
The group identity can then be employed in the `limits` file:
paul@1039 503
paul@1039 504
{{{
paul@1039 505
developers PT10H
paul@1039 506
testers PT20H
paul@1039 507
}}}
paul@1039 508
paul@1039 509
Limits apply to individuals, then to groups, then the general quota applies.
paul@1039 510
Thus, when a group is not listed, the general quota applies; without a general
paul@1039 511
quota (and without matching individually), a group member will be unable to
paul@1039 512
reserve the resource.
paul@1039 513
paul@1039 514
==== Individual Resource Quotas ====
paul@1039 515
paul@1039 516
The trivial case of applying quotas is to give a resource its own quota. This
paul@1039 517
is achieved by not specifying any arguments to the `check_quota` scheduling
paul@1039 518
function or to the `add_to_quota` and `remove_from_quota` functions. See the
paul@1039 519
[[#Confirmation_and_Retraction_Functions|confirmation and retraction functions]]
paul@1039 520
section for an example of this.
paul@1039 521
paul@1039 522
==== Common Resource Quotas ====
paul@1039 523
paul@1039 524
By indicating an argument to the different functions, a common quota can be
paul@1039 525
employed. In the following example, both resources would employ the given
paul@1039 526
function invocations to pool their knowledge about their schedules.
paul@1039 527
paul@1039 528
{{{{#!table
paul@1039 529
'''All Functions''' || '''Decision Process'''
paul@1039 530
==
paul@1039 531
<style="vertical-align: top;">
paul@1039 532
paul@1039 533
Scheduling functions:
paul@1039 534
paul@1039 535
{{{
paul@1039 536
check_quota cars
paul@1039 537
}}}
paul@1039 538
paul@1039 539
Confirmation functions:
paul@1039 540
paul@1039 541
{{{
paul@1039 542
add_to_quota cars
paul@1039 543
}}}
paul@1039 544
paul@1039 545
Retraction functions:
paul@1039 546
paul@1039 547
{{{
paul@1039 548
remove_from_quota cars
paul@1039 549
}}}
paul@1039 550
paul@1039 551
||
paul@1039 552
paul@1039 553
{{{#!graphviz
paul@1039 554
//format=svg
paul@1039 555
//transform=notugly
paul@1039 556
digraph scheduling_decisions {
paul@1039 557
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1039 558
  edge [tooltip="Scheduling decisions"];
paul@1039 559
paul@1039 560
  subgraph {
paul@1039 561
    rank=same;
paul@1039 562
    mail_cadillac [label="Incoming mail\nfrom vincent.vole@example.com\nto resource-car-cadillac@example.com",shape=folder,style=filled,fillcolor=cyan];
paul@1039 563
    mail_pontiac [label="Incoming mail\nfrom vincent.vole@example.com\nto resource-car-pontiac@example.com",shape=folder,style=filled,fillcolor=cyan];
paul@1039 564
    cancel [label="Incoming cancellation",shape=folder,style=filled,fillcolor=cyan];
paul@1039 565
  }
paul@1039 566
paul@1039 567
  subgraph {
paul@1039 568
    rank=same;
paul@1039 569
    check_quota [label="Is allowed by quota?",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 570
    quota_cars [label="Quota for cars",shape=folder];
paul@1039 571
    quota_cars_vole [label="...applying to\nvincent.vole@example.com",shape=folder];
paul@1039 572
  }
paul@1039 573
paul@1039 574
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 575
paul@1039 576
  subgraph {
paul@1039 577
    rank=same;
paul@1039 578
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 579
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 580
  }
paul@1039 581
paul@1039 582
  add_to_quota [label="Add to quota",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 583
  remove_from_quota [label="Remove from quota",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 584
paul@1039 585
  mail_cadillac -> check_quota;
paul@1039 586
  mail_pontiac -> check_quota -> schedule -> accept;
paul@1039 587
  check_quota -> decline [style=dashed];
paul@1039 588
  schedule -> add_to_quota -> quota_cars;
paul@1039 589
  quota_cars -> quota_cars_vole -> check_quota;
paul@1039 590
paul@1039 591
  cancel -> remove_from_quota -> quota_cars;
paul@1039 592
}
paul@1039 593
}}}
paul@1039 594
paul@1039 595
}}}}
paul@1039 596
paul@1039 597
==== Collective Scheduling ====
paul@1039 598
paul@1039 599
Consider two separate resources: both may be reserved at the same time by the
paul@1039 600
same organiser; neither resource would normally decline the reservation on the
paul@1039 601
basis of schedule availability, should the period concerned be free. However,
paul@1039 602
it may be undesirable for one organiser to occupy both resources at the same
paul@1039 603
time.
paul@1039 604
paul@1039 605
Consequently, a mechanism is required to pool the resource schedules in such a
paul@1039 606
way that any reservation performed for one resource at a given point in time
paul@1039 607
prohibits another reservation performed for a related resource at the same
paul@1039 608
point in time by the same user.
paul@1039 609
paul@1039 610
The free/busy records held for a given quota group permit such collective
paul@1039 611
scheduling decisions and are employed as follows:
paul@1039 612
paul@1039 613
{{{{#!table
paul@1039 614
'''All Functions''' || '''Decision Process'''
paul@1039 615
==
paul@1039 616
<style="vertical-align: top;">
paul@1039 617
paul@1039 618
Scheduling functions:
paul@1039 619
paul@1039 620
{{{
paul@1039 621
schedule_within_quota cars
paul@1039 622
}}}
paul@1039 623
paul@1039 624
Confirmation functions:
paul@1039 625
paul@1039 626
{{{
paul@1039 627
add_to_quota_freebusy cars
paul@1039 628
}}}
paul@1039 629
paul@1039 630
Retraction functions:
paul@1039 631
paul@1039 632
{{{
paul@1039 633
remove_from_quota_freebusy cars
paul@1039 634
}}}
paul@1039 635
paul@1039 636
||
paul@1039 637
paul@1039 638
{{{#!graphviz
paul@1039 639
//format=svg
paul@1039 640
//transform=notugly
paul@1039 641
digraph scheduling_decisions {
paul@1039 642
  node [shape=box,fontsize="13.0",fontname="Helvetica",tooltip="Scheduling decisions"];
paul@1039 643
  edge [tooltip="Scheduling decisions"];
paul@1039 644
paul@1039 645
  subgraph {
paul@1039 646
    rank=same;
paul@1039 647
    mail_cadillac [label="Incoming mail\nfrom vincent.vole@example.com\nto resource-car-cadillac@example.com",shape=folder,style=filled,fillcolor=cyan];
paul@1039 648
    mail_pontiac [label="Incoming mail\nfrom vincent.vole@example.com\nto resource-car-pontiac@example.com",shape=folder,style=filled,fillcolor=cyan];
paul@1039 649
    cancel [label="Incoming cancellation",shape=folder,style=filled,fillcolor=cyan];
paul@1039 650
  }
paul@1039 651
paul@1039 652
  subgraph {
paul@1039 653
    rank=same;
paul@1039 654
    schedule_across_quota [label="Can be scheduled within the quota?",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 655
    quota_cars [label="Quota for cars",shape=folder];
paul@1039 656
    freebusy_cars_vole [label="...recording schedule for\nvincent.vole@example.com",shape=folder];
paul@1039 657
  }
paul@1039 658
paul@1039 659
  schedule [label="Schedule event for resource",shape=ellipse,style=filled,fillcolor=gold];
paul@1039 660
paul@1039 661
  subgraph {
paul@1039 662
    rank=same;
paul@1039 663
    accept [label="Accept",shape=folder,style=filled,fillcolor=cyan];
paul@1039 664
    decline [label="Decline",shape=folder,style=filled,fillcolor=cyan];
paul@1039 665
  }
paul@1039 666
paul@1039 667
  add_to_quota_freebusy [label="Add to quota free/busy",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 668
  remove_from_quota_freebusy [label="Remove from quota free/busy",shape=ellipse,style=filled,fillcolor=darkorange];
paul@1039 669
paul@1039 670
  mail_cadillac -> schedule_across_quota;
paul@1039 671
  mail_pontiac -> schedule_across_quota -> schedule -> accept;
paul@1039 672
  schedule_across_quota -> decline [style=dashed];
paul@1039 673
  schedule -> add_to_quota_freebusy -> quota_cars -> freebusy_cars_vole;
paul@1039 674
  freebusy_cars_vole -> schedule_across_quota;
paul@1039 675
paul@1039 676
  cancel -> remove_from_quota_freebusy -> freebusy_cars_vole;
paul@1039 677
}
paul@1039 678
}}}
paul@1039 679
paul@1039 680
}}}}