원클릭으로
pto-block
Block calendar for PTO, offsites, conferences, travel days, and other out-of-office periods while handling conflicting meetings
Codex 또는 Claude로 설치 이 Prompt를 복사해 Codex, Claude 또는 다른 어시스턴트에 붙여 넣으면 Skill 페이지를 검토하고 설치를 진행할 수 있습니다.
메뉴
Block calendar for PTO, offsites, conferences, travel days, and other out-of-office periods while handling conflicting meetings
Codex 또는 Claude로 설치 이 Prompt를 복사해 Codex, Claude 또는 다른 어시스턴트에 붙여 넣으면 Skill 페이지를 검토하고 설치를 진행할 수 있습니다.
SOC 직업 분류 기준
Generate Quarto and HTML reports of local Codex session cost, token usage by model, project, coding vs cowork cost, weekly trends, annual projections, and top expensive sessions.
Check that core Sidekick integrations can authenticate and read common restricted files
Generate summary of 1:1 and meeting notes organized by audience, wins, and kudos
Capture missing TODOs from recent work context. Use when Codex needs to scan the user's Slack DMs with their manager or direct reports, manager/direct-report 1:1 docs, and leadership meeting notes for direct asks or action items assigned to the user, deduplicate against the user's configured todo app, and create missing tasks with source links and searchable metadata.
Draft concise interview scorecards from pasted long-form interview notes, nearby Google Calendar interview context, and memory/miclog/ transcript excerpts. Use when writing hiring feedback, interview scorecards, spikes/troughs, or candidate evaluation summaries.
Calculate a team's average Jira hours from Rovo Jira completed work, with optional Workday Approved Time Off absence adjustments for a date window and team roster.
| name | pto-block |
| description | Block calendar for PTO, offsites, conferences, travel days, and other out-of-office periods while handling conflicting meetings |
| argument-hint | <start-date> <end-date> [reason] [--dry-run] |
| auto-approve | true |
Automates calendar management for PTO, offsites, conferences, travel days, and other out-of-office periods by:
When you are unavailable for PTO, an offsite, conference, or travel day, manual calendar cleanup is tedious:
This agent handles it systematically with optional dry-run preview.
Dry run (recommended first):
"Run pto-block agent for 2026-04-15 to 2026-04-20 for Vacation with --dry-run"
Live execution:
"Run pto-block agent for 2026-04-15 to 2026-04-20 for Vacation"
Custom reason:
"Run pto-block agent for 2026-05-01 to 2026-05-03 for Conference"
Work offsite or travel day:
"Run pto-block agent for 2026-06-01 to 2026-06-04 for Leadership Offsite with --dry-run"
"Run pto-block agent for 2026-06-04 to 2026-06-04 for Travel Day"
By default, this agent uses the --no-notify flag when declining meetings and deleting events. This means:
Why no notifications?
To send notifications instead:
--no-notify flag from the commands in Phase 5Extract arguments from user request:
start_date: YYYY-MM-DD format (required)end_date: YYYY-MM-DD format (required)reason: Text description (default: "PTO")--dry-run: Flag to preview without executingNormalize absence type and labels:
PTO - {reason} unless the reason is exactly "PTO", then use PTO.OOO - {reason}. Do not include "PTO" in these block titles.Out of office - {reason} for all absence types unless the user provides a custom message.Validate date range:
Generate business day list:
Load user context from @AGENTS.override.md:
Determine timezone offset for the date range:
-07:00-08:00from datetime import datetime
import time
dt = datetime.strptime("2026-04-15", "%Y-%m-%d")
is_dst = time.localtime(dt.timestamp()).tm_isdst
offset = "-07:00" if is_dst else "-08:00"
Build date range query:
{start_date}T00:00:00{offset} (Pacific time with offset){end_date}T23:59:59{offset}List all events in range:
python3 -m sidekick.clients.gcalendar list \
"2026-04-15T00:00:00-07:00" \
"2026-04-20T23:59:59-07:00" \
250
Note: Use the calculated offset (-07:00 for PDT or -08:00 for PST)
Get full details for each event (parallel):
python3 -m sidekick.clients.gcalendar get <event_id>
Extract from each event:
For each event, determine its category and action:
Detection: Event has start.date instead of start.dateTime.
Action: Keep unchanged and include in the report as preserved all-day context.
Detection: Event is a timed, no-attendee availability block that overlaps most of the target work-hours block and has a title like "PTO", "OOO", "Out of office", or the requested reason.
Action:
block_title, keep it.block_title.python3 -m sidekick.clients.gcalendar update <event_id> summary "{block_title}"
Detection: Summary, description, or location contains travel/offsite signals such as:
OAK to LAXreason phrase when it appears in the event textAction: Keep unchanged. Do not decline or delete these events, even if they overlap the calendar block or have attendees. Report them under "Travel/Offsite Events Kept".
Example: For a leadership offsite with flight events like "Flight WN 1234: OAK to LAX" and descriptions containing "Trip: Leadership Offsite", preserve the flight events.
Detection: Summary contains any of these keywords:
Action: Delete from calendar
python3 -m sidekick.clients.gcalendar delete <event_id> --no-notify
Reference: See tools/prep_tomorrow_meetings.py:119-127 for skip_keywords list
Detection: organizer.email == user's email address
Action: Report for manual handling
Detection: Attendees list includes boss's boss's email
Action: Decline with message, DO NOT delete
python3 -m sidekick.clients.gcalendar decline <event_id> "Out of office - {reason}" --no-notify
Detection: Summary or description contains:
Action: Decline with message, DO NOT delete
python3 -m sidekick.clients.gcalendar decline <event_id> "Out of office - {reason}" --no-notify
Detection: Everything else with attendees (count > 1)
Action: Decline, then delete
python3 -m sidekick.clients.gcalendar decline <event_id> "Out of office - {reason}" --no-notify
python3 -m sidekick.clients.gcalendar delete <event_id> --no-notify
Build structured report showing all planned actions:
Sections:
block_title)Format: See "Report Format" section below
--dry-run flag present:Write preview report to:
memory/pto-dry-run-{start_date}-to-{end_date}.md
Output message:
Dry run complete. No changes made.
Report saved to: memory/pto-dry-run-2026-04-15-to-2026-04-20.md
Step 1: Create missing calendar blocks (one per business day, using block_title)
python3 -m sidekick.clients.gcalendar create \
"{block_title}" \
"{date}T09:00:00-07:00" \
"{date}T17:00:00-07:00"
For PTO, block_title should look like PTO - Vacation or PTO. For offsites and travel days, it should look like OOO - Leadership Offsite or OOO - Travel Day; do not create PTO-titled blocks for work travel.
CRITICAL: Always include the timezone offset in datetime strings:
-07:00 for PDT (typically April-October)-08:00 for PST (typically November-March)Step 2: Rename mislabeled existing blocks
for event_id in blocks_to_rename:
python3 -m sidekick.clients.gcalendar update {event_id} summary "{block_title}"
Only rename clear personal availability blocks. If a non-PTO request already has a block titled PTO, rename it to the non-PTO block_title.
Step 3: Keep travel/offsite and all-day events unchanged
Do not call decline, delete, or update for preserved travel itinerary events, offsite anchor events, or all-day events unless the user explicitly asks.
Step 4: Delete DNS/Focus/Habit blocks
for event_id in habit_blocks:
python3 -m sidekick.clients.gcalendar delete {event_id} --no-notify
Step 5: Decline and delete regular meetings
for event_id in regular_meetings:
python3 -m sidekick.clients.gcalendar decline {event_id} "Out of office - {reason}" --no-notify
python3 -m sidekick.clients.gcalendar delete {event_id} --no-notify
Step 6: Decline only (keep) special meetings
for event_id in special_meetings:
python3 -m sidekick.clients.gcalendar decline {event_id} "Out of office - {reason}. Regrets!" --no-notify
Note: The --no-notify flag prevents email notifications from being sent to meeting organizers and attendees. Remove this flag if you want people to be notified of your decline/absence.
Step 7: Generate summary report
Write final report to:
memory/pto-block-summary-{start_date}-to-{end_date}.md
Use the same sections for dry runs and live summaries. Dry runs should say no changes were made; live summaries should include execution timestamp and actual counts.
# Calendar Blocking Preview: {start_date} to {end_date}
**Reason**: {reason}
**Block title**: {block_title}
**Mode**: DRY RUN (no changes will be made)
## Actions Planned
### Calendar Blocks to Create or Keep ({count})
- **Mon 2026-06-01**: 9:00 AM - 5:00 PM PDT - OOO - Leadership Offsite
### Existing Blocks to Rename ({count})
- **Thu 2026-06-04 9:00 AM**: PTO -> OOO - Leadership Offsite
### Travel/Offsite Events Kept ({count})
- **Mon 2026-06-01 9:15 AM**: Flight WN 1234: OAK to LAX
- Reason kept: Travel itinerary for Leadership Offsite
- Action: Keep unchanged; do not decline or delete
### All-Day Events Kept ({count})
- **Mon 2026-06-01**: All-day context event
### Focus/Habit Blocks to Delete ({count})
- **Date Time**: Event title
### Meetings to Decline & Delete ({count})
- **Date Time**: Meeting title
- Decline reason: "Out of office - {reason}"
- Action: Decline (no email) then delete
### Special Meetings to Decline Only ({count})
- **Date Time**: Meeting title
- Reason: Interview / boss's boss meeting
- Action: Decline (no email) and keep on calendar
### Manual Action Required ({count})
- **Date Time**: Meeting title
- You are the organizer; cancel or delegate manually.
- If delegating, do not delete the event because that can break the meeting link.
## Summary
- Calendar blocks created or kept: {count} days
- Existing blocks renamed: {count}
- Travel/offsite events kept: {count}
- Automated actions: {count} events
- Manual review needed: {count} meetings
- Notifications: None - all operations use `--no-notify` where supported
This report generated using [chase-sidekick](https://github.com/chase-seibert/chase-sidekick) and the [pto-block skill](https://github.com/chase-seibert/chase-sidekick/tree/main/.agents/skills/pto-block).
block_titlepython3 tools/get_google_refresh_token.pyCRITICAL: Always include explicit timezone offsets in datetime strings to prevent UTC conversion.
Input dates: YYYY-MM-DD format (date only, no time)
Determine correct offset:
-07:00 - approximately mid-March to early November-08:00 - approximately early November to mid-Marchfrom datetime import datetime
import time
dt = datetime.strptime(date_str, "%Y-%m-%d")
is_dst = time.localtime(dt.timestamp()).tm_isdst
offset = "-07:00" if is_dst else "-08:00"
Calendar blocks: Timed events with explicit timezone offset
2026-04-15T09:00:00-07:00 to 2026-04-15T17:00:00-07:002026-04-15T09:00:00 (defaults to UTC, creates 2am-10am PST!)Query datetime format: Include timezone offset
2026-04-15T00:00:00-07:00 to 2026-04-15T23:59:59-07:00Display: Format as "9:00 AM - 5:00 PM PST/PDT" in reports
Dry run first when the request is ambiguous or broad. For live runs, the skill is approved to make the calendar changes described in the action plan:
Never decline or delete travel itinerary events, offsite anchor events, or all-day events unless the user explicitly asks.
Standard PTO:
"Block my calendar for PTO from April 15 to April 20"
With custom reason:
"Block my calendar for a conference from May 1 to May 3"
Leadership offsite:
"Block my calendar for the leadership offsite from June 1 to June 4"
Travel day:
"Block my calendar for June 4 for travel day"
Dry run first:
"Show me what would happen if I blocked my calendar from June 1 to June 5 for vacation"
Single day:
"Block my calendar for tomorrow for a personal day"