RT::Extension::ShiftPlanning - Filter a user list to find those who are
    on shift

    Version 0.01

    Given a list of RT::User, return those who're on shift:

      ClockedInOrScheduled(LocationIdByName('Level1'), @list_of_RT_users);

    Given an RT::Group:

      ClockedInOrScheduled($ShiftID, @{$theGroup->UserMembersObj->ItemsArrayRef});

    To return pager phone numbers only for those users on shift who have
    pager phone numbers set:

      map { $_->PagerPhone }
      ClockedInOrScheduled $ShiftId
      grep { $_->PagerPhone } 

    Filters a user list using shiftplanning data and polls shiftplanning to
    get updated shift data.

      /NoAuth/ShiftPlanning/refresh_schedules.html - invokes RT::Extension::ShiftPlanning::RefreshScheduleData

      /NoAuth/ShiftPlanning/refresh_onnow.html - invokes RT::Extension::ShiftPlanning::RefreshOnNow

      /ShiftPlanning/create_schema.html - generate initial shiftplanning support schema.

      ClockedInOrScheduled($ShiftId, @RTUserObjects)

    Takes a list of RT users and filters it to return only those who are on
    shift according to a cached copy of the shift state,
    returning the filtered list.

    The logic we want for selecting who to notify is as follows:

    - Return true if the user is clocked in to one of the specified shifts -
    Return true if the user is clocked in and not on any particular shift
    (i.e. remember to clock out, people!) - Otherwise return false

    We map RT users to users using the
    ShiftplanningEmployeeId custom field in the RT::User.

    It's entirely possible for an empty array to be returned if none of the
    users passed are on shift. Callers should have a fallback plan to ignore
    shifts and alert everyone.

    You might want to use this as part of a template that decides who gets
    notified, like we do with Pushover:

      use RT::Extension::ShiftPlanning;
      my @recips;
      push(@recips, @{$Ticket->AdminCc->UserMembersObj->ItemsArrayRef});
      push(@recips, @{$Ticket->QueueObj->AdminCc->UserMembersObj->ItemsArrayRef});
      my @recip_api_keys = 
        map { $_->FirstCustomFieldValue('PushoverUserKey') }
         '24x7 L1', @recips
      # Return comma separated list of unique API keys
      join ',', keys %{{ map { $_ => 1 } @recip_api_keys }};

    (Yes, this should be neatly grouped up somewhere else).

    Fetch mostly-static shift data from - the mapping of
    "Location" (which we use to aggregate shifts of the same type) to
    "Positions", which are shifts.

    Hits the shiftplanning api calls location.locations and
    schedule.schedules .

    We look up who is on shift by location and the dashboard.onnow function
    returns only positions, so we need this data to determine which
    positions correspond to the "location" (shift) of interest.

    It's also used for LocationIdByName .

    Fetch the rapidly changing dashboard.onnow data from shiftplanning,
    getting the latest info on who is clocked in or should be clocked in.

    Craig Ringer, "<ringerc at>"

    You may report any bugs to "bug-rt-extension-shiftplanning at", or through the web interface at
    ng>. However, this module is offered as-is without any support by its
    author or by (who did not have anything to do with
    this module). You might also have some luck on the

    The same license as Perl its self