Create the IT Service Fulfiller Agent
SkillProductivitySets up an IT service request fulfillment agent by creating and activating its configuration via Salesforce CLI.
Use Create the IT Service Fulfiller Agent in Claude, ChatGPT or Ahel Desktop
Free. Sign in, add Create the IT Service Fulfiller Agent and connect your AI. About a minute.
Also: Claude Code · Cursor · Codex
Then ask your AI: use the Create the IT Service Fulfiller Agent skill
Details
Instructions available. Your AI can read the instructions. Execution depends on the setup they require.
Account requirements not reviewed. Check the skill instructions before use; ahel provides instructions and does not run this skill.
No other account needed.
Add ahel to your AI once: Claude, ChatGPT, Cursor, Claude Code or Codex. Then ask it to use this.
About this skill
Create and activate the IT Service Fulfiller agent as a Next-Gen Authoring (NGA) native agent from the shipped ITSM Fulfiller template's Agent Script, using the Salesforce CLI (sf): read the template, check idempotency, create the NGA bundle then publish and activate it, then verify it is live. Idem
What this skill tells your AI
The instructions your AI receives, as published by forcedotcom/sf-skills in skills/service-itsm-agentic-setup-fulfiller-agent-configure/SKILL.md and read by ahel’s review.
Create and activate the IT Service Fulfiller Agent as a Next-Gen Authoring (NGA) native agent — Agent-Script-based (AiAuthoringBundleDefVer/bundle), appearing natively in Agentforce Studio's Agents list with no external-link icon — entirely through the Salesforce CLI (sf). This skill does not call the legacy /connect/service-itsm/createAgent; instead it reuses the shipped ITSM Fulfiller template's agentScript and feeds it into the NGA bundle pipeline:
POST /nextgen-authoring/bundles(createBundleWithVersion) — creates the bundle + first version from the template's Agent Script.POST /nextgen-authoring/bundle-versions/{id}/publish— publishes the version (creates the underlyingBotDefinition/BotVersion).POST /nextgen-authoring/bundle-versions/{id}/activate— activates it.
Commands: sf api request rest for Connect API GET/POST; sf data query for the SOQL idempotency + verify reads.
Helper scripts (invoked via Bash) hold every JSON-parsing / decision rule so the model never eyeballs a response body (A9): classify-preflight.mjs (Studio-access + template-provisioning verdict), classify-agent-existence.mjs (idempotency + reactivation-need from the BotDefinition SOQL), build-create-body.mjs (HTML-decodes the template's agentScript, normalizes it for the org's enabled features via strip-release-management.mjs, substitutes config.developer_name/config.agent_label, writes the bundle-create body to a JSON file so large content and free-text quotes never hit an inline shell string), render-report.mjs (deterministic report renderer — single source of report text for chat-turn and harness file).
The Fulfiller agent is the IT-technician-facing assistant — incident triage, case summarization, field updates, related-record automations. The employee self-service surface is service-itsm-agentic-setup-employee-agent-configure.
Scope
- In scope: Reading
agent-templates; extracting the Fulfiller template's Agent Script (svc_itsm_intelligence__ITSrvcMgmtFulfiller); creating the Fulfiller agent as an NGA-native agent viacreateBundleWithVersion→publish→activate; SOQL-verifying live; idempotent skip on duplicate developer name; normalizing the created Agent Script so it activates cleanly on any Agentforce-for-IT-Service org (internal step, never surfaced to the user — see below) — all viasf. - Out of scope: The Employee agent — broad or ~47 specializations under
svc_emp_intelligence__(service-itsm-agentic-setup-employee-agent-configure); enabling org-level feature toggles (validated byservice-itsm-agentic-setup-agentforce-studio-validate); low-level topic/action authoring; perm-set assignment; content-bundle deployment; CMDB CRUD; Discovery / Service Graph; the legacycreateAgentroute.
Preconditions
If any of these are unmet, sf surfaces an auth error or a 401/403/404; surface the raw error verbatim and stop — do not fabricate state.
sfCLI authenticated to the target org (sf org display -o <alias>shows Connected). All calls use--target-org <alias>; never extract the access token by hand.- API v67.0+ — pinned in the URL path; do not hand-edit below the minimum.
- ITSM features + Fulfiller template provisioned (
svc_itsm_intelligence__ITSrvcMgmtFulfiller). Ifagent-templatesreturns nothing or the routes 404, runservice-itsm-agentic-setup-agentforce-studio-validate. node≥ 18 on PATH.
Operations at a glance
| Concern | Command | Notes |
|---|---|---|
| Studio access (precondition read) | sf api request rest "/services/data/v67.0/agentforce-studio/access/Agents" --method GET -o <alias> | hasAccess=false ⇒ prerequisite hand-off |
| List agent templates + Agent Script (read) | sf api request rest "/services/data/v67.0/connect/service-itsm/agent-templates?agentType=AgentforceEmployeeAgent" --method GET -o <alias> | agentType=AgentforceEmployeeAgent required; confirms Fulfiller template + non-empty agentScript |
| Enumerate the existing agent + latest version status (read) | sf data query -q "SELECT Id,DeveloperName,MasterLabel,AgentTemplate,(SELECT Id,Status FROM BotVersions ORDER BY VersionNumber DESC LIMIT 1) FROM BotDefinition WHERE Id='<botDefinitionId>' OR AgentTemplate='<agentTemplate>' OR DeveloperName='<developerName>'" -o <alias> --json | Keyed PRIMARILY on the template's botDefinitionId (Phase-1 row); OR AgentTemplate= is a defensive fallback that would catch a live agent instantiated from the OOTB source template (svc_itsm_intelligence__ITSrvcMgmtFulfiller = Phase-1 template.id) regardless of its DeveloperName; OR DeveloperName= is the real guard here — the normal Fulfiller case (never pre-provisioned; null AgentTemplate) and the guard for a dangling Id link (deleted target). Classified by scripts/classify-agent-existence.mjs; Active latest ⇒ ALREADY-CREATED; Inactive latest ⇒ offer reactivation |
| Create the NGA bundle (write) | sf api request rest "/services/data/v67.0/nextgen-authoring/bundles" --method POST --body @<body-file> -o <alias> | Body built by scripts/build-create-body.mjs; response id = the bundle version Id |
| Publish the bundle version (write) | sf api request rest "/services/data/v67.0/nextgen-authoring/bundle-versions/<bundleVersionId>/publish" --method POST --body '{}' -o <alias> | Returns publishedBotId/publishedBotVersionId — creates the underlying BotDefinition/BotVersion |
| Activate the bundle version (write) | sf api request rest "/services/data/v67.0/nextgen-authoring/bundle-versions/<bundleVersionId>/activate" --method POST --body '{}' -o <alias> | Empty response on success; agent is now live and NGA-native |
| Activate an existing inactive version (write) | sf api request rest "/services/data/v67.0/connect/bot-versions/<latestVersionId>/activation" --method POST --body '{"status":"Active"}' -o <alias> | Reactivation path only (Phase 2b) — skips create/publish |
| Verify agent is live (read) | sf data query -q "SELECT ... FROM BotDefinition WHERE Id='<verifyId>'" -o <alias> --json | <verifyId> = create path's publishedBotId (Phase-5) or the Phase-2 classifier's returned live matched Id (its botDefinitionId/agentId) on ALREADY-CREATED / reactivation — not the null Phase-1 template botDefinitionId, never the collected developerName; confirm BotDefinition present + latest version Active |
Full command shapes and the ITSM Connect API reference live in references/cli-invocation.md; the reactivation-path call + idempotency verdict table live in references/reactivation.md; the response-body error codes and recurring gotchas live in references/error-taxonomy.md.
Never extract the access token. Use
sf api request rest/sf data querydirectly — they use the CLI's stored session for the target org. Do not pull theaccessTokenout ofsf org displayand hand-build an HTTP request with it; that bypasses the CLI session and leaks a bearer token into shell context.
--jsonrule.sf data querytakes--json(results come back in a.result.records[]envelope — that's what the classifier expects).sf api request restdoes not — omit--jsonthere; its raw stdout body is already JSON.
Shipped ITSM Fulfiller agent template
| Template identifier | Default developer name |
|---|---|
svc_itsm_intelligence__ITSrvcMgmtFulfiller (masterLabel "IT Service Fulfiller") | IT_Service_Fulfiller_Agent |
The
agentScriptfield is the source of truth for the NGA create — notid.scripts/build-create-body.mjsmatches onmasterLabel, HTML-decodesagentScript, and substitutes the collected<developerName>/<label>intoconfig.developer_name/config.agent_labelbefore it becomes the bundle'sresourceContent. The Employee-facing agent is handled byservice-itsm-agentic-setup-employee-agent-configure.
Internal template normalization — never surfaced to the user. Before the decoded script becomes
resourceContent,scripts/strip-release-management.mjsremoves thetopic ReleaseManagement:block — plus itsgo_to_ReleaseManagement:selector transition and routing bullet. That topic's only action,svc_itsm_intelligence__SummarizeRelease, is gated behind an org preference (ReleaseManagementPref) and is not surfaced by/actions/custom/generatePromptResponseon an org that has not enabled it; shipping it would makeactivatereturn HTTP 200 with a{success:false, "... does not exist"}silent-failure body.classify-action-availability.mjsapplies the identical transform so Phase 2c scans the same normalized script — the two callers must stay in lock-step. The transform is a no-op if the block is absent (safe against future template revisions). This normalization is an implementation detail: do NOT mention it, the removed subagent, or Release Management in chat narration, the confirm-to-write step, or the report — the admin only ever sees that the agent was created and activated.
Architecture — Creation stages
| Stage | What happens | Tool used |
|---|---|---|
| Preflight | Confirm Studio access (agentforce-studio/access/Agents) and that the template's agentScript is present | Bash (sf api request rest) |
| Enumerate | Read the Fulfiller template (agent-templates) and existing agents + latest version status (SOQL on BotDefinition/BotVersions); classify idempotency and reactivation-need via script | Bash (sf, node) |
| Confirm-to-write | Present the exact developerName + label (the NGA create target), OR — if the existing agent is inactive — present the reactivation option instead, and require explicit "yes" either way | AskUserQuestion |
| Create (create path only) | POST createBundleWithVersion (builds the NGA bundle + first version from the decoded, substituted template Agent Script) | Bash (sf api request rest, node) |
| Publish (create path only) | POST .../bundle-versions/<id>/publish (creates the underlying BotDefinition/BotVersion) | Bash (sf api request rest) |
| Activate | POST .../bundle-versions/<id>/activate (create path) OR POST .../connect/bot-versions/<latestVersionId>/activation with {"status":"Active"} (reactivation path — skips create/publish) | Bash (sf api request rest) |
| Verify | SOQL-read BotDefinition/BotVersions and confirm the agent exists with an Active latest version | Bash (sf data query) |
Idempotency: keyed PRIMARILY on the template's botDefinitionId (Phase-1 agent-templates row — the platform's authoritative template→BotDefinition link), FALLING BACK first to the BotDefinition's AgentTemplate (the OOTB namespaced source template = Phase-1 template.id) and then to the collected <developerName>. The Phase-2 read is BotDefinition WHERE Id='<botDefinitionId>' OR AgentTemplate='<agentTemplate>' OR DeveloperName='<developerName>' (the OR AgentTemplate= half is a defensive key that would catch a live agent instantiated from the source template regardless of its DeveloperName; the OR DeveloperName= half is both the null-botDefinitionId fallback — the normal Fulfiller case — AND the guard for a dangling Id link whose target BotDefinition was deleted), + latest BotVersion.Status (classified by the helper script). Outcomes: no match on any key ⇒ exists:false ⇒ create; latestVersionStatus:"Active" ⇒ ALREADY-CREATED (skip the write, fall through to Phase 7 verification); needsActivation:true (latest version Inactive) ⇒ offer to activate the existing version instead of creating a new agent (Phase 2b) rather than silently skipping or duplicating. Why the fallbacks matter: the Fulfiller is never pre-provisioned and this skill's create path never stamps templateName, so BOTH the template's botDefinitionId AND the agent's AgentTemplate are always null — the <developerName>-keyed fallback is the guard that actually catches a repeat run; short-circuiting straight to create on a null botDefinitionId would re-create and collide with DUPLICATE_VALUE. The server does reject a duplicate DeveloperName at publish (unique-constraint → bundle cleanup), but only this Phase-2 read turns a repeat into a graceful skip instead of that hard error.
Clarifying Questions
Collect from the user (ask only what is not already in conversation context):
| Field | Description | Default |
|---|---|---|
| Target org | The sf org alias to create the agent in | Default org (sf config get target-org) |
| Developer name | Unique DeveloperName for the agent | IT_Service_Fulfiller_Agent |
| Label | User-facing label for the agent | IT Service Fulfiller Agent |
| Confirm the write | Explicit confirmation before the create/publish/activate sequence | REQUIRED — present the developerName + label and require "yes" via AskUserQuestion |
The idempotency read keys PRIMARILY on the template's botDefinitionId (Phase-1 row) and FALLS BACK to the BotDefinition's AgentTemplate (defensive — null on the never-pre-provisioned Fulfiller) and then to the collected <developerName>, the guard that actually catches a repeat here, when that is null; the verify read keys on the publish response's publishedBotId (create path) or the template's botDefinitionId (ALREADY-CREATED / reactivation). The collected <developerName> and <label> (defaults IT_Service_Fulfiller_Agent / IT Service Fulfiller Agent) also thread through the createBundleWithVersion body — both the outer apiName/label AND the substituted config.developer_name/config.agent_label inside the Agent Script. Never hardcode the name in one call and collect it in another — a mismatch between the bundle's outer apiName and the script's internal developer_name causes the platform to diverge the two. Creating an agent provisions a live, activated agent on the org; the user must explicitly approve the write.
Workflow
Substitute <alias> with the collected target org and <developerName> / <label> with the collected values. Full command shapes + per-phase verdict-branch handling live in references/workflow-detail.md — the phase summary below names each step and its load-bearing rule; the reference file holds the exact sf / node invocations to copy.
Shortened here. Read the whole file on GitHub.
Signals
- GitHub stars
- 1k
- Forks
- 351
- Last commit
- Sep 2026
ahel review
K2info
exfiltration (in references/cli-invocation.md)
Automated review, not a security audit. Ruleset v1+k2.
Advanced
- Item type
- skill
- Key
service-itsm-agentic-setup-fulfiller-agent-configure- Source
- github.com/forcedotcom/sf-skills
github.com/forcedotcom/sf-skills
More in Productivity
Skill · coreyhaines31
More in Productivitygws-calendar
Skill · googleworkspace
More in Productivitylark-workflow-standup-report
Skill · larksuite
More in Productivitywriting-plans
Skill · obra
More in Productivityenergy-procurement
Skill · affaan-m
More in Productivityhomelab-pihole-dns
Skill · affaan-m
More in Productivity