update_fields
Update custom field values on existing Asana tasks.
Type
Record<string, string> - Map of field GID to value
Description
The update_fields action updates custom field values on tasks linked in the PR description. This is only allowed when has_asana_tasks: true (default) or when the PR has Asana task URLs.
Use this to automatically update task status, priorities, or other fields based on PR lifecycle events.
Critical Requirement
update_fields requires has_asana_tasks: true (or omit the condition entirely). You cannot update fields when no tasks exist.
Syntax
then:
update_fields:
'1234567890': '0987654321' # Field GID → Value
'1111111111': 'Text value' # Text field
'2222222222': '{{pr.title}}' # Template valueField Types
Different field types require different value formats:
| Field Type | Value Format | Example |
|---|---|---|
| Enum/Dropdown | Option name (text) or option GID | 'In Review' or '1234567890' |
| Text | Plain text or template | 'In Review' |
| Number | Numeric string | '42' |
| Template | Handlebars expression | '\{\{pr.number\}\}' |
Enum Fields Made Easy
For enum/dropdown fields, you can use the option name (e.g., 'In Review') instead of looking up GIDs. The action automatically finds the matching option!
Examples
Basic Status Update
Update status field when PR opens:
rules:
- when:
event: pull_request
action: opened
then:
update_fields:
'1234567890': '0987654321' # Status → "In Review"Multiple Fields
Update several fields at once:
rules:
- when:
event: pull_request
action: opened
then:
update_fields:
'1234567890': '0987654321' # Status → "In Review"
'1111111111': 'High' # Priority
'2222222222': '{{pr.number}}' # PR NumberDifferent Updates per Action
Different field values for different events:
rules:
# When PR opens
- when:
event: pull_request
action: opened
then:
update_fields:
'1234567890': '1111111111' # Status → "In Review"
# When PR merges
- when:
event: pull_request
action: closed
merged: true
then:
update_fields:
'1234567890': '2222222222' # Status → "Shipped"
# When PR closes without merge
- when:
event: pull_request
action: closed
merged: false
then:
update_fields:
'1234567890': '3333333333' # Status → "Cancelled"Using Templates
Extract values from PR:
rules:
- when:
event: pull_request
action: labeled
label: 'build_created'
then:
update_fields:
'1234567890': '0987654321' # Status → "Build Ready"
'1111111111': '{{extract_from_comments "Build #(\\d+)"}}' # Build numberLabel-Based Updates
Change status based on labels:
rules:
# QA label added
- when:
event: pull_request
action: labeled
label: 'ready-for-qa'
then:
update_fields:
'1234567890': '1111111111' # Status → "QA Requested"
# Approved label added
- when:
event: pull_request
action: labeled
label: 'approved'
then:
update_fields:
'1234567890': '2222222222' # Status → "Approved"Conditional Values with Templates
Use helper functions for logic:
rules:
- when:
event: pull_request
action: opened
then:
update_fields:
'1234567890': '{{or (extract_from_title "\\[urgent\\]") "Normal"}}'Field Value Resolution
Enum/Dropdown Fields
For status, priority, or custom dropdown fields, you have two options:
Option 1: Use the option name (recommended)
The easiest approach - just use the text name of the option:
# ✅ Recommended - use option name
update_fields:
'1234567890': 'In Review' # Field GID → Option name
'1111111111': 'High' # Priority field → option nameThe action automatically looks up the correct option GID from the name.
Option 2: Use the option GID (explicit)
If you prefer to be explicit or need to disambiguate:
# ✅ Also correct - use option GID
update_fields:
'1234567890': '0987654321' # Field GID → Option GIDCommon mistakes:
# ❌ Wrong - using field name as key
update_fields:
'Status': 'In Review' # Must use field GID as key
# ❌ Wrong - field GID must be the key, not the value
update_fields:
'1234567890': '1234567890' # Value should be option GID or nameText Fields
Use plain text or templates:
update_fields:
'1234567890': 'Custom text value'
'1111111111': 'PR #{{pr.number}}'
'2222222222': '{{clean_title pr.title}}'Number Fields
Provide numeric values as strings:
update_fields:
'1234567890': '42'
'1111111111': '{{pr.number}}'Template Evaluation
All values support Handlebars templates:
update_fields:
# Extract from PR body
'1234567890': '{{extract_from_body "Version: ([\\d.]+)"}}'
# Clean PR title
'1111111111': '{{clean_title pr.title}}'
# Map GitHub user to Asana
'2222222222': '{{map_github_to_asana pr.author}}'
# Use OR helper for fallback
'3333333333': '{{or pr.assignee "Unassigned"}}'Empty Values
TIP
If a template evaluates to an empty string, that field update is skipped. This is intentional behavior.
# If pr.assignee is empty, the field won't be updated
update_fields:
'1234567890': '{{map_github_to_asana pr.assignee}}'Validation Rules
- Requires:
has_asana_tasks: true(default) or PR must have Asana URLs - Field GIDs: Must be numeric strings (e.g.,
'1234567890') - Values: Any string (including templates)
- Empty values: Skipped (not an error)
Common Errors
Using with has_asana_tasks: false
# ❌ Wrong - can't update non-existent tasks
when:
event: pull_request
has_asana_tasks: false
then:
update_fields:
# Error: has_asana_tasks: false cannot have update_fields
# ✅ Correct - use with existing tasks
when:
event: pull_request
has_asana_tasks: true # Or omit
then:
update_fields:
'1234567890': '0987654321'Non-numeric field GIDs
# ❌ Wrong - field GID must be numeric
update_fields:
'Status': 'In Review'
'abc123': 'Value'
# ✅ Correct - use numeric GIDs
update_fields:
'1234567890': '0987654321'
'1111111111': 'Value'Using field GID instead of option name/GID for enums
# ❌ Wrong - using field GID as value
update_fields:
'1234567890': '1234567890' # This is the field GID!
# ✅ Correct - use option name
update_fields:
'1234567890': 'In Review' # Option name
# ✅ Also correct - use option GID
update_fields:
'1234567890': '0987654321' # Option GIDUnquoted GIDs
# ❌ Wrong - GIDs must be quoted
update_fields:
1234567890: 0987654321
# ✅ Correct - quote both keys and values
update_fields:
'1234567890': '0987654321'Finding Field GIDs
You Only Need Field GIDs
For enum/dropdown fields, you only need to find the field GID - not the option GIDs! Just use the option names (e.g., 'In Review', 'High') as values.
Using Asana API
Get project custom fields:
curl "https://app.asana.com/api/1.0/projects/{project_gid}?opt_fields=custom_field_settings.custom_field" \
-H "Authorization: Bearer YOUR_PAT"This returns:
{
"custom_field_settings": [
{
"custom_field": {
"gid": "1234567890", // Field GID (use as key)
"name": "Status",
"enum_options": [
{
"gid": "0987654321", // Option GID (optional - can use name instead)
"name": "In Review" // Option name (recommended)
}
]
}
}
]
}You can use either the option GID (0987654321) or the option name (In Review) as the value.
Using Browser DevTools
See Finding GIDs guide for detailed instructions on finding field GIDs.
Common Patterns
PR Lifecycle Tracking
Track PR from open to merge:
rules:
# PR opened
- when:
event: pull_request
action: opened
draft: false
then:
update_fields:
'1234567890': '1111111111' # Status → "In Review"
# Changes pushed
- when:
event: pull_request
action: synchronize
then:
update_fields:
'1234567890': '2222222222' # Status → "Updated"
# PR merged
- when:
event: pull_request
action: closed
merged: true
then:
update_fields:
'1234567890': '3333333333' # Status → "Shipped"Label-Driven Workflow
Let labels control field values:
rules:
- when:
event: pull_request
action: labeled
label: 'ready-for-qa'
then:
update_fields:
'1234567890': '1111111111' # Stage → "QA"
- when:
event: pull_request
action: labeled
label: 'qa-approved'
then:
update_fields:
'1234567890': '2222222222' # Stage → "Ready"Extract Metadata
Pull information from PR content:
rules:
- when:
event: pull_request
action: opened
then:
update_fields:
'1234567890': '{{extract_from_body "Version: ([\\d.]+)"}}'
'1111111111': '{{extract_from_title "\\[(\\w+)\\]"}}'See Also
- has_asana_tasks - Required condition
- create_task - Create tasks instead
- Template Helpers - Functions for extracting values
- Context Variables - Available template variables
- Finding GIDs - Detailed guide