本文へ移動
cccskills
無料GitHub で公開

activity-and-task-patterns

Task and Event objects: polymorphic WhatId/WhoId, Activity object model, ActivityHistory vs OpenActivity, activity timeline customization, bulk task creation, Einstein Activity Capture boundaries. NOT for turning on EAC or calendar sync — use admin/einstein-activity-capture-setup. NOT for Email-to-Case — use admin/case-management-setup. Covers ActivitiesSettings metadata, enableActivities, shared Task/Event custom fields and FLS, TaskStatus value sets, Shared Activities and TaskRelation/EventRelation, recurring and child activities, and partial-success bulk DML on Task.

インストール方法を見る

含まれるファイル(8)

  • SKILL.md14.9 KB
  • references/examples.md7.4 KB
  • references/gotchas.md13.9 KB
  • references/llm-anti-patterns.md5.8 KB
  • references/metadata-examples.md21.6 KB
  • references/well-architected.md8.3 KB
  • scripts/check_activity_and_task_patterns.py17.5 KB
  • templates/activity-and-task-patterns-template.md3.8 KB

SKILL.md(原文)

インストールする前に、エージェントに与えられる指示の中身を確認できます。

Activity and Task Patterns

Activate when designing interactions with Salesforce Activities — Task and Event records that attach to other objects via polymorphic WhatId and WhoId. The Activity object model is unusual: Activity is a read-only abstract parent, Task and Event are concrete children, and ActivityHistory / OpenActivity are read-only related lists, not queryable in bulk.

Before Starting

  • Understand the Activity object model. Activity cannot be queried directly; query Task or Event. ActivityHistory and OpenActivity appear on related lists and subqueries only.
  • Know the polymorphic fields. WhatId can reference any object enabled for activities; WhoId references Contact or Lead. Require TYPEOF or explicit type filters in SOQL.
  • Check Einstein Activity Capture. EAC-captured emails/events are stored outside standard Task/Event and are not reportable the same way.

Questions to Ask Before Configuring

Ask these before writing a line of Apex or opening Setup. Each one maps to a platform behaviour documented in references/gotchas.md; skipping them produces activity code that passes review and then misbehaves in production.

AskWhy it mattersWhat a good answer adds
"Is Shared Activities on in this org, and who turned it on?"It cannot be enabled or disabled by a deploy — allowUsersToRelateMultipleContactsToTasksAndEvents has been read-only in every API version since v36.0Whether TaskWhoIds, TaskRelation and multi-contact relates exist at all, before code assumes them
"Who owns these activities, and should each one email its owner?"Apex DML that creates or modifies a Task triggers the assignment notification by defaultA decision to set EmailHeader.triggerUserEmail, and a backfill that doesn't mail thousands of people
"What is the read path — which field will the WHERE clause filter on?"Subject, TaskStatus and TaskPriority are on the platform's can't-index list; WhatId / OwnerId / date ranges are notWhether Task/Event survives the volume, or the design needs a custom Interaction__c
"Does this field make sense on both a Task and an Event?"There is no Task-only custom field; Activity fields land on both children and share field-level securityThe validation rule that scopes it, and the FLS entries for both objects in the same deploy
"Are any of these activities recurring, or occurrences of a series?"Recurring Tasks can't be flipped after creation and reject ActivityDate/Status updates; child Events accept updates to IsReminderSet and ReminderDateTime onlyA partition step before the bulk DML instead of a half-failed job
"Is Einstein Activity Capture on for anyone here?"EAC-captured mail and events live outside the Task/Event tables, so reports and triggers silently miss themAn explicit source-of-truth statement in the data dictionary
"Can one bad row be allowed to fail on its own?"The bare insert verb rolls the whole transaction back; Database.insert(..., dmlOptions, ...) does notA partial-success write plus the Database.SaveResult loop that reports what didn't land

What a proper configuration adds over just creating the records: the activity model matches the org's actual read path and volume, the shared Task/Event surface is deployed as one unit instead of half of it silently disabling FLS, and bulk writes fail one row at a time and quietly instead of rolling back a 200-record save while emailing everyone.

Core Concepts

Task vs Event

Task: to-do item with due date. Event: calendar appointment with start/end time. Both share the polymorphic WhatId / WhoId pattern and an IsTask discriminator on Activity queries.

Polymorphic SOQL

SELECT Id, Subject, What.Type, TYPEOF What
  WHEN Account THEN Name, Industry
  WHEN Opportunity THEN Amount, StageName
END FROM Task

Without TYPEOF, only ID and Type are accessible via What.Type.

ActivityHistory vs OpenActivity

ActivityHistory: closed activities (completed tasks, past events). OpenActivity: open activities (due, upcoming). Only queryable as subqueries from activity-enabled parents. Cannot create/update these objects directly.

Einstein Activity Capture

EAC syncs emails and calendar events from Exchange/Gmail into Salesforce. Data lives in a separate EAC store — visible on timeline, but not in Task/Event tables. Reporting requires Activity Metrics or EAC-specific features.

Common Patterns

Pattern: Bulk task creation from trigger

List<Task> tasks = new List<Task>();
for (Opportunity o : Trigger.new) {
    tasks.add(new Task(WhatId = o.Id, Subject = 'Review',
                       ActivityDate = Date.today().addDays(7), OwnerId = o.OwnerId));
}

Database.DMLOptions dml = new Database.DMLOptions();
dml.optAllOrNone = false;                  // one bad WhoId must not roll back the save
dml.EmailHeader.triggerUserEmail = false;  // suppress "a task was assigned to you"

List<Database.SaveResult> results =
    Database.insert(tasks, dml, AccessLevel.SYSTEM_MODE);

Collect and write once — never loop-DML. The two DMLOptions lines are not optional polish: creating or modifying a Task is one of the events that fires triggerUserEmail, and the bare insert verb has nowhere to put either setting. Full version with result handling in references/metadata-examples.md section 5.

Pattern: Custom Object for high-volume activity-like data

Past roughly 50k activities/day per object — UNVERIFIED (2026-09-05): a field heuristic, no activity-volume ceiling is published in the App Limits cheat sheet or the LDV guide — consider a custom Interaction__c with a real lookup instead of polymorphic Task. The grounded reason to switch is the read path, not the number: the LDV guide lists Activity Subject, TaskStatus and TaskPriority among the standard fields the platform can't index, so a query that must filter on any of them will not get selective on a large Task table.

Pattern: Activity rollup via Lightning component or Apex

Activity count / last-activity-date rollups: use formula-friendly patterns (e.g., Salesforce's Activity Metrics, EAC Insights, or DLRS).

Decision Guidance

NeedApproach
Standard to-do with remindersTask
Calendar appointment with participantsEvent
Query must filter on activity subject or status at volumeCustom Interaction__c with an indexed field
Email tracking without EACEmailMessage + Task linking
Reporting on email activityActivity Metrics or EAC Insights

Recommended Workflow

  1. Establish what the org already does. Retrieve Settings:Activities and check whether Shared Activities is on — it is a read-only field no deploy can change, and TaskWhoIds / TaskRelation / EventRelation.IsParent only exist when it is. Note whether Einstein Activity Capture is enabled for anyone (admin/einstein-activity-capture-setup).
  2. Decide Task/Event vs custom Interaction__c using the Decision Guidance table above and the tradeoff table in references/well-architected.md. Drive the decision from the read path and the sharing requirement, not from record count alone.
  3. Write the metadata from references/metadata-examples.md — Activities.settings-meta.xml, enableActivities on every object that must be a valid WhatId, the custom field under Activity (never under Task), the TaskStatus value set if IsClosed semantics are changing, and FLS entries for Task and Event in the same permission set.
  4. Write the read path with TYPEOF or a What.Type filter, and the write path with Database.insert(records, dmlOptions, accessLevel) carrying optAllOrNone = false and EmailHeader.triggerUserEmail = false. Partition out recurring Tasks and child Events (IsChild = true) before any bulk update.
  5. Lint the working tree with python3 skills/admin/activity-and-task-patterns/scripts/check_activity_and_task_patterns.py --manifest-dir force-app/main/default. It flags FROM Activity, DML on ActivityHistory/OpenActivity, loop-DML on Task/Event, What.<field> without TYPEOF, bare insert/update of Task collections, ActivitiesSettings files that try to set the read-only Shared Activities flag, and permission-set FLS that names one child object but not the other.
  6. Read references/gotchas.md end to end before deploying — the ten entries are the failures this skill exists to prevent, and several of them (the 500-row subquery cap, shared FLS, the EmailMessage task swap) are invisible in a sandbox with test-sized data.
  7. Verify in the target org using the three checks at the end of references/metadata-examples.md: a Task insert against the newly activity-enabled object, a Status/IsClosed/CompletedDateTime query, and a FieldPermissions query that must return a row for both Task.<field> and Event.<field>.

Review Checklist

  • Activity volume estimated and matched to object choice
  • Polymorphic SOQL uses TYPEOF or explicit type filters
  • Bulk DML used for task/event creation
  • ActivityHistory / OpenActivity queries only in subquery form
  • EAC data strategy documented
  • Custom fields on Activity limited (they propagate to both Task and Event)
  • Sharing model for activities understood (inherits from WhatId parent)
  • FLS deployed for Task.<field> and Event.<field> — a missing entry disables, it does not preserve
  • Bulk writes use Database.insert(..., dmlOptions, accessLevel) with optAllOrNone = false
  • EmailHeader.triggerUserEmail set deliberately on any job that creates or modifies Tasks
  • Recurring Tasks and IsChild = true Events partitioned out before bulk update
  • Shared Activities state confirmed in the org, not assumed from a deploy
  • WHERE clauses filter on an indexable field, not Subject / Status / Priority alone
  • scripts/check_activity_and_task_patterns.py --manifest-dir … run clean

Salesforce-Specific Gotchas

  1. Custom fields on Activity propagate to both Task and Event. You cannot add a field only to Task — architect with this in mind.
  2. Activities inherit sharing from the WhatId parent. No independent sharing rules.
  3. OpenActivity and ActivityHistory cannot be modified. They are projections of Task/Event — the Object Reference lists describeSObjects() as their only supported call (object_reference.txt L23515–L23516, L191459–L191460).
  4. Shared Activities is not deployable. Its ActivitiesSettings field has been read-only in every API version since v36.0; a deploy that sets it succeeds and changes nothing.
  5. Task.IsClosed is never written directly. It is derived from the Status value's closed flag in the TaskStatus standard value set, and Event has no Status at all.

The ten platform behaviours behind these — with what happens, when, and how to avoid — are in references/gotchas.md.

Output Artifacts

ArtifactDescription
Activity model decisionTask vs Event vs custom object
SOQL pattern libraryPolymorphic queries with TYPEOF
Bulk creation templateApex trigger / batch pattern

Reference Files

FileRead it when
references/metadata-examples.mdWriting the deployable XML — ActivitiesSettings, enableActivities, an Activity custom field and its FLS, TaskStatus, plus the bulk-safe Apex and the post-deploy verification queries
references/gotchas.mdBefore deploying, and whenever activity behaviour differs between sandbox and production
references/examples.mdTwo worked scenarios end to end: a polymorphic timeline query for an LWC, and bulk task generation from a record-triggered context
references/llm-anti-patterns.mdReviewing AI-generated Apex or metadata that touches Task, Event or Activity
references/well-architected.mdChoosing between Task/Event and a custom Interaction__c, and citing the sources behind any claim in this skill

Related Skills

  • apex/apex-polymorphic-soql — TYPEOF, What.Type and instanceof in depth
  • apex/apex-dml-patterns — Database.DMLOptions beyond the email header, and partial-success result handling
  • apex/trigger-framework — where activity-creating logic belongs in a handler
  • admin/einstein-activity-capture-setup — EAC sync scope, and where EAC data actually lives
  • admin/case-management-setup — case-related activity handling
  • admin/email-to-case-configuration — the intake side of the EmailMessage.ActivityId task
  • admin/picklist-and-value-sets — standard vs global value sets, for the TaskStatus change
  • admin/queues-and-public-groups — Task.OwnerId accepts Groups of type Queue only
  • architect/large-data-volume-architecture — when activity volume forces a custom object
  • data/data-archival-strategies — what to do with IsArchived activities

レビュー

まだレビューはありません。使ってみた感想をお寄せください。

同じリポジトリのスキル

概要と使いどころ

Use this skill when writing test-first, behavior-driven acceptance criteria in Given/When/Then format for a Salesforce user story. Covers happy path, edge cases, negative paths, permission boundaries, and data-state preconditions so the AC block can drive UAT scripts and Apex test design downstream. Trigger keywords: given when then, gherkin, behavior driven AC, test first acceptance criteria, scenario outline, BDD acceptance criteria. NOT for the user-story format itself (use admin/user-story-writing-for-salesforce). NOT for UAT script writing (use admin/uat-test-case-design). NOT for Apex test method generation (use agents/test-class-generator). NOT for high-level UAT planning (use admin/uat-and-acceptance-criteria). More triggers: acceptance criteria record, ac_id, req_id on a criterion, artefact under test, negative case for a rule-type requirement, no-match fall-through criterion, oracle for a Then clause, test type apex flow manual, criteria linter, check_ac_format.py, --manifest-dir.

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

Design Invocable Apex actions that return deterministic, agent-friendly errors instead of surfacing raw exceptions to the LLM. NOT for authoring the action itself — @InvocableMethod schema, labels, security context — use agentforce/custom-agent-actions-apex. NOT for the Apex tests that force each error branch — use agentforce/agent-action-unit-tests.

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

Use when designing how an Agentforce agent extracts structured input parameters (slots) from a user's natural-language utterance to invoke an action. Triggers: 'agent extract date from user', 'agent action argument extraction', 'agentforce slot filling', 'agent invocable input mapping', 'agent fails to fill required parameter'. NOT for action authoring (use agentforce/agent-actions) or for prompt-template variable binding (use agentforce/prompt-builder-templates).

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

Apex test patterns for @InvocableMethod agent actions: per-reason-code branch coverage, bulk safety, callout mocking, deterministic assertions. NOT for testing whether the agent routes to the right topic or answers well — use agentforce/agent-testing-and-evaluation. NOT for designing the error envelope the tests assert on — use agentforce/agent-action-error-handling.

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

Designing or reviewing Agentforce actions: Flow actions, Apex invocable actions, prompt-template actions, action naming, input and output contracts, confirmation requirements, and safe error behavior. Triggers: 'agent actions', 'build an agent that can look up an order', 'make the agent able to check order status', 'give the agent a capability', 'agent that can retrieve a record', 'flow action for agent', 'agent invocable action', 'action schema design'. NOT for writing the Apex class itself — use agentforce/custom-agent-actions-apex. NOT for the reason_code error envelope that stops an agent retry loop — use agentforce/agent-action-error-handling.

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

Use when deploying an Agentforce agent to a channel surface: Embedded Service web chat, Slack, Experience Cloud, Agent REST API, or Salesforce Mobile. Triggers: 'deploy agent to website', 'add Agentforce to Slack', 'enable agent for mobile app', 'configure embedded service for agent', 'agent API for custom integration', 'multi-channel agent deployment'. NOT for agent logic design — use agentforce/agent-topic-design or agentforce/agent-actions for topics, instructions, and action contracts.

日本語の概要は準備中です。原文の説明を表示しています。

PranavNagrecha/AwesomeSalesforceSkills192026年10月4日 更新

PranavNagrecha のスキルをすべて見る

このスキルの問題を報告する