æ¬èšäºã¯ 2025 幎 11 æ 17 æ¥ã«å
¬éããã Aaron ElineïŒResearcherïŒ ã«ãã â Does your code match your spec? â ã翻蚳ãããã®ã§ãã 仿§ã®éèŠæ§ Kiro 㯠7 æã«ããŒã³ãããéã«ä»æ§é§åéçºïŒSpec Driven Developmentã以äžãSDDïŒãå°å
¥ãããšãŒãžã§ã³ãå IDE ã§ããSDD ã§ã¯ãKiro ã®ãšãŒãžã§ã³ããã³ãŒããæžãåã«ãœãããŠã§ã¢ã®å®å
šãªä»æ§ãäœæããŸããããã«ãããéçºåã«ãšãŒãžã§ã³ããšç¹°ãè¿ãããåãããªãããã¢ããªã±ãŒã·ã§ã³ã®èŠä»¶ãå®å
šã«æããããŠããã確èªã§ããŸããKiro ã¯ãã®èŠä»¶ããã¥ã¡ã³ããå®è¡ã㊠Spec ïŒä»æ§ïŒã«å€æããçæãããã³ãŒãã仿§ã«æºæ ããŠãããããã§ãã¯ããŸããKiro ã¯ãã®å®è¡å¯èœãªä»æ§ã䜿ã£ãŠããã°ã©ã ããã¹ãããŸããããã®éã«ããããã£ããŒã¹ãã¹ããšåŒã°ããææ³ã䜿çšããŸããç§ãã¡ã¯ãã®ææ³ã¯ããã°çºèŠã«ãã广çã§ãããšèããŠããŸãã èŠä»¶ããããããã£ãž Kiro ã䜿ããšã仿§ããã³ãŒããçæãããŸãããããããã®ã³ãŒããæ¬åœã«ä»æ§éãã«åäœããããã©ããã£ãŠç¢ºèªããã°ããã®ã§ããããïŒKiro ãä»ã®çæ AI ã³ãŒãçæããŒã«ã¯ããã®åãã«çããããã«èªåçæããããŠããããã¹ãã䜿ã£ãŠããŸãããKiro ã¯ã³ãŒããšäžç·ã«ãŠããããã¹ããçæããã³ãŒãããããããã¹ããããšã確èªããŸããããããããã«ã¯é¶ãšåµã®åé¡ããããŸãããŠããããã¹ãã仿§ã§ç€ºãããåäœãæããŠããããã©ããã£ãŠç¢ºèªããã®ã§ããããïŒåãã¹ããèŠãŠã1/ ãã®ãã¹ããã©ã®ä»æ§èŠä»¶ã«é©çšãããã®ãã2/ ãã¹ãã§èŠå®ãããåäœã仿§ãšäžèŽããŠãããã倿ããå¿
èŠããããŸããã©ã¡ãã®ã¹ããããé¢åã§ãšã©ãŒãèµ·ããããäœæ¥ã§ãã å®éã®ãšããããŠããããã¹ãã®ä»£ããã«ããããã£ããŒã¹ãã¹ãã䜿çšããããšã§ãããåªããçµæãåŸãããå ŽåããããŸãããŠããããã¹ãã¯æ¬è³ªçã«ãäŸããŒã¹ãã®ãã¹ãã§ãåäžã®å
¥åãšåºåã®ãã¢ã§æ§æãããŠããŸããåãã¹ãã¯ç¹å®ã®äŸã«ãããŠãã·ã¹ãã ãç¹å®ã®æ¹æ³ã§åäœããããšã䞻匵ããŸãã察ç
§çã«ãããããã£ããŒã¹ãã¹ãïŒãŸãã¯åã«ããããã£ãã¹ãïŒã¯ãã·ã¹ãã ã®åäœã«ã€ããŠããããã£ãçã§ããããšããã¹ãããŸããã€ãŸããåºç¯å²ã®ïŒå Žåã«ãã£ãŠã¯ç¡éã®ïŒå
¥åã«å¯ŸããŠãããæãç«ã€ããšã確èªããŸãããã®æ®éæ§ããããããããã£ãã¹ãã«åãäžãããã®ã§ããããããã£ãã¹ãã§ã¯ãå€ãã®å
¥åãã©ã³ãã ã«çæããŠãã¹ãããŸããããããã£ãã¹ãã false ãè¿ããå Žåããã®ããããã£ãç ŽãåäŸãèŠã€ããããšã«ãªããŸããããã¯ãã¹ã察象ã®ããã°ã©ã ã®ãã°ã衚ããŠããå¯èœæ§ãé«ãã§ãïŒãã ããããããã£å®çŸ©ã®ãã°ãå
ã®ä»æ§ã®ãã°ã§ããå¯èœæ§ãããããããèŠã€ããããšãæçšã§ãïŒãKiro ã¯ãã®äŸã䜿ã£ãŠãæ£ãããªããŸã§ã³ãŒããä¿®æ£ã§ããŸãã ããããã£ããŒã¹ãã¹ã㯠20 幎以äžåã« Haskell ããã°ã©ãã³ã°èšèªåãã« QuickCheck ãšãããã¬ãŒã ã¯ãŒã¯ã§çºæãããŸããããã以æ¥ãæé·ãæçããŠããŸãããããããã£ãã¹ãã¯ãKiro ãè¡ããããªä»æ§é§åéçºãšéåžžã«çžæ§ãè¯ãã§ãããªããªãã仿§èŠä»¶ã¯å€ãã®å ŽåãçŽæ¥çã«ããããã£ã衚çŸããŠããããããã®ããããã£ã¯ããããã£ããŒã¹ãã¹ãã䜿ã£ãŠãã¹ãã§ããããã§ããããæå³ã§ãããããã£ã¯ä»æ§ã®ïŒäžéšã®ïŒå¥ã®è¡šçŸã§ããããããã£ããŒã¹ãã¹ãã䜿ãã°ãåãããŠç¢ºèªã§ãã仿§è¡šçŸãæã«å
¥ããŸããããããã£ããŒã¹ãã¹ãã§æ§æãããå®è¡å¯èœãªä»æ§ã¯ãããã¹ãã®èŠä»¶ãšç°¡åã«çµã³ã€ãããããããããããã£ãã¹ãããã¹ããéããã³ãŒããèŠä»¶éãã«åäœããŠãããšãã確信ãåŸãããŸãã äŸ äŸãšããŠãPython ã§å°ããªä¿¡å·æ©ã·ãã¥ã¬ãŒã¿ãŒãæžããŠãããšããŸããããKiro ã¯åãå
¥ãåºæºã§æ§æãããèŠä»¶ããã¥ã¡ã³ããå«ã仿§ãäœæããŸããåãå
¥ãåºæºã® 1 ã€ã¯æ¬¡ã®ããã«ãªããããããŸããã èŠä»¶ 2.3: å®å
šæ§ã®äžå€æ¡ä»¶ ã·ã¹ãã ã¯ãççŸãã亀éã®æµããé²ãããã«ãä»»æã®æç¹ã§æå€§ 1 ã€ã®æ¹åã®ã¿ãç·ä¿¡å·ãæã€ããšãä¿èšŒããªããã°ãªããªãã ãã®åºæºã¯ãä¿¡å·æ©ã®éèŠãªæ¡ä»¶ã衚çŸããŠããŸãã2 ã€ã®æ¹åãåæã«ç·ã«ãªãããšã¯æ±ºããŠãªããšããããšã§ãããã®åãå
¥ãåºæºãããã¹ãã®ããããã£ã«å€æãããšæ¬¡ã®ããã«ãªããŸãã ããããã£: å®å
šæ§ã®äžå€æ¡ä»¶ - æå€§1ã€ã®ç·ä¿¡å· *ä»»æã®*æäœã·ãŒã±ã³ã¹ïŒç¶æ
é·ç§»ãç·æ¥ã¢ãŒãã®æå¹åãã¿ã€ãã³ã°æŽæ°ïŒã«å¯ŸããŠã ä»»æã®æç¹ã§ãæå€§1ã€ã®æ¹åã®ã¿ãç·ä¿¡å·ãæã€ã¹ãã§ãã **æ€èšŒå¯Ÿè±¡: èŠä»¶ 2.3** ãã®ããããã£ããä»»æã®ããšããèšèã§å§ãŸã£ãŠããããšã«æ³šç®ããŠãã ããããããããããã£ã§ããçç±ã¯ãåäžã®äŸã®å
¥åãã©ãåŠçãããã¹ããã®èª¬æã§ã¯ãªããå
¥åãšåäœã®ç¯å²ã«ã€ããŠèªã£ãŠããããã§ããKiro ã¯ãã®ããããã£ããã¹ããããšã«ãå®è¡å¯èœãªãã¹ãã³ãŒããžå€æããŸããKiro ã¯ãããã¹ãã®ä»æ§ãããã®ããããã£ããã§ãã¯ãããã¹ããžçŽæ¥ããã²ãŒãã§ããããã«ããããšã§ãäž¡è
ãçµã³ã€ããŸãã Kiro ã¯ããã¹ãã®ããããã£ãã Hypothesis ãšãããã¬ãŒã ã¯ãŒã¯ã䜿ã£ãŠæžãããããããã£ããŒã¹ãã¹ãã«å€æããŸããããã«ã€ããŠã¯åŸã»ã©è©³ããèŠãŠãããŸããä¿¡å·æ©ã®ããããã£ã®ã³ãŒãã¯ä»¥äžã®éãã§ãããã®ã³ãŒããèªãã°ãå®éã«ç§ãã¡ãæ°ã«ããŠããããããã£ããã§ãã¯ããŠããããšãããããŸãããŸããæ£åžžãªç¶æ
ããå§ãŸã£ãŠããããšã確èªããŸããæ¬¡ã«ãæäœã¹ã±ãžã¥ãŒã«ã®åæäœãå埩åŠçããããããé©çšããŠãåžžã« 1 ã€ã®ç·ä¿¡å·ããèŠãããªãããšã確èªããŸãã def test_safety_invariant_at_most_one_green( timing_config: TimingConfig, operations: list ): """æ©èœ: ä¿¡å·å¶åŸ¡ã·ã¹ãã ããããã㣠2: å®å
šæ§ã®äžå€æ¡ä»¶ - æå€§1ã€ã®ç·ä¿¡å· æ€èšŒå¯Ÿè±¡: èŠä»¶ 2.3 """ # ç¶æ
ãããŒãžã£ãŒãšå¶åŸ¡ã¢ãžã¥ãŒã«ãäœæ state_manager = SignalStateManager(timing_config) control_module = ControlModule(state_manager) # åæç¶æ
ïŒãã¹ãŠèµ€ïŒãå®å
šæ§ãæºããããšãç¢ºèª assert control_module.validate_safety(), "åæç¶æ
ã¯å®å
šã§ããã¹ã" # åæäœãå®è¡ããæäœåŸã«æ¯åå®å
šæ§ãç¢ºèª for operation in operations: op_type = operation[0] if op_type == 'transition': _, direction, state = operation control_module.request_transition(direction, state) elif op_type == 'emergency_activate': _, direction = operation control_module.activate_emergency_mode(direction) elif op_type == 'emergency_deactivate': control_module.deactivate_emergency_mode() # ãã¹ãŠã®æäœåŸã«å®å
šæ§ã®äžå€æ¡ä»¶ãç¢ºèª all_states = state_manager.get_all_states() green_count = sum(1 for state in all_states.values() if state == SignalState.GREEN) assert green_count <= 1, ( f"å®å
šæ§éå: æäœ {operation} ã®åŸã« {green_count} åã®ç·ä¿¡å·ã" f"ç¶æ
: {all_states}" ) ãã®ããããã£ãã¹ãã®çŽ æŽãããç¹ã¯ãæåã«å®çŸ©ããèŠä»¶ãçŽæ¥ãã¹ãããŠããããšã§ããã€ãŸããå€ãã®å
¥åã§ãã¹ãããã°ããã®èŠä»¶ãæºãããŠããããšã«é«ã確信ãæãŠãŸããããã«éèŠãªã®ã¯ããã®éãæãç«ã€ããšã§ãããã®é¢æ°ã倱æãããå
¥åãååšããå Žåãããã°ã©ã ã¯æ£ãããªãã®ã§ããKiro ã¯ãã®ç¹æ§ãç©æ¥µçã«å©çšããŸãã ããããã£ãã¹ãã®éèŠãªéšåã¯ãããããã£ãã¹ããå®è¡ããããã®å€æ§ãªå
¥åãã©ã³ãã ã«çæããããšã§ãããã®äŸã§ã¯ãéèŠãªå
¥å㯠test_safety_invariant_at_most_one_green ã«æž¡ãããæäœã® list ã§ããæ¬¡ã®ã»ã¯ã·ã§ã³ã§ã¯ããã®äŸã®æèã§å
¥åçæã«ã€ããŠèª¬æããŸããèªåå
¥åçæã¯ããŠããããã¹ãã«å¯ŸããéèŠãªå©ç¹ãæäŸããŸãã誰ãããŠããããã¹ããæžããšãïŒã¢ãã«ã§ãã人éã§ããïŒããšããžã±ãŒã¹ãèæ
®ããããšããŸããã èªåèªèº«ã®å
éšãã€ã¢ã¹ã«ãã£ãŠå¶éãããŸãã ã©ã³ãã çæãå©çšããããšã§ãèŠèœãšãããã¡ãªãšããžã±ãŒã¹ãã³ã³ããŒãã³ãéã®çžäºäœçšãçºèŠã§ããããšããããããŸããKiro ã¯ãã®äºå®ãæå€§éã«æŽ»çšããŸãã ããããã£ã®å
žåãã¿ãŒã³ ããã°ã©ã ã®æ£ããã«é¢ããæç®ã§ã¯ãããçŸããããããã£ã®å
žåçãªãã¿ãŒã³ãããããšãããã£ãŠããŸããKiro ã¯ãããã®ãã¿ãŒã³ãèªèããŠãããããããã£ãçæããéã«ããããæ¢ããŸããããšãã°ãäºåæ¢çŽ¢æšã®ãããªããŒã¿æ§é ã®äžè¬çãªããããã£ã¯ãå®è¡æã®äžå€æ¡ä»¶ãç¶æããããšã§ããåã
ã®æäœãäžå€æ¡ä»¶ãç¶æããããšãæ€èšŒããããããã£ãæžããŸãã # æ¿å
¥æäœã¯äºåæ¢çŽ¢æšã®æ§è³ªãç¶æãã¹ã def bst_insert(tree, input): if is_bst(tree): tree.insert(input) assert is_bst(tree), "æšã¯äŸç¶ãšããŠäºåæ¢çŽ¢æšã§ããã¹ã" assert tree.contains(input), "æšã¯å
¥åå€ãå«ãã¹ã" å¥ã®äžè¬çãªããããã£ã®ãã¿ãŒã³ã¯ãã©ãŠã³ãããªãããã§ãäžé£ã®æäœã«ãã£ãŠéå§æã®å€ã«æ»ããšãããã®ã§ãããã®ããããã£ã¯ç¹ã«ããŒãµãŒãã·ãªã¢ã©ã€ã¶ãŒã«æçšã§ãã # ããŒãµãŒã§ã»ãŒåžžã«æãç«ã€ã¹ããããã㣠# æŽåœ¢ããŠããå床ããŒã¹ãããšãåãåŒãåŸãããã¹ã def parser_correctness(expression): assert parse(pretty_print(expression)) == expression Web API ã§ã¯ãå逿äœããåªçãã§ããããšãæãããšããããããŸããã€ãŸããã¢ã¯ã·ã§ã³ã 2 åç¹°ãè¿ããŠã 1 åå®è¡ããã®ãšåã广ã«ãªããšããããšã§ãã def delete_idempotence(orders_list, order_id): if order_id in orders_list: assert orders_list.delete(order_id) == orders_list.delete(order_id).delete(order_id) ããããã£ã®èšèšã«ã€ããŠããã«è©³ããç¥ãããå Žåã¯ã次ã®ããã°èšäºããå§ãããŸãã Choosing Properties for Property-Based Testing ãããã³ How To Specify it [PDF] ã®è«æã§ãã å
¥åãžã§ãã¬ãŒã¿ãŒã䜿ã£ãããããã£ã®ãã¹ã ããããã£ããã¹ãããã«ã¯ãå
·äœçãªå
¥åå€ãå¿
èŠã§ãã倿°ã®ïŒæ°çŸã®ïŒå€æ§ãªå€ãååŸãããã€ã¢ã¹ã®åœ±é¿ãæžããããã«ãPBT ãã¬ãŒã ã¯ãŒã¯ã¯ããžã§ãã¬ãŒã¿ãŒãã䜿çšããŸããããã¯äœããã®ã©ã³ãã æ§ãåãåããç¹å®ã®åã®å
¥åå€ãçæãã颿°ã§ããããããã£ããŒã¹ãã¹ããã¬ãŒã ã¯ãŒã¯ã®ãŠãŒã¶ãŒã¯ãç¹å®ã®ããããã£ãã¹ããå®è¡ããéã«ã©ã®å
¥åãžã§ãã¬ãŒã¿ãŒã䜿çšããããæå®ããŸããKiro ã¯çæããããããã£ãã¹ãã«å¯ŸããŠãããèªåçã«è¡ããŸãã Hypothesis ãªã©ã® PBT ãã¬ãŒã ã¯ãŒã¯ã«ã¯ãäžè¬çãªåçšã®ãžã§ãã¬ãŒã¿ãŒã倿°ä»å±ããŠãããããããæ§æèŠçŽ ãšããŠäœ¿ã£ãŠããè€éãªãžã§ãã¬ãŒã¿ãŒãäœæã§ããŸããHypothesis ãã¬ãŒã ã¯ãŒã¯ã¯ãžã§ãã¬ãŒã¿ãŒãã¹ãã©ããžãŒãšåŒã³ãå€ãã®å Žåãã¹ãã©ããžãŒã倿° st ã«æ ŒçŽããŸããæŽæ°ãçæããã¹ãã©ããžãŒã®äŸãããã€ã瀺ããŸãã >>> from hypothesis import strategies as st >>> st.integers().example() -43489276822011488813107857396380363774 >>> st.integers().example() 1944533851 >>> st.integers().example() 3 >>> st.integers().example() -6029 >>> st.integers().example() -3157022535735084108 >>> st.integers(1,500).example() 271 >>> st.integers(1,500).example() 18 >>> st.integers(1,500).example() 20 >>> st.integers(1,500).example() 350 >>> st.integers(1,500).example() 89 Hypothesis ã«ã¯ãã«ã¹ã¿ã ããŒã¿åçšã®ããè€éãªã¹ãã©ããžãŒãä»å±ããŠããŸãã >>> st.emails().example() '^3l@s.K.sM' >>> st.emails().example() '~g0}XGSf|m$6wOgvEI`e~8h@Z.roDeO' >>> st.uuids().example() UUID('ff1fe0e9-c9a7-324d-f04d-c6f7c3fa4059') >>> st.uuids().example() UUID('156c8e91-0ad7-24b0-6e59-0e6b6a114e74') >>> st.complex_numbers() complex_numbers() >>> st.complex_numbers().example() (-inf-infj) >>> st.complex_numbers().example() (nan+352724254975j) >>> st.complex_numbers().example() 0j å°ããªã¹ãã©ããžãŒããè€éãªã¹ãã©ããžãŒãæ§ç¯ããããšãã§ããŸããããšãã°ã lists ã¹ãã©ããžãŒã¯å¥ã®ã¹ãã©ããžãŒãåŒæ°ãšããŠåãåãããã®åŒæ°ã«ãã£ãŠçæããããã®ã®ãªã¹ããæ§ç¯ããŸãã >>> st.lists(st.integers()).example() [297324786, 38] >>> st.lists(st.integers()).example() [13158, 3] >>> st.lists(st.integers()).example() [17, 27825, -25292, 30419, -8472, -30306, 6151414495842486117, 1264487630263387308, -10877, 1076876455, -10851] >>> st.lists(st.booleans()).example() [False, False, False, False, True, False, False, False, True, False] >>> st.lists(st.booleans()).example() [False, False, True, True] >>> st.lists(st.booleans()).example() Kiro ã§ã®ããããã£ããŒã¹ãã¹ã çŸåšãKiro ã¯èŠä»¶ããã¹ãããããã«ãããããã£ãã§ãã¯ã³ãŒããšãžã§ãã¬ãŒã¿ãŒã®äž¡æ¹ãå«ãããããã£ããŒã¹ãã¹ããèªåçã«äœæããŸããå
ã»ã©ã®ä¿¡å·æ©ã®äŸã«æ»ããšãKiro ã¯å
ã»ã©èŠãããããã£ãã§ãã¯ã³ãŒããçæããã ãã§ãªããã¡ãœããã®äžã« @given ã¢ãããŒã·ã§ã³ã远å ãã䜿çšããã 2 ã€ã® Hypothesis ã¹ãã©ããžãŒããªã¹ãããŸãã @given( timing_config=timing_config_strategy(), operations=operation_sequence_strategy() ) def test_safety_invariant_at_most_one_green( timing_config: TimingConfig, operations: list ): 以äžã¯ãKiro ããã®ããããã£ã®ããã«æžããã¹ãã©ããžãŒã§ãããã®ã³ãŒã㯠Hypothesis ã¹ãã©ããžãŒãã¬ãŒã ã¯ãŒã¯ã䜿çšããŠãä¿¡å·æ©ã®é·ç§»ã·ãŒã±ã³ã¹ã«å¯Ÿããã¹ãã©ããžãŒãæ§ç¯ããŸãããã®ã¹ãã©ããžãŒããKiro ãæžãã signal_state_strategy ãªã©ã®ä»ã®ã¹ãã©ããžãŒãåç
§ããŠããããšãããããŸããããã«ãããè€æ°ã®ããããã£ãã¹ãéã§ã³ãŒããå
±æã§ããŸãã # æäœã·ãŒã±ã³ã¹ãçæããã¹ãã©ããžãŒ @st.composite def operation_sequence_strategy(draw): """å¶åŸ¡ã¢ãžã¥ãŒã«ã«å¯ŸããŠå®è¡ããæäœã·ãŒã±ã³ã¹ãçæãã""" operations = [] num_operations = draw(st.integers(min_value=1, max_value=20)) for _ in range(num_operations): op_type = draw(st.sampled_from(['transition', 'emergency_activate', 'emergency_deactivate'])) if op_type == 'transition': direction = draw(direction_strategy) state = draw(signal_state_strategy) operations.append(('transition', direction, state)) elif op_type == 'emergency_activate': direction = draw(direction_strategy) operations.append(('emergency_activate', direction)) else: # emergency_deactivate operations.append(('emergency_deactivate',)) return operations ãã®ãã¹ãã¯ãæšæºç㪠Python ãã¹ããã¬ãŒã ã¯ãŒã¯ã§ãã pytest ãšããã«çµ±åã§ããŸãã pytest ãå®è¡ããããšãHypothesis 㯠100 åã®ãã¹ãã±ãŒã¹ãçæããããããã¹ãŠãããããã£ããã¹ããããšã確èªããŸãã ãã¹ãã®å質ã«ãšã£ãŠãå
¥åçæã¹ãã©ããžãŒãå®éã«å€æ§ãªå
¥åãçæããããšãéèŠã§ãã Tyche ãšããããŒã«ã䜿ã£ãŠããããã®å
¥åãšå®è¡æã«ã«ããŒãããã³ãŒãã調ã¹ãããšã§ãã©ãã ãããŸããã£ãŠããããè©äŸ¡ã§ããŸãã以äžã¯ããžã§ãã¬ãŒã¿ãŒãçæããå
¥åã®ãµã³ãã«ã§ãTyche ã衚瀺ããŠããããã®ã§ãã 以äžã¯ãããããã£ããŒã¹ãã¹ãã«ãã£ãŠå®è¡ãããã³ãŒãã瀺ã Tyche ãçæããèŠèŠåã§ãã50 åã®è©Šè¡åŸã§ãããŸã æ°ããã³ãŒããã¹ãæ¢çŽ¢ããŠããããšãããããŸãã ã³ãŒãã«ãã¬ããžã«ã€ããŠæ³šæç¹ããããŸãããã¹ãã¹ã€ãŒãã®å¹æã枬å®ããéåžžã«äžè¬çãªææšã§ããããã¹ãåè³ªã®æçµçãªå€æåºæºã§ã¯ãããŸãããã³ãŒãã®è¡ãã«ããŒããïŒã€ãŸãå®è¡ããïŒããšã¯ããã®è¡ã®ãã¹ãŠã®åäœãç¶²çŸ
ããããšãæå³ããŸãããããããã£ãã¹ãã¯ç¶²çŸ
çãªææ³ã§ã¯ãªããããããã°ã©ã ã«ãã°ããªãããšãä¿èšŒã§ããŸãããããããã£ããŒã¹ãã¹ããèŠã€ããããªãåäŸãåžžã«ååšããå¯èœæ§ããããŸããããããç§ãã¡ã¯ãããããã£ããŒã¹ãã¹ããåŸæ¥ã®äŸããŒã¹ãã¹ãããããã°ã®çºèŠã«ãããŠå¹æçãªããŒã«ã§ããã仿§ãšãã¹ããããè¯ãçµã³ã€ããããã°ã©ã ã®æ£ããã®åé¡ãå
·äœçã§å®è¡å¯èœãªä»æ§ã®èгç¹ãã衚çŸãããšããéèŠãªã¹ããããèžãã§ãããšèããŠããŸãã åäŸãšçž®å° ãã®èšäºãçµããåã«ãããããã£ããŒã¹ãã¹ãã®æ¬åœã«åœ¹ç«ã€æåŸã®æ©èœã«ã€ããŠè©±ããããšæããŸããããã¯çž®å°ã§ããããããã£ãã¹ãã倱æãããšãããããã£ã倱æãããå
¥åãã€ãŸãåäŸãåŸãããŸããçæ³çã«ã¯ãæå°éã®å
¥åãã€ãŸããã¹ãã倱æãããåé¡ã®æ žå¿ã瀺ãå°ããªäŸã欲ãããšããã§ãã巚倧ãªåäŸã«ã¯åé¡ãšã¯é¢ä¿ã®ãªãäœåãªããŒã¿ãå«ãŸããŠããå¯èœæ§ãé«ãã®ã«å¯Ÿããæå°éã®äŸã¯ãããªãïŒãããŠãããã Kiro ãšãŒãžã§ã³ãïŒãããã°ã©ã ã®å®éã®æ¬ é¥ãç¹å®ãã修埩ããã®ã«åœ¹ç«ã¡ãŸããã»ãšãã©ã®ããããã£ããŒã¹ãã¹ããã¬ãŒã ã¯ãŒã¯ã¯ããçž®å°ããšåŒã°ããããã»ã¹ãéããŠæå°éã®äŸãæäŸããããšããŸãããããã©ã®ããã«æ©èœãããèŠãŠã¿ãŸãããã æ¢çŽ¢æšã«åºã¥ãéåãå®è£
ããŠãããšããŸããããããããæ¬¡ã®ãããªããããã£ãããã§ãããã # ããããã£: ä»»æã®2ã€ã®äºåæ¢çŽ¢æšãçµåãããšã # é©åãªäºåæ¢çŽ¢æšã«ãªãã¹ã @given(left = trees(), right = trees()) def test_union_maintains_invariant(left, right): assert left.union(right).is_bst() ãã®ãã¹ããå®è¡ãããšã次ã®ãããªåºåãåŸããããããããŸããã Falsifying example: left = Node(lhs=Empty(), rhs=Empty(), value=0) right = Node(lhs=Empty(), rhs=Empty(), value=0) ããããããã¯å®éã«ã¯ Hypothesis ãèŠã€ããæåã®å蚌äŸã§ã¯ãããŸããã§ãããHypothesis ã®ãã°ãèŠããšãæåã«å€±æããåäŸã¯å®éã«ã¯æ¬¡ã®ãããªãã®ã§ããã Trying example: test_union( lhs=Node(lhs=Empty(), rhs=Node(lhs=Empty(), rhs=Node(lhs=Empty(), rhs=Empty(), value=30), value=-111), value=-25482), rhs=Node(lhs=Node(lhs=Empty(), rhs=Empty(), value=-26344), rhs=Node(lhs=Empty(), rhs=Node(lhs=Node(lhs=Empty(), rhs=Empty(), value=42), rhs=Node(lhs=Node(lhs=Node(lhs=Empty(), rhs=Empty(), value=6076), rhs=Empty(), value=10768), rhs=Empty(), value=27223), value=121), value=-89), value=-20602), ) ããã¯ãããã°ãããå°é£ãªã±ãŒã¹ã§ãã çž®å°ã¯ã倱æãåŒãèµ·ããç¶ããããšã確èªããªããã倱æããå
¥åãäœç³»çã«åçŽåããŸãã ãã®äŸã§ã¯ãHypothesis ã¯äžèŠãªããŒããåé€ããæŽæ°å€ãæžãããæšæ§é ãåçŽåããŠãæå°éã®ã±ãŒã¹ãèŠã€ããŸãããããã¯ãäž¡æ¹ãšãå€ 0 ãå«ã 2 ã€ã®åäžããŒãæšã§ããããã«ãããè€éãªæšæ§é ã®ãã€ãºãªãã«ãæ žå¿ãšãªãåé¡ãã€ãŸã union æäœãéè€å€ãé©åã«åŠçããŠããªãããšãæããã«ãªããŸãã Kiro ãããããã£ãã¹ããçæããéãåºç€ãšãªã PBT ãã¬ãŒã ã¯ãŒã¯ã®çž®å°æ©èœã掻çšããŸããã€ãŸããéçºäžã«ããããã£ãã¹ãã倱æãããšããããã°ã倧å¹
ã«å®¹æã«ããå®çšçã§æå°éã®åäŸãåŸãããŸãããšãŒãžã§ã³ãã¯ãã®æå°éã®äŸã䜿ã£ãŠæ ¹æ¬åå ãããç°¡åã«çè§£ããä¿®æ£ãææ¡ã§ãã仿§ããã¹ããå®è£
ã®éã«ç·å¯ãªãã£ãŒãããã¯ã«ãŒããäœãåºããŸããKiro ãå®è£
ã¯æ£ãããããããªãã仿§ãšäžèŽããªãããšãçºèŠããå ŽåããŸã㯠AI ãçæããã³ãŒããèªæã§ãªãæ¹æ³ã§æ ¹æ¬çã«ééã£ãŠããããã«èŠããå ŽåãKiro ã¯ãããéçºè
ã«æç€ºããŠéžæãæ±ããŸããã³ãŒããä¿®æ£ãããã仿§ãä¿®æ£ããããPBT ãä¿®æ£ãããã§ããããããããšã§ã人éã®å€æãš AI ããã³ PBT ãçµã¿åãããŠãå®è£
ãéçºè
ã®æå³ã«ããæç¢ºã«åãããŸãã ãŸãšã Kiro ãããããã£ããŒã¹ãã¹ããæ¡çšããããšã§ãAI ã³ãŒãã£ã³ã°ã¿ã¹ã¯ã«ãããæ£ããã®èãæ¹ã倧ããå€ãããŸããåã
ã®äŸããã§ãã¯ããããšãããå
¥å空éå
šäœã«ãããæ®éçãªããããã£ãæ€èšŒããããšãžãšç§»è¡ããŠããŸããèªç¶èšèªã®ä»æ§ãå®è¡å¯èœãªããããã£ã«èªåçã«å€æããå
æ¬çãªãã¹ãã±ãŒã¹ãçæããããšã§ãKiro 㯠AI ãšãŒãžã§ã³ããšäººéã®éçºè
ã®äž¡æ¹ãããä¿¡é Œæ§ã®é«ããœãããŠã§ã¢ãæ§ç¯ããã®ã«åœ¹ç«ã€åŒ·åãªãã£ãŒãããã¯ã«ãŒããäœãåºããŸãããã®ã¢ãããŒãã¯ãåŸæ¥ã®ãã¹ããèŠéããã°ãèŠã€ããã ãã§ãªããèŠä»¶ãšããããæ€èšŒãããã¹ãã®éã«æç¢ºã§è¿œè·¡å¯èœãªãªã³ã¯ãç¶æããŸããPBT ã¯ãã¹ãŠã®ãã°ã®äžåšãä¿èšŒã§ããŸããããäŸããŒã¹ãã¹ãã ãããã倧å¹
ã«åŒ·åãªæ£ããã®èšŒæ ãæäŸãã仿§é§åéçºã«ãšã£ãŠäžå¯æ¬ ãªããŒã«ãšãªã£ãŠããŸãã LLM ãšããããã£ããŒã¹ãã¹ãã«é¢ãã詳现ã«ã€ããŠã¯ã以äžã®ç ç©¶è«æãåç
§ããŠãã ããã QuickCheck Can LLMs write good PBTs Agentic PBT Use Property-Based Testing to Bridge LLM Code Generation and Validation Tyche Kiro ãããŠã³ããŒã ããŠã 仿§ ã§ ããããã£ããŒã¹ãã¹ã ã詊ããŠã¿ãŠãã ããã 翻蚳㯠AppDev Consultant ã®å®è³ç¥ãæ
åœããŸããã