AI & GenAI

[Tech Blog #19 | AI & GenAI] Khung RCRC: Bí Quyết Viết Prompt Chuẩn Công Nghiệp & Tự Động Hóa Với Python

0 views
[Tech Blog #19 | AI & GenAI] Khung RCRC: Bí Quyết Viết Prompt Chuẩn Công Nghiệp & Tự Động Hóa Với Python

1. Đặt vấn đề: Tại sao hầu hết mọi người viết Prompt đều thất bại?

Hãy thừa nhận một sự thật: Rất nhiều người dùng LLM (ChatGPT, Claude, Gemini) giống như đang nhắn tin vu vơ với một người bạn:

"Viết hộ tôi câu lệnh SQL tính doanh thu với."
Hoặc: "Hãy phân tích xem file dữ liệu này có vấn đề gì không."

Kết quả nhận về thường là: Một câu lệnh SQL chung chung sai tên bảng, một đoạn phân tích lan man không trúng trọng tâm, hoặc code viết bằng một ngôn ngữ/phiên bản thư viện mà hệ thống của bạn hoàn toàn không hỗ trợ.

Lý do: LLM là một cỗ máy dự đoán xác suất từ tiếp theo dựa trên ngữ cảnh bạn cung cấp. Bạn nạp vào một ngữ cảnh mù mờ, mô hình sẽ trả ra một kết quả mông lung.

Trong môi trường làm việc chuyên nghiệp (Production), để biến LLM thành một trợ lý đắc lực giải quyết các bài toán dữ liệu phức tạp, bạn cần một bộ khung tiêu chuẩn: Khung RCRC (Role - Context - Request - Constraint).


2. Giải mã bộ khung RCRC (4 trụ cột của một Prompt hoàn hảo)

+-----------------------------------------------------------------------------+
| R - ROLE        : Thiết lập tư duy chuyên gia, góc nhìn và phong cách hành văn|
+-----------------------------------------------------------------------------+
| C - CONTEXT     : Cung cấp bối cảnh nghiệp vụ, cấu trúc bảng dữ liệu (Schema) |
+-----------------------------------------------------------------------------+
| R - REQUEST     : Nhiệm vụ cụ thể từng bước, rõ ràng, không dùng từ mơ hồ   |
+-----------------------------------------------------------------------------+
| C - CONSTRAINT  : Các ranh giới cấm kỵ, định dạng đầu ra, quy tắc bảo mật   |
+-----------------------------------------------------------------------------+

2.1. R - Role (Vai trò chuyên gia)

  • Đừng chỉ viết "Bạn là một lập trình viên".
  • Hãy cụ thể hóa: "Bạn là một Principal Data Engineer có 10 năm kinh nghiệm tối ưu hóa cơ sở dữ liệu PostgreSQL và ClickHouse quy mô hàng tỷ dòng."
  • Tác dụng: Giúp LLM kích hoạt đúng vùng tri thức chuyên sâu và dùng đúng thuật ngữ kỹ thuật tiêu chuẩn.

2.2. C - Context (Bối cảnh bài toán)

  • Đưa vào thông tin nghiệp vụ thực tế: Tên công ty làm mảng gì, cấu trúc các bảng (Schema DDL), kiểu dữ liệu của từng cột, dung lượng dữ liệu dự kiến.
  • Đính kèm người đọc kết quả này là ai (Ban Giám đốc cần nhìn thấy con số tổng kết, hay Đội ngũ Dev cần xem code tối ưu).

2.3. R - Request (Yêu cầu hành động cụ thể)

  • Chia nhỏ yêu cầu thành các bước tuần tự (Step-by-step execution):
    1. Viết câu lệnh SQL đáp ứng bài toán.
    2. Giải thích cơ chế index cần đánh để truy vấn chạy dưới 100ms.
    3. Chỉ ra rủi ro tiềm ẩn (Edge cases) nếu dữ liệu có chứa giá trị NULL.

2.4. C - Constraint (Ràng buộc & Ranh giới đỏ)

  • Đây là phần quan trọng nhất để chống "ảo giác" (Hallucination) và lỗi cú pháp:
    • Về định dạng: "Chỉ trả về mã SQL hợp lệ bên trong khối mã, không kèm lời chào hỏi xã giao."
    • Về phiên bản: "Chỉ sử dụng cú pháp chuẩn PostgreSQL 16, tuyệt đối không dùng các hàm độc quyền của MySQL."
    • Về bảo mật: "Không được sử dụng subquery lồng quá 2 cấp; luôn dùng Prepared Statements để chống SQL Injection."

3. Bí kíp nâng cao: Sử dụng Delimiters (Thẻ XML) & Chain-of-Thought

Khi đưa nhiều dữ liệu vào một prompt, LLM rất dễ bị nhầm lẫn giữa lệnh điều khiển và dữ liệu đầu vào.
Các chuyên gia AI luôn dùng các thẻ đóng mở dạng XML (như <context>, <schema>, <rules>) để phân định ranh giới rõ ràng:

<role>
Bạn là chuyên viên Phân tích Dữ liệu Cao cấp.
</role>

<schema>
CREATE TABLE orders (order_id INT, amount NUMERIC, created_at DATE);
</schema>

<instructions>
Hãy suy nghĩ từng bước một (Think step-by-step) trước khi viết câu truy vấn.
</instructions>

4. Bảng so sánh: Prompt Thô vs. Prompt Chuẩn RCRC

Yếu tốPrompt Thô (Vô kỷ luật)Prompt Chuẩn RCRC (Chuẩn Doanh Nghiệp)
Độ rõ ràng"Viết SQL tính tỷ lệ giữ chân khách hàng hộ tôi."Nêu rõ công thức Retention D30, cung cấp DDL bảng user_activity, định dạng ngày tháng.
Định dạng kết quảTrả về một bài văn dài dòng, code lẫn lộn với giải thích.Bó gọn trong khối mã SQL sạch sẽ, có comment giải thích từng dòng lệnh.
Khả năng tái sử dụngKém, mỗi lần hỏi một kiểu kết quả khác nhau.Có thể đóng gói thành hàm Python template dùng tự động hóa cho cả công ty.
Tỷ lệ lỗi (Bugs)Rất cao (Sai tên cột, dùng sai hàm đặc thù của CSDL).Gần như bằng 0 vì đã được cung cấp Schema và ràng buộc phiên bản chặt chẽ.

5. Thực hành thực chiến: Xây dựng RCRC Prompt Factory bằng Python

Đoạn mã Python dưới đây minh họa cách tự động hóa việc sinh prompt theo chuẩn RCRC, kết nối trực tiếp với LLM API để tạo ra một chuyên gia viết SQL chuẩn chỉ:

import os
from openai import OpenAI

client = OpenAI(api_key=os.environ.get("OPENAI_API_KEY", "your-api-key-here"))

class RCRCPromptBuilder:
    """Lớp hỗ trợ tạo prompt chuyên nghiệp theo chuẩn RCRC kết hợp thẻ XML."""
    
    def __init__(self, role: str):
        self.role = role
        self.context = ""
        self.request = ""
        self.constraints = []
        
    def add_context(self, context_text: str):
        self.context = context_text
        return self
        
    def set_request(self, request_text: str):
        self.request = request_text
        return self
        
    def add_constraint(self, constraint_rule: str):
        self.constraints.append(constraint_rule)
        return self
        
    def build(self) -> str:
        formatted_constraints = "\n".join([f"- {c}" for c in self.constraints])
        prompt = f"""<role>
{self.role}
</role>

<context>
{self.context}
</context>

<request>
{self.request}
</request>

<constraints>
{formatted_constraints}
</constraints>

Hãy suy nghĩ từng bước (Think step-by-step) để đưa ra giải pháp tối ưu nhất."""
        return prompt

# ==============================================================================
# ÁP DỤNG THỰC TẾ: TỰ ĐỘNG SINH CÂU TRUY VẤN TỐI ƯU HÓA POSTGRESQL
# ==============================================================================
def generate_optimized_sql(user_question: str) -> str:
    db_schema = """
    TABLE sales (
        sale_id BIGSERIAL PRIMARY KEY,
        customer_id INT NOT NULL,
        sale_date DATE NOT NULL,
        amount NUMERIC(12, 2) NOT NULL,
        status VARCHAR(20) NOT NULL
    );
    -- Bảng hiện có 50 triệu dòng, đã có index trên (sale_date).
    """
    
    builder = RCRCPromptBuilder(
        role="Bạn là một Lead Database Administrator chuyên về PostgreSQL 16."
    )
    
    builder.add_context(f"Cấu trúc bảng hiện tại:\n{db_schema}\nQuy mô dữ liệu: 50 triệu dòng.")
    builder.set_request(f"Nhiệm vụ: Viết câu lệnh SQL đáp ứng yêu cầu kinh doanh sau:\n'{user_question}'")
    builder.add_constraint("Chỉ sử dụng cú pháp tương thích hoàn toàn với PostgreSQL 16.")
    builder.add_constraint("Ưu tiên tận dụng Index trên cột 'sale_date', tránh các hàm ép kiểu gây Full Table Scan.")
    builder.add_constraint("Chỉ trả về khối mã SQL duy nhất và giải thích ngắn gọn dưới 3 gạch đầu dòng.")
    
    full_prompt = builder.build()
    
    # Gọi LLM API với cấu hình tham số chuẩn kỹ thuật
    response = client.chat.completions.create(
        model="gpt-4o-mini",
        messages=[{"role": "user", "content": full_prompt}],
        temperature=0.1,  # Nhiệt độ thấp để code ra ổn định, chính xác
        max_tokens=800
    )
    
    return response.choices[0].message.content

if __name__ == "__main__":
    task = "Lấy tổng doanh thu của các đơn hàng thành công (status = 'PAID') trong tháng 08 năm 2026."
    print(">>> YÊU CẦU:", task)
    result = generate_optimized_sql(task)
    print("\n<<< KẾT QUẢ TỪ LLM (CHUẨN RCRC):\n")
    print(result)

6. Câu hỏi phỏng vấn thực tế (Interview Q&A)

Câu 1 (Mức độ: Entry / Junior)

Câu hỏi: "Khung RCRC (Role - Context - Request - Constraint) đem lại lợi ích gì lớn nhất cho doanh nghiệp khi triển khai ứng dụng LLM?"

Gợi ý trả lời:
*"Lợi ích lớn nhất của khung RCRC là Tính có thể tái tạo (Reproducibility) và Giảm thiểu tối đa lỗi sai (Error Reduction):

  1. Giúp chuẩn hóa cách thức giao tiếp giữa ứng dụng phần mềm và LLM, biến các yêu cầu nghiệp vụ tự do thành các chỉ dẫn có cấu trúc rõ ràng.
  2. Nhờ có phần Constraint và Context chặt chẽ, mô hình bị khóa chặt trong phạm vi tài liệu và quy tắc cho phép, loại bỏ tới 90% hiện tượng ảo giác (Hallucination) hoặc sinh ra kết quả sai lệch định dạng gây sập ứng dụng phía sau."*

Câu 2 (Mức độ: Junior / Mid-level)

Câu hỏi: "Sự khác biệt giữa tham số temperature và top_p khi gọi LLM API là gì? Trong bài toán tự động sinh mã SQL hoặc trích xuất JSON, bạn sẽ cấu hình hai thông số này như thế nào?"

Gợi ý trả lời:
*"Cả hai tham số đều dùng để điều khiển mức độ ngẫu nhiên khi mô hình chọn từ tiếp theo:

  • Temperature (Nhiệt độ): Điều chỉnh độ 'phẳng' của phân phối xác suất từ ngữ. Temperature càng cao (>0.8> 0.8), các từ có xác suất thấp càng có cơ hội được chọn →\rightarrow câu trả lời sáng tạo, bay bổng hơn. Temperature càng thấp (≈0.0−0.2\approx 0.0 - 0.2), mô hình sẽ chỉ chọn từ có xác suất cao nhất →\rightarrow câu trả lời ổn định, nhất quán và logic.
  • Top_P (Nucleus Sampling): Giới hạn mô hình chỉ được chọn từ vựng nằm trong nhóm tích lũy xác suất hàng đầu (ví dụ top_p = 0.1 nghĩa là chỉ chọn trong số 10% các từ có khả năng xuất hiện cao nhất).
    Cấu hình chuẩn cho bài toán SQL / JSON:
    Em luôn đặt temperature = 0.0 đến 0.1 và top_p = 0.1 (hoặc giữ nguyên 1 trong 2 tham số). Chúng ta hoàn toàn không cần sự 'sáng tạo thơ văn' trong code SQL; điều quan trọng nhất là tính chính xác tuyệt đối, đúng cú pháp và ổn định qua mọi lần chạy."*

7. Key Takeaways (Ghi nhớ nhanh)

  1. Prompt chuyên nghiệp không phải văn nói: Hãy luôn cấu trúc theo 4 trụ cột: R (Role) - C (Context) - R (Request) - C (Constraint).
  2. Dùng Delimiters (Thẻ XML): Sử dụng các thẻ <schema>, <rules>, <input> để ngăn LLM nhầm lẫn giữa dữ liệu đầu vào và chỉ dẫn hệ thống.
  3. Càng cụ thể, kết quả càng tốt: Cung cấp sẵn Schema DDL, phiên bản CSDL và đối tượng người đọc báo cáo.
  4. Nhiệt độ thấp cho bài toán kỹ thuật: Luôn đặt temperature = 0.0 - 0.2 khi cần LLM viết code, trích xuất dữ liệu hoặc sinh JSON chuẩn.
0Claps