Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas
Simpan keadaan agen pada setiap langkah yang selesai agar tugas yang berjalan lama dapat dilanjutkan dari titik pemeriksaan terakhir yang berhasil, bukan dimulai ulang dari awal setelah terjadi kegagalan.
Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas adalah pelajaran AI Engineering Academy gratis di CoddyKit. Ini adalah pelajaran 3 dari 4. Kamu bisa membaca pelajaran lengkapnya di bawah secara gratis — lalu praktikkan langsung di browser dengan editor kode bawaan dan tutor AI 24/7. Ini adalah bagian dari jalur belajar AI Engineering Academy, dan progresmu tersinkronisasi di web dan aplikasi CoddyKit. Kursus AI Engineering Academy mencakup 4 pelajaran total.
Masalah pada Agen yang Berjalan Lama
Agen yang menjalankan tugas riset 50 langkah mungkin berjalan selama 30 menit. Jika agen gagal pada langkah 47 karena batas waktu API atau server dimulai ulang, memulai ulang dari awal akan membuang semua pekerjaan yang telah dilakukan dan menghabiskan token. Checkpointing menyimpan keadaan agen pada setiap langkah yang selesai sehingga tugas dapat dilanjutkan dari titik terakhir yang berhasil, bukan dari awal. Hal ini penting untuk setiap tugas agen yang berlangsung lebih dari beberapa menit.
Status Agen yang Perlu Dipertahankan
Keadaan agen terdiri atas: definisi tugas, langkah yang telah selesai beserta pemanggilan alat dan pengamatannya, indeks langkah saat ini, setiap hasil yang telah terkumpul (file yang ditulis, data yang dikumpulkan), serta metadata seperti waktu mulai dan total penggunaan token. Simpan semua informasi ini setelah setiap langkah selesai. Keadaan harus dapat diserialisasi — utamakan JSON daripada objek Python agar mudah dipindahkan.
from dataclasses import dataclass, field
from typing import List, Any, Optional
@dataclass
class AgentStep:
step_index: int
thought: str
tool_name: str
tool_args: dict
observation: str
tokens_used: int
completed_at: str
@dataclass
class AgentCheckpoint:
task_id: str
task_description: str
status: str # 'running', 'completed', 'failed'
current_step: int
completed_steps: List[AgentStep] = field(default_factory=list)
accumulated_results: dict = field(default_factory=dict)
total_tokens: int = 0
final_answer: Optional[str] = NoneMenyimpan Checkpoint Setelah Setiap Langkah
Setelah setiap langkah berhasil, serialisasikan checkpoint dan tuliskan ke penyimpanan persisten. Gunakan basis data atau penyimpanan objek (S3, Redis), bukan disk lokal, agar checkpoint tetap tersedia setelah server dimulai ulang. Sertakan task_id dalam kunci agar Anda dapat mengambil checkpoint tugas tertentu. Tulis juga entri log langkah untuk setiap langkah guna menjaga jejak audit meskipun file checkpoint rusak.
import json
import redis
from dataclasses import asdict
redis_client = redis.Redis()
def save_checkpoint(checkpoint: AgentCheckpoint):
key = f'agent:checkpoint:{checkpoint.task_id}'
data = json.dumps(asdict(checkpoint), default=str)
redis_client.set(key, data, ex=86400) # 24h TTL
# Also append to step log
log_key = f'agent:log:{checkpoint.task_id}'
if checkpoint.completed_steps:
last = checkpoint.completed_steps[-1]
redis_client.rpush(log_key, json.dumps(asdict(last), default=str))
def load_checkpoint(task_id: str) -> AgentCheckpoint | None:
key = f'agent:checkpoint:{task_id}'
data = redis_client.get(key)
if data:
return AgentCheckpoint(**json.loads(data))
return NoneMelanjutkan dari Checkpoint
Saat melanjutkan tugas, muat checkpoint dan bangun kembali riwayat pesan agen dari langkah-langkah yang telah selesai. Mulai loop eksekusi dari indeks langkah berikutnya yang belum selesai. Model menerima pemikiran dan pengamatan sebelumnya dalam riwayat pesan, sehingga memiliki konteks lengkap tentang pekerjaan yang telah dilakukan dan dapat melanjutkan tanpa mengulang pekerjaan.
async def resume_or_start(task_id: str, task_description: str) -> str:
checkpoint = load_checkpoint(task_id)
if checkpoint and checkpoint.status == 'running':
print(f'Resuming task {task_id} from step {checkpoint.current_step}')
messages = rebuild_history(checkpoint)
start_step = checkpoint.current_step
else:
print(f'Starting new task {task_id}')
checkpoint = AgentCheckpoint(task_id=task_id, task_description=task_description, status='running', current_step=0)
messages = [{'role': 'user', 'content': task_description}]
start_step = 0
save_checkpoint(checkpoint)
return await run_agent_from(checkpoint, messages, start_step)Membangun Kembali Riwayat Pesan dari Langkah-Langkah
Kunci untuk melanjutkan tugas adalah membangun kembali riwayat pesan dari langkah-langkah yang disimpan secara akurat. Setiap langkah yang selesai berhubungan dengan satu pesan asisten (pemikiran + pemanggilan alat) dan satu pesan alat (pengamatan). Putar ulang semua langkah yang telah selesai sebagai pesan sebelum melanjutkan, agar model memiliki konteks yang sama seolah-olah tidak pernah terhenti.
def rebuild_history(checkpoint: AgentCheckpoint) -> list:
messages = [{'role': 'user', 'content': checkpoint.task_description}]
for step in checkpoint.completed_steps:
# Reconstruct the agent's reasoning message
messages.append({
'role': 'assistant',
'content': f'Thought: {step.thought}\nAction: {step.tool_name}({step.tool_args})'
})
# Reconstruct the tool observation
messages.append({
'role': 'user',
'content': f'Observation: {step.observation}'
})
return messagesPemanggilan Alat Idempoten
Jika sebuah langkah baru selesai sebagian sebelum terjadi kerusakan (alat telah dipanggil tetapi pengamatannya belum disimpan), proses pelanjutan mungkin memanggil alat tersebut lagi. Rancang alat agar idempoten: memanggilnya dua kali dengan argumen yang sama menghasilkan hasil yang sama seperti memanggilnya sekali. Untuk operasi penulisan (membuat file, mengirim email), gunakan kunci deduplikasi untuk mencegah efek ganda meskipun alat dipanggil berkali-kali.
async def idempotent_write_file(content: str, path: str, task_id: str, step: int) -> str:
dedup_key = f'{task_id}:step_{step}:write:{path}'
if redis_client.exists(dedup_key):
return f'File {path} already written (dedup key present)'
with open(path, 'w') as f:
f.write(content)
redis_client.set(dedup_key, '1', ex=3600)
return f'Successfully wrote {len(content)} chars to {path}'Pembersihan dan Retensi Checkpoint
Checkpoint menggunakan penyimpanan dan tidak boleh menumpuk tanpa batas. Tetapkan kebijakan retensi: hapus checkpoint yang selesai setelah 24 jam, hapus checkpoint yang gagal setelah 7 hari (untuk analisis pascakejadian), dan jangan pernah menghapus checkpoint yang sedang berjalan secara otomatis. Terapkan tugas pembersihan latar belakang yang berjalan setiap jam dan menghapus checkpoint yang kedaluwarsa sesuai kebijakan.
from datetime import datetime, timedelta
RETENTION = {
'completed': timedelta(hours=24),
'failed': timedelta(days=7),
'running': None # never auto-delete
}
def cleanup_expired_checkpoints():
now = datetime.utcnow()
for key in redis_client.scan_iter('agent:checkpoint:*'):
data = json.loads(redis_client.get(key))
status = data.get('status', 'running')
retention = RETENTION.get(status)
if retention is None:
continue
started = datetime.fromisoformat(data.get('started_at', str(now)))
if now - started > retention:
redis_client.delete(key)Checkpointing dalam LangGraph
LangGraph memiliki dukungan checkpointing bawaan melalui kelas MemorySaver dan SqliteSaver. Pasang checkpointer pada graf Anda dan setiap eksekusi simpul akan disimpan secara otomatis. Untuk melanjutkan, panggil graph.invoke dengan thread_id yang sama. LangGraph menangani pembangunan kembali riwayat dan pelacakan langkah, sehingga Anda tidak perlu menerapkan logika checkpointing secara manual.
from langgraph.checkpoint.sqlite import SqliteSaver
from langgraph.graph import StateGraph
# Create graph with persistent checkpointer
checkpointer = SqliteSaver.from_conn_string('/tmp/agent_state.db')
graph = StateGraph(AgentState)
graph.add_node('reason', reason_node)
graph.add_node('act', act_node)
# ... add edges ...
app = graph.compile(checkpointer=checkpointer)
# Run with thread_id - LangGraph auto-checkpoints
config = {'configurable': {'thread_id': 'task_abc123'}}
result = await app.ainvoke({'task': 'Research climate change'}, config)
# Resume same thread - LangGraph loads from checkpoint
result = await app.ainvoke({'task': 'Continue'}, config)Checkpointing Terdistribusi untuk Agen Paralel
Saat beberapa agen bekerja secara paralel pada subtugas, setiap agen memerlukan namespace checkpoint-nya sendiri. Gunakan struktur kunci hierarkis: parent_task_id:sub_task_id. Checkpoint agen induk mencatat subtugas mana yang telah selesai beserta hasilnya. Saat agen induk melanjutkan, agen tersebut menggunakan kembali hasil subtugas yang telah selesai dari checkpoint, bukan menjalankannya lagi.
async def parallel_with_checkpoints(parent_id: str, subtasks: list) -> list:
results = []
for i, subtask in enumerate(subtasks):
sub_id = f'{parent_id}:sub_{i}'
# Check if subtask already completed
existing = load_checkpoint(sub_id)
if existing and existing.status == 'completed':
print(f'Sub-task {i} already done, using cached result')
results.append(existing.final_answer)
else:
result = await run_agent(sub_id, subtask)
results.append(result)
return resultsMenguji Perilaku Pelanjutan
Tulis pengujian integrasi yang sengaja membuat agen gagal di tengah tugas, lalu verifikasi bahwa pelanjutan menghasilkan hasil akhir yang benar. Simulasikan kerusakan dengan memunculkan pengecualian pada indeks langkah tertentu. Setelah pelanjutan, periksa bahwa hanya langkah setelah kerusakan yang dijalankan ulang, bukan langkah sebelumnya. Uji juga bahwa pemanggilan alat idempoten tidak menghasilkan efek ganda saat sebuah langkah diputar ulang.
import pytest
@pytest.mark.asyncio
async def test_resumption_from_step_3():
task_id = 'test_resume_001'
# Run until step 3, then crash
with pytest.raises(SimulatedCrash):
await run_agent_crashing_at(task_id, 'Research AI trends', crash_at_step=3)
checkpoint = load_checkpoint(task_id)
assert checkpoint.current_step == 3
assert len(checkpoint.completed_steps) == 3
# Resume and complete
result = await resume_or_start(task_id, 'Research AI trends')
assert result is not None
# Verify only steps 4+ were re-executed
assert checkpoint_step_was_not_replayed(task_id, step=0)Pemberian Versi Checkpoint untuk Perubahan Skema
Saat Anda mengubah skema AgentCheckpoint (menambahkan atau mengganti nama kolom), checkpoint lama dalam penyimpanan menjadi tidak kompatibel. Tangani hal ini dengan pemberian versi checkpoint: tambahkan kolom checkpoint_version dan tulis fungsi migrasi untuk meningkatkan checkpoint lama ke skema baru saat checkpoint tersebut dimuat. Dengan demikian, kerusakan dapat dicegah ketika agen melanjutkan tugas setelah penerapan yang mengubah format checkpoint.
def load_and_migrate_checkpoint(task_id: str) -> AgentCheckpoint:
raw = json.loads(redis_client.get(f'agent:checkpoint:{task_id}'))
version = raw.get('checkpoint_version', '1.0')
if version == '1.0':
# Migrate: add new fields added in v2.0
raw['checkpoint_version'] = '2.0'
raw['accumulated_results'] = raw.get('accumulated_results', {})
raw['total_tokens'] = raw.get('total_tokens', 0)
return AgentCheckpoint(**raw)Pemeriksaan Singkat
Uji pemahaman Anda tentang checkpointing dan pelanjutan tugas pada agen.
Ringkasan Pelajaran
Dalam pelajaran ini Anda telah mempelajari bahwa: checkpointing menserialisasi keadaan agen setelah setiap langkah agar tugas yang berjalan lama dapat bertahan dari kegagalan tanpa dimulai ulang dari awal, pembangunan kembali riwayat pesan dari langkah-langkah yang disimpan memberi model konteks lengkap saat pelanjutan, dan alat idempoten dengan kunci deduplikasi mencegah efek ganda saat langkah diputar ulang. Selanjutnya, kita akan merancang pemicu eskalasi human-in-the-loop.
Pertanyaan yang Sering Diajukan
Apakah pelajaran “Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas” gratis?
Ya — teks lengkap “Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas” gratis dibaca di sini di web. Untuk praktiknya secara interaktif (editor kode bawaan dan tutor AI 24/7) dan buka sisa kursus AI Engineering Academy, upgrade ke CoddyKit PRO. Kursus AI Engineering Academy mencakup 4 pelajaran total.
Apa yang akan aku pelajari di “Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas”?
Simpan keadaan agen pada setiap langkah yang selesai agar tugas yang berjalan lama dapat dilanjutkan dari titik pemeriksaan terakhir yang berhasil, bukan dimulai ulang dari awal setelah terjadi kegag… Kamu berlatih AI Engineering Academy dengan kode praktik yang langsung kamu jalankan di browser, dan tutor AI 24/7 menjawab pertanyaanmu saat kamu mengerjakan pelajaran ini.
Apakah aku perlu pengalaman untuk memulai AI Engineering Academy?
Tidak diperlukan pengalaman sebelumnya. AI Engineering Academy di CoddyKit dirancang untuk pemula hingga pelajar tingkat lanjut, jadi kamu bisa memulai di sini atau dari awal dan belajar sesuai kecepatan kamu sendiri. Ini adalah pelajaran 3 dari 4.
Berapa lama pelajaran “Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas” memakan waktu?
Sebagian besar pelajaran CoddyKit memakan waktu sekitar 5–10 menit. Setiap pelajaran ringkas dan interaktif, jadi kamu membuat kemajuan stabil dan melanjutkan dari tempat kamu tinggalkan di web dan aplikasi.
Bisakah aku menulis dan menjalankan kode dalam pelajaran AI Engineering Academy ini?
Ya. Setiap pelajaran AI Engineering Academy menyertakan editor kode bawaan, jadi kamu menulis dan menjalankan kode nyata langsung di browser dan mendapatkan umpan balik AI instan — tidak diperlukan penyiapan lokal.
Semua pelajaran dalam kursus ini
- Mengklasifikasikan Mode Kegagalan Agen
- Koreksi Mandiri dan Pemberian Prompt Reflektif
- Pembuatan Titik Pemeriksaan dan Melanjutkan Tugas
- Eskalasi dengan Keterlibatan Manusia