Take Action
The take-action-v2 API validates user permissions, checks byte balance, deducts costs, and tracks API key usage before allowing workflow execution to proceed.
Endpoint
POST https://api.buildbleu.com/functions/v1/take-action-v2
Authentication & Authorization
This endpoint requires dual authentication:
- User Authentication: Supabase JWT token in Authorization header
- API Key Authentication: Valid API key in
X-Bleu-Tokenheader
Request Format
Headers (Required)
| Header | Description | Example |
|---|---|---|
Authorization | Bearer token with Supabase user JWT | Bearer USER_JWT |
X-Bleu-Token | API key for scope-based authorization | BLEU_API_KEY |
Content-Type | Must be application/json | application/json |
Request Body (Required)
{
"action_id": "ACTION_ID"
}
Optional custom amount
- amount (optional, integer): Custom number of bytes to charge.
- Requires the action to have
variable_amount = true. - Must be a positive integer.
- If provided and the action does not allow variable amounts, the API returns
400with"Custom amount is not allowed for this action.". - If invalid, the API returns
400with"Invalid amount. It must be a positive integer.". - When valid, the provided
amountis used for both user deduction and usage tracking (bytes_used).
- Requires the action to have
Examples
Basic Request
- cURL
- Node.js
- Python
curl -X POST \
--verbose \
--header "Authorization: Bearer USER_JWT" \
--header "X-Bleu-Token: BLEU_API_KEY" \
--header "Content-Type: application/json" \
--data '{
"action_id": "ACTION_ID"
}' \
https://api.buildbleu.com/functions/v1/take-action-v2
const response = await fetch('https://api.buildbleu.com/functions/v1/take-action-v2', {
method: 'POST',
headers: {
'Authorization': `Bearer ${userJWT}`,
'X-Bleu-Token': 'your-api-key-here',
'Content-Type': 'application/json'
},
body: JSON.stringify({ action_id: 'workflow-step-uuid' })
});
if (response.status === 200) {
// Continue with your workflow logic here
} else {
const error = await response.json();
throw new Error(`Workflow blocked: ${error.error}`);
}
import requests
response = requests.post(
'https://api.buildbleu.com/functions/v1/take-action-v2',
headers={
'Authorization': f'Bearer {user_jwt}',
'X-Bleu-Token': 'your-api-key',
'Content-Type': 'application/json'
},
json={'action_id': 'workflow-step-uuid'}
)
if response.status_code == 200:
# Continue with your workflow logic here
pass
else:
error = response.json()
raise Exception(f"Workflow blocked: {error['error']}")
Example body with custom amount (variable amount actions only)
{
"action_id": "ACTION_ID",
"amount": 250
}
Security
Always use environment variables or secure key management systems. Never include API keys in:
- Client-side JavaScript code
- Public repositories
- Log files or error messages
- URL parameters
Response Codes
200 - Success
Action validated successfully. Continue workflow execution.
{
"success": true,
"action_id": "ACTION_ID",
"bytes_used": 100,
"user": {
"id": "user-uuid",
"email": "user@example.com",
"bytes": 900,
"created_at": "2024-01-01T00:00:00Z",
"updated_at": "2024-01-01T00:00:00Z"
}
}
Error Responses
| Status | Description | Common Causes |
|---|---|---|
| 400 | Missing or invalid request data | Missing action_id, invalid JSON format, invalid amount, amount sent for non-variable action |
| 401 | Authentication failure | Missing/invalid X-Bleu-Token header, expired API key, invalid JWT |
| 403 | API key lacks permission | Action ID not in API key's scopes array |
| 404 | Action or user not found | Invalid action_id UUID, user doesn't exist |
| 402 | Insufficient bytes | User's byte balance lower than action cost |
| 500 | Server-side error | Database issues, transaction failures |
All error responses return JSON with an error field containing the error message.
Integration Flow
- Before executing any workflow step, call the
take-action-v2endpoint - Check the response status:
200: Proceed with workflow execution- Any other status: Handle error and stop workflow
- Track bytes used from successful responses for monitoring
- Implement retry logic for transient errors (500 status codes)
Best Practices
Pro Tips
- Cache API keys securely and never expose them in client-side code
- Handle all error cases gracefully to improve user experience