गाइड

AI एजेंट को कार्य कैसे दें: एक बार में एक फ़ीचर, फ़ीचर-सूची और पूर्णता के मानदंड

अपडेट किया गया: · Skillaria.Top

AI एजेंट को कार्य एक-एक करके दें: काम में हमेशा ठीक एक फ़ीचर होता है, उसका देखा जाने वाला व्यवहार और चलने योग्य जाँच-कमांड होती है, और रास्ते में दिखी हर बात एजेंट बैकलॉग में लिखता है, उसे ठीक नहीं करता। सभी फ़ीचरों की स्थिति मशीन-पठनीय सूची (जैसे feature_list.json) में रहती है, और किसी फ़ीचर को «पूर्ण» केवल जाँच-स्क्रिप्ट कर सकती है, एजेंट नहीं।

एजेंट सब कुछ एक साथ क्यों पकड़ता है

आप एजेंट से साइन-अप फ़्लो बनवाते हैं। दो घंटे बाद डिफ़ में बारह बदली हुई फ़ाइलें और आठ सौ नई पंक्तियाँ हैं: यूज़र मॉडल, ईमेल सत्यापन, जुड़ी हुई मेल सेवा, पासवर्ड हैशिंग, फिर से लिखा गया middleware और खिसकाए गए टेस्ट। सब कुछ आपस में गुथा हुआ है, और कोई एक परिदृश्य पूरी तरह पास नहीं होता। अगला सत्र इस कोड को खोलता है और समझ नहीं पाता कि शुरू कहाँ से करे।

कारण «खराब मॉडल» नहीं है। इंसान के पास «आज के लिए बस» की भावना होती है और सामान्य थकान भी, ये दोनों काम का दायरा खुद सीमित कर देते हैं। एजेंट के पास न वह भावना है, न थकान। «और साथ में त्रुटि-प्रबंधन भी ठीक कर दूँगा» लिखने में उसका कुछ दर्जन टोकन लगते हैं, पर प्रोजेक्ट की कीमत असली होती है: ध्यान बिखरता है, आपसी निर्भरता बढ़ती है, और कुछ भी पूरा नहीं होता।

इसके पीछे एक सरल गणित है। मान लीजिए C संदर्भ (context) की उपयोगी क्षमता है, और k वे कार्य हैं जिन्हें एजेंट एक साथ थामे हुए है। हर कार्य को लगभग C/k तर्क-संसाधन मिलता है। जब यह मान एक कार्य पूरा करने के लिए ज़रूरी स्तर से नीचे चला जाता है, तो एक भी कार्य पूरा नहीं होता। इसलिए AI एजेंट को कार्य कैसे दें, इस सवाल का सही उत्तर प्रॉम्प्ट की शब्दावली से नहीं, बल्कि एक सीमा से शुरू होता है: एक समय में एक कार्य।

एक फ़ीचर का नियम (WIP=1)

WIP का अर्थ है work in progress, यानी एक समय में चल रहे कार्यों की संख्या। एजेंट के लिए इसे एक पर रखा जाता है: किसी भी क्षण ठीक एक फ़ीचर सक्रिय होता है, और अगला तभी शुरू होता है जब मौजूदा जाँच पास कर ले। यह नियम प्रोजेक्ट की निर्देश-फ़ाइल (AGENTS.md या CLAUDE.md) में लिखा जाता है, ताकि एजेंट इसे हर सत्र में देखे:

## कार्य के नियम
- किसी भी समय स्थिति `active` में ठीक एक ही फ़ीचर होता है।
- अगला फ़ीचर तभी शुरू करें, जब मौजूदा `passing` हो चुका हो।
- «साथ-साथ» रिफ़ैक्टर करना, नाम बदलना, फ़ोल्डर पुनर्गठित करना
  और असंबंधित बग ठीक करना मना है। समस्या दिखे तो `BACKLOG.md` में लिखें और आगे बढ़ें।
- सक्रिय फ़ीचर के दायरे के बाहर का बदलाव उल्लंघन माना जाएगा, भले ही वह उपयोगी हो।

आखिरी नियम जितना दिखता है उससे ज़्यादा ज़रूरी है। एजेंट अपने «साथ-साथ» वाले बदलावों को सच्चे दिल से उपयोगी मानता है, और अक्सर वे होते भी हैं। पर दायरे से बाहर का उपयोगी बदलाव भी एक ही डिफ़ में दो कार्यों को मिला देता है, और फिर उन्हें अलग-अलग रद्द या जाँचा नहीं जा सकता।

BACKLOG.md: «साथ-साथ» वाली बातें कहाँ जाएँ

«साथ-साथ ठीक कर दो» की इच्छा को केवल मना करना काफ़ी नहीं है, उसे वैध रास्ता चाहिए। यह रास्ता BACKLOG.md फ़ाइल है: एजेंट वहाँ दिखी समस्या एक-दो पंक्तियों में लिखता है और मौजूदा फ़ीचर पर लौट आता है। जानकारी खोती नहीं, और दायरा भी नहीं फैलता। बैकलॉग के बिना एजेंट देर-सवेर इस नियम को तोड़ने लगता है, क्योंकि उसे «बग चुपचाप छोड़ना» नियम तोड़ने से बुरा लगता है।

# BACKLOG.md
- [ ] middleware/errors.py: /auth और /orders में त्रुटियों का अलग-अलग प्रारूप
- [ ] tests/: यूज़र फ़िक्सचर तीन फ़ाइलों में दोहराए गए हैं
- [ ] क्या रजिस्ट्रेशन में ईमेल सत्यापन चाहिए? — पूछना है

पूर्णता के मानदंड: «पूर्ण» का मतलब एक कमांड है

समस्या का दूसरा हिस्सा यह है कि एजेंट खुद तय करता है कि कार्य पूरा हुआ या नहीं। «कोड ठीक दिखता है», «फ़ंक्शन मौजूद है», «कंपाइल एरर नहीं है», ये सब एहसास हैं, तथ्य नहीं। एजेंट के लिए कार्य की पूर्णता का मानदंड ऐसी चलने योग्य कमांड होना चाहिए, जिसका परिणाम साफ़ हो: पास हुई या नहीं।

F01: उपयोगकर्ता पंजीकरण
verification: pytest tests/e2e/test_auth.py::test_register_flow
state: active

कमज़ोर और सख्त मानदंड का फ़र्क उदाहरणों में साफ़ दिखता है:

कमज़ोर मानदंडसख्त मानदंड
कोड कंपाइल होता हैpytest tests/e2e/test_cart.py -q पास होता है
सिंटैक्स एरर नहीं है/cart पर curl कोड 200 लौटाता है
फ़ंक्शन addToCart मौजूद हैउत्पाद जोड़ने के बाद GET /cart उसे और सही राशि दिखाता है
सही दिखता हैnpx playwright test cart.spec.ts पास होता है

अच्छी जाँच-कमांड नियतात्मक (deterministic) होती है, यानी एक जैसे कोड पर एक जैसा परिणाम देती है, इंसान की मदद के बिना चलती है, और व्यवहार को बाहर से जाँचती है, ठीक वैसे जैसे उपयोगकर्ता या API क्लाइंट उसे देखेगा। अगर ऐसी कमांड लिखना संभव न हो, तो यह संकेत है कि कार्य अस्पष्ट है।

विभाजन: फ़ीचर कितना बड़ा होना चाहिए

«एक फ़ीचर एक बार में» के बाद सबसे आम सवाल यह होता है कि फ़ीचर किसे माना जाए। बहुत चौड़ा कार्य एक सत्र में खत्म नहीं होगा, और बहुत संकीर्ण कार्य शुरू करने, संदर्भ लोड करने और जाँचने के खर्च में डूब जाएगा।

  • बहुत चौड़ा: «कार्ट लागू करो»। यह एक सप्ताह का काम है और दर्जनों परिदृश्य।
  • ठीक आकार: «उपयोगकर्ता कोई उत्पाद कार्ट में जोड़ सकता है और उसे वहाँ देख सकता है»। एक देखा जाने वाला व्यवहार, एक जाँच-परिदृश्य।
  • बहुत संकीर्ण: «CartItem मॉडल में quantity फ़ील्ड बनाओ»। यह कार्यान्वयन का एक चरण है, व्यवहार नहीं; इसे अलग से जाँचना बेकार है।

आकार जाँचने का सुविधाजनक तरीका: एक फ़ीचर = एक एजेंट-सत्र = एक सार्थक कमिट = एक एंड-टू-एंड (E2E) परिदृश्य। अगर फ़ीचर एक सत्र में न समाए, तो और तोड़ें। अगर उसके लिए अलग परिदृश्य लिखा ही न जा सके, तो वह बहुत छोटा है, उसे पास के फ़ीचर के साथ मिला दें।

«कार्ट» कार्य के विभाजन का उदाहरण

चौड़ी आवश्यकता को परमाणु इकाइयों में बाँटा जाता है, जिनमें से हर एक का एक व्यवहार और अपनी जाँच-कमांड होती है:

  1. कार्ट में उत्पाद जोड़ना और सूची में उसे देखना।
  2. उत्पाद की मात्रा बदलना, और राशि का फिर से जोड़ होना।
  3. कार्ट से उत्पाद हटाना।
  4. लॉग इन के बाद अतिथि (guest) का कार्ट सुरक्षित रहना।
  5. स्टॉक में न होने वाला उत्पाद न जोड़ पाना, और स्पष्ट त्रुटि दिखना।

अंतिम जाँच विभाजन की: कोई भी इकाई दूसरी को «साथ में» छुए बिना पूरी न हो सके। अगर बिंदु 4 के लिए बिंदु 1 दोबारा लिखना पड़े, तो क्रम या सीमाएँ गलत चुनी गई हैं।

फ़ीचर-सूची: feature_list.json

एक-फ़ीचर नियम सत्र के भीतर क्रम बनाए रखता है। पर सत्रों के बीच कौन याद रखेगा कि क्या तैयार है? चैट में लिखा «auth और कैटलॉग हो गए, कार्ट लगभग तैयार है, पर कुछ बग हैं» नए सत्र के किसी काम का नहीं: «लगभग» का क्या मतलब है, कौन से टेस्ट पास हुए, भुगतान को क्या रोक रहा है, यह पता नहीं चलता। हर नया सत्र उसी मशीन के नए ड्राइवर जैसा है: अगर नोट्स केवल पिछले ड्राइवर के दिमाग में थे, तो नए को कुछ नहीं पता।

इसलिए स्थिति को बाहर, एक मशीन-पठनीय फ़ाइल में रखा जाता है। कोर्स में यह .agent/feature_list.json है:

[
  {
    "id": "F01",
    "behavior": "उपयोगकर्ता ईमेल और पासवर्ड से रजिस्टर करता है और तुरंत लॉग इन हो जाता है",
    "verification": "pytest tests/e2e/test_auth.py::test_register_flow",
    "state": "passing",
    "evidence": "a3f9c12: 1 passed in 2.31s"
  },
  {
    "id": "F02",
    "behavior": "उपयोगकर्ता उत्पाद कार्ट में जोड़ता है और सूची में देखता है",
    "verification": "pytest tests/e2e/test_cart.py::test_add_item -q",
    "state": "active"
  },
  {
    "id": "F03",
    "behavior": "कार्ड से ऑर्डर का भुगतान",
    "verification": "pytest tests/e2e/test_payment.py -q",
    "state": "blocked",
    "blocker": "भुगतान गेटवे की टेस्ट कुंजियाँ नहीं हैं"
  }
]

हर प्रविष्टि में तीन अनिवार्य फ़ील्ड हैं: व्यवहार का वर्णन (बाहर से देखा जाने वाला), जाँच-कमांड (चलने योग्य, इंसान के बिना) और स्थिति। एक वैकल्पिक चौथा फ़ील्ड है evidence: कमिट का हैश और जाँच का आउटपुट, यानी इस बात का सबूत कि passing में बदलाव सचमुच हुआ था।

JSON क्यों, Markdown सूची क्यों नहीं? इसे केवल एजेंट नहीं पढ़ता, स्क्रिप्ट भी पढ़ती हैं: शेड्यूलर not_started में से अगला फ़ीचर चुनता है, सत्यापनकर्ता जाँच-कमांड लेता है, सत्र की रिपोर्ट अपने-आप बनती है, और स्थिति का वितरण प्रोजेक्ट के स्वास्थ्य के मेट्रिक्स देता है। फ़ीचर-सूची हार्नेस की रीढ़ है, केवल याद दिलाने वाली पर्ची नहीं।

चार स्थितियाँ और अनुमत संक्रमण

संक्रमणकब
not_started → activeफ़ीचर काम में लिया जाता है; कोई और सक्रिय नहीं है
active → passingजाँच-स्क्रिप्ट कोड 0 के साथ पूरी होती है
active → blockedबाहरी अवरोध; कारण blocker में लिखा जाता है
blocked → activeअवरोध हट गया है

और कोई संक्रमण नहीं है। खास तौर पर जाँच को बाईपास करके passing तक पहुँचने का रास्ता नहीं है, और «लगभग तैयार» नाम की कोई स्थिति नहीं है।

passing गेट: एजेंट माँग सकता है, घोषित नहीं कर सकता

पूरी योजना का केंद्रीय नियम: एजेंट state फ़ील्ड को हाथ से नहीं बदलता। वह जाँच चला सकता है, पर परिणाम खुद घोषित नहीं कर सकता, यह काम स्क्रिप्ट करती है। «एजेंट ने रिपोर्ट दी» और «स्क्रिप्ट ने पुष्टि की» का फ़र्क शब्द और तथ्य का फ़र्क है। नियम भी निर्देश-फ़ाइल में लिखे जाते हैं:

## फ़ीचर-सूची के नियम
- फ़ाइल: `.agent/feature_list.json`। दायरे का यही एकमात्र स्रोत है।
- ठीक एक फ़ीचर `active` स्थिति में हो।
- तुम `state` फ़ील्ड हाथ से नहीं बदलते। उसे `scripts/verify.sh` बदलती है।
- फ़ीचर को `passing` में ले जाने के लिए चलाओ `./scripts/verify.sh F02` और कोड 0 लाओ।
- अगर फ़ीचर अवरुद्ध है, तो उसे `blocked` करो और `blocker` ज़रूर लिखो।
- नए फ़ीचर केवल `not_started` में और केवल जाँच-कमांड के साथ जोड़े जाते हैं।

स्क्रिप्ट दो स्तरों पर जाँच करती है: पहले पूरे प्रोजेक्ट का रन (फ़ीचर बाकी सब न तोड़े), फिर उस फ़ीचर की अपनी कमांड। स्थानीय सफलता वैश्विक रिग्रेशन के साथ सफलता नहीं मानी जाती।

#!/usr/bin/env bash
# एकमात्र घटक जिसे passing लिखने का अधिकार है।
set -uo pipefail
FID="$1"
FILE=".agent/feature_list.json"

CMD=$(jq -r --arg id "$FID" '.[] | select(.id==$id) | .verification' "$FILE")
if [ -z "$CMD" ] || [ "$CMD" = "null" ]; then
  echo "FAIL: $FID के लिए जाँच-कमांड नहीं है"; exit 2
fi

echo "== वैश्विक जाँच =="
make check || { echo "FAIL: सामान्य जाँच लाल है, $FID passing नहीं हो सकता"; exit 1; }

echo "== फ़ीचर जाँच: $CMD =="
if OUT=$(eval "$CMD" 2>&1); then
  SHA=$(git rev-parse --short HEAD)
  LAST=$(printf '%s\n' "$OUT" | tail -n 1)
  TMP=$(mktemp)
  jq --arg id "$FID" --arg ev "$SHA: $LAST" \
    'map(if .id==$id then .state="passing" | .evidence=$ev else . end)' \
    "$FILE" > "$TMP" && mv "$TMP" "$FILE"
  echo "PASS: $FID"
else
  printf '%s\n' "$OUT"
  echo "FAIL: $FID"; exit 1
fi

टेक्स्ट में लिखा «state को हाथ से मत बदलो» अब भी एक अनुरोध है। इसे बाध्यता बनाने के लिए फ़ाइल में लिखना यांत्रिक रूप से बंद किया जा सकता है: CI की जाँच से, जो evidence को कमिट-इतिहास से मिलाती है, या आपके उपकरण में एजेंट के अधिकारों की सीमा से। सिद्धांत हार्नेस में हर जगह एक ही है: ज़रूरी नियम को मशीनरी से मज़बूत किया जाता है।

कैसे मापें कि एजेंट कार्य पूरा करता है

लुभावना मेट्रिक है सत्र में लिखे कोड की मात्रा। व्यवहार में यह उल्टा काम करता है: बड़ा डिफ़ अक्सर बताता है कि एजेंट कई दिशाओं में बिखर गया। फ़ीचरों को passing स्थिति में गिनें, पंक्तियों को नहीं।

कोर्स का एक सुविधाजनक मेट्रिक है VCR (Verified Completion Rate): सत्यापित कार्यों की संख्या, भाग्य सक्रिय किए गए कार्यों की संख्या। नियम सरल है: जब तक VCR एक से कम है, नए कार्य सक्रिय नहीं किए जा सकते। यह वह उल्टा दबाव है, जो हार्नेस एजेंट पर डालता है, और साथ ही अधूरे काम को एहसास के बजाय एक दिखने वाली संख्या बना देता है।

एजेंट को कार्य देते समय आम गलतियाँ

  • बिना जाँच-कमांड का कार्य। «रजिस्ट्रेशन बनाओ» बिना परिदृश्य के: एजेंट खुद तय करेगा कि कहाँ रुकना है, और गलत तय करेगा।
  • एक अनुरोध में कई फ़ीचर। «कार्ट और भुगतान बनाओ» दो सक्रिय कार्य हैं, और दोनों में से कोई पूरा नहीं होगा।
  • स्थिति केवल चैट में। बातचीत में दर्ज प्रगति सत्र खत्म होते ही गायब हो जाती है। उसे फ़ाइल में रहना चाहिए।
  • जाँच की जगह आत्म-रिपोर्ट। «एजेंट ने कहा टेस्ट पास हुए» वह नहीं है जो स्क्रिप्ट का रिटर्न कोड बताता है।
  • बैकलॉग नहीं। «साथ-साथ» पर रोक, पर दर्ज करने की जगह न हो, तो एजेंट उसे चकमा दे देता है।

जब एक फ़ीचर एक बार में भी कम पड़े

«एक फ़ीचर — एक सत्र — एक जाँच» योजना एक एजेंट के एक चक्र में अच्छी चलती है। जब कार्य बहुत हो जाते हैं और स्वतंत्र शाखाएँ बनती हैं, तो इसे कई चक्रों की व्यवस्था तक बढ़ाया जाता है: अलग योजना-नोड, कार्यान्वयन-नोड, जाँच-नोड और उनके बीच के किनारे, जो समानांतर, शर्तीय हो सकते हैं, और जाँच विफल होने पर कार्यान्वयन की ओर लौट सकते हैं। पर वहाँ भी हर कार्यान्वयन-नोड उसी नियम पर चलता है: एक कार्य, चलने योग्य पूर्णता-मानदंड, और स्थिति एजेंट के सिर के बाहर। ग्राफ़ एक-फ़ीचर अनुशासन को रद्द नहीं करता, वह उसी के ऊपर बनता है।

उसी विश्लेषण की एक चेतावनी: लूप उस मेट्रिक को ईमानदारी से अनुकूलित करता है, जो उसे दिया गया है। अगर पूर्णता का मानदंड गलत चुना गया, जैसे «टिकट बंद» के बजाय «समस्या हल», तो एजेंट मानदंड पूरा करना सीख लेगा, कार्य नहीं। इसलिए व्यवहार और जाँच-कमांड की शब्दावली पर उतना समय लगाना चाहिए जितना दिखता है उससे ज़्यादा।

संक्षेप में

सार यह है कि AI एजेंट को कार्य एक-एक करके दें, देखे जाने वाले व्यवहार और चलने योग्य जाँच-कमांड के साथ, रास्ते में दिखी हर बात के लिए बैकलॉग रखें, और फ़ीचर-सूची फ़ाइल में रखें, जहाँ «पूर्ण» की ओर संक्रमण स्क्रिप्ट करे, एजेंट नहीं। एजेंट पर ब्रेक हार्नेस लगाता है, वह खुद उसे नहीं लगाएगा। WIP=1, feature_list.json और verify.sh कोर्स में हार्नेस इंजीनियरिंग पर, एक एंड-टू-एंड प्रोजेक्ट के उदाहरण से, व्यवहार में समझाए गए हैं।

अक्सर पूछे जाने वाले प्रश्न

क्या एजेंट को एक साथ कई कार्य दिए जा सकते हैं, अगर वे छोटे हों?

उन्हें फ़ीचर-सूची में रखा जा सकता है, पर काम में एक बार में एक ही होना चाहिए। एजेंट अगला तभी उठाता है जब मौजूदा जाँच पास हो चुकी हो, इस तरह हर कार्य पूरा होता है।

अगर किसी कार्य के लिए स्वचालित जाँच लिखना संभव न हो तो क्या करें?

आमतौर पर इसका मतलब है कि कार्य एक क्रिया के रूप में लिखा गया है, व्यवहार के रूप में नहीं। उसे इस तरह दोबारा लिखें कि उपयोगकर्ता या API क्लाइंट क्या देखेगा; दृश्य हिस्से के लिए ब्राउज़र में E2E टेस्ट ठीक रहेंगे।

feature_list.json कौन लिखता है, इंसान या एजेंट?

शुरुआती सूची मिलकर बनाना सुविधाजनक है: एजेंट विभाजन सुझाता है, इंसान उसे सुधारता है। इसके बाद एजेंट नए फ़ीचर जोड़ सकता है, पर केवल not_started स्थिति में और जाँच-कमांड के साथ।

feature_list.json और ट्रैकर के कार्यों में क्या फ़र्क है?

ट्रैकर इंसानों के लिए बना है, जबकि फ़ीचर-सूची मशीन पढ़ने के लिए: हर प्रविष्टि में चलने योग्य कमांड और सख्त स्थिति होती है, जिसे स्क्रिप्ट बदलती है। दोनों को सिंक किया जा सकता है, पर एजेंट को रिपॉज़िटरी में फ़ाइल चाहिए।

क्या WIP=1 का नियम काम की गति धीमी नहीं करता?

सत्र छोटे हो जाते हैं, पर पूरे हुए कार्यों का अनुपात बढ़ता है। जो समय पहले तीन मिले-जुले फ़ीचरों के अधूरे कोड को समझने में जाता था, वह बच जाता है।

इस विषय को वीडियो में सीखें

यह विषय “Harness Engineering: инженерия надёжности AI-агентов” कोर्स में अभ्यास के साथ विस्तार से समझाया गया है।

कोर्स पर जाएँ