{"abstract":"A player cannot lead QS before hearts are broken.","category":"Card game rule engines","checks":8,"contract":"Input [hand, trick_so_far, hearts_broken, first_trick]. Leading: on the first trick the holder of 2C must lead it; hearts may not be led before they are broken unless the hand is all hearts (QS may be led). Following: follow the led suit if possible; on the first trick a void player may not discard hearts or QS unless nothing else is held. Return legal cards in hand order.","evaluation_group":"w2-card-game-rule-engines-hearts-legal","failed_approach":"Returning the filtered list unconditionally leaves an all-heart hand with no legal lead.","family":"w2-card-game-rule-engines-hearts-legal-unbroken-hearts-lead","id":"FA-83366","implementations":{"attempt":{"sha256":"7efb9f560bf643e5d5e48f9647a3c060f6fa12a94adf3a32749c2a0d433c22d0","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\n\nN = 1\nobservations = []\ndef solve(x):\n    hand, trick, broken, first = x\n    def penalty(c):\n        return c[1] == 'H' or c == 'QS'\n    if not trick:\n        if first and '2C' in hand:\n            return ['2C']\n        if not broken:\n            safe = [c for c in hand if c[1] != 'H']\n            return safe\n        return list(hand)\n    suit = trick[0][1]\n    follow = [c for c in hand if c[1] == suit]\n    if follow:\n        return follow\n    if first:\n        clean = [c for c in hand if not penalty(c)]\n        if clean:\n            return clean\n    return list(hand)\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\nfixtures = [[[[['6H', 'AH', 'JC'], ['7S', 'KC'], False, False], ['6H', 'AH', 'JC']], [[['5H', '6C', '7C', '9C', 'KD', 'QC', 'TS'], ['3S', '8S', '2S'], False, True], ['TS']], [[['2C', 'JS'], [], True, True], ['2C']], [[['AS', 'TH'], [], False, True], ['AS']], [[['2C', '8C', 'AS', 'KH'], [], True, False], ['2C', '8C', 'AS', 'KH']], [[['2H', '3C', '3H', 'QC'], [], True, False], ['2H', '3C', '3H', 'QC']], [[['3D', '9H', 'QS'], [], False, False], ['3D', 'QS']], [[['3H'], [], False, False], ['3H']]], [[[['2S', 'KS', 'TH'], ['JC', '2C'], False, True], ['2S', 'KS']], [[['2S'], ['QS'], False, False], ['2S']], [[['2H', '6C', '7H', '9C', '9S'], ['QC', '2C', '6H'], False, False], ['6C', '9C']], [[['3H', '5D', '9D'], ['3C'], True, False], ['3H', '5D', '9D']], [[['AH', 'JH', 'TH'], ['9C', 'TS'], True, False], ['AH', 'JH', 'TH']], [[['2H', '6S', '8D', 'AC', 'JD', 'QH'], ['4H', 'KC', '3S'], True, True], ['2H', 'QH']], [[['2H', '4C', 'AH', 'AS', 'KC', 'QS', 'TS'], [], False, False], ['4C', 'AS', 'KC', 'QS', 'TS']], [[['3H', '5H'], [], False, False], ['3H', '5H']]], [[[['5C'], [], False, True], ['5C']], [[['5D', 'JH'], ['QH', 'KC', '8S'], True, False], ['JH']], [[['4H'], [], True, True], ['4H']], [[['3D', '5C'], [], True, False], ['3D', '5C']], [[['2H', '5H'], ['KS', '9C', '7H'], False, False], ['2H', '5H']], [[['8C', 'AC', 'KD', 'TS'], [], False, True], ['8C', 'AC', 'KD', 'TS']], [[['4H', '6D', '7C', '7S', '9D', 'QS', 'TD'], [], False, True], ['6D', '7C', '7S', '9D', 'QS', 'TD']], [[['4H'], [], False, False], ['4H']]], [[[['2H', '6C', '6D', '7C', 'KS', 'QC'], ['3C', '7D'], True, False], ['6C', '7C', 'QC']], [[['AC'], ['2C', '8D'], False, False], ['AC']], [[['2S', '6D'], [], True, False], ['2S', '6D']], [[['5D', 'AS'], ['5S', '3C'], False, False], ['AS']], [[['3C', '4S', '6S', '7D', '8H', 'AS', 'KC', 'KH'], [], False, False], ['3C', '4S', '6S', '7D', 'AS', 'KC']], [[['2H', '3D', '5H', '9D', 'JC', 'KS', 'QD'], [], False, False], ['3D', '9D', 'JC', 'KS', 'QD']], [[['7H'], [], False, False], ['7H']], [[['QS', 'AD'], [], False, False], ['QS', 'AD']]], [[[['4D', '6S', '9C', 'JD'], ['9H', 'AS', 'KC'], False, True], ['4D', '6S', '9C', 'JD']], [[['3S', '7D'], [], False, True], ['3S', '7D']], [[['2D', '3H', '3S', '4S', '6D', 'QC', 'QH'], ['6C', 'AH'], False, False], ['QC']], [[['3C', '6D', 'TH'], [], False, False], ['3C', '6D']], [[['3D', '5C', '6S', '7H', 'KH', 'TH', 'TS'], [], False, False], ['3D', '5C', '6S', 'TS']], [[['7D', '8H', 'AD', 'AS'], ['AH', '4H', '9C'], True, True], ['8H']], [[['3C', '3S', '4H', 'KC', 'QS'], [], False, False], ['3C', '3S', 'KC', 'QS']], [[['3H'], [], False, False], ['3H']]]]\nfor i, (args, expected) in enumerate(fixtures[N-1]):\n    check(\"legal plays case %d\" % i, solve(args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"},"broken":{"sha256":"c199894d5b9cf2ab23f6bfc98526324e571367c74764009fad914ac5329b9b8f","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\n\nN = 1\nobservations = []\ndef solve(x):\n    hand, trick, broken, first = x\n    def penalty(c):\n        return c[1] == 'H' or c == 'QS'\n    if not trick:\n        if first and '2C' in hand:\n            return ['2C']\n        if not broken:\n            safe = [c for c in hand if not penalty(c)]\n            if safe:\n                return safe\n        return list(hand)\n    suit = trick[0][1]\n    follow = [c for c in hand if c[1] == suit]\n    if follow:\n        return follow\n    if first:\n        clean = [c for c in hand if not penalty(c)]\n        if clean:\n            return clean\n    return list(hand)\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\nfixtures = [[[[['6H', 'AH', 'JC'], ['7S', 'KC'], False, False], ['6H', 'AH', 'JC']], [[['5H', '6C', '7C', '9C', 'KD', 'QC', 'TS'], ['3S', '8S', '2S'], False, True], ['TS']], [[['2C', 'JS'], [], True, True], ['2C']], [[['AS', 'TH'], [], False, True], ['AS']], [[['2C', '8C', 'AS', 'KH'], [], True, False], ['2C', '8C', 'AS', 'KH']], [[['2H', '3C', '3H', 'QC'], [], True, False], ['2H', '3C', '3H', 'QC']], [[['3D', '9H', 'QS'], [], False, False], ['3D', 'QS']], [[['3H'], [], False, False], ['3H']]], [[[['2S', 'KS', 'TH'], ['JC', '2C'], False, True], ['2S', 'KS']], [[['2S'], ['QS'], False, False], ['2S']], [[['2H', '6C', '7H', '9C', '9S'], ['QC', '2C', '6H'], False, False], ['6C', '9C']], [[['3H', '5D', '9D'], ['3C'], True, False], ['3H', '5D', '9D']], [[['AH', 'JH', 'TH'], ['9C', 'TS'], True, False], ['AH', 'JH', 'TH']], [[['2H', '6S', '8D', 'AC', 'JD', 'QH'], ['4H', 'KC', '3S'], True, True], ['2H', 'QH']], [[['2H', '4C', 'AH', 'AS', 'KC', 'QS', 'TS'], [], False, False], ['4C', 'AS', 'KC', 'QS', 'TS']], [[['3H', '5H'], [], False, False], ['3H', '5H']]], [[[['5C'], [], False, True], ['5C']], [[['5D', 'JH'], ['QH', 'KC', '8S'], True, False], ['JH']], [[['4H'], [], True, True], ['4H']], [[['3D', '5C'], [], True, False], ['3D', '5C']], [[['2H', '5H'], ['KS', '9C', '7H'], False, False], ['2H', '5H']], [[['8C', 'AC', 'KD', 'TS'], [], False, True], ['8C', 'AC', 'KD', 'TS']], [[['4H', '6D', '7C', '7S', '9D', 'QS', 'TD'], [], False, True], ['6D', '7C', '7S', '9D', 'QS', 'TD']], [[['4H'], [], False, False], ['4H']]], [[[['2H', '6C', '6D', '7C', 'KS', 'QC'], ['3C', '7D'], True, False], ['6C', '7C', 'QC']], [[['AC'], ['2C', '8D'], False, False], ['AC']], [[['2S', '6D'], [], True, False], ['2S', '6D']], [[['5D', 'AS'], ['5S', '3C'], False, False], ['AS']], [[['3C', '4S', '6S', '7D', '8H', 'AS', 'KC', 'KH'], [], False, False], ['3C', '4S', '6S', '7D', 'AS', 'KC']], [[['2H', '3D', '5H', '9D', 'JC', 'KS', 'QD'], [], False, False], ['3D', '9D', 'JC', 'KS', 'QD']], [[['7H'], [], False, False], ['7H']], [[['QS', 'AD'], [], False, False], ['QS', 'AD']]], [[[['4D', '6S', '9C', 'JD'], ['9H', 'AS', 'KC'], False, True], ['4D', '6S', '9C', 'JD']], [[['3S', '7D'], [], False, True], ['3S', '7D']], [[['2D', '3H', '3S', '4S', '6D', 'QC', 'QH'], ['6C', 'AH'], False, False], ['QC']], [[['3C', '6D', 'TH'], [], False, False], ['3C', '6D']], [[['3D', '5C', '6S', '7H', 'KH', 'TH', 'TS'], [], False, False], ['3D', '5C', '6S', 'TS']], [[['7D', '8H', 'AD', 'AS'], ['AH', '4H', '9C'], True, True], ['8H']], [[['3C', '3S', '4H', 'KC', 'QS'], [], False, False], ['3C', '3S', 'KC', 'QS']], [[['3H'], [], False, False], ['3H']]]]\nfor i, (args, expected) in enumerate(fixtures[N-1]):\n    check(\"legal plays case %d\" % i, solve(args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"},"fixed":{"sha256":"9de8bba53bdbb9ee838a7242a2914ca7a3c7583a16fa7df2c14238baa32d87a6","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\n\nN = 1\nobservations = []\ndef solve(x):\n    hand, trick, broken, first = x\n    def penalty(c):\n        return c[1] == 'H' or c == 'QS'\n    if not trick:\n        if first and '2C' in hand:\n            return ['2C']\n        if not broken:\n            safe = [c for c in hand if c[1] != 'H']\n            if safe:\n                return safe\n        return list(hand)\n    suit = trick[0][1]\n    follow = [c for c in hand if c[1] == suit]\n    if follow:\n        return follow\n    if first:\n        clean = [c for c in hand if not penalty(c)]\n        if clean:\n            return clean\n    return list(hand)\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\nfixtures = [[[[['6H', 'AH', 'JC'], ['7S', 'KC'], False, False], ['6H', 'AH', 'JC']], [[['5H', '6C', '7C', '9C', 'KD', 'QC', 'TS'], ['3S', '8S', '2S'], False, True], ['TS']], [[['2C', 'JS'], [], True, True], ['2C']], [[['AS', 'TH'], [], False, True], ['AS']], [[['2C', '8C', 'AS', 'KH'], [], True, False], ['2C', '8C', 'AS', 'KH']], [[['2H', '3C', '3H', 'QC'], [], True, False], ['2H', '3C', '3H', 'QC']], [[['3D', '9H', 'QS'], [], False, False], ['3D', 'QS']], [[['3H'], [], False, False], ['3H']]], [[[['2S', 'KS', 'TH'], ['JC', '2C'], False, True], ['2S', 'KS']], [[['2S'], ['QS'], False, False], ['2S']], [[['2H', '6C', '7H', '9C', '9S'], ['QC', '2C', '6H'], False, False], ['6C', '9C']], [[['3H', '5D', '9D'], ['3C'], True, False], ['3H', '5D', '9D']], [[['AH', 'JH', 'TH'], ['9C', 'TS'], True, False], ['AH', 'JH', 'TH']], [[['2H', '6S', '8D', 'AC', 'JD', 'QH'], ['4H', 'KC', '3S'], True, True], ['2H', 'QH']], [[['2H', '4C', 'AH', 'AS', 'KC', 'QS', 'TS'], [], False, False], ['4C', 'AS', 'KC', 'QS', 'TS']], [[['3H', '5H'], [], False, False], ['3H', '5H']]], [[[['5C'], [], False, True], ['5C']], [[['5D', 'JH'], ['QH', 'KC', '8S'], True, False], ['JH']], [[['4H'], [], True, True], ['4H']], [[['3D', '5C'], [], True, False], ['3D', '5C']], [[['2H', '5H'], ['KS', '9C', '7H'], False, False], ['2H', '5H']], [[['8C', 'AC', 'KD', 'TS'], [], False, True], ['8C', 'AC', 'KD', 'TS']], [[['4H', '6D', '7C', '7S', '9D', 'QS', 'TD'], [], False, True], ['6D', '7C', '7S', '9D', 'QS', 'TD']], [[['4H'], [], False, False], ['4H']]], [[[['2H', '6C', '6D', '7C', 'KS', 'QC'], ['3C', '7D'], True, False], ['6C', '7C', 'QC']], [[['AC'], ['2C', '8D'], False, False], ['AC']], [[['2S', '6D'], [], True, False], ['2S', '6D']], [[['5D', 'AS'], ['5S', '3C'], False, False], ['AS']], [[['3C', '4S', '6S', '7D', '8H', 'AS', 'KC', 'KH'], [], False, False], ['3C', '4S', '6S', '7D', 'AS', 'KC']], [[['2H', '3D', '5H', '9D', 'JC', 'KS', 'QD'], [], False, False], ['3D', '9D', 'JC', 'KS', 'QD']], [[['7H'], [], False, False], ['7H']], [[['QS', 'AD'], [], False, False], ['QS', 'AD']]], [[[['4D', '6S', '9C', 'JD'], ['9H', 'AS', 'KC'], False, True], ['4D', '6S', '9C', 'JD']], [[['3S', '7D'], [], False, True], ['3S', '7D']], [[['2D', '3H', '3S', '4S', '6D', 'QC', 'QH'], ['6C', 'AH'], False, False], ['QC']], [[['3C', '6D', 'TH'], [], False, False], ['3C', '6D']], [[['3D', '5C', '6S', '7H', 'KH', 'TH', 'TS'], [], False, False], ['3D', '5C', '6S', 'TS']], [[['7D', '8H', 'AD', 'AS'], ['AH', '4H', '9C'], True, True], ['8H']], [[['3C', '3S', '4H', 'KC', 'QS'], [], False, False], ['3C', '3S', 'KC', 'QS']], [[['3H'], [], False, False], ['3H']]]]\nfor i, (args, expected) in enumerate(fixtures[N-1]):\n    check(\"legal plays case %d\" % i, solve(args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"}},"limitations":"A bounded toy rule contract stated explicitly in the contract field; cards are two-character codes (rank, suit). Not a complete implementation of any published rulebook or casino table rules. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.","method":"Deterministic executable model with adversarial boundary fixtures.","provenance":{"created_by":"Failure Map","dependencies":"Python standard library","family":"w2-card-game-rule-engines-hearts-legal-unbroken-hearts-lead","generated_at":"2026-09-29T14:50:20.832696+00:00","license":"CC0-1.0","python":"3.12.14","seed":1,"split":"open-access"},"relevance":"Card-game engines, scoring apps and online tables apply this rule automatically on every hand.","repair":"Before hearts are broken only heart leads are restricted.","root_cause":"The lead filter reuses the penalty-card predicate.","sha256":"e564d4dd3f7a123a3b19146e1a1ebc969820993113b0ff71c7285f2b7cc02b18","title":"Unbroken-hearts lead restriction also forbids the queen of spades · case 01","variant":1,"variant_policy":"Five numbered records share a model and may reuse boundary fixtures.","verification":{"attempt":{"elapsed_ms":39.373,"exit_code":1,"observations":[{"actual":["6H","AH","JC"],"check":"legal plays case 0","expected":["6H","AH","JC"],"passed":true},{"actual":["TS"],"check":"legal plays case 1","expected":["TS"],"passed":true},{"actual":["2C"],"check":"legal plays case 2","expected":["2C"],"passed":true},{"actual":["AS"],"check":"legal plays case 3","expected":["AS"],"passed":true},{"actual":["2C","8C","AS","KH"],"check":"legal plays case 4","expected":["2C","8C","AS","KH"],"passed":true},{"actual":["2H","3C","3H","QC"],"check":"legal plays case 5","expected":["2H","3C","3H","QC"],"passed":true},{"actual":["3D","QS"],"check":"legal plays case 6","expected":["3D","QS"],"passed":true},{"actual":[],"check":"legal plays case 7","expected":["3H"],"passed":false}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"legal plays case 0\", \"actual\": [\"6H\", \"AH\", \"JC\"], \"expected\": [\"6H\", \"AH\", \"JC\"], \"passed\": true}, {\"check\": \"legal plays case 1\", \"actual\": [\"TS\"], \"expected\": [\"TS\"], \"passed\": true}, {\"check\": \"legal plays case 2\", \"actual\": [\"2C\"], \"expected\": [\"2C\"], \"passed\": true}, {\"check\": \"legal plays case 3\", \"actual\": [\"AS\"], \"expected\": [\"AS\"], \"passed\": true}, {\"check\": \"legal plays case 4\", \"actual\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"expected\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"passed\": true}, {\"check\": \"legal plays case 5\", \"actual\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"expected\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"passed\": true}, {\"check\": \"legal plays case 6\", \"actual\": [\"3D\", \"QS\"], \"expected\": [\"3D\", \"QS\"], \"passed\": true}, {\"check\": \"legal plays case 7\", \"actual\": [], \"expected\": [\"3H\"], \"passed\": false}], \"passed\": false}\n"},"broken":{"elapsed_ms":38.637,"exit_code":1,"observations":[{"actual":["6H","AH","JC"],"check":"legal plays case 0","expected":["6H","AH","JC"],"passed":true},{"actual":["TS"],"check":"legal plays case 1","expected":["TS"],"passed":true},{"actual":["2C"],"check":"legal plays case 2","expected":["2C"],"passed":true},{"actual":["AS"],"check":"legal plays case 3","expected":["AS"],"passed":true},{"actual":["2C","8C","AS","KH"],"check":"legal plays case 4","expected":["2C","8C","AS","KH"],"passed":true},{"actual":["2H","3C","3H","QC"],"check":"legal plays case 5","expected":["2H","3C","3H","QC"],"passed":true},{"actual":["3D"],"check":"legal plays case 6","expected":["3D","QS"],"passed":false},{"actual":["3H"],"check":"legal plays case 7","expected":["3H"],"passed":true}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"legal plays case 0\", \"actual\": [\"6H\", \"AH\", \"JC\"], \"expected\": [\"6H\", \"AH\", \"JC\"], \"passed\": true}, {\"check\": \"legal plays case 1\", \"actual\": [\"TS\"], \"expected\": [\"TS\"], \"passed\": true}, {\"check\": \"legal plays case 2\", \"actual\": [\"2C\"], \"expected\": [\"2C\"], \"passed\": true}, {\"check\": \"legal plays case 3\", \"actual\": [\"AS\"], \"expected\": [\"AS\"], \"passed\": true}, {\"check\": \"legal plays case 4\", \"actual\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"expected\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"passed\": true}, {\"check\": \"legal plays case 5\", \"actual\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"expected\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"passed\": true}, {\"check\": \"legal plays case 6\", \"actual\": [\"3D\"], \"expected\": [\"3D\", \"QS\"], \"passed\": false}, {\"check\": \"legal plays case 7\", \"actual\": [\"3H\"], \"expected\": [\"3H\"], \"passed\": true}], \"passed\": false}\n"},"fixed":{"elapsed_ms":39.809,"exit_code":0,"observations":[{"actual":["6H","AH","JC"],"check":"legal plays case 0","expected":["6H","AH","JC"],"passed":true},{"actual":["TS"],"check":"legal plays case 1","expected":["TS"],"passed":true},{"actual":["2C"],"check":"legal plays case 2","expected":["2C"],"passed":true},{"actual":["AS"],"check":"legal plays case 3","expected":["AS"],"passed":true},{"actual":["2C","8C","AS","KH"],"check":"legal plays case 4","expected":["2C","8C","AS","KH"],"passed":true},{"actual":["2H","3C","3H","QC"],"check":"legal plays case 5","expected":["2H","3C","3H","QC"],"passed":true},{"actual":["3D","QS"],"check":"legal plays case 6","expected":["3D","QS"],"passed":true},{"actual":["3H"],"check":"legal plays case 7","expected":["3H"],"passed":true}],"passed":true,"stderr":"","stdout":"{\"observations\": [{\"check\": \"legal plays case 0\", \"actual\": [\"6H\", \"AH\", \"JC\"], \"expected\": [\"6H\", \"AH\", \"JC\"], \"passed\": true}, {\"check\": \"legal plays case 1\", \"actual\": [\"TS\"], \"expected\": [\"TS\"], \"passed\": true}, {\"check\": \"legal plays case 2\", \"actual\": [\"2C\"], \"expected\": [\"2C\"], \"passed\": true}, {\"check\": \"legal plays case 3\", \"actual\": [\"AS\"], \"expected\": [\"AS\"], \"passed\": true}, {\"check\": \"legal plays case 4\", \"actual\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"expected\": [\"2C\", \"8C\", \"AS\", \"KH\"], \"passed\": true}, {\"check\": \"legal plays case 5\", \"actual\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"expected\": [\"2H\", \"3C\", \"3H\", \"QC\"], \"passed\": true}, {\"check\": \"legal plays case 6\", \"actual\": [\"3D\", \"QS\"], \"expected\": [\"3D\", \"QS\"], \"passed\": true}, {\"check\": \"legal plays case 7\", \"actual\": [\"3H\"], \"expected\": [\"3H\"], \"passed\": true}], \"passed\": true}\n"}},"verified":true,"visibility":"public"}