[Catatan Pengembangan] Membuat Agen Saling Berdebat — Desain Roundtable dan Keterbatasannya

119.216.***.***
8

Ini adalah bagian 4 dari seri artikel teknis tunaFlow. Di bagian 3, kami membahas struktur Branch, dan Roundtable (RT) adalah mode perluasan dari Branch. Ketika branches.mode = "roundtable", beberapa agen berdiskusi tentang satu topik.


Mengapa membuat agen berdiskusi satu sama lain

Ketika menyuruh agen melakukan review kode, sebagian besar akan berkata "bagus". Jika Anda mempercayakan desain kepada satu agen, secara struktural sulit baginya untuk mengkritik arah yang dia usulkan sendiri.

Alasan code review bekerja dalam tim manusia adalah karena reviewer adalah orang yang berbeda dari penulis. Perspektif berbeda, hal yang terlewatkan juga berbeda. Kami dapat menerapkan struktur yang sama pada agen — ketika beberapa agen dengan mesin yang berbeda, peran yang berbeda, dan prompt yang berbeda melihat topik yang sama, agen lain akan menangkap apa yang dilewatkan satu agen.

RT adalah implementasi dari ide ini.


RT = Mode Perluasan Branch

RT bukan sistem terpisah, melainkan mode dari Branch.

// tabel branches
pub struct Branch {
    pub mode: String,  // "chat" atau "roundtable"
    // ... sisanya sama dengan Branch biasa
}

Ketika membuat RT, Branch dengan mode = "roundtable" dibuat, dan pesan peserta menumpuk dalam shadow conversation. Di sidebar, ditampilkan di bagian Roundtables, dibuka di drawer, dan adopt berfungsi sama. Kami menggunakan infrastruktur Branch dari bagian 3 apa adanya.

Perbedaannya adalah pesan tidak dikirim oleh pengguna tetapi dikirim oleh peserta secara berurutan (atau bersamaan).


Dua mode diskusi

Sequential — Diskusi Berurutan

Peserta berbicara satu per satu secara berurutan. Peserta berikutnya dapat melihat apa yang dikatakan peserta sebelumnya.

Ronde 1:
  Architect (claude)  → Proposal desain: "Mari pisahkan menjadi 3 modul"
  Reviewer (codex)    → Melihat respons Architect: "Batas modul samar-samar"
  Verifier (gemini)   → Melihat keduanya: "Setuju dengan opini Reviewer, modul 2 masalah"
// sequential.rs — loop inti
for p in participants {
    let prompt = if p.blind {
        // peserta blind: tidak melihat respons peserta lain
        build_round_prompt_with_identity(topic, &[], &[], Some(&identity))
    } else {
        // termasuk respons peserta sebelumnya
        build_round_prompt_with_identity(topic, transcript, &round_responses, Some(&identity))
    };
    let result = stream_participant(p, prompt, ...).await;
    round_responses.push((p.name.clone(), result.content.clone()));
}

Keuntungan mode berurutan adalah percakapan terakumulasi secara alami. Peserta berikutnya dapat membantah atau melengkapi poin yang dibuat sebelumnya.

Deliberative — Diskusi Paralel

Peserta berbicara secara bersamaan. Mereka tidak dapat melihat respons satu sama lain.

Ronde 1:
  Architect (claude)  → (independen) "Pisahkan 3 modul"
  Reviewer (codex)    → (independen) "Perlu abstraksi antarmuka"
  Verifier (gemini)   → (independen) "Cakupan tes tidak cukup"
// deliberative.rs — eksekusi paralel dengan tokio::spawn
for p in participants {
    let prompt = build_round_prompt_with_identity(topic, transcript, &[], Some(&identity));
    //                                                                 ^^^ tidak ada respons ronde saat ini
    tokio::spawn(async move {
        let result = stream_participant(p, prompt, ...).await;
        tx.send((msg_id, result)).await;
    });
}
// kumpulkan hasil sesuai urutan penyelesaian
while let Some((id, result)) = rx.recv().await { ... }

Keuntungan mode paralel adalah perspektif independen. Karena tidak dipengaruhi oleh peserta sebelumnya, perspektif yang benar-benar berbeda muncul. Kerugiannya adalah poin dapat tersebar.

Mode mana yang digunakan kapan

Situasi

Mode yang Direkomendasikan

Alasan

Review kode

Sequential

Reviewer harus melihat dan mengevaluasi hasil Developer

Brainstorming desain

Deliberative

Ide independen diperlukan

Audit keamanan

Deliberative + blind

Evaluasi independen tanpa prasangka

Mencapai konsensus

Sequential 2 ronde

Ronde 1: opini independen, Ronde 2: reaksi saling


Model Eksekusi Peserta

Setiap peserta dijalankan sebagai subproses independen. Bukan berbagi sesi PTY, melainkan panggilan mode -p terpisah untuk setiap peserta.

Eksekusi RT:
  Participant A (claude) → claude -p "..." → subprocess 1
  Participant B (codex)  → codex exec "..." → subprocess 2
  Participant C (gemini) → gemini -p "..." → subprocess 3

Alasan desain ini: peserta RT dapat berupa mesin yang berbeda. Nilai inti RT adalah mencampur Claude, Codex, Gemini untuk diskusi. Sesi PTY adalah satu per mesin, jadi berbagi secara struktural tidak mungkin.

Handler eksekusi per mesin:

Mesin

Cara Eksekusi

Streaming

Claude

claude::stream_run()

chunk real-time

Codex

codex::stream_run()

chunk real-time

Gemini

gemini::stream_run()

chunk real-time

Ollama

openai_compat::stream_run()

async native

OpenCode

opencode::run()

non-streaming

Selama eksekusi, event roundtable:chunk di-stream ke depan, dan respons setiap peserta ditampilkan real-time di drawer.


Manajemen Konteks: Strategi Konteks Minimal

Mengirim seluruh ContextPack (~5-7k token) kepada peserta RT adalah pemborosan token. Jika 3 peserta, 3 kali lipat, jika 2 ronde, 6 kali lipat. Jadi RT menggunakan strategi konteks minimal.

RtContextCache — Hanya Tier 0+1

// context.rs
pub struct RtContextCache {
    pub context: Option,  // ~100-200 token
}

Dari 12 bagian ContextPack, kami hanya menyertakan path proyek + ringkasan Plan aktif. Skills, retrieval, compressed memory, cross-session semuanya dikecualikan. Cukup memberi tahu peserta RT "proyek apa yang sedang dikerjakan dan tugas apa sekarang".

Kompres ronde sebelumnya dengan pencarian vektor

Di ronde 2 atau lebih, mengirim seluruh transcript ronde sebelumnya menyebabkan token meledak. Jika 3 peserta dengan respons masing-masing 4.000 karakter, itu 12.000 karakter (~3.000 token).

RtVectorIndex menyematkan respons ronde sebelumnya dan hanya mengekstrak 5 chunk teratas yang relevan dengan topik saat ini.

// context.rs
pub fn search(&self, topic: &str, limit: usize) -> Vec<(String, String)> {
    // pencarian berbasis kesamaan kosinus, hanya ≥0.2
    // masing-masing chunk truncate ke 800 karakter
}

Hasil: 12.000 karakter → 2.400 karakter. Hemat ~80% token. Jika daemon rawq mati, fallback ke seluruh transcript.


Sistem Peran

Ketika peserta diberi peran, panduan spesifik peran disuntikkan ke dalam prompt, dan token output dibatasi.

4 Peran

fn role_guidance(role: &str) -> &'static str {
    match role {
        "proposer" => "Presentasikan kesimpulan terlebih dahulu dan berikan alasan...",
        "reviewer" | "critic" => "Evaluasi dalam 4 dimensi (plan_coverage, code_quality, test_coverage, convention)...",
        "verifier" | "judge" => "Jangan bergantung pada evaluasi peserta lain, nilai secara independen...",
        "synthesizer" | "lead" => "Ringkas dalam 3 bagian: consensus/contested/dissent...",
        _ => "",
    }
}

Batasan output per peran

Peran

Batasan Token Default

Alasan

proposer

1.200

Hanya proposal inti

reviewer/critic

900

Fokus pada evaluasi

verifier/judge

800

Keputusan harus singkat

synthesizer/lead

2.000

Sintesis bisa lebih panjang

Batasan token disuntikkan di awal prompt sebagai [Output limit: Keep your response under approximately N tokens.]. Bukan paksaan tetapi instruksi, namun sebagian besar model mengikutinya dengan baik.

Peserta Blind

Jika diatur blind: true, peserta tersebut hanya menerima topik dan peran mereka sendiri, dan tidak melihat respons peserta lain sama sekali.

if p.blind {
    build_round_prompt_with_identity(topic, &[], &[], Some(&identity))
    //                                       ^^   ^^ transcript dan ronde saat ini keduanya array kosong
}

Berguna untuk audit keamanan atau verifikasi independen. Secara struktural mencegah bias "reviewer lain pass, jadi saya juga pass".


Review RT: Penggunaan dalam Alur Kerja

Di pipeline alur kerja yang dibahas di bagian 2, tahap Review menggunakan RT.

Deteksi impl-complete
  → Buat Review Branch (mode: "roundtable")
  → Jalankan Reviewer + Verifier 2 orang
  → Hasilkan verdict (pass/fail/conditional)

Alasan Review RT 2 orang: peran jelas berbeda. Reviewer mengevaluasi kualitas kode/tes/konvensi secara numerik, Verifier secara independen memverifikasi evaluasi Reviewer sendiri. 3 orang atau lebih hanya meningkatkan biaya token tanpa menambah perspektif signifikan. Berbeda dengan diskusi desain, review memiliki kriteria yang jelas jadi akurasi lebih penting daripada keragaman perspektif.


Brief: Ringkasan Hasil Diskusi

Setelah RT selesai, ringkasan berbasis aturan (brief) dibuat secara otomatis. Tidak ada panggilan LLM tambahan.

// persist.rs — save_shared_brief
for name in &unique_names {
    if let Some((_, content)) = transcript.iter().rev().find(|(n, _)| n == name) {
        let summary = first_sentences(content, 2);  // 2 kalimat pertama, batasan 300 karakter
        position_lines.push(format!("- **{}**: {}", name, summary));
    }
}

Ekstrak 2 kalimat pertama dari respons terakhir setiap peserta dan ringkas sebagai Key Positions. Brief disimpan di tabel memos dengan type = 'roundtable_brief', dan saat adopt, Key Positions ini disisipkan ke percakapan utama.

Alasan tidak menggunakan ringkasan LLM: RT sendiri sudah banyak mengonsumsi token (basis 3 orang 1 ronde ~10k-20k token), menambah panggilan untuk ringkasan meningkatkan biaya lebih lanjut. Ekstraksi 2 kalimat pertama agak kasar, tetapi karena peserta RT mengikuti panduan peran "katakan kesimpulan terlebih dahulu", 2 kalimat pertama sebenarnya adalah inti posisi mereka.


Pola Penggunaan Aktual

Operasi Ronde

Pola umum dalam diskusi 3 orang adalah minimum 5 ronde. Bukan hanya agen yang berdiskusi tetapi pengguna campur tangan di tengah untuk menjernihkan arah. Campur tangan pengguna juga termasuk dalam hitungan ronde.

Ronde 1: 3 agen masing-masing tampilkan opini
Ronde 2: Pengguna — "Arah A tampak unggul, tapi pertimbangkan juga kekhawatiran B, tinjau ulang"
Ronde 3: 3 agen — Tinjau opini satu sama lain + perbaiki/lengkapi opini sendiri
Ronde 4: Pengguna — "Bagian ini terlihat sudah sepakat, fokus pada sisa isu"
Ronde 5: 3 agen — Opini akhir + synthesizer ringkas

Jika pengguna campur tangan 2 kali, diskusi agen aktual adalah 3 ronde. Ini cukup untuk sebagian besar konvergen. Peserta setuju dengan opini lain, memodifikasi proposal mereka, atau saling melengkapi. Kasus "mempertahankan opini saya" berulang-ulang lebih jarang dari yang diperkirakan.

Dalam diskusi desain kompleks dengan pengguna menjernihkan arah berkali-kali, bisa mencapai 8-10 ronde. Synthesizer melayani untuk meringkas bagian apa yang sudah disepakati dan tidak di akhir, dan jika ada isu yang tidak tercapai konsensus, pengguna menentukan arah.

Konten sederhana atau yang arah sudah jelas tidak perlu sampai RT, cukup percakapan 1:1 dengan Architect.

Kasus Nyata

Ada contoh di mana RT efektif dalam pengembangan tunaFlow. Saat merancang implementasi LLM Wiki untuk tunapi (proyek API) dan seCall (proyek analisis panggilan), diskusi 3 orang mendiskusikan struktur data, strategi indeksing, dan algoritma pencarian. Agen masing-masing mengusulkan pendekatan berbeda, dan melalui ronde, saling meninjau dan melengkapi proposal, hasilnya langsung direfleksikan dalam implementasi aktual. Jika hanya berbicara 1:1 dengan Architect, mungkin hanya satu arah yang dieksplorasi mendalam dan kemungkinan lain terlewatkan, tetapi diskusi membandingkan dan meninjau melalui berbagai kemungkinan tersebut.

Peran Pengguna

Dalam RT, pengguna adalah moderator. Bukan mengharapkan agen mencapai kesepakatan sendiri, tetapi dengan memberikan arah di antara ronde dan menjernihkan isu, kualitas diskusi meningkat. Satu baris seperti "fokus ke arah ini", "ambil proposal A dan kekhawatiran B, keluarkan proposal yang integrasikan keduanya" sangat mengubah kualitas ronde berikutnya.


Keterbatasan Saat Ini

1. Biaya token sebanding dengan ronde

N peserta × R ronde menghasilkan N×R panggilan LLM. 3 orang 3 ronde berarti 9 panggilan. Termasuk transcript ronde sebelumnya, token input juga meningkat seiring ronde. Pencarian vektor mengurangi ~80% konteks ronde sebelumnya, namun secara fundamental biaya proporsional dengan N dan R.

Meski biaya diskusi tinggi, dibanding biaya perbaikan desain yang salah di kemudian hari, biaya token 3 ronde RT cukup masuk akal. Masalahnya adalah sulit memprediksi biaya sebelumnya. Apakah akan selesai 3 ronde atau 8 ronde tergantung kompleksitas topik.

2. Keterbatasan Visual Mode Sequential

Dalam diskusi Sequential, saat melihat respons peserta B, jelas dia melihat dan merespons opini peserta A. Dia mengutip, membantah, atau melengkapi pernyataan sebelumnya. Tetapi di UI, terlihat sebagai "respons berurutan" saja, jadi tidak terlihat jelas bahwa peserta benar-benar berinteraksi.

Respons B dari peserta menerima seluruh respons A dalam prompt, dicerna B sebelum mulai respons sendiri, tetapi "pencernaan" ini terjadi di dalam LLM. Hasilnya menunjukkan referensi silang bagus, tetapi realtime terlihat seperti respons independen.


Ringkasan Keputusan Inti

Keputusan

Alasan

RT = mode Branch

Sistem terpisah tidak perlu. Pakai ulang infrastruktur Branch (shadow conv, drawer, adopt)

Subproses independen per peserta

Bisa campur mesin berbeda. Berbagi sesi PTY struktur tidak mungkin

Konteks minimal (RtContextCache)

Biaya konteks naik × jumlah peserta × ronde. Hanya Tier 0+1

Kompres transcript dengan pencarian vektor

Kirim seluruh ronde sebelumnya → token meledak. Hemat ~80%

Batasan output per peran

Cegah respons panjang. proposer 1200, reviewer 900, synthesizer 2000

Brief berbasis aturan (tanpa LLM)

RT sudah banyak token. Hindari biaya panggilan tambahan

Review RT 2 orang

Review lebih penting akurasi daripada keragaman perspektif. Reviewer + Verifier independen


Pratinjau Bagian Selanjutnya

Bagian 5: "Jika percakapan panjang" — Implementasi Memori Jangka Panjang Agen

Percakapan lama dengan agen melebihi jendela konteks. tunaFlow mengimplementasikan memori jangka panjang dengan compressed memory, pencarian vektor, dan tautan cross-session. Kami bahas timing kompresi, kualitas pencarian, dan keputusan desain "sampai mana agen perlu mengingat masa lalu".


Daftar Seri

  1. [Berikan Proses ke Agen] - Pelajaran dari Membuat AOC

  2. [Plan → Dev → Review] — Implementasi Pipeline Alur Kerja

  3. Cabangkan Percakapan — Desain dan Penggunaan Branch

  4. Buat Agen Berdiskusi — Desain dan Keterbatasan Roundtable (Artikel Ini)

  5. Jika Percakapan Panjang — Implementasi Memori Jangka Panjang Agen

  6. Jalankan Alur Kerja dengan Claude $20 — Arsitektur Mesin

  7. Beri Tahu Agen Struktur Kode — rawq + code-review-graph

  8. Dari 246 Keterampilan Pilih yang Perlu — Implementasi Penerapan Keterampilan Otomatis

  9. Jika Agen Ulangi Kesalahan Sama — Desain Jaminan Kualitas

  10. Jalankan Siklus Lengkap dengan tunaFlow — Tinjauan Uji Coba Alur Kerja

  • [Sudah Diterbitkan] ContextPack — Desain Konteks Orkestrator Multi-Agen


Referensi

  • Dokumen Internal tunaFlow

    • Mesin eksekusi RT: src-tauri/src/commands/roundtable_helpers/executor.rs

    • Mode Sequential: src-tauri/src/commands/roundtable_helpers/sequential.rs

    • Mode Deliberative: src-tauri/src/commands/roundtable_helpers/deliberative.rs

    • Cache konteks: src-tauri/src/commands/roundtable_helpers/context.rs

    • Panduan peran: src-tauri/src/commands/roundtable_helpers/types.rs

    • Rakitan prompt: src-tauri/src/commands/roundtable_helpers/prompt.rs

    • Pembuatan Brief: src-tauri/src/commands/roundtable_helpers/persist.rs

로그인한 회원만 댓글 등록이 가능합니다.

개발한당

KR | ID | EN
  • IDR
  • KOR
8.35 -0.01

2026.07.10 KEB 하나은행 고시회차 1056회

다가오는 한인 행사일정

  • 등록 된 일정이 없어요!