Advanced Case 1: Tech Teams Encapsulate Complex Logic for Business Operations
Overview
The basic guide shows the simplest scenario: a user says one sentence, and the AI auto-creates a requirement. But in real ToB operations, many tasks go far beyond simple CRUD on a single table — changing a requirement's status, for example, requires updating the main table, writing a history record, and notifying stakeholders, all at once.
This case study uses "requirement status change" as an example to demonstrate: when business logic involves multi-table writes, state transition validation, and transactional consistency, how the tech team can build a function endpoint, and how the AI loads a Skill to complete the entire flow with a single sentence.
Business Scenario: Why Function Endpoints Are Needed
In the basic guide, the AI can directly operate on the database. But in real-world business, many operations have stricter requirements:
Strong validation: Status must flow in order (New → Assigned → In Progress → Testing → Completed → Closed). You can't jump from New directly to Completed.
Data consistency: When changing status, you must simultaneously record who changed it, when, and from what to what — the main table and history table must both update, and one cannot succeed while the other fails.
Transactional guarantees: An operation touches multiple tables. If any write fails, everything must roll back.
In these scenarios, the tech team needs to build a function endpoint that encapsulates validation logic and transaction guarantees, registers it on the platform, and lets the AI call it. Business users don't need to know what SQL is inside the function or how many writes it does — they just call the endpoint, and data consistency is guaranteed by the tech layer.
Technical Implementation: Building the Function
Registration Path
The function is an independent endpoint script (ENDPOINT). After registration, it's accessible via:
POST /api/endpoint/{appCode}/{scriptName}
This example uses:
- Script name:
update_requirement_status - App:
app-173e8652(Qizhi Yuntu) - Full path:
POST /api/endpoint/app-173e8652/update_requirement_status
Prerequisites
Before development, the tech team should confirm:
- App
app-173e8652exists and hasyt_requirements(main requirements table) andyt_requirement_history(status history table) data models - The operator has write permissions for both models
Function Code
The tech team implements the status change with simultaneous main table update and history record creation:
/**
* Requirement status change (dual-write: main table + history table)
* Script name: update_requirement_status
* App: app-173e8652
*/
export default async function updateRequirementStatus(params, context) {
const { id, new_status, operator_id, reason } = params;
// -------- Part 1: Query and Validation --------
// 1. Query current requirement info
const requirement = await context.client.models.yt_requirements.findOne({
id: id,
});
if (!requirement) {
throw new Error("Requirement not found");
}
const oldStatus = requirement.status;
// 2. Validate state transition
const validTransitions = {
new: ["assigned", "closed"],
assigned: ["in_progress", "closed"],
in_progress: ["testing", "closed"],
testing: ["completed", "in_progress"],
completed: ["closed"],
closed: [],
};
if (!validTransitions[oldStatus]?.includes(new_status)) {
throw new Error(
`Status cannot transition from ${oldStatus} to ${new_status}`
);
}
// -------- Part 2: Dual Write (Transactional) --------
// The system detects write operations and auto-starts a Best Effort 1PC transaction
// No manual commit/rollback needed — normal return = commit, exception = rollback
// 3. Update main table: requirement status
await context.client.models.yt_requirements.update({
id: id,
status: new_status,
});
// 4. Write history table: change record
await context.client.models.yt_requirement_history.create({
requirement_id: id,
user_id: operator_id,
field_name: "status",
old_value: oldStatus,
new_value: new_status,
created_at: new Date().toISOString(),
});
// -------- Part 3: Return Result --------
return {
success: true,
requirement_id: id,
old_status: oldStatus,
new_status: new_status,
operator_id: operator_id,
message: "Status updated successfully, history record synced",
};
}
Transaction Mechanism
Lovrabet uses a Best Effort 1PC transaction model. The tech team never manages transactions manually:
| Timing | Behavior |
|---|---|
| Read operations (findOne / getList) | No transaction, no connection held |
| First write operation (update / create) | Transaction auto-starts |
| Subsequent writes | Auto-join the same transaction |
| Script returns normally | Auto-commit all transactions |
| Script throws an exception | Auto-rollback all transactions |
The tech team just writes logic in business order. Transactions are managed automatically by the platform.
Skill Encapsulation: One Sentence for Business Users
Once the function endpoint is ready, how do business users interact with it?
Encapsulate the flow into a Skill. The AI loads it and automatically: confirms the requirement exists → calls the function → notifies stakeholders.
Skill Template
---
name: update_requirement_status
version: 0.1.0
description: "Requirement status change. Trigger words: mark as completed, change requirement to, update requirement status."
---
# Requirement Status Change
## Step 1: Confirm the requirement exists
Query whether the requirement ID provided by the user exists and what its current status is. If not found, inform the user and stop.
## Step 2: Change status and record history
Call the update_requirement_status endpoint to simultaneously:
- Update the requirement status to the user-specified value
- Create a history record (original status, new status, operator, timestamp)
If the endpoint returns failure, inform the user of the reason and stop.
## Step 3: Notify the requirement creator
Look up who created the requirement and send them an email or Lark message:
- Which requirement had a status change
- What the new status is
## Notes
- Status values must be valid (new / assigned / in_progress / testing / completed / closed)
- If the user hasn't specified a reason, ask before proceeding
- Step 3 notification is informational only, no further action required
- Do NOT call the raw dataset API directly
Usage Example
User Input
Mark the requirement "App theme auto-adapts to phone case color" as completed
AI Automatically
Loads Skill → Confirms requirement exists → Calls function endpoint (main table update + history write in one transaction) → Notifies the requirement creator
Example Output
✅ Status updated
━━━━━━━━━━━━━━━━━━
Requirement ID: 305
Title: App theme auto-adapts to phone case color
Status: In Progress → Completed
Operator: Zixuan
Change history: Recorded
━━━━━━━━━━━━━━━━━━
Notification: Email sent to requirement creator
FAQ
Q: Do I need to set up my own infrastructure to develop function endpoints?
No. Just develop and register scripts under your existing Lovrabet app. Transactions, connection management, and access control are all provided by the platform. You can use the Rabetbase CLI developer toolkit.
Q: Isn't it hard to maintain state transition rules inside a function?
It's far safer than exposing the database directly to AI. When rules change, the tech team only updates the function code — the Skill and AI prompts don't need any changes.
Q: What if the function endpoint returns an error?
Check the error message. Common causes: requirement ID doesn't exist, invalid status transition, insufficient permissions. Errors are passed through to the AI, which will inform the user.
Q: Do business users need to know the valid status values?
No. The Skill already defines the valid values. Business users just say "mark as completed" and the AI maps it to the correct status code.
Q: What if we need to add more dimensions later, like priority change records?
Just add history table fields in the function. The Skill describes business steps, not specific field names.