งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น
กำหนดงบประมาณเวลาอย่างเข้มงวดในแต่ละชั้นของกระบวนการ และใช้การลดระดับบริการอย่างราบรื่น โดยส่งการตอบกลับจากแคชหรือการตอบกลับแบบง่ายเมื่อ LLM ใช้เวลาเกินงบประมาณ
งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น เป็นบทเรียน AI Engineering Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน AI Engineering Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส AI Engineering Academy มีบทเรียนทั้งหมด 4 บทเรียน
งบประมาณระยะหมดเวลาคืออะไร
งบประมาณระยะหมดเวลาคือเวลาสูงสุดทั้งหมดที่จัดสรรให้คำขอหนึ่งรายการดำเนินการเสร็จสิ้นในทุกขั้นตอนของกระบวนการทำงาน แทนที่จะกำหนดระยะเวลาแบบตายตัวให้กับการเรียกใช้ API แต่ละรายการ คุณจะกำหนดงบประมาณตั้งแต่ต้นจนจบสำหรับการดำเนินการที่ผู้ใช้มองเห็น แล้วแบ่งงบประมาณนั้นให้กับขั้นตอนการดึงข้อมูล การสร้างผลลัพธ์โดย LLM และการประมวลผลภายหลัง วิธีนี้ช่วยให้คุณตอบกลับได้ภายในเวลาที่ยอมรับได้เสมอ แม้บางขั้นตอนจะทำงานช้า
การแบ่งงบประมาณระหว่างขั้นตอนของกระบวนการทำงาน
กระบวนการทำงานแชตแบบ RAG โดยทั่วไปมีสามขั้นตอน ได้แก่ การดึงข้อมูล การสร้างผลลัพธ์โดย LLM และการจัดรูปแบบคำตอบ โปรดจัดสรรช่วงเวลาให้แต่ละขั้นตอนตามระยะเวลาที่ใช้โดยทั่วไปและระดับเวลารอที่ผู้ใช้ยอมรับได้ เวลาส่วนที่เหลือคือ บัฟเฟอร์สำหรับการลดระดับการทำงาน — หากขั้นตอนใดใช้เวลาที่จัดสรรไว้จนหมด คุณจะต้องเริ่มลดความซับซ้อนของขั้นตอนถัดไปเพื่อให้อยู่ภายในงบประมาณโดยรวม
# Total user-facing SLA: 8000ms
BUDGET_TOTAL_MS = 8000
BUDGET_STAGES = {
'retrieval': 1500, # vector search + rerank
'llm_call': 5500, # token streaming
'formatting': 500, # post-processing
'slack': 500, # buffer for overhead
}
assert sum(BUDGET_STAGES.values()) == BUDGET_TOTAL_MSการติดตามการใช้จ่ายงบประมาณ
ใช้ BudgetTracker เพื่อบันทึกเวลาเริ่มต้นและตรวจสอบงบประมาณที่เหลืออยู่เมื่อเปลี่ยนผ่านแต่ละขั้นตอน ก่อนเริ่มขั้นตอนใด ให้ตรวจสอบว่างบประมาณที่เหลือเพียงพอ การทำเช่นนี้ช่วยให้ขั้นตอนถัดไปปรับตัวได้ เช่น หากขั้นตอนการดึงข้อมูลใช้เวลา 1200ms จากงบประมาณ 1500ms จะเหลือเวลาเผื่อเพียง 300ms ซึ่งควรกระตุ้นให้ใช้พรอมต์ LLM ที่ง่ายขึ้นหรือข้ามขั้นตอนการจัดอันดับใหม่
import time
class BudgetTracker:
def __init__(self, total_ms: float):
self.start = time.perf_counter()
self.total_ms = total_ms
def elapsed_ms(self) -> float:
return (time.perf_counter() - self.start) * 1000
def remaining_ms(self) -> float:
return self.total_ms - self.elapsed_ms()
def check(self, stage: str, required_ms: float = 0) -> bool:
remaining = self.remaining_ms()
if remaining < required_ms:
print(f'Budget exhausted before {stage}: {remaining:.0f}ms left, need {required_ms}ms')
return False
return Trueคำจำกัดความของการลดระดับการทำงานอย่างเหมาะสม
การลดระดับการทำงานอย่างเหมาะสมหมายถึงการให้คำตอบที่มีคุณภาพต่ำลงแต่ยังคงมีประโยชน์ เมื่อกระบวนการทำงานทั้งหมดไม่สามารถเสร็จภายในงบประมาณ แทนที่จะส่งคืนข้อผิดพลาด ตัวอย่างเช่น การส่งคืนคำตอบจากแคช การข้ามการจัดอันดับใหม่ การตัดทอนหน้าต่างบริบท การใช้โมเดลที่เร็วกว่าแต่แม่นยำน้อยกว่า หรือการส่งคืนข้อความสำรองที่เขียนเตรียมไว้ เป้าหมายคือการมอบบางสิ่งให้ผู้ใช้เสมอ แทนที่จะไม่มอบอะไรเลย
# Degradation ladder for a RAG chat endpoint:
# Level 0 (normal): retrieve 10 chunks + rerank + GPT-4o -- 8000ms budget
# Level 1 (fast): retrieve 5 chunks + skip rerank + GPT-4o -- 5000ms budget
# Level 2 (minimal): retrieve 3 chunks + GPT-4o-mini -- 3000ms budget
# Level 3 (cached): return semantic cache hit -- 100ms
# Level 4 (sorry): return static 'Try again in a moment' -- 1msการนำลำดับขั้นการลดระดับการทำงานมาใช้
ในแต่ละจุดตัดสินใจของกระบวนการทำงาน ให้ตรวจสอบงบประมาณที่เหลือและเลือกระดับคุณภาพที่เหมาะสม โค้ดด้านล่างจะเลือกความลึกของการดึงข้อมูลและโมเดลตามงบประมาณที่เหลือ ซึ่งหมายความว่าในภาวะการใช้งานปกติ ผู้ใช้จะได้รับคุณภาพดีที่สุด ส่วนในช่วงที่มีความหน่วงสูง ผู้ใช้ก็ยังได้รับคำตอบที่มีประโยชน์แทนที่จะพบข้อผิดพลาดจากระยะหมดเวลา
async def smart_rag_query(question: str, budget_ms: float = 8000) -> str:
tracker = BudgetTracker(budget_ms)
# Retrieval stage
if tracker.remaining_ms() > 5000:
chunks = await retrieve_and_rerank(question, top_k=10)
elif tracker.remaining_ms() > 3000:
chunks = await retrieve(question, top_k=5) # skip rerank
elif tracker.remaining_ms() > 1500:
chunks = await retrieve(question, top_k=3) # minimal retrieval
else:
return await get_cached_or_static(question)
# LLM stage
if tracker.remaining_ms() > 4000:
model = 'gpt-4o'
else:
model = 'gpt-4o-mini' # faster fallback
timeout = tracker.remaining_ms() / 1000 - 0.5
return await generate_answer(question, chunks, model, timeout)การกำหนดระยะหมดเวลาในระดับการเรียกใช้ API
โปรดกำหนดระยะหมดเวลาอย่างชัดเจนสำหรับการเรียกใช้ API ภายนอกทุกครั้ง SDK ภาษา Python ของ OpenAI รองรับพารามิเตอร์ timeout ซึ่งมีหน่วยเป็นวินาที ให้กำหนดค่านี้ต่ำกว่างบประมาณที่เหลือเล็กน้อย เพื่อให้มีเวลาจัดการข้อยกเว้นและอาจลดระดับการทำงานอย่างเหมาะสมก่อนถึงกำหนดเวลาสิ้นสุดของการตอบกลับโดยรวม อย่าพึ่งพาระยะหมดเวลาเริ่มต้นของ SDK เด็ดขาด เพราะอาจนานเกินไปสำหรับคำขอที่ผู้ใช้ต้องรอผล
async def generate_answer(question: str, chunks: list, model: str, timeout_sec: float) -> str:
context = '\n\n'.join(chunks)
prompt = f'Answer using this context:\n{context}\n\nQuestion: {question}'
try:
resp = await client.chat.completions.create(
model=model,
messages=[{'role': 'user', 'content': prompt}],
max_tokens=500,
timeout=max(timeout_sec, 1.0) # minimum 1 second
)
return resp.choices[0].message.content
except openai.APITimeoutError:
return 'I was unable to generate a response in time. Please try again.'การส่งคืนคำตอบแบบสตรีมบางส่วน
เมื่อใช้การสตรีม คุณสามารถส่งคืนคำตอบบางส่วนที่สร้างเสร็จก่อนงบประมาณหมดลงได้ เมื่อเกิดระยะหมดเวลาระหว่างการสตรีม ให้หยุดอ่านโทเค็นใหม่ ต่อท้ายจุดไข่ปลาหรือพรอมต์ต่อเนื่องสั้น ๆ แล้วปิดสตรีม ผู้ใช้จะเห็นคำตอบที่จบลงอย่างเรียบร้อย แทนที่จะเห็นข้อผิดพลาดเปล่า ๆ วิธีนี้ทำได้เฉพาะกับการสตรีมเท่านั้น — การเรียกใช้แบบไม่สตรีมจะสำเร็จทั้งหมดหรือล้มเหลวทั้งหมด
async def stream_with_budget(question: str, budget_ms: float):
tracker = BudgetTracker(budget_ms)
collected = []
stream = await client.chat.completions.create(
model='gpt-4o-mini',
messages=[{'role': 'user', 'content': question}],
stream=True
)
async for chunk in stream:
if tracker.remaining_ms() < 200: # 200ms safety margin
collected.append(' [response truncated]')
break
delta = chunk.choices[0].delta.content or ''
collected.append(delta)
yield delta
# Ensure stream is closed even if budget exceeded
await stream.close()แคชเชิงความหมายในฐานะชั้นการลดระดับการทำงาน
แคชเชิงความหมายเป็นชั้นการลดระดับการทำงานที่ยอดเยี่ยม เนื่องจากมีความหน่วงเกือบเป็นศูนย์ ก่อนเรียกใช้ LLM ให้ค้นหาคำถามก่อนหน้าที่คล้ายกันในแคชเชิงความหมาย หากพบข้อมูลในแคชที่มีความคล้ายคลึงสูง (มีค่าความคล้ายคลึงโคไซน์มากกว่า 0.92) ให้ส่งคืนคำตอบจากแคชทันที วิธีนี้ช่วยทั้งเร่งการตอบกลับและมอบทางเลือกสำรองได้ทันทีเมื่อ LLM ทำงานช้าหรือไม่พร้อมใช้งาน
async def query_with_cache_fallback(question: str, budget_ms: float = 8000) -> str:
# Try semantic cache first (fast)
cached = await semantic_cache.lookup(question, threshold=0.92)
if cached:
return cached.response
tracker = BudgetTracker(budget_ms)
# Try full pipeline
if tracker.remaining_ms() > 3000:
try:
return await smart_rag_query(question, tracker.remaining_ms())
except Exception:
pass # fall through to static response
# Last resort
return 'I am experiencing high load right now. Please try again in a moment.'การบันทึกเหตุการณ์การลดระดับการทำงาน
ทุกครั้งที่กระบวนการทำงานของคุณลดลงไปสู่ระดับคุณภาพที่ต่ำกว่า ให้บันทึกเหตุการณ์นั้นในรูปแบบที่มีโครงสร้าง โดยระบุระดับการลดการทำงานที่เกิดขึ้น งบประมาณที่เหลืออยู่ในแต่ละขั้นตอน และความหน่วงสุดท้าย การวิเคราะห์บันทึกเหล่านี้จะบอกว่าการลดระดับแต่ละระดับถูกเรียกใช้บ่อยเพียงใด ซึ่งช่วยให้คุณปรับงบประมาณ ระบุขั้นตอนที่ใช้งบประมาณเกินอย่างต่อเนื่อง และให้เหตุผลสนับสนุนการลงทุนด้านโครงสร้างพื้นฐาน
import structlog
log = structlog.get_logger()
def log_degradation(level: int, stage: str, remaining_ms: float, total_ms: float):
log.warning(
'pipeline_degradation',
degradation_level=level,
triggered_at_stage=stage,
remaining_budget_ms=round(remaining_ms),
total_budget_ms=total_ms,
budget_consumed_pct=round((total_ms - remaining_ms) / total_ms * 100)
)การกำหนดความคาดหวังของผู้ใช้ด้วยสัญญาณจากส่วนติดต่อผู้ใช้
เมื่อส่งคำตอบที่ลดระดับการทำงาน ให้สื่อสารกับผู้ใช้ว่าคุณภาพอาจต่ำกว่าปกติ สำหรับส่วนติดต่อแชต ให้แสดงตัวบ่งชี้ที่ไม่รบกวน เช่น 'โหมดตอบกลับเร็ว — รายละเอียดบางส่วนอาจมีจำกัด' สำหรับ API การดึงข้อมูล ให้ใส่ฟิลด์ degraded: true ในคำตอบ JSON เพื่อให้ผู้ใช้ปลายทางจัดการผลลัพธ์ที่ลดระดับแล้วได้แตกต่างกัน ความโปร่งใสช่วยรักษาความไว้วางใจของผู้ใช้ได้แม้ในช่วงระบบขัดข้อง
from pydantic import BaseModel
from typing import Optional
class ChatResponse(BaseModel):
content: str
degraded: bool = False
degradation_level: Optional[int] = None # 0=full, 1=fast, 2=minimal, 3=cached
latency_ms: int
# API response when degraded:
# {
# 'content': 'Here is a brief answer...',
# 'degraded': true,
# 'degradation_level': 2,
# 'latency_ms': 2800
# }การปรับการจัดสรรงบประมาณตามเวลา
การจัดสรรงบประมาณเริ่มต้นเป็นเพียงการประมาณการ หลังจากทำงานในระบบจริงเป็นเวลาหนึ่งสัปดาห์ ให้ใช้ข้อมูลการติดตามเพื่อตรวจสอบการกระจายเวลาที่ใช้ในแต่ละขั้นตอน หากการดึงข้อมูลใช้เวลา 800ms อย่างสม่ำเสมอ แทนที่จะเป็น 1500ms ตามงบประมาณที่กำหนดไว้ ให้จัดสรรเวลาส่วนเกินนั้นไปยังขั้นตอน LLM เพื่อให้สร้างโทเค็นผลลัพธ์ได้มากขึ้นหรือใช้หน้าต่างบริบทที่ใหญ่ขึ้น การปรับงบประมาณเป็นกิจกรรมการดำเนินงานที่ต้องทำอย่างต่อเนื่อง ไม่ใช่การกำหนดค่าเพียงครั้งเดียว
# Budget tuning based on production p95 data:
ACTUAL_P95 = {
'retrieval': 780, # vs budget 1500ms -> 720ms headroom
'llm_call': 4200, # vs budget 5500ms -> 1300ms headroom
'formatting': 120, # vs budget 500ms -> 380ms headroom
}
TOTAL_HEADROOM = sum(
BUDGET_STAGES[k] - ACTUAL_P95[k] for k in ACTUAL_P95
)
print(f'Total headroom: {TOTAL_HEADROOM}ms')
# Reallocate headroom to allow longer LLM responsesตรวจสอบความเข้าใจอย่างรวดเร็ว
ทดสอบความเข้าใจของคุณเกี่ยวกับงบประมาณระยะหมดเวลาและการลดระดับการทำงานอย่างเหมาะสม
สรุปบทเรียน
ในบทเรียนนี้ คุณได้เรียนรู้ว่า งบประมาณระยะหมดเวลาจัดสรรเวลาให้กับขั้นตอนต่าง ๆ ของกระบวนการทำงาน เพื่อให้คุณตอบกลับได้ภายในกำหนดเวลาที่ยอมรับได้เสมอ ลำดับขั้นการลดระดับการทำงานจะส่งมอบคำตอบที่มีคุณภาพลดลงตามลำดับ แทนการส่งคืนข้อผิดพลาดเมื่อเวลาเหลือน้อยหรือหมดลง และ การบันทึกเหตุการณ์การลดระดับการทำงานช่วยให้คุณระบุและแก้ไขคอขวดที่เกิดขึ้นเป็นประจำ ต่อไป เราจะสำรวจรูปแบบการใช้ LLM เป็นผู้ประเมินเพื่อประเมินคุณภาพโดยอัตโนมัติ
คำถามที่พบบ่อย
บทเรียน “งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น” ฟรีหรือไม่
ใช่ — ข้อความเต็มของ “งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส AI Engineering Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส AI Engineering Academy มีบทเรียนทั้งหมด 4 บทเรียน
คุณจะเรียนรู้อะไรในบทเรียน “งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น”
กำหนดงบประมาณเวลาอย่างเข้มงวดในแต่ละชั้นของกระบวนการ และใช้การลดระดับบริการอย่างราบรื่น โดยส่งการตอบกลับจากแคชหรือการตอบกลับแบบง่ายเมื่อ LLM ใช้เวลาเกินงบประมาณ คุณปฏิบัติ AI Engineering Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน
คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน AI Engineering Academy หรือไม่
ไม่จำเป็นต้องมีประสบการณ์มาก่อน AI Engineering Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน
บทเรียน “งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น” ใช้เวลานานแค่ไหน
บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย
ฉันเขียนและรันโค้ดในบทเรียน AI Engineering Academy นี้ได้ไหม
ได้ บทเรียน AI Engineering Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ
บทเรียนทั้งหมดในหลักสูตรนี้
- การวัดเวลาแฝงของ LLM: TTFT และ TPOT
- การกระจายโหลดและกลยุทธ์หลายคีย์
- ผู้ให้บริการสำรองและตัวตัดวงจร
- งบประมาณเวลาและการลดระดับบริการอย่างราบรื่น