diff --git a/.agents/skills/atlas/assets/seed/catalog.json b/.agents/skills/atlas/assets/seed/catalog.json
index b7f7a61c1..e616e8ed0 100644
--- a/.agents/skills/atlas/assets/seed/catalog.json
+++ b/.agents/skills/atlas/assets/seed/catalog.json
@@ -1 +1 @@
-{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
+{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
diff --git a/.agents/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json b/.agents/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
new file mode 100644
index 000000000..9e566e7c5
--- /dev/null
+++ b/.agents/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
@@ -0,0 +1 @@
+{"citations":[{"path":"docs/coordination/2026-09-29-coordination-v2-board-design.md","repository":"FS-GG/.github","revision":"3ced04fad887e9840bfcb893834020ece4b2424a","sha256":"f3d8fa3da3bb6b2156e6337e12a4b9bfe44d91ff621c96d0c608249cfc5dcc95"},{"path":"tools/BoardV2Import/Program.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"f154be5f98b6a3845ac73c94e50c441400720a3fc654b8483ce23a1633963428"},{"path":"src/FS.GG.Coord.GitHub/V2Projection.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"c6c4907b54028322b13d112e08f8050482c80165fb359f475f3e595c8ed05c96"},{"path":"tests/coord-board-v2-cli-join/INSPECT.md","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"16f754671ed4e94051b230595e3c46b148a4f696bb8f8aa850c059675c9e3403"}],"conflictsWith":[],"id":"github/programme-binding-custody-recovery","kind":"decision","recordedAt":"2026-10-19T08:55:14Z","repository":"FS-GG/.github","schema":"fsgg.atlas/1","status":"recorded","summary":"Programme/root accepts host receipt6262652143 and independent MATCH6262659355 for the5526-byte private archive: exclusive0600host copy, separate0600client restore, full-byte/hash/manifest/pair readback and file/parent fsync. Home retains the exact archive and proof in ~eugen/.local/state/v3-storage/session-recovery-20261019/ as programme-binding-pairs-20261019-0758.tar.gz until explicitrootdisposition. This host-owned0700ext4 directory is NOT mounted into the client; restoration uses the existing bounded private copy/readback route. Host disk loss, off-machine backup, power-loss behavior and actual client replacement remain unqualified. The original lost directory was outside the persistent mount. The telemetry spool remains dedicated to telemetry.\n\nClient staging ~/.local/share/fs-gg-private/programme-custody-20261019-0756/ is volatile, not sufficient custody. The archive holds both distinct new binding4/schema2 and binding5/schema3 original pairs with their exact templates/payloads and closed manifest, selecting22current issues (previous21plus4682), excluding threevisible members. Recovery retrieves this Atlas ID, reconciles4516receipt and4682ownership, restores to a NEW restrictive path, verifies the exact archive/manifest/commitments, and preserves all originals. Public Atlas/Git never holds private identities, nonce/payload, journals, credentials or runtime assets.\n\nPR4690 protected041a60cb carries the new4 commitment. Actual authenticated installed107 inspection2 exits0 within270seconds:22Current sources,25complete memberships, no population/membership/repository gaps,0mutations.21healthVerified and4682Unknown solelypreservedunsetObservation; read/planning complete. Independent review accepts this bounded fresh4 reader baseline. The final runtime file differs from its original only by protected populationRevision. It is not scheduling authority, UI/product acceptance or executed rollback. Constructor9772/artifact430d, publishedadapter75ab/artifact7ab and protected population revision remain distinct authenticated axes; fresh public107archive comparison matches all82installed payload members.\n\nThe successor candidate selects the separately host-custodied5commitment, not installed adoption. Actual pre-activation inspection3 with current protected4 source rejects5private commitment before issue attempts,0mutations. An earlier draft-source attempt failed canonical acquisition and is retained as setupfailure, not causal proof. Installed5positive qualification must follow its exact protected revision. Real bounded rollback must restore4public commitment through normal source delivery and derive an exclusive runtime binding at that protected revision preserving originalnonce/payload; separately restore/requalify5. UI/product/continuation and actualrestart/rollback remain open. Preserve original20-row history unavailable,439inherited/46later Unknown holds unreleased and reported25+5nativeeffects unreconciled without journals. Current metadata never settles those originals; no write replay or receipt reconstruction is selected. Canonical work-board owns4682/4641continuation.\n\nSuperseding qualification findings: after protected5 delivery4691/a0e392c8, actual installed107 inspection3 of all22 reaches500 requests after187.79s,18Current/4Unknown, zero mutations; final barriers refuse. Source-only108 combines successor membership/planning reads with fresh schema, full pagination, exact identities/options and unchanged500/270 limits. Projection125/125 and CLI75/75 pass; unchanged old source with the same22-item regression fails at exactly500sends/exit3. Independent reader review passed. This establishes causal source repair, not installed108 acceptance.\n\nActual public Creator017 all89members match its release, but fresh Rendering fails before target creation: packaged adapter8fb92b18 differs from published107adapter7ab62708. Strict physical identity stays. Bounded Astra-high plan selects promoted108 original full dependency closure reused by prospectiveCreator018; source-only compilation is separate, real108 pin must be absent until publication, and018 candidate/publisher must refuse without it. No fake digests, compiler-rebuild substitute or017replay. Existing frozen016/099 history remains immutable.\n\nUser visual UI check passed2026-10-19 and root accepts that scoped human evidence; no repeat UI check is required. The earlier statement that UI is open is superseded only for that scope. Actual published108/018, installed instruction/caller qualification, product journeys, programme continuation and real restart/rollback remain open. Work-board remains canonical start/continuation, owner4682 under4641. Current private failure/test reports remain client-local; root owns their durable evidence capture gap. Host-held originalpair archive remains retained, with no new disk-loss or restart qualification.","supersedes":["e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d"],"tags":["coordination","binding","custody","recovery","enrollment","atlas","qualification"],"title":"Retained pairs and passed visual check leave successor request budget and Creator artifact identity to qualify"}
diff --git a/.agents/skills/publishing-and-deployment/SKILL.md b/.agents/skills/publishing-and-deployment/SKILL.md
index 903ddde8f..99b0e41fc 100644
--- a/.agents/skills/publishing-and-deployment/SKILL.md
+++ b/.agents/skills/publishing-and-deployment/SKILL.md
@@ -34,9 +34,9 @@ Registry release inventory: 18 package-bearing contracts across 9 producers; 16
| `game` | `game-scene-adapter` | `0.17.0` | `0.17.0` | `game:0.17.0` | FS.GG.Game.Render package — Adapter (sim-state -> FS.GG.UI.Scene drawables) |
| `audio` | `fs-gg-audio` | `0.6.0` | `0.6.0` | `audio:0.6.0` | FS.GG.Audio.Core/.Host/.Engine/.Elmish/.WebBrowser public .fsi surfaces — AudioEffect vocabulary + IAudioBackend/IMixingBackend seam + mixing Engine + Audio.Cmd Elmish bridge + browser Web Audio host |
| `net` | `fs-gg-net` | `0.6.0` | `0.6.0` | `net:0.6.0` | FS.GG.Net.Core/.WebSocket/.WebSocket.Server/.Protobuf/.Grpc/.Elmish public .fsi surfaces — ITransport/IMessageChannel seam + Sequential/Multiplexed correlation + serve/ServerEcho + WebSocket client/server transport + Google.Protobuf/protobuf-net codecs + gRPC lifecycle bridge + Elmish Cmd/Sub |
-| `github` | `coord-engine` | `0.107.0` | `0.107.0` | `github:0.107.0` | the `fsgg-coord-engine` CLI verb surface (claim/take/batch/who/widen/set-paths/say/landable/done/release/flush/…) + its exit-code contract, emitted from src/FS.GG.Coord.Core/Protocol.fs; shipped as the FS.GG.Coord.Cli dotnet tool |
+| `github` | `coord-engine` | `0.108.0` | `0.107.0` | `github:0.107.0` | the `fsgg-coord-engine` CLI verb surface (claim/take/batch/who/widen/set-paths/say/landable/done/release/flush/…) + its exit-code contract, emitted from src/FS.GG.Coord.Core/Protocol.fs; shipped as the FS.GG.Coord.Cli dotnet tool |
| `github` | `telemetry-host` | `0.7.0` | `0.7.0` | `github:0.7.0` | optional Linux x64 FS.GG.Telemetry.Host dotnet tool — authenticated workspace-scoped ingestion, private dashboard, protected native capture and bounded learning export; independently versioned from the github coordination coherent set |
-| `github` | `new-sdd-workspace` | `0.17.0` | `0.17.0` | `github:0.17.0` | the `new-sdd-workspace` scaffolder CLI (package FS.GG.NewSddWorkspace) — one-command full-stack SDD workspace creation, wrapping the FS.GG.Templates `rendering` provider (ADR-0016); shipped as a dotnet tool |
+| `github` | `new-sdd-workspace` | `0.18.0` | `0.17.0` | `github:0.17.0` | the `new-sdd-workspace` scaffolder CLI (package FS.GG.NewSddWorkspace) — one-command full-stack SDD workspace creation, wrapping the FS.GG.Templates `rendering` provider (ADR-0016); shipped as a dotnet tool |
| `templates` | `fs-gg-workspace-template` | `0.19.0` | `0.19.0` | `templates:0.19.0` | FS.GG.Workspace.Template package, eight template configurations and seven `dotnet new` selectors: workspace-provider identities — `fs-gg-console` (provider `console` — minimal F# executable, no npm lane, ADR-0072 §2); `fs-gg-web` (provider `web` — F# ASP.NET Core + plain TypeScript/Vite website, ADR-0071 §3); `fs-gg-fable-game` (provider `fable-game` — F# ASP.NET Core + Fable/Elmish game client, SignalR for connection-oriented real-time traffic + plain HTTP endpoints with explicit versioned DTOs for typed request/response per ADR-0073, consuming the published `fs-gg-game-core-fable-lockstep-v1` profile per ADR-0069); `fs-gg-fable-bindings` (provider `fable-bindings` — Fable interop library over an exactly pinned npm package/declaration closure, ADR-0072 §3, first proved by the unreleased EHotwagner/babylonjsBindings reference) — plus `fs-gg-governance`, the separately registered pre-existing governance overlay template folded into this package at the same rename; `fs-gg-project-knowledge` and `fs-gg-python` are also already packaged. The current and legacy fable-game configurations share one selector. |
| `game` | `game-skills` | `0.9.0` | `0.9.0` | `game:0.9.0` | FS.GG.Game.Skills 0.9.0 package — owner-sourced game, Fable, replay and rules guidance with schema-v2 per-file digests and workspace bundle predicates; embedded by the SDD 1.8 receiver |
| `rendering` | `rendering-skills` | `0.2.0` | `0.2.0` | `rendering:0.2.0` | FS.GG.Rendering.Skills 0.2.0 package — owner-sourced SVG assets/performance and Fable workspace guidance with schema-v2 per-file digests and bundle predicates; embedded by the SDD 1.8 receiver |
diff --git a/.claude/skills/atlas/assets/seed/catalog.json b/.claude/skills/atlas/assets/seed/catalog.json
index b7f7a61c1..e616e8ed0 100644
--- a/.claude/skills/atlas/assets/seed/catalog.json
+++ b/.claude/skills/atlas/assets/seed/catalog.json
@@ -1 +1 @@
-{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
+{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
diff --git a/.claude/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json b/.claude/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
new file mode 100644
index 000000000..9e566e7c5
--- /dev/null
+++ b/.claude/skills/atlas/assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
@@ -0,0 +1 @@
+{"citations":[{"path":"docs/coordination/2026-09-29-coordination-v2-board-design.md","repository":"FS-GG/.github","revision":"3ced04fad887e9840bfcb893834020ece4b2424a","sha256":"f3d8fa3da3bb6b2156e6337e12a4b9bfe44d91ff621c96d0c608249cfc5dcc95"},{"path":"tools/BoardV2Import/Program.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"f154be5f98b6a3845ac73c94e50c441400720a3fc654b8483ce23a1633963428"},{"path":"src/FS.GG.Coord.GitHub/V2Projection.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"c6c4907b54028322b13d112e08f8050482c80165fb359f475f3e595c8ed05c96"},{"path":"tests/coord-board-v2-cli-join/INSPECT.md","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"16f754671ed4e94051b230595e3c46b148a4f696bb8f8aa850c059675c9e3403"}],"conflictsWith":[],"id":"github/programme-binding-custody-recovery","kind":"decision","recordedAt":"2026-10-19T08:55:14Z","repository":"FS-GG/.github","schema":"fsgg.atlas/1","status":"recorded","summary":"Programme/root accepts host receipt6262652143 and independent MATCH6262659355 for the5526-byte private archive: exclusive0600host copy, separate0600client restore, full-byte/hash/manifest/pair readback and file/parent fsync. Home retains the exact archive and proof in ~eugen/.local/state/v3-storage/session-recovery-20261019/ as programme-binding-pairs-20261019-0758.tar.gz until explicitrootdisposition. This host-owned0700ext4 directory is NOT mounted into the client; restoration uses the existing bounded private copy/readback route. Host disk loss, off-machine backup, power-loss behavior and actual client replacement remain unqualified. The original lost directory was outside the persistent mount. The telemetry spool remains dedicated to telemetry.\n\nClient staging ~/.local/share/fs-gg-private/programme-custody-20261019-0756/ is volatile, not sufficient custody. The archive holds both distinct new binding4/schema2 and binding5/schema3 original pairs with their exact templates/payloads and closed manifest, selecting22current issues (previous21plus4682), excluding threevisible members. Recovery retrieves this Atlas ID, reconciles4516receipt and4682ownership, restores to a NEW restrictive path, verifies the exact archive/manifest/commitments, and preserves all originals. Public Atlas/Git never holds private identities, nonce/payload, journals, credentials or runtime assets.\n\nPR4690 protected041a60cb carries the new4 commitment. Actual authenticated installed107 inspection2 exits0 within270seconds:22Current sources,25complete memberships, no population/membership/repository gaps,0mutations.21healthVerified and4682Unknown solelypreservedunsetObservation; read/planning complete. Independent review accepts this bounded fresh4 reader baseline. The final runtime file differs from its original only by protected populationRevision. It is not scheduling authority, UI/product acceptance or executed rollback. Constructor9772/artifact430d, publishedadapter75ab/artifact7ab and protected population revision remain distinct authenticated axes; fresh public107archive comparison matches all82installed payload members.\n\nThe successor candidate selects the separately host-custodied5commitment, not installed adoption. Actual pre-activation inspection3 with current protected4 source rejects5private commitment before issue attempts,0mutations. An earlier draft-source attempt failed canonical acquisition and is retained as setupfailure, not causal proof. Installed5positive qualification must follow its exact protected revision. Real bounded rollback must restore4public commitment through normal source delivery and derive an exclusive runtime binding at that protected revision preserving originalnonce/payload; separately restore/requalify5. UI/product/continuation and actualrestart/rollback remain open. Preserve original20-row history unavailable,439inherited/46later Unknown holds unreleased and reported25+5nativeeffects unreconciled without journals. Current metadata never settles those originals; no write replay or receipt reconstruction is selected. Canonical work-board owns4682/4641continuation.\n\nSuperseding qualification findings: after protected5 delivery4691/a0e392c8, actual installed107 inspection3 of all22 reaches500 requests after187.79s,18Current/4Unknown, zero mutations; final barriers refuse. Source-only108 combines successor membership/planning reads with fresh schema, full pagination, exact identities/options and unchanged500/270 limits. Projection125/125 and CLI75/75 pass; unchanged old source with the same22-item regression fails at exactly500sends/exit3. Independent reader review passed. This establishes causal source repair, not installed108 acceptance.\n\nActual public Creator017 all89members match its release, but fresh Rendering fails before target creation: packaged adapter8fb92b18 differs from published107adapter7ab62708. Strict physical identity stays. Bounded Astra-high plan selects promoted108 original full dependency closure reused by prospectiveCreator018; source-only compilation is separate, real108 pin must be absent until publication, and018 candidate/publisher must refuse without it. No fake digests, compiler-rebuild substitute or017replay. Existing frozen016/099 history remains immutable.\n\nUser visual UI check passed2026-10-19 and root accepts that scoped human evidence; no repeat UI check is required. The earlier statement that UI is open is superseded only for that scope. Actual published108/018, installed instruction/caller qualification, product journeys, programme continuation and real restart/rollback remain open. Work-board remains canonical start/continuation, owner4682 under4641. Current private failure/test reports remain client-local; root owns their durable evidence capture gap. Host-held originalpair archive remains retained, with no new disk-loss or restart qualification.","supersedes":["e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d"],"tags":["coordination","binding","custody","recovery","enrollment","atlas","qualification"],"title":"Retained pairs and passed visual check leave successor request budget and Creator artifact identity to qualify"}
diff --git a/.claude/skills/publishing-and-deployment/SKILL.md b/.claude/skills/publishing-and-deployment/SKILL.md
index 903ddde8f..99b0e41fc 100644
--- a/.claude/skills/publishing-and-deployment/SKILL.md
+++ b/.claude/skills/publishing-and-deployment/SKILL.md
@@ -34,9 +34,9 @@ Registry release inventory: 18 package-bearing contracts across 9 producers; 16
| `game` | `game-scene-adapter` | `0.17.0` | `0.17.0` | `game:0.17.0` | FS.GG.Game.Render package — Adapter (sim-state -> FS.GG.UI.Scene drawables) |
| `audio` | `fs-gg-audio` | `0.6.0` | `0.6.0` | `audio:0.6.0` | FS.GG.Audio.Core/.Host/.Engine/.Elmish/.WebBrowser public .fsi surfaces — AudioEffect vocabulary + IAudioBackend/IMixingBackend seam + mixing Engine + Audio.Cmd Elmish bridge + browser Web Audio host |
| `net` | `fs-gg-net` | `0.6.0` | `0.6.0` | `net:0.6.0` | FS.GG.Net.Core/.WebSocket/.WebSocket.Server/.Protobuf/.Grpc/.Elmish public .fsi surfaces — ITransport/IMessageChannel seam + Sequential/Multiplexed correlation + serve/ServerEcho + WebSocket client/server transport + Google.Protobuf/protobuf-net codecs + gRPC lifecycle bridge + Elmish Cmd/Sub |
-| `github` | `coord-engine` | `0.107.0` | `0.107.0` | `github:0.107.0` | the `fsgg-coord-engine` CLI verb surface (claim/take/batch/who/widen/set-paths/say/landable/done/release/flush/…) + its exit-code contract, emitted from src/FS.GG.Coord.Core/Protocol.fs; shipped as the FS.GG.Coord.Cli dotnet tool |
+| `github` | `coord-engine` | `0.108.0` | `0.107.0` | `github:0.107.0` | the `fsgg-coord-engine` CLI verb surface (claim/take/batch/who/widen/set-paths/say/landable/done/release/flush/…) + its exit-code contract, emitted from src/FS.GG.Coord.Core/Protocol.fs; shipped as the FS.GG.Coord.Cli dotnet tool |
| `github` | `telemetry-host` | `0.7.0` | `0.7.0` | `github:0.7.0` | optional Linux x64 FS.GG.Telemetry.Host dotnet tool — authenticated workspace-scoped ingestion, private dashboard, protected native capture and bounded learning export; independently versioned from the github coordination coherent set |
-| `github` | `new-sdd-workspace` | `0.17.0` | `0.17.0` | `github:0.17.0` | the `new-sdd-workspace` scaffolder CLI (package FS.GG.NewSddWorkspace) — one-command full-stack SDD workspace creation, wrapping the FS.GG.Templates `rendering` provider (ADR-0016); shipped as a dotnet tool |
+| `github` | `new-sdd-workspace` | `0.18.0` | `0.17.0` | `github:0.17.0` | the `new-sdd-workspace` scaffolder CLI (package FS.GG.NewSddWorkspace) — one-command full-stack SDD workspace creation, wrapping the FS.GG.Templates `rendering` provider (ADR-0016); shipped as a dotnet tool |
| `templates` | `fs-gg-workspace-template` | `0.19.0` | `0.19.0` | `templates:0.19.0` | FS.GG.Workspace.Template package, eight template configurations and seven `dotnet new` selectors: workspace-provider identities — `fs-gg-console` (provider `console` — minimal F# executable, no npm lane, ADR-0072 §2); `fs-gg-web` (provider `web` — F# ASP.NET Core + plain TypeScript/Vite website, ADR-0071 §3); `fs-gg-fable-game` (provider `fable-game` — F# ASP.NET Core + Fable/Elmish game client, SignalR for connection-oriented real-time traffic + plain HTTP endpoints with explicit versioned DTOs for typed request/response per ADR-0073, consuming the published `fs-gg-game-core-fable-lockstep-v1` profile per ADR-0069); `fs-gg-fable-bindings` (provider `fable-bindings` — Fable interop library over an exactly pinned npm package/declaration closure, ADR-0072 §3, first proved by the unreleased EHotwagner/babylonjsBindings reference) — plus `fs-gg-governance`, the separately registered pre-existing governance overlay template folded into this package at the same rename; `fs-gg-project-knowledge` and `fs-gg-python` are also already packaged. The current and legacy fable-game configurations share one selector. |
| `game` | `game-skills` | `0.9.0` | `0.9.0` | `game:0.9.0` | FS.GG.Game.Skills 0.9.0 package — owner-sourced game, Fable, replay and rules guidance with schema-v2 per-file digests and workspace bundle predicates; embedded by the SDD 1.8 receiver |
| `rendering` | `rendering-skills` | `0.2.0` | `0.2.0` | `rendering:0.2.0` | FS.GG.Rendering.Skills 0.2.0 package — owner-sourced SVG assets/performance and Fable workspace guidance with schema-v2 per-file digests and bundle predicates; embedded by the SDD 1.8 receiver |
diff --git a/.github/workflows/new-sdd-workspace-selftest.yml b/.github/workflows/new-sdd-workspace-selftest.yml
index 92411a747..113ec9842 100644
--- a/.github/workflows/new-sdd-workspace-selftest.yml
+++ b/.github/workflows/new-sdd-workspace-selftest.yml
@@ -19,6 +19,8 @@ on:
pull_request:
paths:
- "scripts/NewSddWorkspace/**"
+ - "scripts/creator-current-coord-dependencies.*"
+ - "scripts/creator-frozen-coord-dependencies.*"
- "src/FS.GG.Coord.Cli/**"
- "src/FS.GG.Coord.Cli.BoardOps/**"
- "src/FS.GG.Coord.Cli.Kernel/**"
@@ -48,6 +50,8 @@ on:
branches: [main]
paths:
- "scripts/NewSddWorkspace/**"
+ - "scripts/creator-current-coord-dependencies.*"
+ - "scripts/creator-frozen-coord-dependencies.*"
- "src/FS.GG.Coord.Cli/**"
- "src/FS.GG.Coord.Cli.BoardOps/**"
- "src/FS.GG.Coord.Cli.Kernel/**"
@@ -94,7 +98,7 @@ jobs:
- name: Run the new-sdd-workspace parse fixture
run: |
python3 tests/new-sdd-workspace-successor/run.py WizardReleaseTests.test_current_source_flows_keep_one_isolated_producer
- export FSGG_CREATOR_SOURCE_ARTIFACTS="$RUNNER_TEMP/creator017-source-build-$GITHUB_RUN_ID-$GITHUB_RUN_ATTEMPT"
+ export FSGG_CREATOR_SOURCE_ARTIFACTS="$RUNNER_TEMP/creator018-source-build-$GITHUB_RUN_ID-$GITHUB_RUN_ATTEMPT"
echo "FSGG_CREATOR_SOURCE_ARTIFACTS=$FSGG_CREATOR_SOURCE_ARTIFACTS" >> "$GITHUB_ENV"
bash tests/new-sdd-workspace/run.sh
@@ -107,22 +111,22 @@ jobs:
--reference:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/FS.GG.Coord.Core.dll" \
--exec tests/new-sdd-workspace/product-board.fsx
- - name: Qualify Creator 0.17 normal-source package closure
+ - name: Qualify Creator 0.18 normal-source package closure
env:
SOURCE_SHA: ${{ github.sha }}
run: |
set -euo pipefail
test "$(git rev-parse HEAD)" = "$SOURCE_SHA"
- package_dir="$RUNNER_TEMP/creator017-source-qualification"
+ package_dir="$RUNNER_TEMP/creator018-source-qualification"
mkdir "$package_dir"
dotnet pack scripts/NewSddWorkspace/NewSddWorkspace.fsproj -c Release --no-build \
--artifacts-path "$FSGG_CREATOR_SOURCE_ARTIFACTS" \
-p:RepositoryCommit="$SOURCE_SHA" -o "$package_dir"
- package="$package_dir/FS.GG.NewSddWorkspace.0.17.0.nupkg"
+ package="$package_dir/FS.GG.NewSddWorkspace.0.18.0.nupkg"
manifest="$package_dir/manifest.json"
python3 scripts/new-sdd-workspace-release.py prepare --package "$package" \
- --source-sha "$SOURCE_SHA" --version 0.17.0 \
- --tag new-sdd-workspace/v0.17.0 --output "$manifest"
+ --source-sha "$SOURCE_SHA" --version 0.18.0 \
+ --tag new-sdd-workspace/v0.18.0 --output "$manifest"
python3 scripts/new-sdd-workspace-release.py verify --manifest "$manifest" --package "$package"
python3 tests/new-sdd-workspace-successor/run.py \
--board-package "$package" --source-sha "$SOURCE_SHA" --release-manifest "$manifest" \
diff --git a/.github/workflows/release-new-sdd-workspace-successor-candidate.yml b/.github/workflows/release-new-sdd-workspace-successor-candidate.yml
index 2fb4a7718..8c8c4bb78 100644
--- a/.github/workflows/release-new-sdd-workspace-successor-candidate.yml
+++ b/.github/workflows/release-new-sdd-workspace-successor-candidate.yml
@@ -1,21 +1,17 @@
name: release-new-sdd-workspace-successor-candidate
-# Product V2 wizard 0.17.0: protected source and package-byte qualification only.
-# Normal 0.107 source graph; frozen 0.16/0.99 dependency inputs and historical recovery remain retained.
+# Creator018 release has no source-build fallback. Missing promoted108 pin refuses.
on:
workflow_dispatch:
-
permissions:
contents: read
packages: read
-
concurrency:
group: release-new-sdd-workspace-successor-candidate
cancel-in-progress: false
-
jobs:
candidate:
- name: new-sdd-workspace-017-candidate
+ name: new-sdd-workspace-018-candidate
if: github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
timeout-minutes: 45
@@ -25,6 +21,8 @@ jobs:
ref: ${{ github.sha }}
fetch-depth: 0
persist-credentials: false
+ - name: Refuse missing promoted dependency pin before SDK or graph qualification
+ run: python3 scripts/creator-current-coord-dependencies.py preflight
- uses: actions/setup-dotnet@v6
with:
global-json-file: global.json
@@ -40,60 +38,69 @@ jobs:
test "$(git rev-parse HEAD)" = "$SOURCE_SHA"
test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"
version="$(dotnet msbuild scripts/NewSddWorkspace/NewSddWorkspace.fsproj -getProperty:Version | tr -d '[:space:]')"
- test "$version" = 0.17.0
- test -z "$(git ls-remote --tags origin refs/tags/new-sdd-workspace/v0.17.0)"
+ test "$version" = 0.18.0
+ test -z "$(git ls-remote --tags origin refs/tags/new-sdd-workspace/v0.18.0)"
response="$(curl --silent --show-error --location --output /dev/null --write-out '%{http_code}' \
- https://api.nuget.org/v3-flatcontainer/fs.gg.newsddworkspace/0.17.0/fs.gg.newsddworkspace.0.17.0.nupkg)"
+ https://api.nuget.org/v3-flatcontainer/fs.gg.newsddworkspace/0.18.0/fs.gg.newsddworkspace.0.18.0.nupkg)"
test "$response" = 404
response="$(curl --silent --show-error --location --output /dev/null --write-out '%{http_code}' \
-u "$GITHUB_ACTOR:$GITHUB_TOKEN" \
- https://nuget.pkg.github.com/FS-GG/download/fs.gg.newsddworkspace/0.17.0/fs.gg.newsddworkspace.0.17.0.nupkg)"
+ https://nuget.pkg.github.com/FS-GG/download/fs.gg.newsddworkspace/0.18.0/fs.gg.newsddworkspace.0.18.0.nupkg)"
test "$response" = 404
- name: Refuse mismatched Creator profiles before costly graph qualification
run: python3 tests/new-sdd-workspace-successor/run.py
- - name: Qualify wizard source
- run: |
- export FSGG_CREATOR_SOURCE_ARTIFACTS="$RUNNER_TEMP/creator017-candidate-build-$GITHUB_RUN_ID-$GITHUB_RUN_ATTEMPT"
- echo "FSGG_CREATOR_SOURCE_ARTIFACTS=$FSGG_CREATOR_SOURCE_ARTIFACTS" >> "$GITHUB_ENV"
- bash tests/new-sdd-workspace/run.sh
- - name: Qualify the real compiled product board boundary
+ - name: Acquire verified promoted originals into fresh isolated checkouts
run: |
- dotnet fsi --lib:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/" \
- --reference:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/new-sdd-workspace.dll" \
- --reference:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/fsgg-coord-engine.dll" \
- --reference:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/FS.GG.Coord.GitHub.dll" \
- --reference:"$FSGG_CREATOR_SOURCE_ARTIFACTS/bin/NewSddWorkspace/release/FS.GG.Coord.Core.dll" \
- --exec tests/new-sdd-workspace/product-board.fsx
- - name: Pack and bind one package archive
+ set -euo pipefail
+ work="$RUNNER_TEMP/creator018-published-$GITHUB_RUN_ID-$GITHUB_RUN_ATTEMPT"
+ test ! -e "$work"
+ mkdir -m 700 "$work"
+ git clone --no-hardlinks --no-checkout "$GITHUB_WORKSPACE" "$work/creator"
+ git -C "$work/creator" checkout --detach "$GITHUB_SHA"
+ producer_sha="$(python3 -c 'import json; print(json.load(open("scripts/creator-current-coord-dependencies.json"))["sourceSha"])')"
+ git clone --no-hardlinks --no-checkout "$GITHUB_WORKSPACE" "$work/producer"
+ git -C "$work/producer" checkout --detach "$producer_sha"
+ python3 "$work/creator/scripts/creator-current-coord-dependencies.py" acquire --package "$work/producer.nupkg"
+ python3 "$work/creator/scripts/creator-current-coord-dependencies.py" stage \
+ --producer-source "$work/producer" --dependencies "$work/dependencies" --package "$work/producer.nupkg"
+ echo "CREATOR_PUBLISHED_ROOT=$work" >> "$GITHUB_ENV"
+ - name: Qualify wizard published dependency mode and pack same output
env:
- SOURCE_SHA: ${{ github.sha }}
+ FSGG_CREATOR_DEPENDENCY_MODE: published-dependency
run: |
set -euo pipefail
+ work="$CREATOR_PUBLISHED_ROOT"
+ export FSGG_CREATOR_PRODUCER_SOURCE="$work/producer"
+ export FSGG_CREATOR_DEPENDENCIES="$work/dependencies"
+ export FSGG_CREATOR_CALLER_ROOT="$GITHUB_WORKSPACE"
+ export FSGG_CREATOR_SOURCE_ARTIFACTS="$work/fixture-state"
+ bash "$work/creator/tests/new-sdd-workspace/run.sh"
+ output="$work/creator/scripts/NewSddWorkspace/bin/Release/net10.0"
+ dotnet fsi --lib:"$output" --reference:"$output/new-sdd-workspace.dll" \
+ --reference:"$output/fsgg-coord-engine.dll" --reference:"$output/FS.GG.Coord.GitHub.dll" \
+ --reference:"$output/FS.GG.Coord.Core.dll" --exec "$work/creator/tests/new-sdd-workspace/product-board.fsx"
mkdir -p artifacts/new-sdd-workspace
- dotnet pack scripts/NewSddWorkspace/NewSddWorkspace.fsproj -c Release --no-build \
- --artifacts-path "$FSGG_CREATOR_SOURCE_ARTIFACTS" \
- -p:RepositoryCommit="$SOURCE_SHA" -o artifacts/new-sdd-workspace
- package=artifacts/new-sdd-workspace/FS.GG.NewSddWorkspace.0.17.0.nupkg
+ dotnet pack "$work/creator/scripts/NewSddWorkspace/NewSddWorkspace.fsproj" -c Release --no-build \
+ -p:FsggCurrentCoordDependencies=true -p:BuildProjectReferences=false \
+ -p:CompileUsingReferenceAssemblies=false \
+ -p:FsggFrozenCoordSource="$work/producer" -p:FsggFrozenCoordDependencies="$work/dependencies" \
+ -p:RepositoryCommit="$GITHUB_SHA" -o "$GITHUB_WORKSPACE/artifacts/new-sdd-workspace"
+ package=artifacts/new-sdd-workspace/FS.GG.NewSddWorkspace.0.18.0.nupkg
manifest=artifacts/new-sdd-workspace/manifest.json
- test -f "$package"
python3 scripts/new-sdd-workspace-release.py prepare --package "$package" \
- --source-sha "$SOURCE_SHA" --version 0.17.0 \
- --tag new-sdd-workspace/v0.17.0 --output "$manifest"
+ --source-sha "$GITHUB_SHA" --version 0.18.0 --tag new-sdd-workspace/v0.18.0 --output "$manifest"
python3 scripts/new-sdd-workspace-release.py verify --manifest "$manifest" --package "$package"
- python3 tests/new-sdd-workspace-successor/run.py
- python3 tests/new-sdd-workspace-successor/run.py \
- --board-package "$package" --source-sha "$SOURCE_SHA" --release-manifest "$manifest" \
- --build-artifacts "$FSGG_CREATOR_SOURCE_ARTIFACTS" \
- > artifacts/new-sdd-workspace/package-evidence.json
+ python3 tests/new-sdd-workspace-successor/run.py --board-package "$package" \
+ --source-sha "$GITHUB_SHA" --release-manifest "$manifest" \
+ --published-coord-dependencies "$work/dependencies" --published-coord-source "$work/producer" \
+ --creator-source "$work/creator" > artifacts/new-sdd-workspace/package-evidence.json
- name: Refuse changed main before retaining candidate
- env:
- SOURCE_SHA: ${{ github.sha }}
- run: test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"
+ run: test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$GITHUB_SHA"
- uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7
with:
name: new-sdd-workspace-successor-candidate-${{ github.sha }}-${{ github.run_id }}
path: |
- artifacts/new-sdd-workspace/FS.GG.NewSddWorkspace.0.17.0.nupkg
+ artifacts/new-sdd-workspace/FS.GG.NewSddWorkspace.0.18.0.nupkg
artifacts/new-sdd-workspace/manifest.json
artifacts/new-sdd-workspace/package-evidence.json
if-no-files-found: error
diff --git a/.github/workflows/release-new-sdd-workspace.yml b/.github/workflows/release-new-sdd-workspace.yml
index ee8335731..370470b33 100644
--- a/.github/workflows/release-new-sdd-workspace.yml
+++ b/.github/workflows/release-new-sdd-workspace.yml
@@ -1,9 +1,9 @@
name: release-new-sdd-workspace
-run-name: ${{ inputs.promotion_recovery != 'off' && format('Wizard 0.13 recovery {0} {1} {2}', inputs.promotion_recovery, inputs.recovery_correlation, inputs.recovery_binding_sha256) || format('Wizard 0.17 successor {0}', inputs.candidate_run_id) }}
+run-name: ${{ inputs.promotion_recovery != 'off' && format('Wizard 0.13 recovery {0} {1} {2}', inputs.promotion_recovery, inputs.recovery_correlation, inputs.recovery_binding_sha256) || format('Wizard 0.18 successor {0}', inputs.candidate_run_id) }}
# TSDD-KNOWLEDGE-01.4: retain the existing NuGet Trusted Publishing filename.
# GS2-08.9's no-effect seal is superseded only for this exact-source, protected-
-# main-directory Creator 0.17.0 successor. Default publication remains false.
+# main-directory Creator 0.18.0 successor. Default publication remains false.
# App mint and explicitly selected NuGet login are separately admitted credential effects.
on:
workflow_dispatch:
@@ -67,7 +67,7 @@ concurrency:
jobs:
publish:
- name: new-sdd-workspace-017-publisher
+ name: new-sdd-workspace-018-publisher
if: github.ref == 'refs/heads/main' && github.actor == 'EHotwagner' && inputs.promotion_recovery == 'off'
runs-on: ubuntu-latest
environment: release-successor
@@ -78,6 +78,8 @@ jobs:
ref: ${{ github.sha }}
fetch-depth: 0
persist-credentials: false
+ - name: Refuse absent promoted dependency pin before credentials or effects
+ run: python3 scripts/creator-current-coord-dependencies.py preflight
- uses: actions/setup-dotnet@v6
with:
global-json-file: global.json
@@ -137,8 +139,8 @@ jobs:
timeout-minutes: 2
uses: actions/upload-artifact@v7
with:
- name: creator017-publication-summary-${{ github.run_id }}
- path: ${{ runner.temp }}/creator017-publication-summary.json
+ name: creator018-publication-summary-${{ github.run_id }}
+ path: ${{ runner.temp }}/creator018-publication-summary.json
if-no-files-found: error
retention-days: 7
diff --git a/.github/workflows/release-successor-candidate.yml b/.github/workflows/release-successor-candidate.yml
index 3d0976464..6a4c6c072 100644
--- a/.github/workflows/release-successor-candidate.yml
+++ b/.github/workflows/release-successor-candidate.yml
@@ -1,6 +1,6 @@
name: release-successor-candidate
-# Source/byte qualification for coherent set 0.107.0 only. This route has no tag, release,
+# Source/byte qualification for coherent set 0.108.0 only. This route has no tag, release,
# journal, package-feed, OIDC or promotion write. Its retained Actions artifact
# is an unpromoted candidate, not a published release or an admission receipt.
on:
@@ -43,7 +43,7 @@ jobs:
test "$(git rev-parse HEAD)" = "$SOURCE_SHA"
test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"
version="$(dotnet msbuild src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj -getProperty:Version | tr -d '[:space:]')"
- test "$version" = 0.107.0
+ test "$version" = 0.108.0
echo "version=$version" >> "$GITHUB_OUTPUT"
- name: Verify the stable predecessor and unused package version
env:
@@ -53,24 +53,24 @@ jobs:
run: |
set -euo pipefail
mkdir -p artifacts/predecessor artifacts/packages
- gh release download coherent-set/v0.106.0 --repo "$GITHUB_REPOSITORY" \
+ gh release download coherent-set/v0.107.0 --repo "$GITHUB_REPOSITORY" \
--pattern stable-channel.json --dir artifacts/predecessor
python3 scripts/release-saga.py predecessor \
--channel artifacts/predecessor/stable-channel.json \
- --release-tag coherent-set/v0.106.0 \
- --tag-source 2e42faaa994367b9f50be87439e8fd973ad21501 \
+ --release-tag coherent-set/v0.107.0 \
+ --tag-source 75ab98dd28b1a818cc3986d595bf21e0fe691ec6 \
> artifacts/predecessor/identity.json
- test "$(jq -r .version artifacts/predecessor/identity.json)" = 0.106.0
+ test "$(jq -r .version artifacts/predecessor/identity.json)" = 0.107.0
python3 scripts/check-release-candidate-uniqueness.py \
- --version "$VERSION" --predecessor 0.106.0
+ --version "$VERSION" --predecessor 0.107.0
release_status="$(curl --silent --show-error --location -o /dev/null -w '%{http_code}' \
-H "Authorization: Bearer $GH_TOKEN" \
-H 'Accept: application/vnd.github+json' \
- "https://api.github.com/repos/$GITHUB_REPOSITORY/releases/tags/coherent-set/v0.107.0")"
+ "https://api.github.com/repos/$GITHUB_REPOSITORY/releases/tags/coherent-set/v0.108.0")"
test "$release_status" = 404
test -z "$(git ls-remote --tags origin \
- 'refs/tags/coherent-set/v0.107.0' 'refs/tags/kit/v0.107.0' \
- 'refs/tags/drivers/v0.107.0' 'refs/tags/coord-engine/v0.107.0')"
+ 'refs/tags/coherent-set/v0.108.0' 'refs/tags/kit/v0.108.0' \
+ 'refs/tags/drivers/v0.108.0' 'refs/tags/coord-engine/v0.108.0')"
- name: Test the telemetry producer and prepare the browser fixture
run: |
set -euo pipefail
@@ -183,7 +183,7 @@ jobs:
set -euo pipefail
test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"
python3 scripts/check-release-candidate-uniqueness.py \
- --version "$VERSION" --predecessor 0.106.0
+ --version "$VERSION" --predecessor 0.107.0
- uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7
with:
name: release-successor-candidate-${{ github.sha }}-${{ github.run_id }}
diff --git a/.github/workflows/release-successor-feed-readiness.yml b/.github/workflows/release-successor-feed-readiness.yml
index 26c172d60..17fc83e2e 100644
--- a/.github/workflows/release-successor-feed-readiness.yml
+++ b/.github/workflows/release-successor-feed-readiness.yml
@@ -1,6 +1,6 @@
name: release-successor-feed-readiness
-# Informational freshness observation for a prospective 0.107.0 coherent set.
+# Informational freshness observation for a prospective 0.108.0 coherent set.
# This does not select a release, qualify source bytes, or authorize publication.
on:
workflow_dispatch:
@@ -35,10 +35,10 @@ jobs:
test "$(git rev-parse HEAD)" = "$SOURCE_SHA"
test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"
python3 tests/release-successor-candidate/run.py
- - name: Observe both feeds for 0.107.0 against published 0.106.0
+ - name: Observe both feeds for 0.108.0 against published 0.107.0
env:
GITHUB_TOKEN: ${{ github.token }}
run: |
set -euo pipefail
python3 scripts/check-release-candidate-uniqueness.py \
- --version 0.107.0 --predecessor 0.106.0
+ --version 0.108.0 --predecessor 0.107.0
diff --git a/Directory.Build.props b/Directory.Build.props
index 3776b2df4..8dfd95ce9 100644
--- a/Directory.Build.props
+++ b/Directory.Build.props
@@ -616,8 +616,11 @@
+
- 0.107.0
+ 0.108.0
diff --git a/dist/dotnet/.config/dotnet-tools.json b/dist/dotnet/.config/dotnet-tools.json
index 8ccfccc20..7d07d25bc 100644
--- a/dist/dotnet/.config/dotnet-tools.json
+++ b/dist/dotnet/.config/dotnet-tools.json
@@ -9,7 +9,7 @@
]
},
"fs.gg.coord.cli": {
- "version": "0.107.0",
+ "version": "0.108.0",
"commands": [
"fsgg-coord-engine"
]
diff --git a/docs/architecture.md b/docs/architecture.md
index 36e36007d..0861d42d8 100644
--- a/docs/architecture.md
+++ b/docs/architecture.md
@@ -653,9 +653,9 @@ product's `FS.GG.UI.*` pin), which is a different axis from the template package
| `game-scene-adapter` | FS.GG.Game | `0.17.0` | `0.17.0` |
| `fs-gg-audio` | FS.GG.Audio | `0.6.0` | `0.6.0` |
| `fs-gg-net` | FS.GG.Net | `0.6.0` | `0.6.0` |
-| `coord-engine` | FS-GG/.github | `0.107.0` | `0.107.0` |
+| `coord-engine` | FS-GG/.github | `0.108.0` | `0.107.0` |
| `telemetry-host` | FS-GG/.github | `0.7.0` | `0.7.0` |
-| `new-sdd-workspace` | FS-GG/.github | `0.17.0` | `0.17.0` |
+| `new-sdd-workspace` | FS-GG/.github | `0.18.0` | `0.17.0` |
| `fs-gg-workspace-template` | FS.GG.Templates | `0.19.0` | `0.19.0` |
| `game-skills` | FS.GG.Game | `0.9.0` | `0.9.0` |
| `rendering-skills` | FS.GG.Rendering | `0.2.0` | `0.2.0` |
diff --git a/docs/atlas/catalog.json b/docs/atlas/catalog.json
index b7f7a61c1..e616e8ed0 100644
--- a/docs/atlas/catalog.json
+++ b/docs/atlas/catalog.json
@@ -1 +1 @@
-{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
+{"records":["000ada42299601fba29016e5c0e0d4012876fb42670bb10fa0b1315477254ba4","003893cc49855d17a15295d7adbe57ee301ea20281dff216461baee0810853ff","00641d046d6869fdd0023ab3df99e0e67a6ea28f0dcb701f622b1cec8b3e07c6","026b08fb343aefe19177e95b759560d340d372def4b71acf613fefee3438ade2","0357495d23fac4fad210b6dd7ed7cc57dd33d107e1659a81f085cad78300797f","036c148f6d0e89858c9bf4cf380272ca6904bb4ca277a909fb71c47f5450cef7","04e404d89dca295564813149472b1de8e6c43357e2f6d91d169ded7600ed3a02","0509e5c6fdbd2dde0c0db8558647080560714804d00e4f9268342f2e84858a3d","06ad2c8aa0ff3b862edf3ba99e0e4e8801ee163709e66333cd06c3fc61232b05","0a6d7dc5b64970bfdadc9049ace95e8bc163fc421beea70129ff0eaa692c6d06","0ad4403c8f4078dbfa543310c69bd1dfc768e305987214ffc37d7b2600c4687c","0c22360d4653eb0f450e4d3d34564875f1660cfcb2d546095d98b3faa3967cbc","0da4d093b49c0a1f654b38008bb01195e816829279ca1989bd2448194e15361b","0e560af7d9dd2e0f2f588a74cd35512973747f20bdfe0bee0bc889105ea53dc9","0ea7107c2c8edaab3ff2bae32f63cfbef6903a51cdaff257278f757ed5ef429d","0eef4d717eb03f0906aa3be7336aa71f831726afabe8a56077b76f6e82fd08e1","11fe30832d93706c60efd836b09f35f049c4a715ad6144cf277ca240c5780704","1244d27db0cf5075353bcc622d0fb3b5ca6a7d08526e2c5754e8b745c250bf3f","126c817ad25ca9cbac2a0f7446e76c79852459ac7b9c61e3ba5d5cbfe5d37dfb","13824d6bce0f961c89eef4bd3c8a72ae6ecf7a1339b9e06eec964dc5c12dc544","14156f1c6bf0fa8dfcb5cfafac09e012db446d528dad0e4301404fd693b9bed3","155fe673b8ae12549c978e1bf1d5c43e360937fcf2135cdcd5aea6f6c771da44","1945f527afc3c2930ec4d7fa57ebb2ef7dd6321c0dd3ab9233c9963e9e613165","19d657b67672257ece127f3b957674b7fb4780843148db0a36a0b329c2a418ba","1a24f6ef0c08a898f309c1b925fc19b29526f913a61a1dfe4b1a4308ebdd97ac","1b5351b2dc647aba864e387168db5128435cb80da94fc42581cd60a05fc34b9a","1da011289116fe88fe92cb8f0e83ed7ccbbca251681d4e136c5a61c40364f8d3","1ec9445b242d2a2e149fe71c67bf13d8c0e4ebe5a6ed7b022656b9941973909d","1edc36731a9c76ad07d269d8b4fd84c8c956bb43d6f56de17d6208164856ffbe","20901b579f69cc97eb56b492938864667576e1c9bfacf13f8a529c4f6e543448","21338155cb4f52c49e5072c877771be67c75590d9b238ea025fba5209fd6e018","23af79bd1e7995fc8162ddc4d830318acb054bbfcc9c7d5cb141ec306da67386","24d4f2730d94d1b7f149771ef0e59192f4936d142b21f4a56b1a391e4514d38d","2591526ddabbea03fbdc38bf172bc54f42df9bc51eba7ad2b70d6e67215f08f1","26259abc7fe745f52e06f2aa2abb0e50f189bc7608065f04d5c669a0a99941cd","26290a0990d6dac0ce9448e05eb934210603356043dcf14a5d80585288e2aa92","26d6b31965013079d4db67a2c403e01f21e3c30ae65953400dbed92e289a0925","288daf614247c260cb673d8674e8b3874ccc4e269347836851f702d7ac8e2f7c","28abfaf6d50ca38af0b88aa50524200c17af9000da83ddbab3d8f9e06e020fa5","291d3db272eae084d34c04bc1305f2abb26a7e7acbc5515208469b46719a4ed1","2a38ddebfe3380232e35d5a24f9cb9f7c38abbc9c68add4ea5952c1e65d328d2","2c76ce93500601e281a41f5985fe4e3926fc8bc9d01ee687f14052cb553ad2d2","2d599c722a08306b98f2d833fb3e4a7acb9dea92e6a58820caa2f65c09803fb8","2e1bc31ff6b6fb14d0ca8703a02833db749b03e172f2e91f9423f0751e88c256","2ecd502add2d801eebed39411fadc9a80098ba9ce04a5f4b728a0e4e331232d6","2f7357367d921995f4c6fdaa693392adcd2df4860ef4d25c8dc47f7ddea8c755","2fb2ed7902a8e35dc36489a23245d963026d688008c92fed6fdc1f6bc27198a6","3018f389f6928af5830bdd081c9d03530a379f37d1c2f9196e6fb3c44eb337d5","310bfb5b2d061bb733771e5cb7b3b7d25db43af5eda9f806169b7ef9330c2fe7","32f69a7b8997ae98b9305ee578145d795dbcd39ca4469bf2465e57a0295cda51","335683e33b94cb86b5e426b4faed200673bf850151191a08458136ceb164fd4e","3407ec53a884d3945d86a88d6b9a883419dd426e96b1108a8e6686f30397a629","34463778cf2d29e3896a65613cf9e3eb3e9f2d8946d17f12b609e70eec63d128","35da3938b72cf3520e126ad595157104b69ab748904c7b4e12f563d6b103172b","37c8908ea2a349cd3034018027160ad810b28ad1fc203a9a353971e1f7396b4c","37e39faee019bb041627510f1f02746ba9a85696417a083b438eb4974b72c2bf","38a75fd804821f4836f0a7ba8d41af3d3a3a5f5d7dcea68487009297824258d9","397476cf107b48e7a662264f8fea9f880231fd3d1e0401622650f214cfaa35c7","3ad8b0398ba6c354c9e31b7438b2515579fc0b1f17de4b35a914c862a3a11e3b","3b3c6cf083b12a840565e00458e2fd4ee8a61f97cda452703a6b13d7776b6c13","3b4af144afed3d52dd2e1f64e23bc25b3475eee5f7af3bde9886761b15c33dfd","3b5d82795e9f5d1992ab67e078fcf1108247ab9b6d1baeac944d3ec0294cec5d","3d0274f77576abdbdf442c8843e955e1bbc91e9f8cbfe3646b119337cdb13c96","3e2f66baa16c7ea936eba34720a55897438f60b343cbe8fda4eab1e5dde044eb","41c768ea17144c6ec225e9a65d4c3c127fdd7264dcba1a89aa17b20fd5d7e3ee","42aeb46fcc3d10b95e4067bc9cda875fa933b4102873f67c7bf1f8ca6799a598","4320b92712bc14dbe10b56f1cd3d1bdc093fc4be6016732839d0be4dd4d027d3","46cdf2c207f79d388001f6636dfb7a98bb2ba72b9d1c6df4938f0a27691e07a6","480f1ede18ae031b164d49d676feeb1090fb33932676ff52e1e2eb24e8d154cd","4855e1947afc954cb1b20bb45e7af10b098fa34714bd32e9bc77941cf58fdaaa","48797c44c92cb34fd9a57a08020b45c6920b2268dc8ad616c0f814a3710d5316","48d094622ada1806cb30335926007c1abc476b1f7b45a2e250c490afa25e847b","4a724a6a842a132c2185279513f341b79f9be93e42660f1255770eeae3b1323c","4c8c327dacf345e184042092e96ad3ea02ed4cece57dac5fa68ea52fbb5a6adf","4d5a44ba07fafeab823b54a21846269330ce35b4c190f3ddd5434bc8530d9b41","4da0a5be70e8af9c39623deac83822749482187f6a0fc3d186dcfddaa7111576","4f1e58fc658a4ceda181e2a7fa249305b09b573ffd68c2489f204f4957224957","4f2750b974c1404acb721ffc84cbd1d0756a24211dd6f6503c10ea74dbc45676","509ec9c08864b9dd0029f32ffeac85fbac863e2dad459994c65b7cb5264faffa","52049cc9cee43bb27229e6b3e983e02c6aa20dd7d153b13e3c74bc6d2b47cf92","5382c901d160ca2d79888d8acd7a690a5349826b5da486274b0800c9d7513f11","540879695d41205515aaabe5466971014cb43b960a26b8e5958e37fed63df762","548d237f42167af5cf5caa0ba20f0e7a6387deb6f27765637f078325172396a7","5560616d1e72f0a539f9ebbfea3b7d195c1ef5622f97994af1963748d4f97533","556ee783d8e2e4ca50f656c095758be613983f904d998a6534fb155510114f21","55a4711e799294d06988ab4acf77eacd7d424123082bba3ec987dff0ae13999c","55ae095961d78a1514c4dd1e63d477c60179a8662571ab5a90abd3eb2b83eb10","56e7158313357bb145bd98c5f790e569be2203fb2601565a30091a597a7e7ff5","5962dd14d3923433cf723d698d1af19ac37a270b6e88445643fc56a646faab5b","5a2064cdf51026eed65457c05f34bec919b31d96d35c29498d298685965f0b5a","5b77bd6dfa81cc339e729e4195e258facbfeb64b9c680512f742e3fb1961fdd5","5c3527e43fe24c5aa171c6fa4a3de7fe5e78f2527aed0dd19cb21d154d43da21","5c79c77f00167ca140127b00f1a79e1ffac621e46fc461089594206a7df8d7cc","5d015880319af666943e68169ca906bf2f0c813d8bf2c5c0262aeb5a40366350","5f2a75b89983d1005a38afa2cabccc3a39f31989807120281d8505ffd564e0c6","5f43c837f39d207c35a58e9b36fe3144017b2012ac7da334714247606f1906d2","5f4fa6dde5930fe1b42f805895f0f5fb135c2b3ff9830f2bd30ae7526a3295a1","630fdcff1f227b5baf5d10bd78ef0fde68791ac0cd8a15f65065f5cc4501b17b","63113617f2e4ee6b827a69bce6afb3949190a282f5feaaa9e2c9f82372623bb8","63544fa69b09916d52b305700eb9816305ff22b77162a44edd13897acea3a655","63a4394e689acf4a4762cfb4df691d05f923fdf592fd2f8ea41e6a54f98d1136","69ebfc7eb8427db3c5c59bdde652d0cb269426126f8540b1b58caa29ccf130e2","69edc4285578313d1dd2f914d69add075a7b354f7fba717606d1abe15292576b","6a34d9279cae58765d6ee4a980192c0e15f3ca217b9f1815861d472a281b3cf8","6c3c592efe9c684ada5661b8cc88a5c3f6e57c841db06b9e070687504cbf6236","6ce6d164c3e31463fb9e144fdf91413e55d077cfc4f25092bb02923fb538a84f","6e08a638e1e28020923effd4c65fc517dbe7b06100ff76cde74e427191503b84","6f3a7020233cd77cfe59eefec0a277f6dda323743c8d80e4e54a95cd3cbc23cf","6fccc6f0c5fa71c43211785dced8abd0f3295040eab56063f4e8d77f1c09b8ef","700cd21af9ed7e81900fad9d52de2fb11db48e64b038e4293168f85e5dd0e043","702d1dfa75e92a916a446429f474d4c296e6ea4e8c487995852d0525e8440659","704cf778db6086c3e282c81249fb0ef09c1d7c2043335ef74c7ecb69bb3e84ad","71ef1ed2d5e4bc7eebe7a73bb3e9423e5bc2f8319186380fe8b38334952d3b01","7256ba00af1cf759b95b7bf8ae3b9943f31349bd10a7652a26bb419b368d73a3","7369b339daca0fcf46ac7fe82d65ae95c75d7dbcaaae51209e6d90b6587a014e","73ec844fb3e2b9febd00ba37508b284fad141630f03cb9f74e36a195180f5054","7410de003c7b582e30470d1209eefc796a70c76fe8d61dd9ccfe01ecfa41310c","76bf5a9c126db6eb466287a7c0d823327ee9882a70eaaa6efb03d169b5dba808","781a64598efb2a11156f07271ba1c14c4f6b3d73aa2943b26eae02063df7af70","799abc1e8d381b8d97349479139985e383bb49179b5a80f39807cb35a3ee78ce","79faec494bdd6d098c9d2a9d8559f822938c6b2104188db95321d89e7a732979","7a032dbf0351aa32c77c8d187f7eb697500ff186c88c5946ecc15adc972246a6","7a134e7f1822183ed1c0ded720971539350feaaf92612761210cfc3ccdc55870","7aa52373f2721dd76fc8eeb3d6061794f27ea8d11e96bcb1ff25a97994a77d5c","7ad4ef4b8d3221758a9e7f9577750ee03f6cba11c8eae8bf25f74a3131bd21a2","7baa35131ece7ed9860607157d2531d4d70a061bdc9bb9876e20328f127cec53","7cbf970a11bdb91a40e248eee97ef789205910ebc913349698fc75ed35e82fdf","7d6133667f81aa66a98755d253ea43301b45ada338225df034d2ffdfc79829e7","7e89b59b456dde4bbbdbf8079665bd82c51d8e500018472981c15618b3893959","7ead0c68ffa0ced241af74dde58b3831343dff3f7eaab64bddb9954545b7ba12","7f8188b57ad3b0c28210c95954e5623376a4262dd5e75f002700c6094b8d6b6c","7f91dfc2ea1a3131c4090375db0f489c2a572e245ade6cda4ebd440446d6d60e","7fcb8cba3ed0ee9c342947aa88f0f699bb4f5c23244d21c6c739c9b66d7c6101","800060d7b4934508d0277f90a464e3112fd2fc99af4ef23825d09b0ff53f91c3","800a802a4ce9e597a102f0a566535c1f9f7adfc60c41af6bd2db4fb7fe3c0d0e","820c12fcbded9048a363b9e0ebbc48b24f85fd4a68131b5dfc1b19057bf09ddb","824bff7541ec2a4b0be126f0b0791314d568a0eb4e29073de4f9dbe0ee4918b8","82c419e5de083e423330432c9d45c744043d1bccd8eeccb41e3014ce9ae3c32f","8343a4211a4d0ffdb320d5a4305174d85bb707d15dad978f6436297d022daa11","83a97b9ebb29f5cd014ef5e178970a601ee92c44678f05d1860b383c5f63b79d","85a962a7c23c14dff8d683e738b53f422221697b213cafeb616d3a172a6c4223","8629fddeb4f273b35df69d4d28923adc14eff59d919b1a495d1a68818137c561","872ab2b2d65fe685b91e355f5af051c85b79569ece16448160d01fef38039624","87f2b3634baa504f2ed9508c6cf6a47bbfb36214a177eb13d70d6a987706818c","88b615ef6a31bd9958e98b8ea522f49f0360ccac5d9fa8deb9e3ef3fe3147d9d","89cafbb20d6029656266d8cb0f85103fa519c8032598282fea58c94cc59c4125","89f2105745b3a7cfd30e7d7c598d6c8fdde0a599f30fd0db7382cba50412445e","8b3eec010d1eae43a28c88434f2410a751f790a9d6ec4a08e75e68c171629ab2","8cecfa09651c40be4d7c11c117c80e1911dc75bf6f1cc34be64706823cc024c3","8d250acd40c8a24ba0d51cc73e65bba6856509b5fbf4c7d7a435897a01c6e764","8df1420c27503370db9382f68a0af8d2b4d56f9dbc94b24ffae450a905083a79","8e7371228a726f381fb811d1d812c39917788a3df7e53dba1a3c364e755a0c03","8fae27ba5117e202afbd523b249fc454912571900fc909f5419b8ac96c773c44","902b958b4db7d8d8bf73a82a8aa86e5485b39477047c8ad60175d118fe31d987","91c9ced5e9ab8da897b7f69166a7d0bade5c58d511b42d60d5430d536da45d09","941f70c384905ab77cb9a88e2671301117e4df553da6fc7a09210710deb9b6ca","9442788fa51227044803f1d3efdfc1c2b2da372871a85f0f7a6bb3596a5c003f","947a1cdd43831936480167169d30334f818bb5d882650a3547827c05204af111","971f59cc197732d0c0b6b8aabbbefca4550fb8fb04f8522bdb4257c05a28848a","98a097d6ebb754334250dfd3ccc5f3dfaf5966524758cbfc9e10adf4a0229693","98c7e4bc2f05e9b4ca703db4a02347db7355a44f04e3a4003e26c46a56bded2c","9944d1a9674e555a41d31d069d136461eb06dd4052d40f2e4ea4368dd978e01b","9b466e8fcabe551bb6292d23a359be3ea15b7627a6ad9c9e6a4ff11444c20860","9bac7daf255467f47b83723095f93fa4b574d5fc08593f48825a2b2ebb8e2dd8","9bbd03293bf53e9db51401d157b3eb2aa51e9c70449350e98b9a0a3fc9a684ce","9cf90b3aa59f3ca0e40fd9e1fec9703428752d63bded6b091d28f614c9ba99ae","9d8637e5adebaca208f21af0a254e80712988867411be560031f4b7a23cc04f6","9eb67ea41c5bcb9557ba51bbbd1b321a78f16335cadebbed848d8e6c1fc68bab","9ed400941ed49b2d90ebe3cc111d90d8bc966608ca61fe9bc315a3c1dbe8bc1b","a0ff0d0bb3a3c801b637d091293f2eeaac68e934274e4116d298ba60ec3461cc","a1baa1f699fd4ce19e8ef6cdfe346e1b0be63e16d5c5cd5feddcccb16a62f269","a3c84d76be9d891812e795dd46470c2978dceeff928d729c0d5dd6def599923b","a64e8aee389ae696d0d4b045c0153092113fa522ed5a0fd9b5658b8418db4ded","a6c531ed9bbafabfdd649f3030daf2f24461163aaf99dc73bb24dddb77bbcb90","a7ff7302e668dcea1cd1db2241ff95c0d73534539bd03fdefebbfb57f60d3849","a8b4a33078335d2811bffb78eee49aab5fcb31597dae366d43e20c7f7800994b","a91a47fb4fa5c1b1a834fa602030e435ad641240e6ceeb99eeeab7341ca09dec","a91c8a1431a4120667cd523cf56bac004794fc5b8b24275ad2f9c8a15c75fba1","a986593807953215f834ba73e7d2565659b32aa849986013f8614bb1c61ea8cf","aa131e74e695292adab9f57b3ccc5a503a836dd4b95a3b2b107c69f35dba3637","acd7884bca46ea9422503cead985691da05cca25bd5ed52a199783cae7b8b01f","ae69fe306bf5db346ddfa4367cda24c95e44213baca27b0ee7d7167bcdd85af6","ae8c200dbcea29f43b29974cc247d70647c80d5d76385396f1c82ee9f669e2f1","aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de","af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a","b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d","b0ecfca0d114bae34ffa62ac3ea05159a4415fc6eb73ab1fcc4d79f657268f19","b25c41f19ba40e646fd9b6f82051ee4c38985539e445b26bd628eae98537df53","b262187aa66e8a97083bf7f79b91595bf7a4077abe7f8be5b00b4998f4579d20","b4091f93c3d96e36b0708f5dcd46e0e7a0a48f098036ccef6164e4a6429ed94c","b4093c67a9195ee7d28d2575e967ac80057b92339489c244243c7c504c669ff0","b44352445272089cf90967d4d413cf7009bed0ac19f3fa95cb831d5ebad081c3","b4ce73bea5219f1b27bffb36c6a9dee14447a710a8938db807770083db4552ac","b5102ef50e7d4ed1925af5a8b45192e737df02fafb75d7065995a2bb93d2e8e1","b5428b5775526a00645566822530fb969b82247ba83f2c80c06d34151e1f9061","b6cf3b02f36e0efa93b04667cdc5701340033a09e41a7196277cf6756999a666","b77c6669bcd54e0fa949faf2f7205f2631acfbc1ccf79f93f8dab5c5717f0e93","b7ffd6cddb12384224772e8de79aec89d8f4bca966a3c2a05763889f92a6db5c","b8abe10a2a92bf537a49e8dee92baf8de3ed591848a1b25151dab0d7ab3134e5","b96cea09313d481dfff1ed1a2c552ea29e8fe68f52139458996a4e36157748d2","b96f9beb6d6d8fbf88c4b8b2b807a362f2640479cab6173cf64c7710817785a0","b9ad2510d8249ec4c8e7fd8b2471727aa1bd0ce8f3dde78e545fb2f8f2985a1d","ba7d7464da8e13722232c8f86273774054693681becc450a68aea21a5a0e9b91","ba87e5d43ddb10937bb17941f055f80a223d0981fbba44107aeec8530e3a7774","bac3431138e986d6426c1e81bdfe0a968394896c0751cbbcc8f36002fd0ed069","bb230236c4ab6353afb4147014c93204d3d1eb8a6d18558075df5fe79ed7f392","bb7fa81e41820d63d58313460f5a3999a1f9fc2cd2fb10cbb5b41a931d8be6a2","bd714f38c881208f1190ad714bf8fa5aa63adf302bdaa8ad8810ff279e43459e","be75cc1ee935f783be39978de91ae196c16141d4096e16eb6d07f59583296b4b","be8c3cb2d8d67e63c8b069920b74c6272922febbc6a0a2c4a0072a7a213681d2","beed0f36d9b1b9a20bfbf89c96862482b8d5b9d4284bc89539efe9c9b11f000d","bfd21b5c8eb26e9d475868bb30d66ee08f20876e9df5cd06aa8fec01ffe666df","bfe97e65f2cbe6bcd0f14ff57ea4dc1dedb2e5f0db92d04d0982cf1932ac1c3e","c112d36ba38c362da1c022945db5b6bbdc3014685ca9bb7d940f5086f00a675c","c23cf45c1dcb748145d87f5c173dd3c8becaf9e3f6fdcb3e2ca91d6726b0842a","c29b8d250a7b5e73f4ef675329da2251b8de032501e4836445b6aafd90c645fa","c329c9df0dae8a036da9be440432d045be3ee13cf5664cfa6ccf11576ed11acb","c4600cd5358b5798a075beb54539d952f200def1c9a573bd237c795fd33ba36f","c6752cc3c7ad06d1e9f127365f078919ac46b77f8a8fe413650094d914838ec3","c6867ec30530fd3feca89a4e968522f783b636b165ef74f288c42dd50bd51a3d","c6bfbb004af355e96ed5b4c8c9b8b7a96d1c08d24bcde7c666728eb9497d6d71","c77c4d3f536cda10a71fe6a9cd17ea7c1408200e2f7aa7c5325d6915ff250c85","c8bd340e6fc7fa3e97415f7ad4c22c51d88c6e77f782c12923e841c04d3f882b","cad13b6653fd9f811e67d13c5f01f9dec047f8c384097cee01dd2e2db39e539f","cc24c3770587f2421514fa399d2617201752bdca145ac39058de91d45d3d19c1","cd2da00f6f1bad8fb7c1b87cff80e122eb017e44a471cdea769efc67db369038","cdbb7338988f2fd35fd92f21909b7801d9954d1c7ca78401f52c9313f21fb6dc","ce887fb65b6977a2046e7583d704863624e55909ebcc9c3ed065b3d13079a410","cf9223c369b6fb7baa52f301f904352ba8e8d5e4c2a06f70de6ef1cf76fe1b84","cfc3b5044af37ae7485fba8067dcb22b2438bdaa6e3a30c22ce0f9e2c00aa597","d0481d9b6111ab4afba0462e88970b863284807ff44ca97364c84952e3f88583","d0973a1aca6a118375b466d6e91821f8450110fdf042ac848ee16912012d2b0f","d0df3068db679e24d9487ee09a6462ac5cf3df30f46ee466b66feb6dd5ff71e2","d227e0a73e3c5452bc5ab41ea2c695dfc0ff9b0c1c81e59ab3173f796a4157cf","d2cba4dbbfe3d026f825a8b470a2f6011f9b8e245cf042ae8889afbb17dac6b2","d2e4c515093f8a2aa824c8b542a016e5c321065f4525931b2fac4f8af2fe52c6","d31e8aa21d1498f2d4a07c4cc89ea6f5a6d3ce54d334dbff230e0f55db35c85e","d37de74aadd5916eeae243decf347821c4e946356b9f70471658638ac3092f91","d3cf9b1433fd9a083c60baf6ade1df7f2a33e0cc7d519f491f9d6a93139a41e4","d49d02cad8bbfeac607457b08aac6068916ef45d8f6c980279d6e654407cc7be","d4f51c31a454d9abac29457cbbc21e1b5767c0eac1b37c41ee787a3efb05c80f","d5c084e12da4a5111487c166b879042a21a056f761ee22d9237cb4f65f366341","d6077d547aa21ea10a9bdf6c752b8d1a0a6382b4b43a0fdf790f245e66a609fc","d67e8c1aaab1ce6ec1755599ecde153c47c6b90dd4c301663abe9057bc31af57","d6abcc1484c3df45bde915abf48324af1e995c3266a3c6c069e98e94c8d9a4d7","d8ca8e025e226ad6bdd32a6a9fceae2982b0413a0ad09314558b54bdc724bf99","d8d03142030c11a0aa1012102fce2b202baf88e424a1236832937e87450dc579","d9823dfddf6c507ec030fce4bd2d98fbda18e595c2ebc563574d9196cc7a5e33","d9b0972f3406075b860ba7cd2e71d4492c826960319b10389c2c2820e2981254","da37a61fab07ec8856b725854e4064f55a59149aa69cad1bcbf89ec478b9f578","dad01e5bfb13a6c4419f4d24fa8dbb424e93a1c4be656b0e5dd48ac546e0a0d9","db049e7abb7c75b608ae25cc8a9f95959f7aedaa53e22390290319cc2eed3977","db21a75b4fa6165f75268963474f3262124795d816ba80f685bab2c6eaedb028","dd97ab52fd89f42352c595ce137684cc519c473fa17969e8a6adcde7322a4748","dda0a34d6704887eb36bbc0173334b49d755cac8cea3bbd17bfa972f04183dd4","ddbda9408727a19a4a55d516bed99331edf67d8301de9c78564716465c949619","e0288c94ca9c16a6de217e6baeed720fcf83e401bec45bd15ca47ba8fc9b44dd","e1667469384ec775a3df665679cb3fef057dc84dcb18ed8db8b9c5723835968a","e16c328504278cfe520d6d99990f2a4370cc48159aba86694d0f7598fd4b0611","e24df071f5325bb3a5b20f355143556bc7712535ee8b6ce4c426598f06fd2448","e28d8e6b71264d0bfab853e63178f2c151367cce0dbd16125596ff3604b6658d","e2c734504d211580b4e6674eb1c7d31fb6fb730c037210c34c980a96f9098269","e3f19c383354cdf45311f92f00b90fed25dfba7e9892ab2f5f3aa4885876b75f","e409fbfe439455330c0fe003de860e30f7093cc3cc83a32f886c9b539a29f60b","e6300ee8e6c2c4ce6d7ab02b7b06fd1cabe3c5c52b99a6ea3ea8b5acd5092e0b","e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d","e734d068446591aba283d136c21b4fb0209f91352cb4fc6589bd651cdbfec163","e7a333109a7aaec2b71048868500c15e721900628eb48790dfeaa1fd4c2dabc3","e7c9175fbfd9fd84bed95d552bc0a439b07a233c3e91fb39ae2f23197ee53f1b","ea1b8a251ecc1fd96697d0c602d3e14ec46383d27bb9485a0326cea5576ffacb","ea311dca2ef14e02b9aae563bb28dc737b04b7f01c1ceb2be3d92007d2c74ac6","ea8e5b79bbe5329ae8437677c8316f2f9fd75bb1d40c88308c269140a7e564c7","eb996138bc91c0ee63bafe1ba10b130ff5a2fc82aa4918296222e0a831a569fe","eba6e8e5a12a86f17fade41bef365aa95491c469e18aa91aef64908a4263c905","edc160a11c07dda8072748b66db7f27b6cd8efbd1faa3f6c826a0fe445859c17","edfcbe4773eac1fe2964179a4ad21294efede89568f2efd8e283ac18bc5693b1","f0f90dee84db760cc1bb0f6e6983d4de0e3d5d9f4adf7b2b52f0d3dbe6d585a4","f1d4a6e98f41ab3f6cfd67cddeab9d0ed287b92cb3dbe575e3ce61925510a792","f21c3a9267110e469f224ac7eb76ca5bb084fc90df014f1ca6791d5770483944","f379a1b9e29aa7fc25c4c0c897eaa3c0e90d66a201a0ade8cbf523a5cdc8cf50","f3e04891c79b604f9235f438adfa49ee27db43d25c7be0d1cc06ae53b8f6d2d8","f46904e701174fe2850798d9e1b077bdac42fcac01dbc385298da01118c82aa6","f53265f53af0b0856911ab08b373736964d0c443e8ba61d7f1d45f5e5b04edf3","f686173d310f41e26e3fe8a7c1dbf4313e4d793323335348badbcf4633f5d699","f704c9c9e2cab1ed44578f48d161320b5fb4384ecdd8b40a5e22c4078a8594da","f89156489d35f9992d5971a52a6e03a7d7f095e15c2c782e85efb1408a2bd6be","f99ef6fa3c9c6bf572ec69eb6eeea9f88ce6590d3a5565bec62b001b6f2a376a","fa2dfc22b4fdbcf402a822e8dd376925655d997a0f96284a60f10665ba3581ba","fa3df5f8349aec4805bbcd279b88697def63f2462d8ada0b5fe1d9983d9a6daa","fa6b97cbca1d4f09662e706293b0aec1eb76b8e2277441f54ab6c548b5423236","faac0c3fa7cdf67b452d407e9a1db5cbe1e9140ecfe300200b0b0a6279c97c66","fbc8b53b5c6f3727c084e5e0429e410a3fed5a17e1a0144692fd196d9836a4bb","fd04d7588bb9e6ca0a8b65ed0c9635082a9ee5f46b2d1b5b25866a072236c1fc","fd60f2a432086c6fc4a4c39d8d2d6edf5794c763c05a6401db2bb5fa2c601775","fd618761103380d690cb98804e8f116b6c66ef049fbf67c1a059ce49188658b3","ff532716738e2fc716c10797d9717f324cca3a1234320a84a73a0b89569f11ab","ffd0fe3449e449c7b9fcdcc7e2c1ffb677e57ad935a252de88a0122d437efa67","ffde5c700732beac27a9b5162213d387422ce199400e56d9cefe550005b6a542"],"schema":"fsgg.atlas/1"}
diff --git a/docs/atlas/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json b/docs/atlas/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
new file mode 100644
index 000000000..9e566e7c5
--- /dev/null
+++ b/docs/atlas/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json
@@ -0,0 +1 @@
+{"citations":[{"path":"docs/coordination/2026-09-29-coordination-v2-board-design.md","repository":"FS-GG/.github","revision":"3ced04fad887e9840bfcb893834020ece4b2424a","sha256":"f3d8fa3da3bb6b2156e6337e12a4b9bfe44d91ff621c96d0c608249cfc5dcc95"},{"path":"tools/BoardV2Import/Program.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"f154be5f98b6a3845ac73c94e50c441400720a3fc654b8483ce23a1633963428"},{"path":"src/FS.GG.Coord.GitHub/V2Projection.fs","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"c6c4907b54028322b13d112e08f8050482c80165fb359f475f3e595c8ed05c96"},{"path":"tests/coord-board-v2-cli-join/INSPECT.md","repository":"FS-GG/.github","revision":"9772af87da9cf299754ab106bba051e65bed88c0","sha256":"16f754671ed4e94051b230595e3c46b148a4f696bb8f8aa850c059675c9e3403"}],"conflictsWith":[],"id":"github/programme-binding-custody-recovery","kind":"decision","recordedAt":"2026-10-19T08:55:14Z","repository":"FS-GG/.github","schema":"fsgg.atlas/1","status":"recorded","summary":"Programme/root accepts host receipt6262652143 and independent MATCH6262659355 for the5526-byte private archive: exclusive0600host copy, separate0600client restore, full-byte/hash/manifest/pair readback and file/parent fsync. Home retains the exact archive and proof in ~eugen/.local/state/v3-storage/session-recovery-20261019/ as programme-binding-pairs-20261019-0758.tar.gz until explicitrootdisposition. This host-owned0700ext4 directory is NOT mounted into the client; restoration uses the existing bounded private copy/readback route. Host disk loss, off-machine backup, power-loss behavior and actual client replacement remain unqualified. The original lost directory was outside the persistent mount. The telemetry spool remains dedicated to telemetry.\n\nClient staging ~/.local/share/fs-gg-private/programme-custody-20261019-0756/ is volatile, not sufficient custody. The archive holds both distinct new binding4/schema2 and binding5/schema3 original pairs with their exact templates/payloads and closed manifest, selecting22current issues (previous21plus4682), excluding threevisible members. Recovery retrieves this Atlas ID, reconciles4516receipt and4682ownership, restores to a NEW restrictive path, verifies the exact archive/manifest/commitments, and preserves all originals. Public Atlas/Git never holds private identities, nonce/payload, journals, credentials or runtime assets.\n\nPR4690 protected041a60cb carries the new4 commitment. Actual authenticated installed107 inspection2 exits0 within270seconds:22Current sources,25complete memberships, no population/membership/repository gaps,0mutations.21healthVerified and4682Unknown solelypreservedunsetObservation; read/planning complete. Independent review accepts this bounded fresh4 reader baseline. The final runtime file differs from its original only by protected populationRevision. It is not scheduling authority, UI/product acceptance or executed rollback. Constructor9772/artifact430d, publishedadapter75ab/artifact7ab and protected population revision remain distinct authenticated axes; fresh public107archive comparison matches all82installed payload members.\n\nThe successor candidate selects the separately host-custodied5commitment, not installed adoption. Actual pre-activation inspection3 with current protected4 source rejects5private commitment before issue attempts,0mutations. An earlier draft-source attempt failed canonical acquisition and is retained as setupfailure, not causal proof. Installed5positive qualification must follow its exact protected revision. Real bounded rollback must restore4public commitment through normal source delivery and derive an exclusive runtime binding at that protected revision preserving originalnonce/payload; separately restore/requalify5. UI/product/continuation and actualrestart/rollback remain open. Preserve original20-row history unavailable,439inherited/46later Unknown holds unreleased and reported25+5nativeeffects unreconciled without journals. Current metadata never settles those originals; no write replay or receipt reconstruction is selected. Canonical work-board owns4682/4641continuation.\n\nSuperseding qualification findings: after protected5 delivery4691/a0e392c8, actual installed107 inspection3 of all22 reaches500 requests after187.79s,18Current/4Unknown, zero mutations; final barriers refuse. Source-only108 combines successor membership/planning reads with fresh schema, full pagination, exact identities/options and unchanged500/270 limits. Projection125/125 and CLI75/75 pass; unchanged old source with the same22-item regression fails at exactly500sends/exit3. Independent reader review passed. This establishes causal source repair, not installed108 acceptance.\n\nActual public Creator017 all89members match its release, but fresh Rendering fails before target creation: packaged adapter8fb92b18 differs from published107adapter7ab62708. Strict physical identity stays. Bounded Astra-high plan selects promoted108 original full dependency closure reused by prospectiveCreator018; source-only compilation is separate, real108 pin must be absent until publication, and018 candidate/publisher must refuse without it. No fake digests, compiler-rebuild substitute or017replay. Existing frozen016/099 history remains immutable.\n\nUser visual UI check passed2026-10-19 and root accepts that scoped human evidence; no repeat UI check is required. The earlier statement that UI is open is superseded only for that scope. Actual published108/018, installed instruction/caller qualification, product journeys, programme continuation and real restart/rollback remain open. Work-board remains canonical start/continuation, owner4682 under4641. Current private failure/test reports remain client-local; root owns their durable evidence capture gap. Host-held originalpair archive remains retained, with no new disk-loss or restart qualification.","supersedes":["e65e28b172b77d093f5425112bdae7ab93756487226fd7363057f85bb2a2556d"],"tags":["coordination","binding","custody","recovery","enrollment","atlas","qualification"],"title":"Retained pairs and passed visual check leave successor request budget and Creator artifact identity to qualify"}
diff --git a/docs/coordination/2026-09-29-coordination-v2-board-design.md b/docs/coordination/2026-09-29-coordination-v2-board-design.md
index 88f600878..5cfa34705 100644
--- a/docs/coordination/2026-09-29-coordination-v2-board-design.md
+++ b/docs/coordination/2026-09-29-coordination-v2-board-design.md
@@ -240,6 +240,49 @@ continuation and parent acceptance remain open. Recovery uses Atlas ID
`github/programme-binding-custody-recovery`, the exact host-retention receipt and private manifest;
a public commitment or volatile staging path alone cannot recover private bytes.
+### Successor reader and Creator qualification findings — 2026-10-19
+
+The user confirmed that the visual UI check has passed. Root accepts that scoped human evidence
+separately from API metadata and installed caller qualification; no repeat visual check is required.
+The full #4682 and #4641 promises remain unchanged.
+
+After PR4691 protected the separately retained binding5 commitment at
+`a0e392c873246a1184f94befd87485525fdf87ed`, actual installed107 inspection3 selected the full22-item
+cohort but reached its unchanged500-request ceiling after187.79seconds. Eighteen sources were Current
+and four Unknown; final enrollment and membership barriers failed closed with zero mutations.
+This is an actual qualification failure, not successor acceptance. Preserve the private original
+report and pairs; reducing enrollment or raising the500-request/270-second limits is not selected.
+
+The source repair combines membership and planning acquisition only for binding5. It preserves
+fresh schema and final barriers, complete membership pagination, owner/content identities and bound
+field/option checks, without cross-item caching. Binding4, product binding3 and writer behavior retain
+their existing paths. All125 projection and75 CLI integration tests passed. The same22-item CLI
+regression against unchanged old source fails with exit3 and exactly500 sends at the determining
+request ceiling; its setup/build succeeds. Independent bounded reader review passed. These are source
+and synthetic transport results, not a published or installed108 qualification.
+
+Fresh public Creator017 installation matches all89 release tool members, but its actual fresh
+Rendering invocation refuses the published107 adapter before creating the target. Creator's adapter
+SHA256 is `8fb92b182d9f862700a52cb047dc16791fe06772db99afdf19e833add02d1c36`;
+published CLI107 uses `7ab6270814383cdb96e06f06aab3feb592aae8000c551464df0edd78d29d9887`.
+Rebuilding a nominally matching F# graph does not establish physical identity. Keep the strict hash
+check, original failure, immutable017 publication and Creator016/frozen099 history.
+
+The bounded material replan selects coherent108 publication first, followed by prospective Creator018
+reuse of the exact promoted108 dependency closure. Normal source qualification may compile the108
+source graph, but018 candidate/publication must refuse before costly build/effects until a real
+promoted108 dependency pin is delivered. No future digest, rebuilt adapter substitute or017 replay is
+admitted. Package evidence must be parsed and independently matched to all shared dependency bytes.
+Pipeline preflight reuses the maintained static workflow-order, artifact-body and fake-provider
+controls, with a bounded local warm target below60seconds. They must prove missing/invalid pins stop
+before SDK/credential launch and source-only evidence cannot enter publication. The publication state
+machine and historical seals remain unchanged, so a new custom model would duplicate existing controls;
+none is selected. No measured runner-minute saving is claimed.
+
+New source, actual publication/install, product fresh/upgrade journeys, programme continuation and real
+restart/rollback remain separate acceptance steps. Root owns the Atlas capture and original private
+evidence custody gap until those findings and artifacts are durably delivered.
+
### Accepted installed real-use qualification — 2026-10-18
Root accepted the original installed 0.105 invocations against that final binding:
diff --git a/docs/registry/compatibility.md b/docs/registry/compatibility.md
index 3c5a68da9..7a345a1bb 100644
--- a/docs/registry/compatibility.md
+++ b/docs/registry/compatibility.md
@@ -179,9 +179,9 @@ authored `Version` cells of the Versioned contracts table (#748).*
| `fs-gg-audio` | FS.GG.Audio | `0.6.0` | `0.6.0` |
| `fs-gg-net` | FS.GG.Net | `0.6.0` | `0.6.0` |
| `keyboard-input` | FS.GG.Rendering | `0.5.0` | — |
-| `coord-engine` | FS-GG/.github | `0.107.0` | `0.107.0` |
+| `coord-engine` | FS-GG/.github | `0.108.0` | `0.107.0` |
| `telemetry-host` | FS-GG/.github | `0.7.0` | `0.7.0` |
-| `new-sdd-workspace` | FS-GG/.github | `0.17.0` | `0.17.0` |
+| `new-sdd-workspace` | FS-GG/.github | `0.18.0` | `0.17.0` |
| `fs-gg-workspace-template` | FS.GG.Templates | `0.19.0` | `0.19.0` |
| `game-skills` | FS.GG.Game | `0.9.0` | `0.9.0` |
| `rendering-skills` | FS.GG.Rendering | `0.2.0` | `0.2.0` |
diff --git a/docs/reports/gs2-08-9-release-route-dispositions.json b/docs/reports/gs2-08-9-release-route-dispositions.json
index 8f9ffca3c..38583c639 100644
--- a/docs/reports/gs2-08-9-release-route-dispositions.json
+++ b/docs/reports/gs2-08-9-release-route-dispositions.json
@@ -31,17 +31,17 @@
},
{
"path": ".github/workflows/release-new-sdd-workspace.yml",
- "sha256": "4029accb49163dca405159077e4b2e24ce18c20aa7f121708cd1422ddd24b971",
+ "sha256": "dab56ded18ce504f3a1506bd082e72d7527923664c79e9c07aa8e58c7773ffbd",
"disposition": "exact-source-protected-journal-successor-only",
"successorAmendment": {
- "unit": "COORD-BOARD-V2-01.11",
- "version": "0.17.0",
- "reason": "Independent Creator0.17 source packages the canonical work-board materializer and normal coherent0.107 eleven-project graph. Retained Creator0.16/frozen0.99 and historical0.13 recovery remain history; coherent0.107 does not publish Creator.",
+ "unit": "CBC-01",
+ "version": "0.18.0",
+ "reason": "Creator018 source-only current graph qualification is distinct from exact promoted108 dependency reuse. The real fixed pin remains absent; candidate and publisher refuse before compilation or credential/effect admission. Historical017/016/013 identities and seals remain retained.",
"sealedPredecessorSha256": "28bb782d48c1d0fbf4f71e1000dc73fb1517fda3a8b71942358c604855a2360f",
- "previousSuccessorWorkflowSha256": "cef8b997e05cca5c9d5c0c97d74cb55afe34220e821e46fa650e7360d0b6d746",
- "previousAcceptedSource": "2e60210be1e04d52fe0735a56333b3e3aef42284",
- "sourceQualification": "source and fake-provider controls; actual package qualification is separately recorded",
- "operationAcceptance": "candidate, journal initialization, protected preflight and 0.17 publication not performed"
+ "previousSuccessorWorkflowSha256": "4029accb49163dca405159077e4b2e24ce18c20aa7f121708cd1422ddd24b971",
+ "previousAcceptedSource": "a0e392c873246a1184f94befd87485525fdf87ed",
+ "sourceQualification": "inert synthetic closure/evidence controls; staged current SDK compilation and genuine publication remain separate",
+ "operationAcceptance": "Source only; no108/018 candidate, pin, journal initialization, protected preflight, publication, installation or native adoption acceptance."
},
"historicalDisposition": "manual-local-pack-only",
"historicalCapabilityLoss": [
@@ -89,7 +89,7 @@
"recovery-diagnostic": "521da9edc1772ecd845bd7f6cae4ad461e2f49ce93bc2110747bc32a819d9dcf",
"recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
},
- "currentBinding": "CURRENT_017",
+ "currentBinding": "CURRENT_018",
"historicalBinding": "HISTORICAL_013",
"effectAdmission": "pending independent native candidate, held-main and protected-journal authority; no source-test admission",
"historicalRecoveryAssignmentSourceSha256": {
@@ -318,6 +318,25 @@
"originalH4Accepted": false,
"oldEffectGrantRenewed": false,
"operationAcceptance": "Source only; no candidate, journal initialization, protected preflight or Creator017 publication acceptance."
+ },
+ "creator018ProfileAmendment": {
+ "unit": "CBC-01",
+ "previousAcceptedSource": "a0e392c873246a1184f94befd87485525fdf87ed",
+ "previousSuccessorWorkflowSha256": "4029accb49163dca405159077e4b2e24ce18c20aa7f121708cd1422ddd24b971",
+ "previousPublishJobSourceSha256": "4abc07aba92442ab73cb6ce8c93793397bb5df2f862ddac335f816891a618c11",
+ "currentPublishJobSourceSha256": "8aadf9b2c45feacb2f1e739aec2d383aa38946c4ce81ec0d5e6c8085b752951f",
+ "currentBinding": "CURRENT_018",
+ "retainedBindings": [
+ "CURRENT_017",
+ "CURRENT_016",
+ "HISTORICAL_013"
+ ],
+ "coherentSourceVersion": "0.108.0",
+ "freshLogicalJournal": "board-v2-product-creator-018",
+ "dependencyMode": "published-dependency",
+ "realPinPresent": false,
+ "oldEffectGrantRenewed": false,
+ "operationAcceptance": "Source only; no108/018 candidate, pin, journal initialization, protected preflight, publication, installation or native adoption acceptance."
}
}
},
@@ -1077,6 +1096,302 @@
}
}
}
+ },
+ {
+ "status": "non-current-history",
+ "acceptedSource": "a0e392c873246a1184f94befd87485525fdf87ed",
+ "route": {
+ "path": ".github/workflows/release-new-sdd-workspace.yml",
+ "sha256": "4029accb49163dca405159077e4b2e24ce18c20aa7f121708cd1422ddd24b971",
+ "disposition": "exact-source-protected-journal-successor-only",
+ "successorAmendment": {
+ "unit": "COORD-BOARD-V2-01.11",
+ "version": "0.17.0",
+ "reason": "Independent Creator0.17 source packages the canonical work-board materializer and normal coherent0.107 eleven-project graph. Retained Creator0.16/frozen0.99 and historical0.13 recovery remain history; coherent0.107 does not publish Creator.",
+ "sealedPredecessorSha256": "28bb782d48c1d0fbf4f71e1000dc73fb1517fda3a8b71942358c604855a2360f",
+ "previousSuccessorWorkflowSha256": "cef8b997e05cca5c9d5c0c97d74cb55afe34220e821e46fa650e7360d0b6d746",
+ "previousAcceptedSource": "2e60210be1e04d52fe0735a56333b3e3aef42284",
+ "sourceQualification": "source and fake-provider controls; actual package qualification is separately recorded",
+ "operationAcceptance": "candidate, journal initialization, protected preflight and 0.17 publication not performed"
+ },
+ "historicalDisposition": "manual-local-pack-only",
+ "historicalCapabilityLoss": [
+ "tag-trigger",
+ "packages-write",
+ "oidc-token",
+ "github-package-publish",
+ "nuget-package-publish"
+ ],
+ "capabilityLoss": [
+ "tag-trigger",
+ "direct-package-publish",
+ "repack-after-candidate",
+ "unadmitted-release-effects"
+ ],
+ "forwardRecoveryAmendment": {
+ "unit": "W013-FR-H1",
+ "owner": "TSDD-KNOWLEDGE-01.4",
+ "version": "0.13.0",
+ "previousSuccessorWorkflowSha256": "5704613f20a68efce211f699189f439af46c1a8387d1859625e06882978efa7a",
+ "scope": "Default-off, uniquely selected first-attempt native Wizard diagnostic or promotion-only forward completion of the original candidate and protected open intent. No package push/repack, new tag/assets, journal reset or generic replay. Diagnostic permissions are read-only; correction permits one exact release PATCH and ordinary forward protected CAS after independent matching readback. Private raw custody leaves the runner only as recipient-bound AES-GCM CMS ciphertext. Source readiness is not operation admission or publication acceptance."
+ },
+ "bindingIsolationProof": {
+ "test": "tests/release-effect-sealing/run.py",
+ "historicalRecoverySource": "d8297c9b5510fb2cf7d2ea4023fe6a99e2f813d9",
+ "historicalRecoveryConstants": {
+ "PROC_CAP": 8192,
+ "MEMBER_CAP": 128,
+ "CUSTODY_MEMBER_CAP": 323,
+ "CUSTODY_PATH_CAP": 256,
+ "REF": "refs/heads/fsgg/v2/journal/release/tsdd-knowledge-wizard-013",
+ "REPO": "FS-GG/.github",
+ "CANDIDATE_SOURCE": "f891b5b0723070c67e08d1a87b7d12b0b4d8bebe",
+ "CANDIDATE_RUN": 37159899280,
+ "ARTIFACT": 11287256853,
+ "ARCHIVE": "46055667bb35affacbc7c3be47a4eaea8983ae786267ff00bd9173d66b538244",
+ "ORIGINAL_PACKAGE": "accab9375f0adff5cc770f096ada7c56428674fc5c801449ad91cff4c39ccc37",
+ "FAILED_RUN": 37160659521,
+ "RELEASE": 402727082,
+ "JOURNAL_HEAD": "dbc2c4e578cb41e9f6aa31f18557cd95745346f7",
+ "PREVIOUS_SOURCE": "4889c446de0a431d1168a61a89ab660fc2062314",
+ "WORKFLOW": ".github/workflows/release-new-sdd-workspace.yml"
+ },
+ "historicalRecoveryJobSha256": {
+ "recovery-diagnostic": "521da9edc1772ecd845bd7f6cae4ad461e2f49ce93bc2110747bc32a819d9dcf",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "currentBinding": "CURRENT_017",
+ "historicalBinding": "HISTORICAL_013",
+ "effectAdmission": "pending independent native candidate, held-main and protected-journal authority; no source-test admission",
+ "historicalRecoveryAssignmentSourceSha256": {
+ "Path": "2f4c7565b6098124301826b8ae62a305c58187badcba2ccbafa0dfd3e8a05819",
+ "STREAM_CAP": "3dc581ee96f7b54a539768574d979742ff24658cf7bfa956c90c4fc12e12e06b",
+ "PROC_CAP": "b1bbe79c5ca89b2cefcbf98979d76640cc0466cd02c6f0acc326e6daac47a762",
+ "MEMBER_CAP": "0937996c2a29fe3a23d2ee81090cf9452f825820c1326cb5c05941168d5d771f",
+ "JSON_CAP": "99cfcf5da994279b14aac9901fb6d30f6d051d540540a195f3135ce208a8eb3c",
+ "BINARY_CAP": "065df542f62e536600807e09cb2a5ead4bf8e195ff79dc5d87cbe3bea3cf7b44",
+ "ZIP_CAP": "fe5bdef0143584cfae9398d0fdbd5a66c90e8b2988ac004aeebd3d5d288f49bb",
+ "CUSTODY_CAP": "9cada8fce6b294c1899cd3ea1209196cf4fcbe24502240276346299f9f525889",
+ "READINESS_CAP": "b59b681160b18d599aba76d3552fbecf5998016ed5944f5ba9f9a17d116e4bca",
+ "SMALL_JSON_CAP": "eb2462c97d2cdbf44b739da9faf075253693ce14aaa592d2a58df965187e0401",
+ "ANCESTRY_JSON_CAP": "6630a5b7e4767971fd413fe4fcfcd1485a5eb312415376a55f0f0b42c206b73c",
+ "INSTALL_TREE_CAP": "a8226171f0e527836b165dca817b190d20e64ae3684d475574972fec3ae314db",
+ "CUSTODY_MEMBER_CAP": "6dcb5e78948273b8e868629e226d56332821c2a2ec08e51d81144b2b0893a3e0",
+ "CUSTODY_PATH_CAP": "ebd0f367b8f7555b3e073f3255d0fdadcb9e8edb4bb12c7117bf96fec13768df",
+ "PHYSICAL_CUSTODY_CAP": "590fcb75332cf0ab0afd7392e1f3eea54f2f63b49792f6e12f6c22c47c02ca07",
+ "REF": "cb7e2cc2adeba05e1f7f92b2035b77ba69b33180f0869b026b72910a4b0de7f3",
+ "REPO": "cc3d010f98e52f2015466de845d26ce855547d4e626c5a374fae3f826a0bbfef",
+ "CANDIDATE_SOURCE": "63720fb2390ac212486c4bf23db45a587ecf0b0506c9cb601e8162a91fab28e9",
+ "CANDIDATE_RUN": "7b63f3cf4f4b1f799e6aa2c9823ca9a6a0648fd3fe4bf059e35f4dc6b2cc9c8d",
+ "ARTIFACT": "40b9d2fd062fde331f4efc3186ffd3323f1a64754ed994e9226e2bc9ac10eed8",
+ "ARCHIVE": "eca567c491b600a6bc8c19a28e08339b8db87b8e1a1cb4ad5c3883d0ca80aa09",
+ "ORIGINAL_PACKAGE": "fac8fdb444b704ef7a44f111b27c6a7a3fca0b01928bec02891b560a2f881542",
+ "FAILED_RUN": "e79e033b2a2dc0997ec9b2e12ea7c3786d2dd010eb546ff3ac3a43428f104a90",
+ "RELEASE": "4aca661088dac0b975d97c1167ac555ec88fee9aa81b130eb62457eaa2eff7ce",
+ "JOURNAL_HEAD": "9afa971b72680910b5eda5e616747cf4346284e764598a69002d2c40c9571b8f",
+ "PREVIOUS_SOURCE": "acb357db0dcb29ea4396fcd5dddb90cb4436ea38fd93b9758475d6b03d6e53b5",
+ "WORKFLOW": "f16467d0fb13fbdbea70965d02fbe1e180bc149b41f850c602efe3fb7f5a3046",
+ "SAFE_REFUSAL_CODES": "9cd639b58d32fd1668090605eb2661f46b48f7c326b1f129a809a27ebfb2339a",
+ "SAFE_PHASES": "b617d494cdc7bd0056c7ec584d0642e355289b551fcc98f7e7720c536492e1da",
+ "_current_phase": "7515b5f7c15cff32643f32d9a440e65ae0ff3a8bf780362e9c8099829fe7815a",
+ "SDK_SCOPE_POLICY": "4461d8a05e9c1c8b1d2e3b6c89cbb0d48724eed177e1cd9844425641b8454ed0",
+ "ORIGINAL_RUNTIME_CONFIG_MEMBER": "949de1cedcb3efe922ccbda0f06c680bfa09dce89e78405ffcc0df27173bf99e",
+ "ORIGINAL_RUNTIME_CONFIG_SHA256": "489d5e8e00e03d36f1417124f6b6996491bd8508b95341d0bf579ebf7eccde6f",
+ "ORIGINAL_RUNTIME_OPTIONS": "ac6b4f012de73e44a0442a6604be4cd074ba96d1be3f356d13bdd7cb5cc4fd52",
+ "SDK_FORBIDDEN_ENV": "aafde3e9875b1ef610aa22475c35130ff0ec6e07b8ebcb1dd5bbb37baf7f46a8"
+ },
+ "historicalGuardFunctionSourceSha256": {
+ "require": "911f7b9d9387f8dc174f050d2fa1a36fa73217a9acca24356570d42c403ba44e",
+ "digest": "c36fee10252da2653bd4463a40c0b17609ec00a6c1c18c61ea743db668e851b1",
+ "canonical": "928ef04c56d4adb1bccc6771a20def6aef5746b265f98e9e0a9411b8ef8e5e69",
+ "load_module": "8abadd91fcdfbd33ef5fa2999c284fe7646de712a22a624123115972f5ea2c2d",
+ "validate_binding": "fcf1aa0418a9c93af13ea980528ddb26cf81793c0807ad69fba14b5d1ee3ffaf",
+ "recovery_phase": "8c76d1346a333028493c8ec1aa76d1235000e3a311bc94fc57bc39b0136e5fd2",
+ "recovery_refusal": "4b9d69d1f42588fec1d327970fd94b4bc84d5770defad2f75d491933c11963a2",
+ "existing_sdk_root": "4df3979f72f9dbbe8dae7d087460e3398ffb610cd9e2cfe425e7c1589a9e6b47",
+ "proc_identity": "519c48c35b0d8a3094fd2e502d2d5588001cb6ee65c894b8341e8666bbcdbf56",
+ "all_processes": "5a77c37c4a3be495af8b0d96f38550ee85f2102d2f3aede8ed2df2b46628b1e6",
+ "same_process": "17bd73576055550bca2598eb4003d774d4ad112b71614d3b76765f5b1f201118",
+ "capture": "bdb6a437b90f6b5b10c165439a4552c2ace032081b8985cb45aeaf2214d1943c",
+ "subreaper": "9b99f6cbe121e4e259a61384cdc4fa921a1a58f7992a213357ca6fff0ff263ae",
+ "child_environment": "2039265e1e185b8045c1589971fc8826906cbc4fa667f1be15df1c13716c60f5",
+ "sdk_input_environment": "460ae71b64949d261b85b3320b668369f6a37551a0776296fba96ea3487b0d7b",
+ "sdk_scope_versions": "0c7157d4e60261298945004e4a61d5b9953d26155008fd26cc287dc8fd9375ad",
+ "sdk_scope_requirements": "08c02c2f772b2b4c428c3df4fb078fe833fb8b4bc85ece34bfc37c634315fe02",
+ "selected_sdk_scope": "ce983bc30e0e73fd1787904a5bfbda8382e918fb3fc11b7442237c05196ffd7c",
+ "selected_sdk_roster": "c40cefb18383c044dea795ff7d8d44be9dedd5b063dea14b45f7ce52e5f33f8c",
+ "sdk_snapshot": "62ab34d292556b777d0871d0a2341f45422d01c89086007546f29ec721721887",
+ "physical_roster": "276d9bbae6e0708b876d2745abaf7ad7a858a4956a2b2244c357c185615e437a",
+ "source_snapshot": "76f77fa96921bc21d29ace61f952a9cb749981888084129124373be2fdbe374c",
+ "safe_zip": "72a08fa2d2bf9c5be4dca84724262eb5aea434b7503f3dc7ef9b7569766ab44f",
+ "native_context": "0af5921c1ef18e9b801240f757056ff93313f0f0ef7915b9b309b0b5b99fc704",
+ "original_runs": "f1e7a7523106e1255be9fc8763c6005614caab957eb1f16855b8b3092f8fbcfd",
+ "readiness": "b5df49c97c5b75fed60c22fb8aa01f60748c1d5529be12550a01d26c7a4eaf61",
+ "predecessor": "42ce73c68a363113e8a6292188ed482efa89589fd9ae20f7e3ea4d5508636bf4",
+ "candidate": "fc27b8c7e2001b638c64ad1c0e6122cf0ab3a84645495c334391197525a4aeb1",
+ "installed_closure": "1a30a74878ee4c7be99ae028f54ecd5546f06da8f088bb1e48c3e4fc06bee13f",
+ "public_install": "b1c360bad8b3d0946733bc0690e3c707b775cac07e0f54cc947e1f13fac7a2c7",
+ "recipient": "7b9f4c3730b9ed1e08e8b54bda70eb83980f20f267fb54cae111874f799ee40d",
+ "encrypted_custody": "024c0407712abe23d3d9a78c0ad6a945f05470a96b5ed0265089777cf2574143",
+ "outer": "45c982686a927efca46eb86aaef65275b2c48bbdc1a26668498a5d633ff95c93",
+ "entry": "85d410ecd5190a086a14b9d8dbec0ef88e9c5bf1a65acfa4be525b5f591ac770",
+ "ancestry_url": "d4d2d11483a8145dee1439610bea2616af30f0021289dbd542269d633a49ce2e",
+ "validate_ancestry": "224e6b4fbed77a449910be7f99830923ff9c2ea252398e580f3082afb0b4eea4",
+ "http_failure_projection": "ffcbb64df9c3865db0696f78a1adc5fd48b96d9c8af8c4c36dcd91daa2d3d014",
+ "worker": "abc1e27c729b7408ff26bedb4e42370220afb29630be292c25854722249a2692"
+ },
+ "sourceSpanContract": "SHA-256 of exact UTF-8 ast.get_source_segment bytes for each named top-level assignment/function and explicitly named method, including internal whitespace/comments; AST serialization is not evidence.",
+ "pagedAncestryMethodSourceSha256": {
+ "FiniteAPI.request": "9e1f15f7345d9d86cc1893102f76e2906889dc3a4c4cd75d3f3604462448941f",
+ "Redirect.redirect_request": "b4c529308be5f519e01cf4a27f6e230d1c55834b5e22451ffb7ab98ae7ab65fe",
+ "FiniteAPI.capture_http_error": "93f2ee934ac9dc0a2cb5b577498af753dfbf33b26b73b7f2de40b79d006d6c6b"
+ },
+ "pagedAncestryAmendment": {
+ "unit": "TSDD-KNOWLEDGE-01.4",
+ "originalItem": "TEMPLATES-H2",
+ "sourceCandidate": "44667c54a81ed9fdc63ab5bc4174b8448bb49f32",
+ "acceptedReviewSha256": "05928c08a8bc9ab59c76d65b0d2a5cac25f3458e37f43769bf38f2ada2e298e3",
+ "previousOriginalRunsSourceSha256": "0a5cbcb4ec4143998834aee2018ca303d87b00f37da757fdc1089badb35385c6",
+ "currentOriginalRunsSourceSha256": "f1e7a7523106e1255be9fc8763c6005614caab957eb1f16855b8b3092f8fbcfd",
+ "scope": "One exact bodyless fixed-header second-page comparison GET and typed native ancestry joins; HTTP200, at least two commits, no files. Complete original raw response custody, source/effect identities and all prior caps/admission controls remain. This source-span amendment is not H3 or publication acceptance."
+ },
+ "httpErrorCustodyAmendment": {
+ "unit": "TSDD-KNOWLEDGE-01.4",
+ "originalItem": "TEMPLATES-H2",
+ "decisionSha256": "f2cd587a96859d7d8ab30e130f6563a63ef1fcd1c5b90f9bc579d683f2569798",
+ "previousRequestSourceSha256": "116cad46812e920fb713681ad37143450a1f4fcaadcc8fa81b90de14af18c775",
+ "scope": "Original bounded HTTPError custody and diagnostic GET/bodyNone guard only; diagnostic contents:read unchanged; no capability/effect acceptance",
+ "failedRun": 37269305353,
+ "previousWorkerSourceSha256": "baac8aa72df7d9f7fd13a6e51aa61236c7b143155d4be58d289a17f9c1314cbe",
+ "durableFallback": "Existing bounded worker report retains primary HTTP status and finite capture/close/transport failure kinds if transport custody fails; raw values never enter this fallback"
+ },
+ "draftReadCapabilityAmendment": {
+ "unit": "TSDD-KNOWLEDGE-01.4",
+ "originalItem": "TEMPLATES-H2",
+ "decisionSha256": "42c6a8e8cf7e0ad947ec2c4ff1ee26e0fe1221536c0355b52bf85cac09e94893",
+ "previousProtectedSource": "1b064690647dcfc871520b8f572d8a5bf7394344",
+ "failedRun": 37273763257,
+ "originalHTTPStatus": 403,
+ "originalErrorBodySha256": "7caac76bcb938ccbb5aa84f338b2f4ce5b59c2f31d7b524231d699a62d3673d2",
+ "previousWorkflowSha256": "060d63be16394bca11cbb8ced3d05b1916c07b029ae065399c2c1b2e581fc9da",
+ "previousRecoveryJobSha256": {
+ "recovery-diagnostic": "521da9edc1772ecd845bd7f6cae4ad461e2f49ce93bc2110747bc32a819d9dcf",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "currentJobSourceSha256": {
+ "publish": "21c6dbe4b43845835a01062baa1c600eb087a1f96007cbf3a332142d0b85b797",
+ "recovery-diagnostic": "cfe0642f9c65edba2873cda1b1e17ab89d52b01e08d78c9d3c2675497eca5e4b",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "diagnosticPermissions": {
+ "actions": "read",
+ "contents": "write",
+ "packages": "read"
+ },
+ "scope": "Explicit capability increase: only existing diagnostic job ephemeral repository GITHUB_TOKEN contents:read to contents:write for draft visibility. Actual diagnostic source remains GET/bodyNone only; zero release PATCH/Authority CAS. Authority App remains repository-scoped contents:read. No PAT/new credential, job, environment, publisher/current015 or historical013 binding change.",
+ "sourceQualification": "exact job permissions/role controls and production guard mutants; no diagnostic admission or acceptance",
+ "priorFailedDiagnostics": [
+ 37178852784,
+ 37186728763,
+ 37269305353,
+ 37273763257
+ ]
+ },
+ "currentRecoveryJobSha256": {
+ "recovery-diagnostic": "4940506bc96750b3dbd6f468d8cf1975b95575aec0da81f348048d9c781f84cb",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "postCompletionReadbackAmendment": {
+ "unit": "TSDD-KNOWLEDGE-01.4",
+ "scope": "Explicit post-completion-readback selection only: fresh generation17 public release and exact feeds; GET/bodyNone guarded at transport and redirects; no reinstall, publication, settlement, original H4 acceptance or effect grant renewal. Existing job read grants unchanged.",
+ "previousWorkflowSha256": "b3d61bfbabbc0f7eed13c4cc224352d913d444843800d2d7c2391ecce3a820c8",
+ "previousRecoveryJobSha256": {
+ "recovery-diagnostic": "d9b5b274b23370c956b61135974a2e0b959540fc63c9b14202c0f7109426833c",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "previousDraftReadJobSourceSha256": {
+ "publish": "21c6dbe4b43845835a01062baa1c600eb087a1f96007cbf3a332142d0b85b797",
+ "recovery-diagnostic": "cfe0642f9c65edba2873cda1b1e17ab89d52b01e08d78c9d3c2675497eca5e4b",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "currentJobSourceSha256": {
+ "publish": "21c6dbe4b43845835a01062baa1c600eb087a1f96007cbf3a332142d0b85b797",
+ "recovery-diagnostic": "235568b19eccd10461d9d6344f707b84200b410eb95f73e8639478afd0acc315",
+ "recovery-complete": "2011d23b1ef1e51f35afe89fa55f5c4b3fb334ba3b2c28a27d518f507dec924d"
+ },
+ "originalH4Source": "49a5e93668d4647999cd7171a26d4ad4d151b66b",
+ "sourceQualification": "Pure source controls only; fresh root admission required; original H4 remains unaccepted.",
+ "role": "post-completion-readback",
+ "journalGeneration": 17,
+ "method": "GET",
+ "body": "None",
+ "releaseMutation": false,
+ "journalMutation": false,
+ "install": false,
+ "originalH4Accepted": false,
+ "oldEffectGrantRenewed": false,
+ "freshRootAdmissionRequired": true,
+ "readerSourceSpanSha256": {
+ "READBACK_MODE": "b90aa61dd9bae99bbdcff8092b30f105413703b2fd0df6988ec058931e599fa4",
+ "ORIGINAL_H4": "8fb7bed604e046294489897ec5beec24e160eeaedff2b458e3b77ad4145e7544",
+ "readback_binding": "ed037504b60fb1c66bd943a3605be41ccd80a3e9256644076c03674317ce8455",
+ "ReadbackRedirect": "69d69267fa0f96d103a240a306bd4bf1c98cea9709df7b7d9cd97bb1c9c630f9",
+ "ReadbackTransport": "728b37a75e3dfa14903edb46fa7b4562bc2ece911c0b7001ec095e12100c8c9e",
+ "ReadbackAPI": "00c18647cac7f4c72c23e7abfe629bce7fa70989225eeb9a4e87593573a60807",
+ "readback_native": "2cf591fae814af27d47c1810bec00033f71b60b4ac14384cf95b8397c6009d85",
+ "post_complete_readback": "1207c64e171da2bc03bf4ea668755f9c11420ee99f7aba3d350583cfe78a7e1b",
+ "readback_worker": "89a60c6cb3f4c5857ee2d4d45ca5b1b07901b4795f7aa132fd42843542f5bec2",
+ "readback_entry": "eceb24157be209bb138ac7e00dbe19dc29c4a1e85623d34b3f260e72501be98c",
+ "api_contents_bytes": "2b3e641322f2cfb38dd8f594318900a0a0fc781aa9396aec0fc5b95fa2c589e1"
+ }
+ },
+ "apiContentsWrappingAmendment": {
+ "unit": "TSDD-KNOWLEDGE-01.4",
+ "sourceCandidate": "b9418c5555e3c9a1978f6f217d9b93c795219c8b",
+ "previousReaderSourceSpanSha256": {
+ "READBACK_MODE": "b90aa61dd9bae99bbdcff8092b30f105413703b2fd0df6988ec058931e599fa4",
+ "ORIGINAL_H4": "8fb7bed604e046294489897ec5beec24e160eeaedff2b458e3b77ad4145e7544",
+ "readback_binding": "ed037504b60fb1c66bd943a3605be41ccd80a3e9256644076c03674317ce8455",
+ "ReadbackRedirect": "69d69267fa0f96d103a240a306bd4bf1c98cea9709df7b7d9cd97bb1c9c630f9",
+ "ReadbackTransport": "728b37a75e3dfa14903edb46fa7b4562bc2ece911c0b7001ec095e12100c8c9e",
+ "ReadbackAPI": "0007d692aea4dee9eafba155be769d9b113e911d62ffe31e8a76d29a4fe297a5",
+ "readback_native": "b955cb22efc325d07bf1f47a557f1c1b057fb667c7aed7efd7e32e43ab684924",
+ "post_complete_readback": "1207c64e171da2bc03bf4ea668755f9c11420ee99f7aba3d350583cfe78a7e1b",
+ "readback_worker": "89a60c6cb3f4c5857ee2d4d45ca5b1b07901b4795f7aa132fd42843542f5bec2",
+ "readback_entry": "eceb24157be209bb138ac7e00dbe19dc29c4a1e85623d34b3f260e72501be98c"
+ },
+ "currentApiContentsBytesSourceSha256": "2b3e641322f2cfb38dd8f594318900a0a0fc781aa9396aec0fc5b95fa2c589e1",
+ "currentOriginal16PrimerSourceSha256": "e623de971fabb7c1e25b3716e3c36d57a3026f30844e1538319e9fd917e4941d",
+ "scope": "Inbound GitHub API contents CR/LF wrapping only, followed by strict base64 validation; original Git blob/tree/workflow digest joins unchanged. Outbound CAS strict validation and GET-only reader role unchanged. Original failed run37349422772 retained, first refusal cause unknown, no native replay or operation acceptance."
+ },
+ "creator016PublicationSummaryAmendment": {
+ "unit": "COORD-BOARD-V2-01.6",
+ "scope": "Ordinary Creator016 publish job bounded summary retention only; historical recovery job and original post-completion readback seals unchanged.",
+ "previousPublishJobSourceSha256": "21c6dbe4b43845835a01062baa1c600eb087a1f96007cbf3a332142d0b85b797",
+ "currentPublishJobSourceSha256": "21b76924d0be61c5723203f805b4e0bd1820424bbaceb70121dc8fb4350224e9",
+ "summaryArtifactName": "creator016-publication-summary-${{ github.run_id }}",
+ "summaryPath": "${{ runner.temp }}/creator016-publication-summary.json",
+ "originalH4Accepted": false,
+ "oldEffectGrantRenewed": false,
+ "operationAcceptance": "Source only; no candidate, journal initialization, protected preflight or Creator016 publication acceptance."
+ },
+ "creator017ProfileAmendment": {
+ "unit": "COORD-BOARD-V2-01.11",
+ "scope": "Only ordinary current job identity and bounded publication summary labels advance to Creator017. Reconstructing their exact prior spellings retains the complete Creator016 job seal; historical013 jobs remain byte-identical.",
+ "previousAcceptedSource": "2e60210be1e04d52fe0735a56333b3e3aef42284",
+ "previousSuccessorWorkflowSha256": "cef8b997e05cca5c9d5c0c97d74cb55afe34220e821e46fa650e7360d0b6d746",
+ "previousPublishJobSourceSha256": "21b76924d0be61c5723203f805b4e0bd1820424bbaceb70121dc8fb4350224e9",
+ "currentPublishJobSourceSha256": "4abc07aba92442ab73cb6ce8c93793397bb5df2f862ddac335f816891a618c11",
+ "currentBinding": "CURRENT_017",
+ "retainedBinding": "CURRENT_016",
+ "coherentSourceVersion": "0.107.0",
+ "freshLogicalJournal": "board-v2-product-creator-017",
+ "originalH4Accepted": false,
+ "oldEffectGrantRenewed": false,
+ "operationAcceptance": "Source only; no candidate, journal initialization, protected preflight or Creator017 publication acceptance."
+ }
+ }
+ }
}
]
}
diff --git a/docs/roadmaps/utel-release-successor.md b/docs/roadmaps/utel-release-successor.md
index 6b529c45c..331e10937 100644
--- a/docs/roadmaps/utel-release-successor.md
+++ b/docs/roadmaps/utel-release-successor.md
@@ -1888,3 +1888,21 @@ The offline import preflight remains the existing linear locked-restore/validate
closure and build configuration. Existing static path-coherence controls are proportionate; no
new model, gate, credential route or measured CI savings is claimed. The private real-input
preparation and native qualification remain separate from synthetic/public fixtures.
+
+### Prospective coherent108 operating window — 2026-10-19
+
+Owning delivery [#4682](https://github.com/FS-GG/.github/issues/4682), under #4641, selects source108
+for the full-cohort successor read-budget repair. Published107 at
+`75ab98dd28b1a818cc3986d595bf21e0fe691ec6`, release416724931, remains immutable; its promoted content ID
+is `sha256:c193dbf487f643a8b78300b568e4bfd09f8c56086ce96dc52865e219e8f98c9b`.
+The prospective current composition uses a distinct `utel-rel-26` logical journal and
+`state/releases/utel-rel-26` directory, predecessor107 and the existing unchanged finite resource and
+sixteen-effect publication rules. Completed utel-rel-25/107 and historical selectors stay original.
+This source selection grants no operation, creates no journal and authorizes no replay. Qualify and
+merge the exact source, then authenticate a fresh candidate and native preflight before publication.
+
+Creator018 remains independently versioned and release-fenced until real promoted108 artifacts supply
+its exact current dependency pin. Neither source108 nor normal Creator source compilation establishes
+that pin, package evidence, installed adoption or native successor acceptance. Preserve the actual107
+inspection ceiling failure and Creator017 adapter mismatch in the owning plan; do not narrow the22-item
+cohort, increase operation bounds or weaken physical artifact identity to obtain acceptance.
diff --git a/registry/CHANGELOG.md b/registry/CHANGELOG.md
index 27bbd4551..9dd01d37a 100644
--- a/registry/CHANGELOG.md
+++ b/registry/CHANGELOG.md
@@ -38,6 +38,8 @@ no gate behaviour changes — this is purely how humans record the log.
## Entries
+- **2026-10-19** — — `coord-engine` / `new-sdd-workspace`: coherent108-source-creator018-fence (github; #4682/#4641, PR4692): prepare source108 bounded full-cohort successor planning reads and independent Creator018 reuse of exact future promoted108 dependencies. Keep published coordination107/Creator017 pins unchanged; current018 pin remains absent until actual108 publication. Retain strict physical identity, historical publications/Unknown holds and separate source, installed, native and restart qualification. User visual UI check passed; no native write replay.
+
- **2026-10-19** — `coord-engine`: reconcile accepted coherent107 publication and canonical pin (github; #4682):
Record the already accepted coherent107 publication from source75ab98dd and release416724931,
diff --git a/registry/dependencies.yml b/registry/dependencies.yml
index d8770fe7d..45d26f886 100644
--- a/registry/dependencies.yml
+++ b/registry/dependencies.yml
@@ -960,7 +960,7 @@ contracts:
# release416724931 and all16/final33 were independently accepted2026-10-18T22:19:39Z under #4682.
# Published source75ab98dd28b1a818cc3986d595bf21e0fe691ec6 is immutable; later source prep is not in that archive.
# Installed/discovery, binding5/schema3 migration and consumer/restart/rollback acceptance remain separate.
- version: "0.107.0" # HISTORICAL SOURCE PREPARATION: canonical work-board coordinator, explicit outcome/delivery binding5/schema3/inspection3 and integrator2, bounded migration and progress. Source delivery #4677 under #4641; independent coherent107 publication, installed caller adoption and native schema/enrollment/view acceptance remain separate. Accepted binding4/schema2/inspection2 stays unchanged; retained105 qualification is historical scope. Later selector106 observation has unknown change timing and proves neither whole runtime nor instruction discovery. Published106 pins stay unchanged. PRIOR SOURCE/PUBLISHED: exact source 2e42faaa994367b9f50be87439e8fd973ad21501, candidate 39124245029, same-journal forward 39130246438 accepted all 16 effects at final generation 33 and release 416441527. Active installed 0.105 and board binding unchanged; Host receiver adoption remains separate. PRIOR SOURCE PREPARATION: SOURCE PREPARATION ONLY: prospective coherent 0.106.0 over published 0.105.0 for passive native observation; candidate/publication/installation unselected, both-feed collision guards remain required. Published package-version/tag and active board pin stay 0.105.0. PRIOR CURRENT SOURCE/PUBLISHED: coherent-set/v0.105.0, exact candidate e54a59885580c894c8fbc67b0b27af3571ea9883; original candidate39095711219/a1 and publisher resume39098313280/a1 accepted; initial39096861301 remains an incomplete generation14 checkpoint. Maintained developer update and exact82-member installed105 payload correspondence accepted; board migration, binding and consumer acceptance remain separately scoped. PRIOR source0.104.0 is published from immutable candidate 912eba8bbd707dabcbc5011d508c479109010b71; executor 5a2d13d0 is the continuation controller only. HISTORICAL SOURCE PREPARATION: SOURCE PREPARATION ONLY: current programme migration and prospective release-specific .103 suspension; literal utel-rel-22 selection grants no allocation/publication/installed authority. Original .103 tag:intent remains Unknown with all reservations preserved. Published package-version/tag stay0.102.0. PRIOR 0.103 SOURCE PREPARATION ONLY: receiver-first bounded CI continuation and authenticated suite graphs; original utel-rel-21 effects remain unresolved, original0.102/utel-rel-20 recovery is frozen. PRIOR SOURCE/PUBLISHED: coherent-set/v0.101.0 source79051e56b025dadfc6fcaabd58b79e33f2854928, original publisher38094091013/a1; canonical generation33/all16 effects and independent both-feed CLI/Kit/Drivers payloads accepted. Installed adoption, current channel, collector activation and adapter SDK pairing remain separate. PRIOR SOURCE PREPARATION ONLY: exact CI attribution/native association and additive immutable causal receiver; selected utel-rel-19 source rail, packed receiver qualification/publication/adoption pending. Published package-version/tag remain0.100.0; current14 and local receiver-first boundary, no Host dependency. PRIOR SOURCE/PUBLISHED: coherent-set/v0.100.0 at 3ed8ad419a64253ca6f665e9779e5e4d110f50a5; retained original manifest and both-feed payload readbacks verified, stable channel promoted. Installed payload identity82/82 matches; global collector activation and genuine usage unverified, original UTEL19 custody unknown. PRIOR SOURCE ONLY: breaking current receipt ABI, current14 init/restore, explicit13 maintenance and scoped14 dashboard; prospective utel-rel-18, collision/qualification/publication pending. PRIOR SOURCE PREPARATION: 0.99.1 compatible bounded private dispatch-state IO; proposed utel-rel-17. Published frontier0.99.0; no new publication/adoption. PRIOR SOURCE ONLY: EFF schema14, prospective assessment gate and closed Drivers helper inputs. Not published/installed; package frontier remains0.98.0 and immutable utel-rel-15. Independent Host0.5 required for Store14 collection; native pilot/package qualification pending. PRIOR SOURCE/PUBLISHED: verified coherent 0.98.0 at producer 3d4f7e9c6337fb020e269e632653de0faeef6d72, journal utel-rel-15 and publisher 37434982959. PRIOR SOURCE SELECTION: additive schema 13 CI attribution correction and native compact/3 report contract; exact-source integration/qualification remains required. Published frontier remains accepted0.97.1 from99ea75286f5c3cea2a261fef4e5b45cd70378185; consumedutel-rel-13 and historical0.97.2/utel-rel-14 source are preserved. SOURCE/PUBLISHED: compatible equal feature/item telemetry fact identity and native agent binding repairs (PRs 4242/4243/4245); accepted coherent-set/v0.97.1 producer 99ea75286f5c3cea2a261fef4e5b45cd70378185 has both-feed verification. Installed root adoption and the fresh two-fact local cycle are scoped acceptance; historical and unsupported usage remain unknown. PRIOR 0.97.0 SOURCE/PUBLISHED: COORD-BOARD-V2-01.5 product adapter and guidance; publisher 37235030417 promoted exact source 2ab0c0ff9f37bdec9a11ba3604ebdc230711934f with all 16 journal effects verified and both-feed payload readback. Installed product adoption remains separate. PRIOR 0.96.0 SOURCE/PUBLISHED: UTEL-H3 coherent successor carries telemetry CI legacy-default selection repair from PR #4152 (a0044731f432b9f3f7dffa4f9d0a0c85eebb8a1b); publisher 37161212706 promoted exact source f891b5b0723070c67e08d1a87b7d12b0b4d8bebe; installed selections and receiver adoption remain separate. PRIOR 0.95.0 SOURCE/PUBLISHED — MINOR coherent successor for bounded read-only board-v2 inspection and gated organization guidance; publisher 37071597534 promoted exact source 3b5de3367f8647cea0cd9366b8cb11eddf53feae with all 16 protected-journal effects verified; installed qualification and four-target Board adoption remain pending. PRIOR 0.94.0 SOURCE/PUBLISHED — MINOR, Drivers removes the retired Python skill-helper implementations from both mirrored skill roots and the compatibility wrapper after supported callers moved to packaged F# commands; installed-package verification rejects reintroduction; includes protected native learning capture and export accumulated since 0.93.0; immutable coherent-set/v0.94.0 was promoted from source 337b6a1d53571b07ca8e1417e18e52546ad319a7 after exact both-feed readback; receiver adoption remains separate. PRIOR 0.93.0 SOURCE/PUBLISHED — MINOR, supported skill callers use packaged F# telemetry and preflight commands; includes protected native telemetry collection provenance accumulated since 0.92.0; immutable coherent release github:0.93.0 was promoted from source d53d5c4fa0a54894da87e96ae2999288fb280ea5 after protected both-feed readback; no receiver adoption is claimed. PRIOR 0.92.0 SOURCE/PUBLISHED — MINOR, additive bounded read-only `skill telemetry-config discover` for installed workflows; immutable coherent release github:0.92.0 was promoted from source eb0f73186a07daf26e0f7bb5d4c1ee2054a8adaf after exact both-feed readback; no receiver adoption is claimed. PRIOR 0.91.5 SOURCE PREPARED — FSharp.Core 10.1.401 and compatible telemetry/driver updates; package-version remains published 0.91.4 until both-feed promotion. PRIOR 0.91.4 SOURCE/PUBLISHED — coherent telemetry-capable set from f0b1bb8748cbb7b27aeaf7346b8690c82ed03343; PRIOR 0.89.0 SOURCE/PUBLISHED — MINOR, FS.GG.Drivers adds the content-addressed installed routine policy, helper and native-check closure; immutable coherent release github:0.89.0 was promoted from source 535970a06055dfcdbb96aad8726b4d7d981a5b72 after exact both-feed readback. PRIOR 0.88.0 SOURCE/PUBLISHED — MINOR, independently activated private telemetry, source-free scoped dashboard, durable receipt transport, release qualification, and intake-audit hardening. Immutable tags `coord-engine/v0.88.0` and `coherent-set/v0.88.0` resolve the accepted source d77fe195bc4e133ace8763c2158834410ca72bc0. PRIOR 0.87.0 SOURCE PREPARED — MINOR, prospective private SQLite telemetry, repository-owned Codex lifecycle observation, exact-head CI reconciliation, native outcomes, and derived whole-item budget inputs (UTEL-06.1–06.4, .github#3360–#3363). Published from exact source bffc370933ec4f35af2af4acf5f72b5888844365 and promoted after both-feed verification. PRIOR 0.86.1 SOURCE/PUBLISHED — PATCH, routed board drivers reserve the three-round fresh implementer/critic repair chain for strict items so admitted routine work remains reduced through repair (.github#3338); immutable coherent release github:0.86.1 is promoted from source ce6edfd8e3f569867e6809ca3933c6ae65769a1d with content sha256:ccea15d2acd633188f34bdaa9761137538dd834fafa43cda185dbf90c473307c. PRIOR 0.86.0 SOURCE/PUBLISHED — MINOR, reduced one-owner routine route; immutable coherent release github:0.86.0 is promoted from source beb3456ecb2c4b4cadb6bc8dc268598246449aaf with content sha256:01d0c921ab23b6807e1d6da1a9c623cd0cfb5a595bf790b51662746a0681b974. PRIOR 0.85.2 SOURCE/PUBLISHED — PATCH, guarded two-phase implementation landing accepts a missing closing keyword only under an exact typed positive acceptance-receipt obligation and fresh same-item authority, while terminal completion remains reserved for the canonically closing receipt PR (.github#3286); immutable coherent release github:0.85.2 is promoted from source e94f7da34e2c3792a2c532a4969123fd26fd601b with content sha256:3fb04e68d9b90dff5d37f3ad9d0533346cf753444effdb6de5721191557d58fa. PRIOR 0.85.1 SOURCE/PUBLISHED — PATCH, acceptance survives a forward-only, complete, path-disjoint base advance while changed candidates, conflicts, relevant overlap, and unverifiable equivalence remain fail-closed (.github#3274); immutable coherent release github:0.85.1 is promoted from source 503a07d24a6087c549bc47b5322d6f05cce2a6c5 with content sha256:f0f3706c755c767c9f761c993bb01f7a9c52c08cd74d504c1de7322aadaf471c. PRIOR 0.85.0 SOURCE/PUBLISHED — MINOR, human-authorized scope-bound synthetic lifecycle checkpoint with mandatory functional verification and strict post-anchor resumption (.github#3263); immutable coherent release github:0.85.0 is promoted from source 9307b85458b326019415f8bcf6a1d13d0139eb6a with content sha256:95892fd5d1765ec3020168f71b103a1849ae645e00de77f8fcb549ddbd510081. PRIOR 0.84.0 SOURCE/PUBLISHED — MINOR, durable content-addressed private telemetry receipts, automatic digest resolution, and separately reviewed non-counting legacy recovery (.github#3259); immutable coherent release github:0.84.0 is promoted from source 17f400d70db2cdd28efd8d7ce14327f1495411d2 with content sha256:ec226689bf12f9ede6aebab4f1f045cc1bcb24e0c8208a9fcae031387cf776d5. PRIOR 0.83.5 SOURCE/PUBLISHED — PATCH, roadmap acceptance recognizes native FS.GG.SDD.Artifacts/1.5.0 verify and ship stage schemas while retaining exact revision, work, and evidence identity (.github#3255); immutable coherent release github:0.83.5 is promoted from source 97666e7f0193b71fde5642d5950093490fbabbdb with content sha256:3519327ac384e1549a2fed7fc431f47047c63f335341ce3d8eaf8b1b63aa3a9a. PRIOR 0.83.4 SOURCE/PUBLISHED — PATCH, roadmap unit acceptance now permits a single immutable implementation/acceptance PR only under equal identities, derives the repository from applied unit authority, and proves exact one-commit canonical critique ancestry (.github#3251); immutable coherent release github:0.83.4 is promoted from source a3641ca0827187fa4ff693f627f5024dab4093b0 with content sha256:aea555a3e8a6acf9d319b42cf714b605067be23ce2c8b39647780db4a96930bf. PRIOR 0.83.3 SOURCE/PUBLISHED — PATCH, roadmap acceptance uses separately authorable structured-review and immutable-envelope identities and binds SDD observation to the current structured route work ID (.github#3247); immutable coherent release github:0.83.3 is promoted from source 5e4c23790c714b892b0c5efa25b515ae4eaf252e with content sha256:aa95e6038bd0630eb163b0001c2f5628bc0daf71d0da8170f9e6fb6e44697ec2. PRIOR 0.83.2 SOURCE/PUBLISHED — PATCH, live acceptance relies on independently regenerated ignored SDD artifacts while retaining exact-revision observation and canonical comparison (.github#3242); immutable coherent release github:0.83.2 is promoted from source 0697e72f0f5b0d6bcc9728da3589f71d24dde420 with content sha256:40072e5998da0476a0bb7ad177d5c68129268b120d2cf3a2d554dbc7490dc7ed. PRIOR 0.83.1 SOURCE/PUBLISHED — PATCH, ordered partial roadmap catalog acceptance (.github#3233); immutable coherent release github:0.83.1 is promoted from source 2237ab8282433234e0d1af3f4716ef099422e282 with content sha256:43f9d6a386ce2988e1825d0439642e2965c937ee264bec3dca107dcd78ee2c1d. PRIOR 0.83.0 SOURCE/PUBLISHED — MINOR, additive typed roadmap work-unit preparation and atomic acceptance transaction (.github#3210); immutable coherent release github:0.83.0 is promoted from source fe13bf08d82091a3d024583e0315c50d30c59376 with content sha256:0e0df10f52fdd68747739aa6083f7d5b34cdaffd35e6d16976bcfdfa1106ebaa. PRIOR 0.82.0 SOURCE/PUBLISHED — MINOR, deterministic qualification/evidence runner; immutable coherent release github:0.82.0 is promoted from source 3c53e4600110974bb1b22d3522a7d794fd24e3fd with content sha256:20cd31e6a90658237571d37874f6885789217db329ca613d4a5e819432223a0d. PRIOR 0.81.1 SOURCE/PUBLISHED — PATCH, publish-before-adopt completion; packed callers use compiled telemetry and compatibility helpers are removed. PRIOR 0.78.1 SOURCE/PUBLISHED — PATCH, stable. Documentation-only orchestration visualization design plus the auto-publish frontier repair; no engine wire change. PRIOR 0.78.0 SOURCE/PUBLISHED — MINOR, stable. Intake derives Class from the shared board vocabulary and recovers only enumerated legacy drafts after a partial create; the exact predecessor body and authoritative post-PATCH read gate receipt advancement. Packed filing skills remove the unprojectable capability example. package-version is 0.78.0 after immutable dual-feed promotion. PRIOR 0.77.0 SOURCE/PUBLISHED — MINOR. ADR-0079 makes one Accountable Delivery Owner the sole routine authorization boundary; packed pnext-item retains exact-head critique/repair/acceptance evidence under distinct phase identities but requires no external person, account, agent, or approval quorum. PRIOR 0.76.0 SOURCE/PUBLISHED — MINOR. The coherent Kit adds initialize-sdd-workspace as a new receiver-visible member; Drivers and Coord.Cli advance on the shared scalar with no engine wire change. PRIOR 0.75.5 SOURCE/PUBLISHED — PATCH, stable (.github#2983, source PR #2990, merge 34b1fd8b). Three compatible lifecycle repairs ship: successful completed post-merge runs classify correctly, completion provenance preserves the full GraphQL merge OID, and closed delivery reads authoritative issue Paths while retaining unread-versus-undeclared state. Protocol.fs has zero wire commits across the span. PRIOR 0.75.4 SOURCE/PUBLISHED — PATCH, stable (.github#2941, source PR #2967, merge 8d720471). Nine accumulated non-wire engine commits ship with corrected cumulative release notes; Protocol.fs has zero wire commits across the release span. PRIOR 0.75.3 SOURCE/PUBLISHED — PATCH, stable, source 264725f374e3f05da46d7c3089462076a1f9bf7a; the immutable release predates this correction and its embedded notes misdescribe the accumulated changes. PRIOR: 0.74.0 SOURCE/PUBLISHED — MINOR, stable (.github#2876, source PR #2879). Five pre-existing non-wire engine-path commits plus the release-preparation commit are shipped from d4458d8fdfff0c332c80d920202ab0230bd9de0f; Protocol.fs is unchanged across the release span. PRIOR: 0.71.0 SOURCE/PUBLISHED — MINOR, stable (.github#2813, source PR #2814). Forward recovery ships the live stable-predecessor authority from source 3890c8f6b20fcd2c1fdd5b2a9a5356877c217397 while poisoned 0.70.0 remains unpromoted. Previous coherent registry frontier: 0.68.0. PRIOR 0.68.0 SOURCE/PUBLISHED — MINOR, stable (.github#2794, source PR #2803). Four additive exhausted-review/forced-claim commits are shipped with zero Protocol.fs wire commits. Previous coherent registry frontier: 0.67.0. PRIOR 0.67.0 SOURCE/PUBLISHED — MINOR, stable (.github#2756, PR #2792). Durable bounded review-wait receipts and the ordinary full fresh-successor review route are additive receiver-visible semantics. Previous coherent registry frontier: 0.66.0. PRIOR 0.66.0 SOURCE/PUBLISHED — MINOR, stable (.github#2757, PR #2789). The packaged findings-and-filing contract adds the named `disclosed residual` terminal state: measured bound, caller-facing disclosure, executable red pin, and durable authorized decision are conjunctive; a #266 check that cannot fail is explicitly excluded. Previous coherent registry frontier: 0.65.0. PRIOR 0.61.0 SOURCE/PUBLISHED — MINOR, stable. Two receiver-observable legs, either of which carries the line on the criterion the 0.56.0, 0.57.0, 0.59.0 and 0.60.0 entries used (.github#2712, PR #2745, engine commit 73024dc3): the board gains a `Kind:` body-line sentinel with a CLOSED four-value vocabulary — work|anchor|register|directive — in the same grammar as `Paths:`/`Class:`/`Blocked on:`, and a row declaring a NON-`work` kind is EXEMPT FROM THE LIFECYCLE REDUCER ENTIRELY (no projected Status, no persisted watermark, no park, no promotion, no Done), which the scheduler reports through a NEW verdict `not-a-unit-of-work` naming the kind rather than the row's column; and `ready --json` plus the board reads gain two per-row fields, `kind` (null until an operator creates the field) and `commentCount` (observable REGISTER DEPTH, riding the existing board page query as a connection totalCount and selecting no nodes, so the board read costs what it did before). AN ABSENT `Kind:` LINE MEANS `work`, so every row that existed at 0.60.0 behaves exactly as it did — the opposite default from an absent `Class:` line, deliberately. THE WIRE SURFACE DID MOVE HERE, AND ADDITIVELY, which is the honest difference from the 0.59.0 and 0.60.0 entries and is measured rather than asserted: src/FS.GG.Coord.Core/Protocol.fs is 214 insertions/254 deletions across coord-engine/v0.60.0..v0.61.0, but classifying that diff line by line finds ZERO removed type/DU/let/member definitions and exactly ONE added case, `Schedulability.NotAUnitOfWork` — the churn is the projected rule PROSE, not surface removal, so this is a MINOR BY ADDITION and not a MAJOR. THE SPAN IS 32 commits, of which 15 touch the engine paths under `git rev-list --full-history` and only 12 under default history simplification; BOTH numbers are stated because the smaller one is what a reader gets by default, and .github#2743 — the row that ordered this cut — records exactly that merge-vs-squash sensitivity as a real gate defect. Cut under per-cut operator authorisation (.github#2743 Sequencing; the 0.60.0 authorisation explicitly did not extend forward). PRIOR 0.60.0 SOURCE/PUBLISHED — MINOR, stable. Two receiver-visible legs, either of which carries the line on the criterion the 0.56.0, 0.57.0 and 0.59.0 entries used (.github#2645, PR #2650, engine commit aea56a4a): `claim --json` reports differently — `statusWrite` gains a FIFTH value `withheld`, distinct from `failed` (asserts a mutation was sent) and `deferred` (promises `flush`), and `converged` now means agreement with the DERIVED destination rather than with the literal column `In progress` — and the packed kit retires a start-gate `jq` predicate asserting `.status == "In progress"` that receivers copy verbatim. THE WIRE SURFACE IS UNCHANGED and that is measured, not assumed: check-engine-freshness reported 0 of the 2 unreleased engine commits touching src/FS.GG.Coord.Core/Protocol.fs, so `withheld` is a new INHABITANT of an existing reported field, not a new verb, flag, help entry, render name, result name or exit code. Cut by .github#2409's MANUAL path (.github#2713) because nothing automatic can cut it: kit-auto-publish.py:99-100 refuses this candidate `candidate-not-next-patch` — 0.60.0 opens a NEW minor line against a 0.59.0 frontier, failing the first clause and short-circuiting before the sibling-tag block at :101 — which is the rail working by design (.github#2442), verified here by driving decide() over the live facts with a 0.59.1 control that clears that same rail. PRIOR 0.59.0 SOURCE/PUBLISHED — MINOR, stable. Five receiver-visible engine defect fixes (.github#2575/#2662/#2683/#2678/#2694) plus a new reviewer protocol boundary in the packed pnext-item skill (finding-packet contract + independent-review consolidation), which is the 0.57.0 entry's shape. The 290 lines of new .fsi surface are corroboration only: FS.GG.Coord.Core.Operation is IsPackable=false and unreferenced by the CLI, so it reaches no receiver, and Protocol.fs is byte-identical across the span (.github#2648, PR #2706, round-1 finding by critic heron-d444). This cut ABANDONS 0.58.1, whose three tags at a415652f published nothing on either feed (.github#2654); those tags are immutable and are deliberately left alone (.github#1772). PRIOR 0.58.0 — 0.58.1 was never published and must not be read as a prior.
+ version: "0.108.0" # SOURCE PREPARATION ONLY: successor planning read-budget repair; publication and installed qualification pending. Published107 remains unchanged. PRIOR HISTORICAL SOURCE PREPARATION: canonical work-board coordinator, explicit outcome/delivery binding5/schema3/inspection3 and integrator2, bounded migration and progress. Source delivery #4677 under #4641; independent coherent107 publication, installed caller adoption and native schema/enrollment/view acceptance remain separate. Accepted binding4/schema2/inspection2 stays unchanged; retained105 qualification is historical scope. Later selector106 observation has unknown change timing and proves neither whole runtime nor instruction discovery. Published106 pins stay unchanged. PRIOR SOURCE/PUBLISHED: exact source 2e42faaa994367b9f50be87439e8fd973ad21501, candidate 39124245029, same-journal forward 39130246438 accepted all 16 effects at final generation 33 and release 416441527. Active installed 0.105 and board binding unchanged; Host receiver adoption remains separate. PRIOR SOURCE PREPARATION: SOURCE PREPARATION ONLY: prospective coherent 0.106.0 over published 0.105.0 for passive native observation; candidate/publication/installation unselected, both-feed collision guards remain required. Published package-version/tag and active board pin stay 0.105.0. PRIOR CURRENT SOURCE/PUBLISHED: coherent-set/v0.105.0, exact candidate e54a59885580c894c8fbc67b0b27af3571ea9883; original candidate39095711219/a1 and publisher resume39098313280/a1 accepted; initial39096861301 remains an incomplete generation14 checkpoint. Maintained developer update and exact82-member installed105 payload correspondence accepted; board migration, binding and consumer acceptance remain separately scoped. PRIOR source0.104.0 is published from immutable candidate 912eba8bbd707dabcbc5011d508c479109010b71; executor 5a2d13d0 is the continuation controller only. HISTORICAL SOURCE PREPARATION: SOURCE PREPARATION ONLY: current programme migration and prospective release-specific .103 suspension; literal utel-rel-22 selection grants no allocation/publication/installed authority. Original .103 tag:intent remains Unknown with all reservations preserved. Published package-version/tag stay0.102.0. PRIOR 0.103 SOURCE PREPARATION ONLY: receiver-first bounded CI continuation and authenticated suite graphs; original utel-rel-21 effects remain unresolved, original0.102/utel-rel-20 recovery is frozen. PRIOR SOURCE/PUBLISHED: coherent-set/v0.101.0 source79051e56b025dadfc6fcaabd58b79e33f2854928, original publisher38094091013/a1; canonical generation33/all16 effects and independent both-feed CLI/Kit/Drivers payloads accepted. Installed adoption, current channel, collector activation and adapter SDK pairing remain separate. PRIOR SOURCE PREPARATION ONLY: exact CI attribution/native association and additive immutable causal receiver; selected utel-rel-19 source rail, packed receiver qualification/publication/adoption pending. Published package-version/tag remain0.100.0; current14 and local receiver-first boundary, no Host dependency. PRIOR SOURCE/PUBLISHED: coherent-set/v0.100.0 at 3ed8ad419a64253ca6f665e9779e5e4d110f50a5; retained original manifest and both-feed payload readbacks verified, stable channel promoted. Installed payload identity82/82 matches; global collector activation and genuine usage unverified, original UTEL19 custody unknown. PRIOR SOURCE ONLY: breaking current receipt ABI, current14 init/restore, explicit13 maintenance and scoped14 dashboard; prospective utel-rel-18, collision/qualification/publication pending. PRIOR SOURCE PREPARATION: 0.99.1 compatible bounded private dispatch-state IO; proposed utel-rel-17. Published frontier0.99.0; no new publication/adoption. PRIOR SOURCE ONLY: EFF schema14, prospective assessment gate and closed Drivers helper inputs. Not published/installed; package frontier remains0.98.0 and immutable utel-rel-15. Independent Host0.5 required for Store14 collection; native pilot/package qualification pending. PRIOR SOURCE/PUBLISHED: verified coherent 0.98.0 at producer 3d4f7e9c6337fb020e269e632653de0faeef6d72, journal utel-rel-15 and publisher 37434982959. PRIOR SOURCE SELECTION: additive schema 13 CI attribution correction and native compact/3 report contract; exact-source integration/qualification remains required. Published frontier remains accepted0.97.1 from99ea75286f5c3cea2a261fef4e5b45cd70378185; consumedutel-rel-13 and historical0.97.2/utel-rel-14 source are preserved. SOURCE/PUBLISHED: compatible equal feature/item telemetry fact identity and native agent binding repairs (PRs 4242/4243/4245); accepted coherent-set/v0.97.1 producer 99ea75286f5c3cea2a261fef4e5b45cd70378185 has both-feed verification. Installed root adoption and the fresh two-fact local cycle are scoped acceptance; historical and unsupported usage remain unknown. PRIOR 0.97.0 SOURCE/PUBLISHED: COORD-BOARD-V2-01.5 product adapter and guidance; publisher 37235030417 promoted exact source 2ab0c0ff9f37bdec9a11ba3604ebdc230711934f with all 16 journal effects verified and both-feed payload readback. Installed product adoption remains separate. PRIOR 0.96.0 SOURCE/PUBLISHED: UTEL-H3 coherent successor carries telemetry CI legacy-default selection repair from PR #4152 (a0044731f432b9f3f7dffa4f9d0a0c85eebb8a1b); publisher 37161212706 promoted exact source f891b5b0723070c67e08d1a87b7d12b0b4d8bebe; installed selections and receiver adoption remain separate. PRIOR 0.95.0 SOURCE/PUBLISHED — MINOR coherent successor for bounded read-only board-v2 inspection and gated organization guidance; publisher 37071597534 promoted exact source 3b5de3367f8647cea0cd9366b8cb11eddf53feae with all 16 protected-journal effects verified; installed qualification and four-target Board adoption remain pending. PRIOR 0.94.0 SOURCE/PUBLISHED — MINOR, Drivers removes the retired Python skill-helper implementations from both mirrored skill roots and the compatibility wrapper after supported callers moved to packaged F# commands; installed-package verification rejects reintroduction; includes protected native learning capture and export accumulated since 0.93.0; immutable coherent-set/v0.94.0 was promoted from source 337b6a1d53571b07ca8e1417e18e52546ad319a7 after exact both-feed readback; receiver adoption remains separate. PRIOR 0.93.0 SOURCE/PUBLISHED — MINOR, supported skill callers use packaged F# telemetry and preflight commands; includes protected native telemetry collection provenance accumulated since 0.92.0; immutable coherent release github:0.93.0 was promoted from source d53d5c4fa0a54894da87e96ae2999288fb280ea5 after protected both-feed readback; no receiver adoption is claimed. PRIOR 0.92.0 SOURCE/PUBLISHED — MINOR, additive bounded read-only `skill telemetry-config discover` for installed workflows; immutable coherent release github:0.92.0 was promoted from source eb0f73186a07daf26e0f7bb5d4c1ee2054a8adaf after exact both-feed readback; no receiver adoption is claimed. PRIOR 0.91.5 SOURCE PREPARED — FSharp.Core 10.1.401 and compatible telemetry/driver updates; package-version remains published 0.91.4 until both-feed promotion. PRIOR 0.91.4 SOURCE/PUBLISHED — coherent telemetry-capable set from f0b1bb8748cbb7b27aeaf7346b8690c82ed03343; PRIOR 0.89.0 SOURCE/PUBLISHED — MINOR, FS.GG.Drivers adds the content-addressed installed routine policy, helper and native-check closure; immutable coherent release github:0.89.0 was promoted from source 535970a06055dfcdbb96aad8726b4d7d981a5b72 after exact both-feed readback. PRIOR 0.88.0 SOURCE/PUBLISHED — MINOR, independently activated private telemetry, source-free scoped dashboard, durable receipt transport, release qualification, and intake-audit hardening. Immutable tags `coord-engine/v0.88.0` and `coherent-set/v0.88.0` resolve the accepted source d77fe195bc4e133ace8763c2158834410ca72bc0. PRIOR 0.87.0 SOURCE PREPARED — MINOR, prospective private SQLite telemetry, repository-owned Codex lifecycle observation, exact-head CI reconciliation, native outcomes, and derived whole-item budget inputs (UTEL-06.1–06.4, .github#3360–#3363). Published from exact source bffc370933ec4f35af2af4acf5f72b5888844365 and promoted after both-feed verification. PRIOR 0.86.1 SOURCE/PUBLISHED — PATCH, routed board drivers reserve the three-round fresh implementer/critic repair chain for strict items so admitted routine work remains reduced through repair (.github#3338); immutable coherent release github:0.86.1 is promoted from source ce6edfd8e3f569867e6809ca3933c6ae65769a1d with content sha256:ccea15d2acd633188f34bdaa9761137538dd834fafa43cda185dbf90c473307c. PRIOR 0.86.0 SOURCE/PUBLISHED — MINOR, reduced one-owner routine route; immutable coherent release github:0.86.0 is promoted from source beb3456ecb2c4b4cadb6bc8dc268598246449aaf with content sha256:01d0c921ab23b6807e1d6da1a9c623cd0cfb5a595bf790b51662746a0681b974. PRIOR 0.85.2 SOURCE/PUBLISHED — PATCH, guarded two-phase implementation landing accepts a missing closing keyword only under an exact typed positive acceptance-receipt obligation and fresh same-item authority, while terminal completion remains reserved for the canonically closing receipt PR (.github#3286); immutable coherent release github:0.85.2 is promoted from source e94f7da34e2c3792a2c532a4969123fd26fd601b with content sha256:3fb04e68d9b90dff5d37f3ad9d0533346cf753444effdb6de5721191557d58fa. PRIOR 0.85.1 SOURCE/PUBLISHED — PATCH, acceptance survives a forward-only, complete, path-disjoint base advance while changed candidates, conflicts, relevant overlap, and unverifiable equivalence remain fail-closed (.github#3274); immutable coherent release github:0.85.1 is promoted from source 503a07d24a6087c549bc47b5322d6f05cce2a6c5 with content sha256:f0f3706c755c767c9f761c993bb01f7a9c52c08cd74d504c1de7322aadaf471c. PRIOR 0.85.0 SOURCE/PUBLISHED — MINOR, human-authorized scope-bound synthetic lifecycle checkpoint with mandatory functional verification and strict post-anchor resumption (.github#3263); immutable coherent release github:0.85.0 is promoted from source 9307b85458b326019415f8bcf6a1d13d0139eb6a with content sha256:95892fd5d1765ec3020168f71b103a1849ae645e00de77f8fcb549ddbd510081. PRIOR 0.84.0 SOURCE/PUBLISHED — MINOR, durable content-addressed private telemetry receipts, automatic digest resolution, and separately reviewed non-counting legacy recovery (.github#3259); immutable coherent release github:0.84.0 is promoted from source 17f400d70db2cdd28efd8d7ce14327f1495411d2 with content sha256:ec226689bf12f9ede6aebab4f1f045cc1bcb24e0c8208a9fcae031387cf776d5. PRIOR 0.83.5 SOURCE/PUBLISHED — PATCH, roadmap acceptance recognizes native FS.GG.SDD.Artifacts/1.5.0 verify and ship stage schemas while retaining exact revision, work, and evidence identity (.github#3255); immutable coherent release github:0.83.5 is promoted from source 97666e7f0193b71fde5642d5950093490fbabbdb with content sha256:3519327ac384e1549a2fed7fc431f47047c63f335341ce3d8eaf8b1b63aa3a9a. PRIOR 0.83.4 SOURCE/PUBLISHED — PATCH, roadmap unit acceptance now permits a single immutable implementation/acceptance PR only under equal identities, derives the repository from applied unit authority, and proves exact one-commit canonical critique ancestry (.github#3251); immutable coherent release github:0.83.4 is promoted from source a3641ca0827187fa4ff693f627f5024dab4093b0 with content sha256:aea555a3e8a6acf9d319b42cf714b605067be23ce2c8b39647780db4a96930bf. PRIOR 0.83.3 SOURCE/PUBLISHED — PATCH, roadmap acceptance uses separately authorable structured-review and immutable-envelope identities and binds SDD observation to the current structured route work ID (.github#3247); immutable coherent release github:0.83.3 is promoted from source 5e4c23790c714b892b0c5efa25b515ae4eaf252e with content sha256:aa95e6038bd0630eb163b0001c2f5628bc0daf71d0da8170f9e6fb6e44697ec2. PRIOR 0.83.2 SOURCE/PUBLISHED — PATCH, live acceptance relies on independently regenerated ignored SDD artifacts while retaining exact-revision observation and canonical comparison (.github#3242); immutable coherent release github:0.83.2 is promoted from source 0697e72f0f5b0d6bcc9728da3589f71d24dde420 with content sha256:40072e5998da0476a0bb7ad177d5c68129268b120d2cf3a2d554dbc7490dc7ed. PRIOR 0.83.1 SOURCE/PUBLISHED — PATCH, ordered partial roadmap catalog acceptance (.github#3233); immutable coherent release github:0.83.1 is promoted from source 2237ab8282433234e0d1af3f4716ef099422e282 with content sha256:43f9d6a386ce2988e1825d0439642e2965c937ee264bec3dca107dcd78ee2c1d. PRIOR 0.83.0 SOURCE/PUBLISHED — MINOR, additive typed roadmap work-unit preparation and atomic acceptance transaction (.github#3210); immutable coherent release github:0.83.0 is promoted from source fe13bf08d82091a3d024583e0315c50d30c59376 with content sha256:0e0df10f52fdd68747739aa6083f7d5b34cdaffd35e6d16976bcfdfa1106ebaa. PRIOR 0.82.0 SOURCE/PUBLISHED — MINOR, deterministic qualification/evidence runner; immutable coherent release github:0.82.0 is promoted from source 3c53e4600110974bb1b22d3522a7d794fd24e3fd with content sha256:20cd31e6a90658237571d37874f6885789217db329ca613d4a5e819432223a0d. PRIOR 0.81.1 SOURCE/PUBLISHED — PATCH, publish-before-adopt completion; packed callers use compiled telemetry and compatibility helpers are removed. PRIOR 0.78.1 SOURCE/PUBLISHED — PATCH, stable. Documentation-only orchestration visualization design plus the auto-publish frontier repair; no engine wire change. PRIOR 0.78.0 SOURCE/PUBLISHED — MINOR, stable. Intake derives Class from the shared board vocabulary and recovers only enumerated legacy drafts after a partial create; the exact predecessor body and authoritative post-PATCH read gate receipt advancement. Packed filing skills remove the unprojectable capability example. package-version is 0.78.0 after immutable dual-feed promotion. PRIOR 0.77.0 SOURCE/PUBLISHED — MINOR. ADR-0079 makes one Accountable Delivery Owner the sole routine authorization boundary; packed pnext-item retains exact-head critique/repair/acceptance evidence under distinct phase identities but requires no external person, account, agent, or approval quorum. PRIOR 0.76.0 SOURCE/PUBLISHED — MINOR. The coherent Kit adds initialize-sdd-workspace as a new receiver-visible member; Drivers and Coord.Cli advance on the shared scalar with no engine wire change. PRIOR 0.75.5 SOURCE/PUBLISHED — PATCH, stable (.github#2983, source PR #2990, merge 34b1fd8b). Three compatible lifecycle repairs ship: successful completed post-merge runs classify correctly, completion provenance preserves the full GraphQL merge OID, and closed delivery reads authoritative issue Paths while retaining unread-versus-undeclared state. Protocol.fs has zero wire commits across the span. PRIOR 0.75.4 SOURCE/PUBLISHED — PATCH, stable (.github#2941, source PR #2967, merge 8d720471). Nine accumulated non-wire engine commits ship with corrected cumulative release notes; Protocol.fs has zero wire commits across the release span. PRIOR 0.75.3 SOURCE/PUBLISHED — PATCH, stable, source 264725f374e3f05da46d7c3089462076a1f9bf7a; the immutable release predates this correction and its embedded notes misdescribe the accumulated changes. PRIOR: 0.74.0 SOURCE/PUBLISHED — MINOR, stable (.github#2876, source PR #2879). Five pre-existing non-wire engine-path commits plus the release-preparation commit are shipped from d4458d8fdfff0c332c80d920202ab0230bd9de0f; Protocol.fs is unchanged across the release span. PRIOR: 0.71.0 SOURCE/PUBLISHED — MINOR, stable (.github#2813, source PR #2814). Forward recovery ships the live stable-predecessor authority from source 3890c8f6b20fcd2c1fdd5b2a9a5356877c217397 while poisoned 0.70.0 remains unpromoted. Previous coherent registry frontier: 0.68.0. PRIOR 0.68.0 SOURCE/PUBLISHED — MINOR, stable (.github#2794, source PR #2803). Four additive exhausted-review/forced-claim commits are shipped with zero Protocol.fs wire commits. Previous coherent registry frontier: 0.67.0. PRIOR 0.67.0 SOURCE/PUBLISHED — MINOR, stable (.github#2756, PR #2792). Durable bounded review-wait receipts and the ordinary full fresh-successor review route are additive receiver-visible semantics. Previous coherent registry frontier: 0.66.0. PRIOR 0.66.0 SOURCE/PUBLISHED — MINOR, stable (.github#2757, PR #2789). The packaged findings-and-filing contract adds the named `disclosed residual` terminal state: measured bound, caller-facing disclosure, executable red pin, and durable authorized decision are conjunctive; a #266 check that cannot fail is explicitly excluded. Previous coherent registry frontier: 0.65.0. PRIOR 0.61.0 SOURCE/PUBLISHED — MINOR, stable. Two receiver-observable legs, either of which carries the line on the criterion the 0.56.0, 0.57.0, 0.59.0 and 0.60.0 entries used (.github#2712, PR #2745, engine commit 73024dc3): the board gains a `Kind:` body-line sentinel with a CLOSED four-value vocabulary — work|anchor|register|directive — in the same grammar as `Paths:`/`Class:`/`Blocked on:`, and a row declaring a NON-`work` kind is EXEMPT FROM THE LIFECYCLE REDUCER ENTIRELY (no projected Status, no persisted watermark, no park, no promotion, no Done), which the scheduler reports through a NEW verdict `not-a-unit-of-work` naming the kind rather than the row's column; and `ready --json` plus the board reads gain two per-row fields, `kind` (null until an operator creates the field) and `commentCount` (observable REGISTER DEPTH, riding the existing board page query as a connection totalCount and selecting no nodes, so the board read costs what it did before). AN ABSENT `Kind:` LINE MEANS `work`, so every row that existed at 0.60.0 behaves exactly as it did — the opposite default from an absent `Class:` line, deliberately. THE WIRE SURFACE DID MOVE HERE, AND ADDITIVELY, which is the honest difference from the 0.59.0 and 0.60.0 entries and is measured rather than asserted: src/FS.GG.Coord.Core/Protocol.fs is 214 insertions/254 deletions across coord-engine/v0.60.0..v0.61.0, but classifying that diff line by line finds ZERO removed type/DU/let/member definitions and exactly ONE added case, `Schedulability.NotAUnitOfWork` — the churn is the projected rule PROSE, not surface removal, so this is a MINOR BY ADDITION and not a MAJOR. THE SPAN IS 32 commits, of which 15 touch the engine paths under `git rev-list --full-history` and only 12 under default history simplification; BOTH numbers are stated because the smaller one is what a reader gets by default, and .github#2743 — the row that ordered this cut — records exactly that merge-vs-squash sensitivity as a real gate defect. Cut under per-cut operator authorisation (.github#2743 Sequencing; the 0.60.0 authorisation explicitly did not extend forward). PRIOR 0.60.0 SOURCE/PUBLISHED — MINOR, stable. Two receiver-visible legs, either of which carries the line on the criterion the 0.56.0, 0.57.0 and 0.59.0 entries used (.github#2645, PR #2650, engine commit aea56a4a): `claim --json` reports differently — `statusWrite` gains a FIFTH value `withheld`, distinct from `failed` (asserts a mutation was sent) and `deferred` (promises `flush`), and `converged` now means agreement with the DERIVED destination rather than with the literal column `In progress` — and the packed kit retires a start-gate `jq` predicate asserting `.status == "In progress"` that receivers copy verbatim. THE WIRE SURFACE IS UNCHANGED and that is measured, not assumed: check-engine-freshness reported 0 of the 2 unreleased engine commits touching src/FS.GG.Coord.Core/Protocol.fs, so `withheld` is a new INHABITANT of an existing reported field, not a new verb, flag, help entry, render name, result name or exit code. Cut by .github#2409's MANUAL path (.github#2713) because nothing automatic can cut it: kit-auto-publish.py:99-100 refuses this candidate `candidate-not-next-patch` — 0.60.0 opens a NEW minor line against a 0.59.0 frontier, failing the first clause and short-circuiting before the sibling-tag block at :101 — which is the rail working by design (.github#2442), verified here by driving decide() over the live facts with a 0.59.1 control that clears that same rail. PRIOR 0.59.0 SOURCE/PUBLISHED — MINOR, stable. Five receiver-visible engine defect fixes (.github#2575/#2662/#2683/#2678/#2694) plus a new reviewer protocol boundary in the packed pnext-item skill (finding-packet contract + independent-review consolidation), which is the 0.57.0 entry's shape. The 290 lines of new .fsi surface are corroboration only: FS.GG.Coord.Core.Operation is IsPackable=false and unreferenced by the CLI, so it reaches no receiver, and Protocol.fs is byte-identical across the span (.github#2648, PR #2706, round-1 finding by critic heron-d444). This cut ABANDONS 0.58.1, whose three tags at a415652f published nothing on either feed (.github#2654); those tags are immutable and are deliberately left alone (.github#1772). PRIOR 0.58.0 — 0.58.1 was never published and must not be read as a prior.
# HISTORICAL PACKAGE: 0.91.2, immutable coherent-set/v0.91.2 from source fc64f351a6c7733c3df6520ad1e1671bfcc1714b; content sha256:a3073f2b92d64048e1b8ee08e76263a1b5d6d56b6c75dd930505aa9eb3fcecd6. Publisher run 35506239965 and protected journal fsgg/v2/journal/release/utel-rel-03 verified all three members on both feeds and promotion. Manifest SHA-256 1f98d1f970810ecd357252663ad0582c97b0dd42008bb3b55b9b585bfa4f4cfa; stable-channel SHA-256 317ff8d08f484ecec5063ce7495da63bc33b18e40707ecb0ae9c46bd158d6984. PRIOR 0.91.1 from source 05e3feadcce3d546a05b2a4e0b1780e8a642a228; content sha256:3a87727ed7178b79e00f904457f19abcff1e7b00b0a93cc593568735eb28aefc. Both feeds verified all three members; producer CLI 0.91.1 adopted on both dev containers. PRIOR 0.91.0 from source 85c356b2c44cfea4b83659b14b6946d64bbd9a22; content sha256:c8b03938aa6357f696ff9ca257315e02f79e0a23ef8b6d87d37430139f2e600c. Prior package-version: 0.90.0.
package-version: "0.107.0" # PUBLISHED coherent-set/v0.107.0 at source75ab98dd; #4682 accepted original39170373582/a1 complete. PRIOR PUBLISHED: coherent-set/v0.106.0, release 416441527, original candidate 2e42faaa994367b9f50be87439e8fd973ad21501/content sha256:351a435c1f162f3ff8ca8e6722d58b34b193b44744a6a207f9bb57f015f8204d. Original 39127872315 remains incomplete generation 16; separately admitted 39130246438 settled Drivers without resend and verified all 16 effects at final generation 33. Both feeds match original normalized payloads; signed NuGet archives differ. Later global selector106 observation has no pre-entry preimage/change timing; whole runtime/discovery, board binding, fleet and receiver acceptance remain separate. PRIOR immutable 0.105.0: PUBLISHED: coherent-set/v0.105.0, candidate e54a59885580c894c8fbc67b0b27af3571ea9883, initial39096861301 stopped at generation14; separately selected39098313280/a1 completed all16/final33 without resending the settled Kit intent, release416229635 promoted/latest; final coherent channel and installed82-file correspondence remain bounded to their original evidence. PRIOR immutable0.104.0: coherent-set/v0.104.0, release416097241, candidate912eba8bbd707dabcbc5011d508c479109010b71/content sha256:86a776fe591b5b98bf189fdf2c47148b1b417551c44f091146a1d6ce1acfd987; continuation39080633461/a1 at controller5a2d13d0 accepted final journal22 generation34/all16 effects. Original39073648848/a1 remains an incomplete checkpoint; original .103 Unknown and all inherited reservations remain. Installed update and private-caller/consumer acceptance are separate. PRIOR 0.102: PUBLISHED: fixed candidate6e9be17bacd288ece103b67ecd5842d37a9c8e50, content sha256:fc16321e011ea616648ccc1dafda00bfc06fa34210fd49ddb008bb56c9ceecf5; original publisher38133108945/a1, continuation38156868958/a1 accepted generation33/all16effects including both feeds and promotion. Installed selector custody and C3 provider acceptance remain separate. PRIOR Published coherent-set/v0.101.0, release408709919; candidate content sha256:e8ed439047f663dfcb34aba1152ffd4c6966a0c3a27be0ebb48eebcf47e26996, source79051e56b025dadfc6fcaabd58b79e33f2854928; all three normalized candidate payloads match both feeds. No installed-adoption or current-channel claim. PRIOR Published coherent-set/v0.100.0, source3ed8ad419a64253ca6f665e9779e5e4d110f50a5; original manifest0b31c416 and both-feed normalized payloads verified, fresh tag/release/feed metadata confirmed2026-10-09. Original operation custody remains unknown. PRIOR Accepted coherent-set/v0.99.0 publisher37566865635, source64e95ebec1a8294e16edaafdb27e6aa96f32c6f7, release405346080; both-feed readbacks accepted by root. PRIOR Verified coherent-set/v0.98.0 publication 37434982959, journal utel-rel-15, producer 3d4f7e9c6337fb020e269e632653de0faeef6d72, content sha256:15a3bc4c133216cde77d1fef5b639d1842588a5754802eaa11b098e7b62c2a06. PRIOR Both-feed publication accepted for coherent-set/v0.97.1 at source 99ea75286f5c3cea2a261fef4e5b45cd70378185; exact-head hosted feed readback also confirms both feeds. PRIOR0.97.0 publication: run 37235030417; coherent-set/v0.97.0, release 403211100, content sha256:b78fd7bdff1251e32c07ffb181c31b8c2009e3174cfe305b0761f5ca8b4e245d. Prior 0.96.0 receipts remain immutable.
package-tag: "coherent-set/v0.107.0" # Release416724931 at source75ab98dd28b1a818cc3986d595bf21e0fe691ec6. PRIOR coherent-set/v0.106.0: Exact candidate source 2e42faaa994367b9f50be87439e8fd973ad21501; release 416441527 promoted 2026-10-18T13:18:34Z. Prior coherent-set/v0.105.0 remains immutable. Prior coherent-set/v0.104.0, coherent-set/v0.102.0 and all earlier release identities remain immutable.
@@ -1005,7 +1005,7 @@ contracts:
surface: "optional Linux x64 FS.GG.Telemetry.Host dotnet tool — authenticated workspace-scoped ingestion, private dashboard, protected native capture and bounded learning export; independently versioned from the github coordination coherent set"
consumers: [] # DELIBERATELY EMPTY: operators install this optional service; no repository in the contract graph restores it.
- id: new-sdd-workspace
- version: "0.17.0" # SOURCE/PUBLISHED: original Creator017 candidate39168423443/a1 and publisher39172890714/a1 completed all8/final17; promoted release416751979 at75ab98dd. Fresh authenticated feed-coherence39212372585 independently sees017 on both feeds; public manifest/journal match source and payload70162fa2. Installed/consumer acceptance remains separate. PRIOR SOURCE PREPARATION: canonical work-board full driver materialization and normal coherent107 eleven-project build/package closure. Creator017 has its own candidate/publisher and fresh journal017; coherent107 publication does not publish Creator. Published016/frozen099 and historical013 recovery bytes/identities remain unchanged. Actual published107 consumer and installed017 qualification remain separate. PRIOR SOURCE/PUBLISHED: genuine candidate38098763409 from protected51261fa186da2a1ca6c6a33f39238a022cd66f6f; same-candidate canonical receivers and decoder accepted. Original publisher38106767120 failed; recovery38111692161 at37cb18d9 settled existing intent without NuGet resend, canonical generation17/all eight effects verified. Public installed adoption remains pending. PRIOR0.16 SOURCE PREPARATION: same-invocation absent-target and SDD-owned tool-manifest preimage repair; frozen accepted 0.97.1 dependency bytes and source are pinned; prior0.97.0 remains immutable. New0.16 qualification/publication/installed acceptance pending. PRIOR0.15 SOURCE/PUBLISHED: fresh-scaffold origin repair, first-attempt publisher37269935925 at b1181b1afd6d0aa7da57e179c44bddcea50d8054 accepted; actual fresh015 journey refused generatedSDD094 pin; consumedreceiver preserved. PRIOR 0.14 SOURCE/PUBLISHED: explicit product V2 creation/retrofit; publisher 37236913897 promoted exact source 2ab0c0ff9f37bdec9a11ba3604ebdc230711934f, eight journal effects and public install/help verified; actual product journeys remain separate. PRIOR 0.13.0 SOURCE/PUBLISHED: typed project-knowledge bootstrap with public SDD 2.1.0, Templates 0.18.0 and unchanged Rendering 0.31.0; both-feed package publication is verified; GitHub release promotion and installed/receiver qualification remain pending. PRIOR immutable source/tag: 4889c446de0a431d1168a61a89ab660fc2062314, new-sdd-workspace/v0.12.0.
+ version: "0.18.0" # SOURCE PREPARATION ONLY: prospective Creator018 exact published108 dependency-closure reuse; publication blocked until real promoted108 pin exists. Published017 remains unchanged. PRIOR SOURCE/PUBLISHED: original Creator017 candidate39168423443/a1 and publisher39172890714/a1 completed all8/final17; promoted release416751979 at75ab98dd. Fresh authenticated feed-coherence39212372585 independently sees017 on both feeds; public manifest/journal match source and payload70162fa2. Installed/consumer acceptance remains separate. PRIOR SOURCE PREPARATION: canonical work-board full driver materialization and normal coherent107 eleven-project build/package closure. Creator017 has its own candidate/publisher and fresh journal017; coherent107 publication does not publish Creator. Published016/frozen099 and historical013 recovery bytes/identities remain unchanged. Actual published107 consumer and installed017 qualification remain separate. PRIOR SOURCE/PUBLISHED: genuine candidate38098763409 from protected51261fa186da2a1ca6c6a33f39238a022cd66f6f; same-candidate canonical receivers and decoder accepted. Original publisher38106767120 failed; recovery38111692161 at37cb18d9 settled existing intent without NuGet resend, canonical generation17/all eight effects verified. Public installed adoption remains pending. PRIOR0.16 SOURCE PREPARATION: same-invocation absent-target and SDD-owned tool-manifest preimage repair; frozen accepted 0.97.1 dependency bytes and source are pinned; prior0.97.0 remains immutable. New0.16 qualification/publication/installed acceptance pending. PRIOR0.15 SOURCE/PUBLISHED: fresh-scaffold origin repair, first-attempt publisher37269935925 at b1181b1afd6d0aa7da57e179c44bddcea50d8054 accepted; actual fresh015 journey refused generatedSDD094 pin; consumedreceiver preserved. PRIOR 0.14 SOURCE/PUBLISHED: explicit product V2 creation/retrofit; publisher 37236913897 promoted exact source 2ab0c0ff9f37bdec9a11ba3604ebdc230711934f, eight journal effects and public install/help verified; actual product journeys remain separate. PRIOR 0.13.0 SOURCE/PUBLISHED: typed project-knowledge bootstrap with public SDD 2.1.0, Templates 0.18.0 and unchanged Rendering 0.31.0; both-feed package publication is verified; GitHub release promotion and installed/receiver qualification remain pending. PRIOR immutable source/tag: 4889c446de0a431d1168a61a89ab660fc2062314, new-sdd-workspace/v0.12.0.
package-version: "0.17.0" # Publication accepted: original publisher39172890714/a1, all8/final17; promoted release416751979 and journal equal producer payload70162fa2 on both feeds, signed NuGet rawa7a240c4 distinct from prepared raw2c5df221. Fresh authenticated hosted feed39212372585 sees017 on both feeds; local403 capability gap remains. No install or native adoption inferred. PRIOR Publication accepted2026-10-11: original512 candidate/raw GitHub package SHA256 cfccaea9966cd8e3c86dbb003b262953c7f7d7fe80976b87b5d513a1a0e27122; signed public raw SHA-256:192b5803abd2bcd8d2c2383746a3fd32a775b9f3eb7d132d8b5a222a95e94314; all93 common package members and producer payload SHA-256:5872dbdca24818bf9ec59ff42dc84d7f531775d388713f1f6791e89a7cf59d70 match. Additional signature member retained; no cryptographic signature verification claim. PRIOR0.15 Publication execution accepted: run 37269935925, release 403405565, eight verified effects across 17 canonical journal generations. Candidate/release archive sha256:89cfd28574a7f80082eefb1fa81e6004d7455e8fd91a3d45c625e1ee36c6198e; nuget.org signed archive sha256:433dbdea9cc2f9f5e7635ed357ce2250c643662d03fc127dbd0a013dcfe72340; normalized producer payload sha256:8f83d971475a1e8e8363657e6fdf68d22ec61d0f7ff47af14d47d0d767b5b3f2. Independent GitHub feed download/metadata refused 403; hosted feed verification remains joined. PRIOR immutable 0.14: run 37236913897, release 403220770, payload sha256:367ac42ccb0420c4e22064d0aed6405d44ec44e2d4aa05cefd8447bfc83bd234; 0.13 publication/recovery receipts remain unchanged.
package-tag: "new-sdd-workspace/v0.17.0" # Exact source75ab98dd28b1a818cc3986d595bf21e0fe691ec6; original candidate39168423443/a1 and publisher39172890714/a1. PRIOR016 Candidate source51261fa186da2a1ca6c6a33f39238a022cd66f6f; recovery publisher source37cb18d9e2a70e0ba2981c543a5d84851ae8e9b8. Full original intent/history retained. PRIOR0.15 tag new-sdd-workspace/v0.15.0, exact protected source b1181b1afd6d0aa7da57e179c44bddcea50d8054; promoted three-asset stable release. Installed adoption remains separate.
owner: github # Registry.fs resolves owner against repoIds + the literal `github`. `.github` owns the scaffolder: ADR-0016 retired FS.GG.Templates' local `new-fullstack` for this single org CLI, and its release workflow lives here because the tool does (mirrors coord-engine).
diff --git a/registry/driver-skill-manifest.json b/registry/driver-skill-manifest.json
index c676e2593..8d8895147 100644
--- a/registry/driver-skill-manifest.json
+++ b/registry/driver-skill-manifest.json
@@ -5,7 +5,7 @@
"id": "atlas",
"scope": "driver",
"sha256": "c18e56fcc56abf80903e2fc6829cd94b44f42947724a26318ebcbf1ac5e1b35b",
- "tree-sha256": "7fad1e6fe02ac9e2e89ca5f781ab8631bcfa5fb73f6ad032aa8aa7c8d730bc79",
+ "tree-sha256": "27d15658613e4d090022d57871e61a1550606076d49d640252a8210fcdc2fe3f",
"files": [
{
"path": "SKILL.md",
@@ -24,7 +24,7 @@
},
{
"path": "assets/seed/catalog.json",
- "sha256": "75c6c33ff0b096cd093e46b1714148bb2b5f71b1b066cbbf79cb9d5a2424f882",
+ "sha256": "d8d3b5ece64bfa9b043d36371700e392a7bae6e4624bb3dea28a6ef3f4556363",
"executable": false
},
{
@@ -947,6 +947,11 @@
"sha256": "aec13a075b84253397fb97e1c93a23e1aaee6d6bff2a9161bfd00a5b1d7611de",
"executable": false
},
+ {
+ "path": "assets/seed/records/af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a.json",
+ "sha256": "af6b60ae365a6cbeb140430b030bdb667f53a2a97508ae92dfc9ed91ca73b54a",
+ "executable": false
+ },
{
"path": "assets/seed/records/b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d.json",
"sha256": "b09355a97e3aef396f681943b37a404a98fccc6bcb97781eddb2fc000d1d985d",
@@ -2099,12 +2104,12 @@
{
"id": "publishing-and-deployment",
"scope": "operator",
- "sha256": "d26de2ed4cbf7953af34adde9f0e99420280f93155c0f68e85c9549e723a7b42",
- "tree-sha256": "f7f634e09837e3b4806da79073ed9b4b3f36b44fc9782f7cada819fa630cca56",
+ "sha256": "98bbcc099471796a9ca787d7892b02baa722176edd3c81afbbc1985dd6d20cbb",
+ "tree-sha256": "9fa25ad9ba4fdb3c7c420ddb7aa6676023c11e1691bc978bb9ae7083d7551cbc",
"files": [
{
"path": "SKILL.md",
- "sha256": "d26de2ed4cbf7953af34adde9f0e99420280f93155c0f68e85c9549e723a7b42",
+ "sha256": "98bbcc099471796a9ca787d7892b02baa722176edd3c81afbbc1985dd6d20cbb",
"executable": false
},
{
diff --git a/registry/skills.yml b/registry/skills.yml
index d3bc18d64..6e81a02ab 100644
--- a/registry/skills.yml
+++ b/registry/skills.yml
@@ -398,7 +398,7 @@ skills:
# publishing-and-deployment — homed beside its owner+predicate siblings and reconciled verbatim from
# .github's producer manifest by `--write` (.github#299/.github#1200). The position
# and this annotation are generated; the row's bytes are the manifest's.
- - { id: publishing-and-deployment,scope: operator,owner: .github, source: .github/.claude/skills/publishing-and-deployment/SKILL.md, sha256: d26de2ed4cbf7953af34adde9f0e99420280f93155c0f68e85c9549e723a7b42, materializes-when: "false" }
+ - { id: publishing-and-deployment,scope: operator,owner: .github, source: .github/.claude/skills/publishing-and-deployment/SKILL.md, sha256: 98bbcc099471796a9ca787d7892b02baa722176edd3c81afbbc1985dd6d20cbb, materializes-when: "false" }
# drive-board-best — homed beside its owner+predicate siblings and reconciled verbatim from
# .github's producer manifest by `--write` (.github#299/.github#1200). The position
# and this annotation are generated; the row's bytes are the manifest's.
diff --git a/scripts/NewSddWorkspace/NewSddWorkspace.fsproj b/scripts/NewSddWorkspace/NewSddWorkspace.fsproj
index 36a188965..eacd9abb6 100644
--- a/scripts/NewSddWorkspace/NewSddWorkspace.fsproj
+++ b/scripts/NewSddWorkspace/NewSddWorkspace.fsproj
@@ -18,9 +18,9 @@
new-sdd-workspace
FS.GG.NewSddWorkspace
- 0.17.0
- 0.17.0: package the canonical work-board instruction closure and explicit product-board materializer against the normal coordination 0.107 source graph. Publication and installed adoption use this tool's independent release route.
+ Coherent 0.108 does not publish this tool; its own candidate and publisher qualify 0.18. -->
+ 0.18.0
+ 0.18.0: package the canonical work-board instruction closure and explicit product-board materializer with exact promoted coordination 0.108 runtime dependencies. Publication and installed adoption use this tool's independent release route.
new-sdd-workspace
FS.GG workspace scaffolder — composes a selectable Standard or Typed SDD lifecycle, a runnable provider workspace, and an optional Governance overlay in one command, with a rich Spectre.Console progress UI. Orchestrates existing published machinery; no FS.GG.Templates checkout required.
@@ -82,6 +82,7 @@
-
+
+
diff --git a/scripts/check-paths-coherence.py b/scripts/check-paths-coherence.py
index fcf65c156..abdf517ab 100755
--- a/scripts/check-paths-coherence.py
+++ b/scripts/check-paths-coherence.py
@@ -555,9 +555,22 @@ def frozen_creator_reference(root: str, rel: str, project: ET.ElementTree, refer
verify = [t for t in xml.findall("Target") if t.get("Name") == "VerifyFrozenCoordDependencies"]
command = 'python3 "$(MSBuildThisFileDirectory)../creator-frozen-coord-dependencies.py" verify-layout --producer-source "$(FsggFrozenCoordSource)" --dependencies "$(FsggFrozenCoordDependencies)"'
if (len(verify) != 1 or verify[0].attrib != {"Name": "VerifyFrozenCoordDependencies", "BeforeTargets": "PrepareForBuild", "Condition": scope}
- or len(list(verify[0])) != 1 or verify[0][0].tag != "Exec" or verify[0][0].attrib != {"Command": command}):
+ or any(child.tag != "Exec" or list(child) for child in verify[0])):
return False
- # The external recipe remains explicit source input, never a guessed property target.
+ historical = [{"Command": command}]
+ current = [
+ {"Condition": "'$(FsggCurrentCoordDependencies)' != 'true'", "Command": command},
+ {"Condition": "'$(FsggCurrentCoordDependencies)' == 'true'",
+ "Command": command.replace("creator-frozen-coord-dependencies.py", "creator-current-coord-dependencies.py")},
+ ]
+ # These are the only two supported selectors: the retained single frozen route,
+ # or the paired retained/current route. Both keep the same ordinary local graph
+ # and no-producer-build/copy guards. Unknown conditions/helpers remain no-verdict.
+ # A genuine current pin is deliberately not required by this static source graph:
+ # the current adapter refuses its absent pin at the release boundary independently.
+ if [child.attrib for child in verify[0]] not in (historical, current):
+ return False
+ # Authenticate the retained recipe only; its fixed census is not a current108 census.
pin_path = os.path.join(root, "scripts", "creator-frozen-coord-dependencies.json")
try:
with open(pin_path, encoding="utf-8") as source:
diff --git a/scripts/creator-current-coord-dependencies.py b/scripts/creator-current-coord-dependencies.py
new file mode 100644
index 000000000..2a0bd5747
--- /dev/null
+++ b/scripts/creator-current-coord-dependencies.py
@@ -0,0 +1,215 @@
+#!/usr/bin/env python3
+"""Current Creator release join; historical staging primitives remain immutable.
+
+No pin is shipped until the producer has genuinely promoted. Source-only builds
+never need one. This module imports no command entrypoint and runs no compiler.
+"""
+from __future__ import annotations
+import argparse
+import json
+import pathlib
+import re
+import runpy
+import stat
+import zipfile
+import subprocess
+import urllib.request
+
+ROOT = pathlib.Path(__file__).resolve().parents[1]
+PIN_PATH = pathlib.Path('scripts/creator-current-coord-dependencies.json')
+old = runpy.run_path(str(ROOT / 'scripts/creator-frozen-coord-dependencies.py'))
+require, regular, digest = (old[name] for name in ('require', 'regular', 'digest'))
+PREFIX = old['PREFIX']
+MODE = 'published-dependency'
+SCHEMA = 'fsgg.creator-published-dependencies/1'
+
+
+def object_pairs(pairs):
+ value = {}
+ for key, body in pairs:
+ require(key not in value, 'duplicate JSON field: ' + key)
+ value[key] = body
+ return value
+
+
+def read_json(body):
+ require(len(body) <= 4 * 1024 * 1024, 'dependency JSON bound exceeded')
+ return json.loads(body, object_pairs_hook=object_pairs)
+
+
+def validate_pin(pin):
+ require(isinstance(pin, dict) and pin.get('schema') == 'fsgg.creator-current-coord-dependencies/1'
+ and pin.get('version') == '0.108.0', 'current dependencies require promoted coherent 0.108.0 pin')
+ for field, size in (('sourceSha', 40), ('archiveSha256', 64), ('promotedManifestSha256', 64)):
+ require(isinstance(pin.get(field), str) and re.fullmatch('[0-9a-f]{' + str(size) + '}', pin[field]),
+ 'invalid current dependency ' + field)
+ for field in ('releaseId', 'assetId', 'promotedManifestAssetId'):
+ require(type(pin.get(field)) is int and pin[field] > 0, 'missing promoted dependency ' + field)
+ require(pin.get('downloadUrl') == 'https://github.com/FS-GG/.github/releases/download/coherent-set/v0.108.0/FS.GG.Coord.Cli.0.108.0.nupkg',
+ 'current dependency download identity differs')
+ members = pin.get('members')
+ require(isinstance(members, dict) and {'FS.GG.Coord.GitHub.dll', 'fsgg-coord-engine.dll',
+ 'fsgg-coord-engine.deps.json', 'fsgg-coord-engine.runtimeconfig.json'} <= members.keys(),
+ 'current dependency closure missing required runtime members')
+ for name, sha in members.items():
+ path = pathlib.PurePosixPath(name)
+ require(name and not path.is_absolute() and '..' not in path.parts and '\\' not in name
+ and path.as_posix() == name and name != 'DotnetToolSettings.xml'
+ and not name.startswith('new-sdd-workspace.')
+ and isinstance(sha, str) and re.fullmatch('[0-9a-f]{64}', sha), 'invalid dependency member')
+ require(isinstance(pin.get('projects'), dict) and pin['projects'].get(
+ 'scripts/NewSddWorkspace/NewSddWorkspace.fsproj') == 'new-sdd-workspace', 'missing current source graph')
+ require(isinstance(pin.get('sourceLeaves'), list) and pin['sourceLeaves'], 'missing current source census')
+ paths = set()
+ for leaf in pin['sourceLeaves']:
+ require(isinstance(leaf, dict) and set(leaf) == {'path', 'sha256'}, 'invalid dependency source leaf')
+ path = pathlib.PurePosixPath(leaf['path'])
+ require(not path.is_absolute() and '..' not in path.parts and '\\' not in leaf['path']
+ and path.as_posix() == leaf['path'] and leaf['path'] not in paths
+ and re.fullmatch('[0-9a-f]{64}', leaf['sha256']), 'invalid dependency source path or digest')
+ paths.add(leaf['path'])
+ return pin
+
+
+def load_pin(root=ROOT):
+ """Only the fixed protected-source path; no caller-provided provenance path."""
+ path = root / PIN_PATH
+ require(path.exists(), 'Creator 0.18 release fenced: genuine promoted 0.108 dependency pin absent')
+ return validate_pin(read_json(regular(path)))
+
+
+def protected_pin(source_sha):
+ pin = load_pin()
+ require(re.fullmatch('[0-9a-f]{40}', source_sha) is not None, 'invalid protected creator source')
+ original = subprocess.check_output(['git', '-C', str(ROOT), 'show', source_sha + ':' + PIN_PATH.as_posix()], timeout=10)
+ protected = subprocess.check_output(['git', '-C', str(ROOT), 'show', 'HEAD:' + PIN_PATH.as_posix()], timeout=10)
+ require(read_json(original) == pin == read_json(protected), 'candidate dependency pin differs from protected publisher source')
+ return pin
+
+
+def acquire(destination, pin):
+ """Acquire original promoted assets with independent native identity readback."""
+ require(not destination.exists(), 'dependency acquisition destination exists')
+ def request(url):
+ with urllib.request.urlopen(urllib.request.Request(url, headers={'Accept': 'application/vnd.github+json'}), timeout=60) as response:
+ body = response.read(134217729)
+ require(len(body) <= 134217728, 'dependency acquisition bound exceeded')
+ return body
+ release = read_json(request('https://api.github.com/repos/FS-GG/.github/releases/' + str(pin['releaseId'])))
+ require(release.get('id') == pin['releaseId'] and release.get('tag_name') == 'coherent-set/v0.108.0'
+ and release.get('draft') is False and release.get('prerelease') is False, 'producer release not promoted')
+ asset_rows = read_json(request('https://api.github.com/repos/FS-GG/.github/releases/' + str(pin['releaseId']) + '/assets?per_page=100&page=1'))
+ require(isinstance(asset_rows, list) and len(asset_rows) < 100
+ and len({row['id'] for row in asset_rows}) == len(asset_rows)
+ and len({row['name'] for row in asset_rows}) == len(asset_rows), 'incomplete or duplicate producer assets')
+ assets = {row['id']: row for row in asset_rows}
+ package = assets.get(pin['assetId'], {})
+ manifest = assets.get(pin['promotedManifestAssetId'], {})
+ require(package.get('browser_download_url') == pin['downloadUrl']
+ and package.get('name') == 'FS.GG.Coord.Cli.0.108.0.nupkg', 'producer asset identity differs')
+ require(manifest.get('name') == 'release-manifest.json', 'promoted manifest asset identity differs')
+ manifest_body = request(manifest['browser_download_url'])
+ require(digest(manifest_body) == pin['promotedManifestSha256'], 'promoted manifest digest differs')
+ promoted = read_json(manifest_body)
+ require(promoted.get('descriptor', {}).get('sourceSha') == pin['sourceSha'] and promoted.get('descriptor', {}).get('version') == pin['version'],
+ 'promoted manifest producer identity differs')
+ body = request(pin['downloadUrl'])
+ require(digest(body) == pin['archiveSha256'], 'producer archive digest differs')
+ with destination.open('xb') as stream:
+ stream.write(body)
+ old['archive_members'](destination, pin)
+ return {'producerArchiveSha256': pin['archiveSha256'], 'promotedManifestSha256': pin['promotedManifestSha256']}
+
+
+def pin_digest(pin):
+ return digest(json.dumps(pin, sort_keys=True, separators=(',', ':')).encode())
+
+
+def package_members(package, pin):
+ """Recompute every producer member and reject alternate DLL shadowing."""
+ validate_pin(pin)
+ with zipfile.ZipFile(package) as archive:
+ entries = archive.infolist()
+ names = [row.filename for row in entries]
+ require(len(names) == len(set(names)) and sum(row.file_size for row in entries) <= 134217728,
+ 'duplicate or oversized creator package')
+ for row in entries:
+ path = pathlib.PurePosixPath(row.filename)
+ require(not path.is_absolute() and '..' not in path.parts and '\\' not in row.filename
+ and not stat.S_ISLNK(row.external_attr >> 16), 'unsafe creator member')
+ for name, expected in pin['members'].items():
+ require(PREFIX + name in names and digest(archive.read(PREFIX + name)) == expected,
+ 'creator package changed published dependency: ' + name)
+ shared_dlls = {pathlib.PurePosixPath(name).name.casefold() for name in pin['members'] if name.endswith('.dll')}
+ for name in names:
+ if name.endswith('.dll') and pathlib.PurePosixPath(name).name.casefold() in shared_dlls:
+ require(name.startswith(PREFIX) and name[len(PREFIX):] in pin['members'], 'alternate dependency DLL shadow')
+ deps = read_json(archive.read(PREFIX + 'new-sdd-workspace.deps.json'))
+ cli = 'FS.GG.Coord.Cli/0.108.0'
+ require(deps.get('libraries', {}).get(cli, {}).get('type') == 'project'
+ and deps.get('targets') and all(
+ target.get('new-sdd-workspace/0.18.0', {}).get('dependencies', {}).get('FS.GG.Coord.Cli') == '0.108.0'
+ and 'fsgg-coord-engine.dll' in target.get(cli, {}).get('runtime', {})
+ for target in deps['targets'].values()), 'Creator 0.18 dependency metadata differs')
+ selected = {pathlib.PurePosixPath(path).stem: assembly for path, assembly in pin['projects'].items()
+ if assembly != 'new-sdd-workspace'}
+ for name, assembly in selected.items():
+ key = name + '/0.108.0'
+ require(deps.get('libraries', {}).get(key, {}).get('type') == 'project'
+ and all(assembly + '.dll' in target.get(key, {}).get('runtime', {})
+ for target in deps['targets'].values()), 'missing coherent dependency metadata: ' + name)
+ for library in deps.get('libraries', {}):
+ name, _, version = library.partition('/')
+ if name in selected:
+ require(version == '0.108.0', 'mixed coherent dependency metadata')
+ for target in deps['targets'].values():
+ for library in target.values():
+ require(all(version == '0.108.0' for name, version in library.get('dependencies', {}).items()
+ if name in selected), 'mixed coherent dependency edge')
+ return dict(pin['members'])
+
+
+def evidence(package, source_sha, pin, *, fixtures_passed):
+ require(fixtures_passed is True, 'published dependency compiled fixtures not accepted')
+ members = package_members(package, pin)
+ return {'schema': SCHEMA, 'mode': MODE, 'version': '0.18.0', 'sourceSha': source_sha,
+ 'publishedDependencySourceSha': pin['sourceSha'], 'coherentVersion': pin['version'],
+ 'dependencyPinSha256': pin_digest(pin), 'producerArchiveSha256': pin['archiveSha256'],
+ 'promotedManifestSha256': pin['promotedManifestSha256'],
+ 'archiveSha256': digest(regular(package)), 'dependencyMembers': members,
+ 'fixturesPassed': True, 'installedAdoptionAccepted': False}
+
+
+def verify_evidence(body, package, manifest, pin):
+ require(isinstance(body, dict), 'published dependency evidence body missing')
+ expected = evidence(package, manifest['sourceSha'], pin, fixtures_passed=True)
+ require(body == expected, 'published dependency evidence body differs or is source-only')
+ require(manifest.get('version') == '0.18.0' and manifest.get('archiveSha256') == expected['archiveSha256'],
+ 'Creator manifest/package dependency join differs')
+ return expected
+
+
+if __name__ == '__main__':
+ parser = argparse.ArgumentParser(description=__doc__)
+ parser.add_argument('command', choices=('preflight', 'acquire', 'verify-source', 'stage', 'verify-layout', 'verify-package'))
+ parser.add_argument('--producer-source', type=pathlib.Path)
+ parser.add_argument('--dependencies', type=pathlib.Path)
+ parser.add_argument('--package', type=pathlib.Path)
+ parser.add_argument('--source-sha')
+ args = parser.parse_args()
+ pin = load_pin()
+ if args.command == 'preflight':
+ print(json.dumps({'mode': MODE, 'dependencyPinSha256': pin_digest(pin)}))
+ elif args.command == 'acquire':
+ print(json.dumps(acquire(args.package, pin), sort_keys=True))
+ elif args.command == 'verify-package':
+ print(json.dumps(evidence(args.package, args.source_sha, pin, fixtures_passed=True), sort_keys=True))
+ else:
+ require(args.producer_source is not None, 'isolated producer source required')
+ if args.command == 'verify-source':
+ result = old['source_projects'](ROOT, pin, args.producer_source)
+ elif args.command == 'stage':
+ result = old['stage'](ROOT, args.dependencies, args.package, pin, args.producer_source)
+ else:
+ result = old['layout'](ROOT, args.dependencies, pin, args.producer_source)
+ print(json.dumps(result, sort_keys=True))
diff --git a/scripts/new-sdd-workspace-successor-artifact.py b/scripts/new-sdd-workspace-successor-artifact.py
index 0520b53dd..2bfecc005 100644
--- a/scripts/new-sdd-workspace-successor-artifact.py
+++ b/scripts/new-sdd-workspace-successor-artifact.py
@@ -13,13 +13,14 @@
import subprocess
import sys
import tempfile
+import runpy
import zipfile
-from new_sdd_workspace_successor_execution import CURRENT_017, CURRENT_016
+from new_sdd_workspace_successor_execution import CURRENT_018, CURRENT_017, CURRENT_016
REPOSITORY_ID = 1269292704
WORKFLOW = ".github/workflows/release-new-sdd-workspace-successor-candidate.yml"
-VERSION = CURRENT_017.version
+VERSION = CURRENT_018.version
PACKAGE = f"FS.GG.NewSddWorkspace.{VERSION}.nupkg"
MEMBERS = {PACKAGE, "manifest.json", "package-evidence.json"}
@@ -30,9 +31,11 @@ def require(ok: bool, detail: str) -> None:
def verify(artifact: dict, run: dict, archive_path: pathlib.Path, output: pathlib.Path, source_sha: str,
- *, release_binding=CURRENT_017) -> dict:
- require(release_binding is CURRENT_017 or release_binding is CURRENT_016, "unknown Creator artifact binding")
- # An explicit retained 0.16 reader is inert; the ordinary publisher always selects 0.17.
+ *, release_binding=CURRENT_018) -> dict:
+ require(any(release_binding is item for item in (CURRENT_018, CURRENT_017, CURRENT_016)), "unknown Creator artifact binding")
+ current = runpy.run_path(str(pathlib.Path(__file__).with_name("creator-current-coord-dependencies.py")))
+ pin = current["protected_pin"](source_sha) if release_binding is CURRENT_018 else None
+ # Explicit retained 0.16/0.17 readers are inert; the publisher selects 0.18.
VERSION = release_binding.version
PACKAGE = f"FS.GG.NewSddWorkspace.{VERSION}.nupkg"
MEMBERS = {PACKAGE, "manifest.json", "package-evidence.json"}
@@ -76,7 +79,7 @@ def verify(artifact: dict, run: dict, archive_path: pathlib.Path, output: pathli
mode = (member.external_attr >> 16) & 0xFFFF
require(not member.is_dir() and not stat.S_ISLNK(mode) and member.file_size <= 250_000_000,
"unsafe candidate archive member")
- manifest = json.loads(archive.read("manifest.json"))
+ manifest = current["read_json"](archive.read("manifest.json"))
require(manifest.get("sourceSha") == source_sha and manifest.get("version") == VERSION,
"Wizard manifest source or version differs")
with tempfile.TemporaryDirectory(prefix="wizard-candidate-", dir=output.parent) as temporary:
@@ -84,6 +87,9 @@ def verify(artifact: dict, run: dict, archive_path: pathlib.Path, output: pathli
for name in names:
with archive.open(name) as source, (work / name).open("xb") as target:
shutil.copyfileobj(source, target)
+ if release_binding is CURRENT_018:
+ current["verify_evidence"](current["read_json"](archive.read("package-evidence.json")),
+ work / PACKAGE, manifest, pin)
checker = pathlib.Path(__file__).with_name("new-sdd-workspace-release.py")
subprocess.run([sys.executable, str(checker), "verify", "--manifest", str(work / "manifest.json"),
"--package", str(work / PACKAGE)], check=True)
diff --git a/scripts/new-sdd-workspace-successor-publish.py b/scripts/new-sdd-workspace-successor-publish.py
index 2146e3df7..ea97bfe49 100644
--- a/scripts/new-sdd-workspace-successor-publish.py
+++ b/scripts/new-sdd-workspace-successor-publish.py
@@ -1,5 +1,5 @@
#!/usr/bin/env python3
-"""Publish the exact Wizard 0.17.0 candidate through fresh admitted effects."""
+"""Publish the exact Wizard 0.18.0 candidate through fresh admitted effects."""
from __future__ import annotations
@@ -21,7 +21,7 @@
from new_sdd_workspace_successor_provider import WizardProvider, publisher_error
REPOSITORY = "FS-GG/.github"
-REF = "refs/heads/fsgg/v2/journal/release/board-v2-product-creator-017"
+REF = "refs/heads/fsgg/v2/journal/release/board-v2-product-creator-018"
def require(ok: bool, detail: str) -> None:
@@ -40,12 +40,12 @@ def publication_primitives():
def publication_report(candidate_run, artifact, archive, mode):
- return {"schema": "fsgg.creator017-publication-summary/1", "mode": mode,
+ return {"schema": "fsgg.creator018-publication-summary/1", "mode": mode,
"candidateRunId": candidate_run, "candidateArtifactId": artifact,
"candidateArchiveSha256": archive, "candidateSourceSha": None,
"publisherSourceSha": None, "publisherRunId": None,
"logicalJournalRef": REF, "physicalJournalRef": "refs/heads/main",
- "physicalJournalDirectory": "state/releases/board-v2-product-creator-017",
+ "physicalJournalDirectory": "state/releases/board-v2-product-creator-018",
"classifiedPhysicalHead": None, "fresh": None, "startingJournal": None,
"lastObservedJournal": None, "journalMutationMayHaveOccurred": False,
"lastDispatch": None, "iterationsAttempted": 0, "complete": False,
@@ -206,10 +206,13 @@ def main() -> int:
args.candidate_archive_sha256,
"preflight" if args.preflight_only else "publish")
counted = None
- summary = args.workdir.parent / "creator017-publication-summary.json"
+ summary = args.workdir.parent / "creator018-publication-summary.json"
outcome = 1
try:
require(args.recovery_binding is None, "recovery binding outside selected mode")
+ import runpy
+ current_dependencies = runpy.run_path(str(pathlib.Path(__file__).with_name("creator-current-coord-dependencies.py")))
+ dependency_pin = current_dependencies["load_pin"]()
publisher_sha = os.environ["GITHUB_SHA"]
report["publisherSourceSha"] = publisher_sha
operator = os.environ["GITHUB_ACTOR"]
@@ -253,6 +256,11 @@ def main() -> int:
"--source-sha", candidate_source, "--output", str(candidate)], check=True)
manifest_path = candidate / "manifest.json"
manifest = json.loads(manifest_path.read_text())
+ require(current_dependencies["protected_pin"](candidate_source) == dependency_pin,
+ "dependency pin changed between publisher preflight and candidate verification")
+ current_dependencies["verify_evidence"](
+ current_dependencies["read_json"]((candidate / "package-evidence.json").read_bytes()),
+ candidate / "FS.GG.NewSddWorkspace.0.18.0.nupkg", manifest, dependency_pin)
content_id, ordered = effects(manifest)
primitives = publication_primitives()
report["stage"] = "quota"
@@ -261,7 +269,7 @@ def main() -> int:
admission = primitives.ProtectedPublisherAdmission(
WizardAdmission(api, manifest, publisher_sha, run_id, operator, "refs/heads/main"), counted, REF)
provider = primitives.ReportingProvider(WizardProvider(api, manifest_path, github_token, nuget_key), report)
- intent = {"contentId": content_id, "sourceSha": candidate_source, "version": "0.17.0",
+ intent = {"contentId": content_id, "sourceSha": candidate_source, "version": "0.18.0",
"candidateArchiveSha256": args.candidate_archive_sha256, "operator": operator}
journal = primitives.ReportingJournal(ProtectedReleaseJournal(counted, REF, main_directory=True), report)
report["stage"] = "preparation"
diff --git a/scripts/new_sdd_workspace_successor_admission.py b/scripts/new_sdd_workspace_successor_admission.py
index 959fad23a..7046ac3cb 100644
--- a/scripts/new_sdd_workspace_successor_admission.py
+++ b/scripts/new_sdd_workspace_successor_admission.py
@@ -3,7 +3,7 @@
from __future__ import annotations
from release_successor_provider import GitHubAPI
-from new_sdd_workspace_successor_execution import effects, CURRENT_017, HISTORICAL_013
+from new_sdd_workspace_successor_execution import effects, CURRENT_018, HISTORICAL_013
REPOSITORY = "FS-GG/.github"
REPOSITORY_ID = 1269292704
@@ -17,7 +17,7 @@ class Refused(RuntimeError):
class WizardAdmission:
def __init__(self, api: GitHubAPI, manifest: dict, publisher_sha: str, run_id: int, actor: str, ref: str,
- *, release_binding=CURRENT_017):
+ *, release_binding=CURRENT_018):
self.api = api
self.publisher_sha = publisher_sha
self.run_id = run_id
@@ -30,7 +30,7 @@ def __init__(self, api: GitHubAPI, manifest: dict, publisher_sha: str, run_id: i
def authorize(self, content_id: str, effect: str, action: str, request_digest: str) -> bool:
if (
- self.release_binding is not CURRENT_017
+ self.release_binding is not CURRENT_018
or content_id != self.content_id
or self.requests.get(effect) != request_digest
or action not in {"intent", "dispatch", "settle"}
diff --git a/scripts/new_sdd_workspace_successor_execution.py b/scripts/new_sdd_workspace_successor_execution.py
index 04c95bb55..b1822c228 100644
--- a/scripts/new_sdd_workspace_successor_execution.py
+++ b/scripts/new_sdd_workspace_successor_execution.py
@@ -23,11 +23,12 @@ class ReleaseBinding:
CURRENT_016 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.16.0", "new-sdd-workspace/v0.16.0")
# Explicit source successor; retained 0.16 descriptors do not confer current publication authority.
CURRENT_017 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.17.0", "new-sdd-workspace/v0.17.0")
-PACKAGE, VERSION, TAG = CURRENT_017.package, CURRENT_017.version, CURRENT_017.tag
+CURRENT_018 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.18.0", "new-sdd-workspace/v0.18.0")
+PACKAGE, VERSION, TAG = CURRENT_018.package, CURRENT_018.version, CURRENT_018.tag
-def effects(manifest: dict, *, binding: ReleaseBinding = CURRENT_017) -> tuple[str, tuple[Effect, ...]]:
- if binding is not CURRENT_017 and binding is not CURRENT_016 and binding is not HISTORICAL_013:
+def effects(manifest: dict, *, binding: ReleaseBinding = CURRENT_018) -> tuple[str, tuple[Effect, ...]]:
+ if binding is not CURRENT_018 and binding is not CURRENT_017 and binding is not CURRENT_016 and binding is not HISTORICAL_013:
raise Refused("unknown Wizard release binding")
if (
manifest.get("schema") != "fsgg.new-sdd-workspace-release/1"
diff --git a/scripts/release_successor_journal.py b/scripts/release_successor_journal.py
index 3f0f09aa4..9d5bcc9fe 100644
--- a/scripts/release_successor_journal.py
+++ b/scripts/release_successor_journal.py
@@ -30,11 +30,11 @@
SCHEMA = "fsgg.release-successor-journal/1"
# One selected current source composition, independent of frozen original cuts.
-CURRENT_RELEASE = {"version": "0.107.0", "predecessor": "0.106.0",
- "logicalRef": "refs/heads/fsgg/v2/journal/release/utel-rel-25",
- "directory": "state/releases/utel-rel-25",
- "predecessorSource": "2e42faaa994367b9f50be87439e8fd973ad21501",
- "predecessorContentId": "sha256:351a435c1f162f3ff8ca8e6722d58b34b193b44744a6a207f9bb57f015f8204d"}
+CURRENT_RELEASE = {"version": "0.108.0", "predecessor": "0.107.0",
+ "logicalRef": "refs/heads/fsgg/v2/journal/release/utel-rel-26",
+ "directory": "state/releases/utel-rel-26",
+ "predecessorSource": "75ab98dd28b1a818cc3986d595bf21e0fe691ec6",
+ "predecessorContentId": "sha256:c193dbf487f643a8b78300b568e4bfd09f8c56086ce96dc52865e219e8f98c9b"}
diff --git a/src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj b/src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj
index b7c84e521..1f318a89f 100644
--- a/src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj
+++ b/src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj
@@ -130,19 +130,16 @@ bytes under 0.52.0 would make the same version identify different artifacts. Ado
coherent set cut from corrected source. All three partial sets are recorded in
`registry/dependencies.yml`.
- 0.107.0 — Coordinate organization and selected product V2 work through canonical work-board.
-
-Drivers carries dependency-closed recovery, handoff and advisory routine entrypoints with one
-ownership/capacity/qualification/delivery workflow. Historical programme instructions redirect;
-Roadmap field, roadmap-telemetry and persisted wire identities remain compatible. The compiled
-plan grammar retains the original observation path and additionally admits the canonical path.
-Source supports explicit Work level Outcome/Delivery through binding5/schema3, inspection3 and
-integrator2 hierarchy-digest joins. Bounded native hierarchy and scoped closure reporting do not infer
-parent acceptance or dispatch unenrolled children. The maintained migration writer creates the selected
-field and initializes only explicit absent classifications, preserving conflicts and view settings.
-Source delivery does not switch an installed caller, binding, selector or operation authority.
-Existing qualified 0.105 caller and accepted 0.106 publication retain their distinct evidence.
-All unavailable historical effects and 439 inherited plus 46 later original holds remain Unknown.
+ 0.108.0 — Keep complete successor board inspection within its existing request budget.
+
+Binding5 combines project membership and planning reads, retaining fresh schema and final barriers,
+complete pagination and exact owner/content/field/option checks. The full22-item cohort is preserved;
+request and deadline limits stay500/270. Binding4 and product binding3 retain their existing behavior.
+Canonical work-board remains the entry for authorized organization and selected product coordination.
+This source release does not establish installed successor acceptance, a selector change or native
+operation authority. Published107 and independent Creator017 remain immutable. Prospective Creator018
+must reuse the exact promoted108 dependency closure through its independently qualified release route.
+All unavailable historical effects and439 inherited plus46 later original holds remain Unknown.
$(FsggStandingAdvisories)
diff --git a/src/FS.GG.Coord.GitHub/V2Projection.fs b/src/FS.GG.Coord.GitHub/V2Projection.fs
index 96cc8e0d5..b3a089a93 100644
--- a/src/FS.GG.Coord.GitHub/V2Projection.fs
+++ b/src/FS.GG.Coord.GitHub/V2Projection.fs
@@ -539,7 +539,7 @@ module V2Projection =
{ ItemId: string; Status: string option; Roadmap: string option; Track: string option
Observation: string option; MembershipPages: int }
- let readPlanning (transport: IGitHubTransport) (binding: Binding) (request: Request) =
+ let private readPlanningLegacy (transport: IGitHubTransport) (binding: Binding) (request: Request) =
let admitted = validateBinding binding |> Result.bind (fun () ->
if request.Issue.Number <= 0 || not (binding.Repositories.Contains $"{request.Issue.Owner}/{request.Issue.Repository}") || Map.tryFind request.ExpectedNodeId binding.SelectedIssues <> Some $"{request.Issue.Owner}/{request.Issue.Repository}#{request.Issue.Number}" then
Error(Malformed("bound V2 planning fields", "request is outside the explicitly selected native cohort"))
@@ -579,6 +579,93 @@ module V2Projection =
select "track" binding.Track |> Result.bind (fun track -> select "observation" binding.Observation |> Result.map (fun observation ->
{ ItemId = itemId; Status = status; Roadmap = roadmap; Track = track; Observation = observation; MembershipPages = pages }))))))))))
+ // Read the successor's membership and planning values together. Each invocation still
+ // reads the exact schema, and every membership page independently joins the owner and
+ // native issue. No response is cached across items or across the final barrier.
+ let private readSuccessorPlanning (transport: IGitHubTransport) (binding: Binding) (request: Request) =
+ let subject = "bound V2 successor planning memberships"
+ let invalid detail = Error(Malformed(subject, detail))
+ validateBinding binding |> Result.bind (fun () ->
+ if request.Issue.Number <= 0 || not (binding.Repositories.Contains $"{request.Issue.Owner}/{request.Issue.Repository}")
+ || Map.tryFind request.ExpectedNodeId binding.SelectedIssues <> Some $"{request.Issue.Owner}/{request.Issue.Repository}#{request.Issue.Number}" then
+ invalid "request is outside the explicitly selected native cohort"
+ else
+ let expected: ExactProject = { Owner = binding.Owner; Number = binding.ProjectNumber; Title = binding.ProjectTitle; Id = binding.ProjectId }
+ bootstrapExactProject transport expected |> Result.bind (fun board ->
+ verifyFieldSchema binding board |> Result.bind (fun () ->
+ let document = "query($projectOwner:String!,$owner:String!,$repo:String!,$number:Int!,$after:String){organization(login:$projectOwner){id login} repository(owner:$owner,name:$repo){nameWithOwner issue(number:$number){id number projectItems(first:50,after:$after){totalCount pageInfo{hasNextPage endCursor} nodes{id project{id} content{... on Issue{id number repository{nameWithOwner}}} status:fieldValueByName(name:\"Status\"){__typename ... on ProjectV2ItemFieldSingleSelectValue{name optionId field{... on ProjectV2SingleSelectField{id}}}} roadmap:fieldValueByName(name:\"Roadmap\"){__typename ... on ProjectV2ItemFieldTextValue{text field{... on ProjectV2Field{id}}}} track:fieldValueByName(name:\"Track\"){__typename ... on ProjectV2ItemFieldSingleSelectValue{name optionId field{... on ProjectV2SingleSelectField{id}}}} observation:fieldValueByName(name:\"Observation\"){__typename ... on ProjectV2ItemFieldSingleSelectValue{name optionId field{... on ProjectV2SingleSelectField{id}}}}}}}} rateLimit{cost remaining}}"
+ let mutable pages = 0
+ let fetch after =
+ let variables =
+ [ "projectOwner", VString binding.Owner; "owner", VString request.Issue.Owner
+ "repo", VString request.Issue.Repository; "number", VNumber(double request.Issue.Number) ]
+ @ (after |> Option.map (fun cursor -> [ "after", VString cursor ]) |> Option.defaultValue [])
+ GraphQl.read transport (graphRequest document variables subject) (fun data ->
+ try
+ let organization = data.GetProperty "organization"
+ let repository = data.GetProperty "repository"
+ let native = repository.GetProperty "issue"
+ let repo = $"{request.Issue.Owner}/{request.Issue.Repository}"
+ if organization.GetProperty("id").GetString() <> binding.OrganizationId
+ || organization.GetProperty("login").GetString() <> binding.Owner
+ || repository.GetProperty("nameWithOwner").GetString() <> repo
+ || native.GetProperty("id").GetString() <> request.ExpectedNodeId
+ || native.GetProperty("number").GetInt32() <> request.Issue.Number then
+ invalid "immutable owner or native issue identity differs"
+ else
+ let decode (node: JsonElement) =
+ let itemId = node.GetProperty("id").GetString()
+ let projectId = node.GetProperty("project").GetProperty("id").GetString()
+ let content = node.GetProperty "content"
+ if not (nonBlank itemId) || not (nonBlank projectId)
+ || content.GetProperty("id").GetString() <> request.ExpectedNodeId
+ || content.GetProperty("number").GetInt32() <> request.Issue.Number
+ || content.GetProperty("repository").GetProperty("nameWithOwner").GetString() <> repo then
+ invalid "membership content identity differs"
+ else Ok(itemId, projectId, node.Clone())
+ let connection = native.GetProperty "projectItems"
+ if connection.GetProperty("totalCount").GetInt32() < 0 || connection.GetProperty("nodes").GetArrayLength() > 50 then
+ invalid "membership count/window is invalid"
+ else
+ GraphQl.page subject "native issue project memberships" (fun (id, _, _) -> id) decode connection
+ |> Result.map (fun page -> pages <- pages + 1; page)
+ with
+ | :? Collections.Generic.KeyNotFoundException
+ | :? InvalidOperationException -> invalid "unreadable native membership identity")
+ GraphQl.drain subject "native issue project memberships" { MaxPages = 10; MaxItems = 500 } fetch
+ |> Result.bind (fun memberships ->
+ match memberships |> List.filter (fun (_, projectId, _) -> projectId = binding.ProjectId) with
+ | [ (itemId, _, node) ] ->
+ try
+ let select (alias: string) (field: SelectFieldBinding) =
+ let value = node.GetProperty alias
+ if value.ValueKind = JsonValueKind.Null then Ok None
+ else
+ let name = value.GetProperty("name").GetString()
+ if value.GetProperty("__typename").GetString() <> "ProjectV2ItemFieldSingleSelectValue"
+ || value.GetProperty("field").GetProperty("id").GetString() <> field.Id
+ || Map.tryFind name field.Options <> Some(value.GetProperty("optionId").GetString()) then
+ invalid "single-select field/value differs from bound schema"
+ else Ok(Some name)
+ let roadmap =
+ let value = node.GetProperty "roadmap"
+ if value.ValueKind = JsonValueKind.Null then Ok None
+ elif value.GetProperty("__typename").GetString() <> "ProjectV2ItemFieldTextValue"
+ || value.GetProperty("field").GetProperty("id").GetString() <> binding.RoadmapFieldId then
+ invalid "Roadmap field identity/type differs"
+ else Ok(Some(value.GetProperty("text").GetString()))
+ select "status" binding.Status |> Result.bind (fun status -> roadmap |> Result.bind (fun roadmap ->
+ select "track" binding.Track |> Result.bind (fun track -> select "observation" binding.Observation |> Result.map (fun observation ->
+ { ItemId = itemId; Status = status; Roadmap = roadmap; Track = track; Observation = observation; MembershipPages = pages }))))
+ with
+ | :? Collections.Generic.KeyNotFoundException
+ | :? InvalidOperationException -> invalid "unreadable bound planning fields"
+ | _ -> invalid "expected exactly one membership in the bound project"))))
+
+ let readPlanning (transport: IGitHubTransport) (binding: Binding) (request: Request) =
+ if binding.BindingVersion = 5 then readSuccessorPlanning transport binding request
+ else readPlanningLegacy transport binding request
+
let private repositoryAllowed (binding: Binding) (issue: IssueRef) =
let candidate = $"%s{issue.Owner}/%s{issue.Repository}"
binding.Repositories |> Seq.exists (fun allowed -> String.Equals(allowed, candidate, StringComparison.OrdinalIgnoreCase))
diff --git a/tests/coord-board-v2-cli-join/BoardV2ApplicationTests.fs b/tests/coord-board-v2-cli-join/BoardV2ApplicationTests.fs
index ba4d60cc1..53027dc65 100644
--- a/tests/coord-board-v2-cli-join/BoardV2ApplicationTests.fs
+++ b/tests/coord-board-v2-cli-join/BoardV2ApplicationTests.fs
@@ -68,6 +68,62 @@ let ``invalid loaded artifact and unknown flags perform no transport calls or re
Assert.False(File.Exists reportPath)
finally Directory.Delete(directory, true)
+[]
+let ``successor actual CLI reconciles twenty two items before its unchanged request ceiling`` () =
+ let repositories = [| ".github"; "FS.GG.Rendering"; "FS.GG.Game"; "FS.GG.Audio"; "FS.GG.Net"; "FS.GG.SDD" |]
+ let rows =
+ [ for index in 0 .. 21 ->
+ let issue: IssueRef = { Owner = "FS-GG"; Repository = repositories[index % repositories.Length]; Number = 6000 + index }
+ "I_cohort_" + string index, issue, "docs/coordination/programme.md" ]
+ let selected =
+ ProgrammeFixture.enroll
+ { ProgrammeFixture.successorBinding () with
+ SelectedIssues = rows |> List.map (fun (id, issue, _) -> id, $"{issue.Owner}/{issue.Repository}#{issue.Number}") |> Map.ofList
+ Repositories = repositories |> Array.map (fun name -> "FS-GG/" + name) |> Set.ofArray } rows
+ let change (request: Transport.Request) result =
+ result |> Result.map (fun (response: Transport.Response) ->
+ let root = Text.Json.Nodes.JsonNode.Parse response.Body
+ if request.Subject = "complete V2 project memberships" then
+ let connection = root.["data"].["node"].["items"]
+ for index in 0 .. 2 do
+ connection.["nodes"].AsArray().Add(JsonSerializer.SerializeToNode
+ {| id = "PVTI_unselected_" + string index
+ content = {| __typename = "Issue"; id = "I_unselected_" + string index
+ number = 8000 + index; repository = {| nameWithOwner = "FS-GG/.github" |} |} |})
+ connection.["totalCount"] <- Text.Json.Nodes.JsonValue.Create 25
+ elif request.Subject = "selected work classification" then
+ let item = match request.Body with Query(_, variables) -> variables |> List.pick (function "itemId", VId value -> Some value | _ -> None) | _ -> failwith "expected query"
+ let index = rows |> List.findIndex (fun (id, _, _) -> item = "synthetic-member-" + id)
+ let level, option = if index < 17 then "Outcome", "outcome-option" else "Delivery", "delivery-option"
+ root.["data"].["node"].["workLevel"].["name"] <- Text.Json.Nodes.JsonValue.Create level
+ root.["data"].["node"].["workLevel"].["optionId"] <- Text.Json.Nodes.JsonValue.Create option
+ { response with Body = root.ToJsonString() })
+ let reads = ProgrammeFixture.successorTransportFor selected rows (Some "Delivery") change
+ let directory = Path.Combine(Path.GetTempPath(), "board-v2-cohort-budget-" + Guid.NewGuid().ToString("N"))
+ Directory.CreateDirectory(directory, UnixFileMode.UserRead ||| UnixFileMode.UserWrite ||| UnixFileMode.UserExecute) |> ignore
+ try
+ let input, output = Path.Combine(directory, "binding.json"), Path.Combine(directory, "report.json")
+ File.WriteAllText(input, ProgrammeFixture.bindingJsonFor selected)
+ let code = BoardV2Application.runWithTransport reads ["inspect"; "--binding-file"; input; "--report-file"; output]
+ use report = JsonDocument.Parse(File.ReadAllText output)
+ let root = report.RootElement
+ let sends = reads.GraphQlCalls + reads.RestCalls
+ let populationGap, membershipGap = root.GetProperty("populationGap").ToString(), root.GetProperty("membershipGap").ToString()
+ Assert.True((code = 0), $"exit={code}; sends={sends}; populationGap={populationGap}; membershipGap={membershipGap}")
+ Assert.InRange(sends, 1, 499)
+ Assert.Equal(22, root.GetProperty("selected").GetInt32())
+ Assert.Equal(25, root.GetProperty("memberships").GetArrayLength())
+ Assert.Equal(3, root.GetProperty("memberships").EnumerateArray() |> Seq.filter (fun item -> not (item.GetProperty("enrolled").GetBoolean())) |> Seq.length)
+ let items = root.GetProperty("items").EnumerateArray() |> Seq.toList
+ Assert.Equal(22, items.Length)
+ Assert.All(items, fun item ->
+ Assert.Equal("Current", item.GetProperty("sourceCurrentness").GetString())
+ Assert.True(item.GetProperty("workItem").GetProperty("hierarchy").GetProperty("complete").GetBoolean()))
+ Assert.Equal(17, items |> List.filter (fun item -> item.GetProperty("workItem").GetProperty("workLevel").GetString() = "Outcome") |> List.length)
+ Assert.Equal(0, root.GetProperty("mutationAttempts").GetInt32())
+ Assert.Empty reads.Mutations
+ finally Directory.Delete(directory, true)
+
[]
let ``report history roundtrip strips current authority while retaining last verification`` () =
let issue = { Owner = "FS-GG"; Repository = ".github"; Number = 2963 }
diff --git a/tests/coord-board-v2-projection/ProgrammeFixture.fs b/tests/coord-board-v2-projection/ProgrammeFixture.fs
index 27a277977..79befc7c4 100644
--- a/tests/coord-board-v2-projection/ProgrammeFixture.fs
+++ b/tests/coord-board-v2-projection/ProgrammeFixture.fs
@@ -305,6 +305,21 @@ module ProgrammeFixture =
Fake.Recorder(fun request ->
let result =
match request.Body with
+ | Query(_, variables) when request.Subject = "bound V2 successor planning memberships" ->
+ let number = variables |> List.pick (function "number", VNumber value -> Some(int value) | _ -> None)
+ let repository = variables |> List.pick (function "repo", VString value -> Some value | _ -> None)
+ let id, issue, roadmap = rows |> List.find (fun (_, issue, _) -> issue.Number = number && issue.Repository = repository)
+ let repository = issue.Owner + "/" + issue.Repository
+ let select fieldId name option =
+ {| __typename = "ProjectV2ItemFieldSingleSelectValue"; name = name; optionId = option; field = {| id = fieldId |} |}
+ let memberItem =
+ {| id = "synthetic-member-" + id; project = {| id = project |}
+ content = {| id = id; number = issue.Number; repository = {| nameWithOwner = repository |} |}
+ status = select "status" "Blocked" "Blocked"; track = select "track" "Active delivery" "active"
+ observation = select "observation" "Unknown" "unknown"
+ roadmap = {| __typename = "ProjectV2ItemFieldTextValue"; text = roadmap; field = {| id = "roadmap" |} |} |}
+ wire {| organization = {| id = selected.OrganizationId; login = selected.Owner |}
+ repository = {| nameWithOwner = repository; issue = {| id = id; number = number; projectItems = connection [ memberItem ] |} |} |}
| Query(_, variables) when request.Subject = "selected work classification" ->
let itemId = variables |> List.pick (function "itemId", VId id -> Some id | _ -> None)
let id, _, _ = rows |> List.find (fun (id, _, _) -> itemId = "synthetic-member-" + id)
@@ -314,11 +329,14 @@ module ProgrammeFixture =
| Query(_, variables) when request.Subject = "selected native work hierarchy" ->
let number = variables |> List.pick (function "number", VNumber number -> Some(int number) | _ -> None)
let id, selectedIssue, _ = rows |> List.find (fun (_, issue, _) -> issue.Number = number)
- let child = {| id = "I_unselected-child"; number = 9999; state = "OPEN"; stateReason = (None: string option); closedAt = (None: string option); repository = {| nameWithOwner = "FS-GG/.github" |} |}
+ let child = {| id = if rows.Length = 1 then "I_unselected-child" else "I_unselected-child-" + id
+ number = if rows.Length = 1 then 9999 else 10000 + selectedIssue.Number
+ state = "OPEN"; stateReason = (None: string option); closedAt = (None: string option); repository = {| nameWithOwner = "FS-GG/.github" |} |}
let parent = {| id = "I_parent"; number = 9998; repository = {| nameWithOwner = "FS-GG/.github" |} |}
- wire {| repository = {| nameWithOwner = "FS-GG/.github"; issue =
+ let repository = selectedIssue.Owner + "/" + selectedIssue.Repository
+ wire {| repository = {| nameWithOwner = repository; issue =
{| id = id; number = selectedIssue.Number; updatedAt = revision; state = "OPEN"; stateReason = (None: string option); closedAt = (None: string option)
- body = ownerBody.Replace("https://github.com/FS-GG/.github/pull/42", "None"); repository = {| nameWithOwner = "FS-GG/.github" |}
+ body = ownerBody.Replace("https://github.com/FS-GG/.github/pull/42", "None"); repository = {| nameWithOwner = repository |}
parent = parent; subIssues = connection [child] |} |} |}
| Query(document, _) when document.Contains("projectV2(number:") ->
(original :> IGitHubTransport).Send request |> Result.map (fun response ->
diff --git a/tests/coord-board-v2-projection/V2ProjectionTests.fs b/tests/coord-board-v2-projection/V2ProjectionTests.fs
index 4f3b70329..bc77d3c20 100644
--- a/tests/coord-board-v2-projection/V2ProjectionTests.fs
+++ b/tests/coord-board-v2-projection/V2ProjectionTests.fs
@@ -1584,9 +1584,10 @@ let ``done and completed parent discrepancies never use child count as acceptanc
issue.["stateReason"] <- System.Text.Json.Nodes.JsonValue.Create "COMPLETED"
issue.["closedAt"] <- System.Text.Json.Nodes.JsonValue.Create "2026-10-17T12:00:00Z"
{value with Body = root.ToJsonString()}
- elif request.Subject = "bound V2 planning fields" then
- root.["data"].["node"].["status"].["name"] <- System.Text.Json.Nodes.JsonValue.Create "Done"
- root.["data"].["node"].["status"].["optionId"] <- System.Text.Json.Nodes.JsonValue.Create "Done"
+ elif request.Subject = "bound V2 successor planning memberships" then
+ let status = root.["data"].["repository"].["issue"].["projectItems"].["nodes"].[0].["status"]
+ status.["name"] <- System.Text.Json.Nodes.JsonValue.Create "Done"
+ status.["optionId"] <- System.Text.Json.Nodes.JsonValue.Create "Done"
{value with Body = root.ToJsonString()}
else value)
let reads = ProgrammeFixture.successorTransport selected (Some "Outcome") change
@@ -1744,3 +1745,87 @@ let ``selected hierarchy joins exact issue and node pairs while independent deli
Assert.Equal("ready", result.Head.Decision)
Assert.Equal(independent, result.Head.Issue)
Assert.Empty reads.Mutations
+
+let private successorPlanningPages mode =
+ let selected = ProgrammeFixture.successorBinding ()
+ let change (request: Transport.Request) result =
+ if request.Subject <> "bound V2 successor planning memberships" then result
+ else result |> Result.map (fun (response: Transport.Response) ->
+ let root = System.Text.Json.Nodes.JsonNode.Parse response.Body
+ let page = root.["data"].["repository"].["issue"].["projectItems"]
+ let target = page.["nodes"].[0]
+ let after = match request.Body with Query(_, variables) -> variables |> List.exists (function "after", _ -> true | _ -> false) | _ -> false
+ let paginated = mode = "pages" || mode = "owner-on-page-two"
+ if paginated then
+ page.["totalCount"] <- System.Text.Json.Nodes.JsonValue.Create 2
+ page.["pageInfo"].["hasNextPage"] <- System.Text.Json.Nodes.JsonValue.Create(not after)
+ page.["pageInfo"].["endCursor"] <- System.Text.Json.Nodes.JsonValue.Create(if after then "last" else "next")
+ if not after then
+ target.["id"] <- System.Text.Json.Nodes.JsonValue.Create "PVTI_other"
+ target.["project"].["id"] <- System.Text.Json.Nodes.JsonValue.Create "PVT_other"
+ for field in ["status"; "track"; "roadmap"; "observation"] do target.AsObject().Remove field |> ignore
+ elif mode = "owner-on-page-two" then
+ root.["data"].["organization"].["id"] <- System.Text.Json.Nodes.JsonValue.Create "O_wrong"
+ match mode with
+ | "duplicate-target" ->
+ let duplicate = target.DeepClone()
+ duplicate.["id"] <- System.Text.Json.Nodes.JsonValue.Create "PVTI_duplicate"
+ page.["nodes"].AsArray().Add duplicate
+ page.["totalCount"] <- System.Text.Json.Nodes.JsonValue.Create 2
+ | "partial-page" -> page.["pageInfo"].["hasNextPage"] <- System.Text.Json.Nodes.JsonValue.Create true
+ | "field-id" -> target.["status"].["field"].["id"] <- System.Text.Json.Nodes.JsonValue.Create "wrong"
+ | "field-type" -> target.["track"].["__typename"] <- System.Text.Json.Nodes.JsonValue.Create "ProjectV2ItemFieldTextValue"
+ | "option-id" -> target.["observation"].["optionId"] <- System.Text.Json.Nodes.JsonValue.Create "wrong"
+ | "missing-field" -> target.AsObject().Remove "roadmap" |> ignore
+ | "content-id" -> target.["content"].["id"] <- System.Text.Json.Nodes.JsonValue.Create "I_wrong"
+ | _ -> ()
+ { response with Body = root.ToJsonString() })
+ selected, ProgrammeFixture.successorTransport selected (Some "Delivery") change
+
+[]
+let ``successor planning drains membership pages and ignores other project planning values`` () =
+ let selected, reads = successorPlanningPages "pages"
+ match readPlanning reads selected {Issue = ProgrammeFixture.issue; ExpectedNodeId = "I_outcome"} with
+ | Error error -> failwith (Errors.explain error)
+ | Ok planning ->
+ Assert.Equal(2, planning.MembershipPages)
+ Assert.Equal("synthetic-member-I_outcome", planning.ItemId)
+ Assert.Equal(Some "Blocked", planning.Status)
+ Assert.Equal(Some "Unknown", planning.Observation)
+ Assert.Empty reads.Mutations
+
+[]
+[]
+[]
+[]
+[]
+[]
+[]
+[]
+[]
+let ``successor planning refuses incomplete or conflicting native facts`` mode =
+ let selected, reads = successorPlanningPages mode
+ Assert.True(Result.isError(readPlanning reads selected {Issue = ProgrammeFixture.issue; ExpectedNodeId = "I_outcome"}), mode)
+ Assert.Empty reads.Mutations
+
+[]
+let ``successor planning changes at the final barrier remain Unknown`` () =
+ let selected = ProgrammeFixture.successorBinding ()
+ let mutable planningReads = 0
+ let change (request: Transport.Request) result =
+ if request.Subject <> "bound V2 successor planning memberships" then result
+ else
+ planningReads <- planningReads + 1
+ if planningReads = 1 then result
+ else result |> Result.map (fun (response: Transport.Response) ->
+ let root = System.Text.Json.Nodes.JsonNode.Parse response.Body
+ let track = root.["data"].["repository"].["issue"].["projectItems"].["nodes"].[0].["track"]
+ track.["name"] <- System.Text.Json.Nodes.JsonValue.Create "Follow-up"
+ track.["optionId"] <- System.Text.Json.Nodes.JsonValue.Create "follow"
+ { response with Body = root.ToJsonString() })
+ let reads = ProgrammeFixture.successorTransport selected (Some "Delivery") change
+ let report = V2ProjectionSource.inspectFixed reads selected None
+ Assert.Equal(2, planningReads)
+ Assert.Equal("Unknown", report.Items.Head.SourceCurrentness)
+ Assert.Equal("Unknown", report.Items.Head.Evidence.Health)
+ Assert.Empty reads.Mutations
diff --git a/tests/engine-build-siting/run.py b/tests/engine-build-siting/run.py
index a14b0899b..d67ac474e 100644
--- a/tests/engine-build-siting/run.py
+++ b/tests/engine-build-siting/run.py
@@ -48,6 +48,7 @@
from __future__ import annotations
+import hashlib
import re
import subprocess
import sys
@@ -148,7 +149,8 @@
"builds only the standalone inactive-reader console with FSharp.Core; "
"no project references or coordination-engine tier-2a output path"
),
- # Creator017's normal graph references Coord.Cli: enforce its actual redirect.
+ # Creator018's normal graph requires an explicit redirect. Its published mode
+ # has a separate closed, tested no-producer-build/isolation contract below.
"tests/new-sdd-workspace/run.sh": None,
}
@@ -384,6 +386,73 @@ def is_redirected(cmd: str) -> bool:
return any(f in cmd for f in REDIRECT_FLAGS)
+# A generic BuildProjectReferences=false flag is not a redirect. Only Creator's
+# exact published mode is admitted: fresh separate creator/producer/caller roots,
+# original staged dependency verification, producer builds disabled and before/after
+# producer/caller census. The conventional producer bin layout must remain intact;
+# an ArtifactsPath/OutputPath global would change MSBuild GetTargetPath resolution.
+# Seal the complete setup/build/census prefix as well as the two explicit commands.
+# This is a closed source-shape check, not a filename exemption or shell evaluator;
+# any prefix change requires reviewing/resealing that contract and its mutants.
+CREATOR_PREFIX_END = "# Exercise the wizard's pure decision boundary directly."
+CREATOR_PREFIX_SHA256 = "789f38f25a055cfa4498bb2ba0b52cd68f3a701c7301f6980164a18dadb531a9"
+CREATOR_PUBLISHED_COMMAND = ('dotnet build "$PROJ" -c Release --no-restore --nologo -v quiet '
+ '-p:FsggCurrentCoordDependencies=true -p:BuildProjectReferences=false '
+ '-p:CompileUsingReferenceAssemblies=false '
+ '"-p:FsggFrozenCoordSource=$FSGG_CREATOR_PRODUCER_SOURCE" '
+ '"-p:FsggFrozenCoordDependencies=$FSGG_CREATOR_DEPENDENCIES" '
+ '-m:1 -nr:false -p:UseSharedCompilation=false 1')
+CREATOR_SOURCE_COMMAND = ('dotnet build "$PROJ" -c Release --artifacts-path "$BUILD_ROOT" '
+ '--nologo -v quiet -m:1 -nr:false -p:UseSharedCompilation=false 1')
+
+
+def normalized_command(command: str) -> str:
+ return " ".join(command.replace("\\\n", " ").split())
+
+
+def isolated_creator_build(text: str, command: str) -> bool:
+ if text.count(CREATOR_PREFIX_END) != 1:
+ return False
+ prefix = text.split(CREATOR_PREFIX_END, 1)[0]
+ if hashlib.sha256(prefix.encode()).hexdigest() != CREATOR_PREFIX_SHA256:
+ return False
+ builds = [normalized_command(cmd) for cmd in invocations(text) if is_candidate(cmd)]
+ return (builds == [CREATOR_PUBLISHED_COMMAND, CREATOR_SOURCE_COMMAND]
+ and normalized_command(command) == CREATOR_PUBLISHED_COMMAND)
+
+
+def creator_siting_controls(text: str) -> list[str]:
+ problems = []
+ builds = [cmd for cmd in invocations(text) if is_candidate(cmd)]
+ if len(builds) != 2 or not isolated_creator_build(text, builds[0]) or not is_redirected(builds[1]):
+ return ["Creator source/published build contract changed or lost its literal source redirect"]
+ mutations = (
+ ('--artifacts-path "$BUILD_ROOT"', ''),
+ ('-p:BuildProjectReferences=false', '-p:BuildProjectReferences=true'),
+ ('-p:CompileUsingReferenceAssemblies=false', '-p:CompileUsingReferenceAssemblies=true'),
+ ('a == b or a.is_relative_to(b)', 'False'),
+ ('roots != canonical', 'False'),
+ ('any(parent.is_symlink() for parent in (p, *p.parents))', 'False'),
+ ('p.resolve(strict=True)', 'p'),
+ ("if any(p.exists() for p in", "if False and any(p.exists() for p in"),
+ ('verify-layout', 'preflight'),
+ ('cmp "$BUILD_ROOT/producer-before.json" "$BUILD_ROOT/producer-after.json"', 'true'),
+ ('cmp "$BUILD_ROOT/active-before.json" "$BUILD_ROOT/active-after.json"', 'true'),
+ ('if [ "$MODE" = published-dependency ]; then', 'if true; then'),
+ ('--no-restore', ''),
+ )
+ for original, changed in mutations:
+ if original not in text:
+ problems.append("Creator siting mutation preimage missing: " + original)
+ elif isolated_creator_build(text.replace(original, changed), builds[0]):
+ problems.append("Creator siting mutant admitted: " + original)
+ if isolated_creator_build(builds[0], builds[0]):
+ problems.append("Creator unguarded published command admitted")
+ if isolated_creator_build(text + '\ndotnet build "$PROJ" -c Release\n', builds[0]):
+ problems.append("Creator additional unredirected build admitted")
+ return problems
+
+
# ---------------------------------------------------------------------------------------------------
# THE SELF-TEST CORPUS — mechanism 2. Spellings that MUST be seen and lookalikes that MUST NOT, every
# one drawn from a real line in this repo, from a shape that broke a draft of this matcher, or from the
@@ -500,6 +569,8 @@ def standalone_progress_project(xml: str) -> bool:
def main() -> int:
corpus = selftest()
+ creator_source = (REPO / "tests/new-sdd-workspace/run.sh").read_text()
+ corpus.extend(creator_siting_controls(creator_source))
if corpus:
print("::error::engine-build-siting: NO VERDICT — the matcher failed its own corpus, so an", file=sys.stderr)
print(" empty finding list would mean nothing. Repair the matcher before trusting a green.", file=sys.stderr)
@@ -591,7 +662,9 @@ def main() -> int:
reason = DECLARED_SITES[rel]
if reason is not None:
continue
- unredirected = [c for c in discovered[rel] if not is_redirected(c)]
+ unredirected = [c for c in discovered[rel] if not is_redirected(c)
+ and not (rel == "tests/new-sdd-workspace/run.sh"
+ and isolated_creator_build(creator_source, c))]
if unredirected:
findings.append(
f"{rel}: declared as building OUT OF TREE, but an invocation carries no redirect flag\n"
@@ -614,7 +687,10 @@ def main() -> int:
f"{len(MUST_MATCH)} must-match / {len(MUST_NOT_MATCH)} must-not-match all held."
)
for rel, reason in sorted(DECLARED_SITES.items()):
- print(f" {rel}: {'out of tree (redirect verified)' if reason is None else reason}")
+ if reason is None:
+ reason = ("source redirect and closed Creator-only published-mode isolation verified"
+ if rel == "tests/new-sdd-workspace/run.sh" else "out of tree (redirect verified)")
+ print(f" {rel}: {reason}")
return 0
diff --git a/tests/new-sdd-workspace-successor/current_dependencies.py b/tests/new-sdd-workspace-successor/current_dependencies.py
new file mode 100644
index 000000000..1c0611fc6
--- /dev/null
+++ b/tests/new-sdd-workspace-successor/current_dependencies.py
@@ -0,0 +1,210 @@
+"""Inert synthetic current-pin/package controls; never publish or execute DLLs."""
+import contextlib
+import io
+import hashlib
+import importlib.util
+import json
+import pathlib
+import runpy
+import sys
+import tempfile
+import unittest
+import zipfile
+from unittest.mock import patch
+
+ROOT = pathlib.Path(__file__).resolve().parents[2]
+sys.path.insert(0, str(ROOT / 'scripts'))
+CURRENT = runpy.run_path(str(ROOT / 'scripts/creator-current-coord-dependencies.py'))
+PREFIX = CURRENT['PREFIX']
+
+
+class CurrentDependencies(unittest.TestCase):
+ def setUp(self):
+ self.temporary = tempfile.TemporaryDirectory()
+ self.addCleanup(self.temporary.cleanup)
+ self.root = pathlib.Path(self.temporary.name)
+ self.package = self.root / 'FS.GG.NewSddWorkspace.0.18.0.nupkg'
+ self.members = {name: b'explicit synthetic unexecutable member ' + name.encode() for name in (
+ 'FS.GG.Coord.GitHub.dll', 'fsgg-coord-engine.dll', 'fsgg-coord-engine.deps.json',
+ 'fsgg-coord-engine.runtimeconfig.json', 'FS.GG.Coord.Core.dll', 'runtimes/linux-x64/native/test.so')}
+ sha = lambda body: hashlib.sha256(body).hexdigest()
+ self.pin = {'schema': 'fsgg.creator-current-coord-dependencies/1', 'version': '0.108.0',
+ 'sourceSha': 'b' * 40, 'archiveSha256': 'c' * 64, 'promotedManifestSha256': 'd' * 64,
+ 'releaseId': 1, 'assetId': 2, 'promotedManifestAssetId': 3,
+ 'downloadUrl': 'https://github.com/FS-GG/.github/releases/download/coherent-set/v0.108.0/FS.GG.Coord.Cli.0.108.0.nupkg',
+ 'projects': {'scripts/NewSddWorkspace/NewSddWorkspace.fsproj': 'new-sdd-workspace',
+ 'src/FS.GG.Coord.Cli/FS.GG.Coord.Cli.fsproj': 'fsgg-coord-engine'},
+ 'sourceLeaves': [{'path': 'global.json', 'sha256': 'e' * 64}],
+ 'members': {name: sha(body) for name, body in self.members.items()}}
+ self.deps = {'libraries': {'FS.GG.Coord.Cli/0.108.0': {'type': 'project'}}, 'targets': {
+ '.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.108.0'}},
+ 'FS.GG.Coord.Cli/0.108.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}}
+ self.write()
+
+ def write(self, members=None, deps=None, extra=None):
+ with zipfile.ZipFile(self.package, 'w') as archive:
+ for name, body in (self.members if members is None else members).items():
+ archive.writestr(PREFIX + name, body)
+ archive.writestr(PREFIX + 'new-sdd-workspace.deps.json', json.dumps(self.deps if deps is None else deps))
+ for name, body in (extra or {}).items():
+ archive.writestr(name, body)
+
+ def evidence(self):
+ return CURRENT['evidence'](self.package, 'a' * 40, self.pin, fixtures_passed=True)
+
+ def test_complete_exact_closure_and_mutations(self):
+ self.assertEqual(CURRENT['package_members'](self.package, self.pin), self.pin['members'])
+ for name in self.members:
+ mutated = dict(self.members)
+ mutated[name] = bytes([mutated[name][0] ^ 1]) + mutated[name][1:]
+ self.write(mutated)
+ with self.subTest(member=name), self.assertRaisesRegex(ValueError, 'changed published dependency'):
+ CURRENT['package_members'](self.package, self.pin)
+ self.write({k: v for k, v in self.members.items() if k != name})
+ with self.assertRaisesRegex(ValueError, 'changed published dependency'):
+ CURRENT['package_members'](self.package, self.pin)
+ self.write(extra={PREFIX + 'alternate/FS.GG.Coord.GitHub.dll': self.members['FS.GG.Coord.GitHub.dll']})
+ with self.assertRaisesRegex(ValueError, 'shadow'):
+ CURRENT['package_members'](self.package, self.pin)
+
+ def test_source_only_evidence_and_old_pins_refuse(self):
+ evidence = self.evidence()
+ manifest = {'sourceSha': 'a' * 40, 'version': '0.18.0', 'archiveSha256': evidence['archiveSha256']}
+ CURRENT['verify_evidence'](evidence, self.package, manifest, self.pin)
+ for field, value in [('mode', 'source-only'), ('sourceSha', 'c' * 40), ('fixturesPassed', False),
+ ('dependencyMembers', {}), ('dependencyPinSha256', '0' * 64), ('unknown', True)]:
+ with self.subTest(field=field), self.assertRaisesRegex(ValueError, 'evidence body'):
+ CURRENT['verify_evidence']({**evidence, field: value}, self.package, manifest, self.pin)
+ for version in ('0.99.0', '0.107.0'):
+ with self.assertRaisesRegex(ValueError, '0.108.0 pin'):
+ CURRENT['validate_pin']({**self.pin, 'version': version})
+ self.write(deps={'libraries': {}, 'targets': {}})
+ with self.assertRaisesRegex(ValueError, 'metadata'):
+ CURRENT['package_members'](self.package, self.pin)
+
+ def test_fixed_pin_absence_and_duplicate_json_refuse(self):
+ # Only this disposable root is missing the pin. A later genuine source
+ # pin in the production repository must not invalidate this control.
+ fixed = self.root / CURRENT['PIN_PATH']
+ self.assertFalse(fixed.exists())
+ with self.assertRaisesRegex(ValueError, 'pin absent'):
+ CURRENT['load_pin'](self.root)
+ (self.root / 'arbitrary-pin.json').write_text(json.dumps(self.pin))
+ with self.assertRaisesRegex(ValueError, 'pin absent'):
+ CURRENT['load_pin'](self.root)
+ fixed.parent.mkdir()
+ fixed.write_text(json.dumps(self.pin))
+ self.assertEqual(CURRENT['load_pin'](self.root), self.pin)
+ with self.assertRaisesRegex(ValueError, 'duplicate JSON'):
+ CURRENT['read_json'](b'{"mode":"published-dependency","mode":"source-only"}')
+
+ def test_actual_artifact_reader_checks_body_before_extraction_and_checker(self):
+ spec = importlib.util.spec_from_file_location('current_artifact_control', ROOT / 'scripts/new-sdd-workspace-successor-artifact.py')
+ verifier = importlib.util.module_from_spec(spec)
+ spec.loader.exec_module(verifier)
+ evidence = self.evidence()
+ manifest = {'sourceSha': 'a' * 40, 'version': '0.18.0', 'archiveSha256': evidence['archiveSha256']}
+ run = {'id': 1, 'path': verifier.WORKFLOW, 'head_sha': 'a' * 40, 'head_branch': 'main',
+ 'event': 'workflow_dispatch', 'conclusion': 'success', 'run_attempt': 1,
+ 'repository': {'id': verifier.REPOSITORY_ID}}
+ artifact = {'id': 2, 'name': 'new-sdd-workspace-successor-candidate-' + 'a' * 40 + '-1',
+ 'expired': False, 'workflow_run': {'id': 1, 'head_sha': 'a' * 40, 'head_branch': 'main',
+ 'repository_id': verifier.REPOSITORY_ID, 'head_repository_id': verifier.REPOSITORY_ID}}
+ injected = {**CURRENT, 'protected_pin': lambda source: self.pin}
+ for index, body in enumerate((evidence, {}, {**evidence, 'mode': 'source-only'})):
+ archive = self.root / f'candidate{index}.zip'
+ with zipfile.ZipFile(archive, 'w') as zipped:
+ zipped.writestr('manifest.json', json.dumps(manifest))
+ zipped.writestr('package-evidence.json', json.dumps(body))
+ zipped.writestr(self.package.name, self.package.read_bytes())
+ artifact['digest'] = 'sha256:' + hashlib.sha256(archive.read_bytes()).hexdigest()
+ output = self.root / f'output{index}'
+ with patch.object(verifier.runpy, 'run_path', return_value=injected), patch.object(verifier.subprocess, 'run') as checker:
+ if index == 0:
+ verifier.verify(artifact, run, archive, output, 'a' * 40)
+ checker.assert_called_once()
+ else:
+ with self.assertRaisesRegex(ValueError, 'evidence body'):
+ verifier.verify(artifact, run, archive, output, 'a' * 40)
+ checker.assert_not_called()
+ self.assertFalse(output.exists())
+
+ def test_candidate_has_only_staged_release_mode_and_preflights_before_sdk(self):
+ source = (ROOT / '.github/workflows/release-new-sdd-workspace-successor-candidate.yml').read_text()
+ def validate(workflow):
+ required = ('FSGG_CREATOR_DEPENDENCY_MODE: published-dependency',
+ 'bash "$work/creator/tests/new-sdd-workspace/run.sh"',
+ '-p:FsggCurrentCoordDependencies=true -p:BuildProjectReferences=false',
+ '-p:CompileUsingReferenceAssemblies=false',
+ '-p:FsggFrozenCoordSource="$work/producer" -p:FsggFrozenCoordDependencies="$work/dependencies"',
+ '--published-coord-dependencies "$work/dependencies" --published-coord-source "$work/producer"',
+ '--creator-source "$work/creator"', '-c Release --no-build')
+ for token in required:
+ if workflow.count(token) != 1:
+ raise ValueError('published candidate path differs: ' + token)
+ if ('--artifacts-path' in workflow or '--build-artifacts' in workflow
+ or workflow.count('creator-current-coord-dependencies.py preflight') != 1
+ or workflow.index('creator-current-coord-dependencies.py preflight') > workflow.index('actions/setup-dotnet')):
+ raise ValueError('published candidate preflight/output route differs')
+ validate(source)
+ for original, changed in (('published-dependency', 'source-only'),
+ ('-p:BuildProjectReferences=false', '-p:BuildProjectReferences=true'),
+ ('--no-build', '--artifacts-path stale'),
+ ('creator-current-coord-dependencies.py preflight', ':'),
+ ('--creator-source "$work/creator"', '')):
+ with self.subTest(original=original), self.assertRaises(ValueError):
+ validate(source.replace(original, changed))
+ selftest = (ROOT / '.github/workflows/new-sdd-workspace-selftest.yml').read_text()
+ self.assertEqual(selftest.count('"scripts/creator-current-coord-dependencies.*"'), 2)
+
+ def test_real_publisher_entry_refuses_missing_pin_before_any_provider_or_journal(self):
+ spec = importlib.util.spec_from_file_location('current_publisher_fence', ROOT / 'scripts/new-sdd-workspace-successor-publish.py')
+ publisher = importlib.util.module_from_spec(spec)
+ spec.loader.exec_module(publisher)
+ argv = ['publisher', '--preflight-only', '--candidate-run-id', '1', '--candidate-artifact-id', '2',
+ '--candidate-archive-sha256', 'd' * 64, '--workdir', str(self.root / 'uncreated')]
+ injected = {**CURRENT, 'load_pin': lambda: CURRENT['load_pin'](self.root)}
+ with patch.object(sys, 'argv', argv), patch.object(runpy, 'run_path', return_value=injected), \
+ patch.object(publisher, 'GitHubAPI') as api, \
+ patch.object(publisher, 'WizardProvider') as provider, \
+ patch.object(publisher, 'ProtectedReleaseJournal') as journal, \
+ patch.object(publisher.subprocess, 'run', side_effect=AssertionError('missing pin may not launch children')), \
+ contextlib.redirect_stderr(io.StringIO()):
+ self.assertEqual(publisher.main(), 1)
+ api.assert_not_called()
+ provider.assert_not_called()
+ journal.assert_not_called()
+ self.assertFalse((self.root / 'uncreated').exists())
+ summary = json.loads((self.root / 'creator018-publication-summary.json').read_text())
+ self.assertFalse(summary['preflightPassed'])
+ self.assertFalse(summary['journalMutationMayHaveOccurred'])
+ self.assertEqual(summary['firstCause']['kind'], 'ValueError')
+
+ def test_candidate_and_publisher_source_pin_are_independently_joined(self):
+ function = CURRENT['protected_pin']
+ with patch.dict(function.__globals__, {'load_pin': lambda: self.pin}), \
+ patch.object(function.__globals__['subprocess'], 'check_output', return_value=json.dumps(self.pin).encode()) as reads:
+ self.assertEqual(function('a' * 40), self.pin)
+ self.assertEqual(reads.call_count, 2)
+ wrong = {**self.pin, 'sourceSha': 'f' * 40}
+ with patch.dict(function.__globals__, {'load_pin': lambda: self.pin}), \
+ patch.object(function.__globals__['subprocess'], 'check_output', side_effect=[json.dumps(self.pin).encode(), json.dumps(wrong).encode()]):
+ with self.assertRaisesRegex(ValueError, 'protected publisher source'):
+ function('a' * 40)
+
+ def test_same_size_exact_byte_mutant_breaks_negative_control(self):
+ changed = dict(self.members)
+ name = 'FS.GG.Coord.GitHub.dll'
+ changed[name] = b'X' + changed[name][1:]
+ self.write(changed)
+ with self.assertRaises(ValueError):
+ CURRENT['package_members'](self.package, self.pin)
+ real = CURRENT['package_members'].__globals__['digest']
+ expected = self.pin['members'][name]
+ def relaxed(body):
+ return expected if body == changed[name] else real(body)
+ with patch.dict(CURRENT['package_members'].__globals__, {'digest': relaxed}):
+ # The weakened predicate lets the bad package escape; the same negative assertion fails.
+ with self.assertRaises(AssertionError):
+ with self.assertRaises(ValueError):
+ CURRENT['package_members'](self.package, self.pin)
diff --git a/tests/new-sdd-workspace-successor/frozen_dependencies.py b/tests/new-sdd-workspace-successor/frozen_dependencies.py
index 1659d3149..496f75aaf 100644
--- a/tests/new-sdd-workspace-successor/frozen_dependencies.py
+++ b/tests/new-sdd-workspace-successor/frozen_dependencies.py
@@ -150,13 +150,13 @@ def test_actual_pin_matches_selected_source_and_candidate_download(self):
with self.assertRaisesRegex(ValueError, "published dependency source changed"):
HELPER["source_projects"](ROOT, pin, historical)
workflow = (ROOT / ".github/workflows/release-new-sdd-workspace-successor-candidate.yml").read_text()
- # The exact historical pin/helper remain qualified above; the current 0.17
- # candidate deliberately builds its normal 0.107 graph, never rebinds that pin.
- self.assertIn('test "$version" = 0.17.0', workflow)
- self.assertIn("bash tests/new-sdd-workspace/run.sh", workflow)
+ # The exact historical pin/helper remain qualified above; the current 0.18
+ # candidate selects the separate current adapter, never rebinds this pin.
+ self.assertIn('test "$version" = 0.18.0', workflow)
+ self.assertIn('bash "$work/creator/tests/new-sdd-workspace/run.sh"', workflow)
self.assertNotIn(pin["downloadUrl"], workflow)
- self.assertNotIn("FsggFrozenCoordSource", workflow)
- self.assertNotIn("FsggFrozenCoordDependencies", workflow)
+ self.assertIn("FsggCurrentCoordDependencies=true", workflow)
+ self.assertIn("creator-current-coord-dependencies.py preflight", workflow)
self.assertNotIn("creator-frozen-coord-dependencies.py", workflow)
def test_missing_wrong_and_linked_source_roots_refuse(self):
diff --git a/tests/new-sdd-workspace-successor/run.py b/tests/new-sdd-workspace-successor/run.py
index 7524d2298..7ff8e80cf 100644
--- a/tests/new-sdd-workspace-successor/run.py
+++ b/tests/new-sdd-workspace-successor/run.py
@@ -26,7 +26,7 @@
from release_successor_execution import Dispatch, JournalState, Observation, Refused, advance_effects
from release_successor_journal import Refused as JournalRefused
from new_sdd_workspace_successor_admission import WizardAdmission
-from new_sdd_workspace_successor_execution import effects, CURRENT_017, CURRENT_016, CURRENT_015, CURRENT_014, HISTORICAL_013, ReleaseBinding
+from new_sdd_workspace_successor_execution import effects, CURRENT_017, CURRENT_018, CURRENT_016, CURRENT_015, CURRENT_014, HISTORICAL_013, ReleaseBinding
from new_sdd_workspace_successor_provider import WizardProvider, NotFound, output_signals, publisher_error, DIAGNOSTIC_LIMIT
@@ -34,10 +34,7 @@
"new-sdd-workspace-selftest.yml": (
"Run the new-sdd-workspace parse fixture",
"Qualify the compiled product binding and complete driver materialization",
- "Qualify Creator 0.17 normal-source package closure", "source"),
- "release-new-sdd-workspace-successor-candidate.yml": (
- "Qualify wizard source", "Qualify the real compiled product board boundary",
- "Pack and bind one package archive", "candidate"),
+ "Qualify Creator 0.18 normal-source package closure", "source"),
}
@@ -54,7 +51,7 @@ def step(name):
return "\n".join(line[10:] for line in body.splitlines() if line.startswith(" "))
producer, materializer, package = map(step, names[:3])
- assignment = ('export FSGG_CREATOR_SOURCE_ARTIFACTS="$RUNNER_TEMP/creator017-'
+ assignment = ('export FSGG_CREATOR_SOURCE_ARTIFACTS="$RUNNER_TEMP/creator018-'
+ names[3] + '-build-$GITHUB_RUN_ID-$GITHUB_RUN_ATTEMPT"')
retention = 'echo "FSGG_CREATOR_SOURCE_ARTIFACTS=$FSGG_CREATOR_SOURCE_ARTIFACTS" >> "$GITHUB_ENV"'
launch = 'bash tests/new-sdd-workspace/run.sh'
@@ -94,7 +91,7 @@ def commands(body):
def manifest():
return {
"schema": "fsgg.new-sdd-workspace-release/1", "packageId": "FS.GG.NewSddWorkspace",
- "version": "0.17.0", "tag": "new-sdd-workspace/v0.17.0", "sourceSha": "a" * 40,
+ "version": "0.18.0", "tag": "new-sdd-workspace/v0.18.0", "sourceSha": "a" * 40,
"archiveSha256": "b" * 64, "producerPayloadSha256": "sha256:" + "c" * 64,
}
@@ -103,19 +100,19 @@ def board_package_closure(package: pathlib.Path, source_sha: str, *, source_root
frozen_dependencies: pathlib.Path | None = None,
frozen_source: pathlib.Path | None = None,
build_artifacts: pathlib.Path | None = None,
- release_binding=CURRENT_017):
+ release_binding=CURRENT_018):
"""Join the actual current package to its freshly built creator/dependency output."""
spec = importlib.util.spec_from_file_location("wizard_package_identity", source_root / "scripts/new-sdd-workspace-release.py")
checker = importlib.util.module_from_spec(spec)
spec.loader.exec_module(checker)
- if release_binding is not CURRENT_017 and release_binding is not CURRENT_016:
+ if release_binding is not CURRENT_018 and release_binding is not CURRENT_016:
raise ValueError("unknown Creator package binding")
if checker.package_identity(package) != (release_binding.package, release_binding.version, source_sha):
raise ValueError("current creator package/source identity differs")
dependency_pin = json.loads((source_root / "scripts/creator-frozen-coord-dependencies.json").read_text())
- coherent_version = "0.107.0" if release_binding is CURRENT_017 else dependency_pin["version"]
- if release_binding is CURRENT_017 and (frozen_dependencies is not None or frozen_source is not None):
- raise ValueError("Creator 0.17 requires its normal 0.107 source graph, not retained frozen inputs")
+ coherent_version = "0.108.0" if release_binding is CURRENT_018 else dependency_pin["version"]
+ if release_binding is CURRENT_018 and (frozen_dependencies is not None or frozen_source is not None):
+ raise ValueError("Creator 0.18 requires its normal 0.108 source graph, not retained frozen inputs")
if (frozen_dependencies is None) != (frozen_source is None):
raise ValueError("frozen package qualification requires paired source and binary roots")
project = source_root / "scripts/NewSddWorkspace/NewSddWorkspace.fsproj"
@@ -152,7 +149,7 @@ def visit(path):
visit(path.parent / declared)
visit(project)
if build_artifacts is not None:
- if release_binding is not CURRENT_017 or not build_artifacts.is_absolute():
+ if release_binding is not CURRENT_018 or not build_artifacts.is_absolute():
raise ValueError("isolated build artifacts require the current Creator and an absolute root")
if (build_artifacts.is_symlink() or not build_artifacts.is_dir()
or build_artifacts.resolve().is_relative_to(source_root.resolve())):
@@ -192,7 +189,7 @@ def visit(path):
result = {"schema": "fsgg.creator-board-package-closure/1", "version": release_binding.version,
"sourceSha": source_sha, "currentCreatorSourceSha": source_sha, "coherentVersion": coherent_version, "projectCount": len(projects),
"builtFilesCompared": len(required), "archiveSha256": hashlib.sha256(package.read_bytes()).hexdigest(),
- "installedAdoptionAccepted": False}
+ "mode": "source-only", "releaseEligible": False, "installedAdoptionAccepted": False}
if frozen_dependencies is not None:
result["publishedDependencyClosure"] = helper["package_closure"](
package, frozen_dependencies, source_root, frozen_source)
@@ -272,14 +269,14 @@ def test_release_bindings_are_explicit_immutable_and_route_specific(self):
self.assertEqual([effect.identity for effect in ordered], [effect.identity for effect in self.ordered])
with self.assertRaises(Refused):
effects(manifest(), binding=HISTORICAL_013)
- for forged in (ReleaseBinding(CURRENT_017.package, CURRENT_017.version, CURRENT_017.tag),
+ for forged in (ReleaseBinding(CURRENT_018.package, CURRENT_018.version, CURRENT_018.tag),
ReleaseBinding(HISTORICAL_013.package, HISTORICAL_013.version, HISTORICAL_013.tag), None):
with self.assertRaises(Refused):
effects(manifest(), binding=forged)
with self.assertRaises(AttributeError):
- CURRENT_017.version = "0.13.0"
+ CURRENT_018.version = "0.13.0"
- def test_retained016_effect_descriptors_cannot_become_current017_authority(self):
+ def test_retained016_effect_descriptors_cannot_become_current018_authority(self):
class NoReads:
def get(self, path): raise AssertionError("retained route cannot read native authority")
prior={**manifest(), "version":"0.16.0", "tag":"new-sdd-workspace/v0.16.0"}
@@ -289,6 +286,12 @@ def get(self, path): raise AssertionError("retained route cannot read native aut
retained=WizardAdmission(NoReads(),prior,"a"*40,1,"EHotwagner","refs/heads/main",release_binding=CURRENT_016)
self.assertFalse(retained.authorize(content,"journal","intent",content))
self.assertEqual((CURRENT_016.version,CURRENT_016.tag),("0.16.0","new-sdd-workspace/v0.16.0"))
+ prior017 = {**manifest(), "version": "0.17.0", "tag": "new-sdd-workspace/v0.17.0"}
+ with self.assertRaises(Refused): effects(prior017)
+ content017, ordered017 = effects(prior017, binding=CURRENT_017)
+ self.assertEqual(len(ordered017), 8)
+ retained017 = WizardAdmission(NoReads(), prior017, "a"*40, 1, "EHotwagner", "refs/heads/main", release_binding=CURRENT_017)
+ self.assertFalse(retained017.authorize(content017, "journal", "intent", content017))
self.assertEqual((HISTORICAL_013.version,HISTORICAL_013.tag),("0.13.0","new-sdd-workspace/v0.13.0"))
def test_admission_cannot_cross_current_and_historical_routes(self):
@@ -405,9 +408,9 @@ def copy_project(path):
xml = ElementTree.parse(root / relative)
name = next((e.text for e in xml.iter('AssemblyName') if e.text), relative.stem) + '.dll'
members[name] = ('synthetic, never executed: ' + name).encode()
- deps = {'libraries': {'FS.GG.Coord.Cli/0.107.0': {'type': 'project'}}, 'targets': {
- '.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.17.0': {'dependencies': {'FS.GG.Coord.Cli': '0.107.0'}},
- 'FS.GG.Coord.Cli/0.107.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}}
+ deps = {'libraries': {'FS.GG.Coord.Cli/0.108.0': {'type': 'project'}}, 'targets': {
+ '.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.108.0'}},
+ 'FS.GG.Coord.Cli/0.108.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}}
members['new-sdd-workspace.deps.json'] = json.dumps(deps).encode()
members['new-sdd-workspace.runtimeconfig.json'] = b'{}'
for name, body in members.items():
@@ -416,7 +419,7 @@ def copy_project(path):
(output / 'publish').mkdir()
for name, body in members.items():
(output / 'publish' / name).write_bytes(body)
- nuspec = b'FS.GG.NewSddWorkspace0.17.0'
+ nuspec = b'FS.GG.NewSddWorkspace0.18.0'
package = root / 'creator.nupkg'
def pack(selected):
with zipfile.ZipFile(package, 'w') as archive:
@@ -447,7 +450,7 @@ def pack(selected):
board_package_closure(package, 'a' * 40, source_root=root, build_artifacts=artifacts)
with self.assertRaisesRegex(ValueError, 'outside the source checkout'):
board_package_closure(package, 'a' * 40, source_root=root, build_artifacts=root)
- with self.assertRaisesRegex(ValueError, '0.17 requires its normal 0.107 source graph'):
+ with self.assertRaisesRegex(ValueError, '0.18 requires its normal 0.108 source graph'):
board_package_closure(package, 'a' * 40, source_root=root,
frozen_dependencies=root, frozen_source=root)
for omitted in ('FS.GG.Coord.GitHub.dll', 'fsgg-coord-engine.dll', 'new-sdd-workspace.deps.json'):
@@ -458,13 +461,13 @@ def pack(selected):
pack({**members, 'FS.GG.Coord.GitHub.dll': b'old assembly'})
with self.assertRaisesRegex(ValueError, 'differs from built source'):
board_package_closure(package, 'a' * 40, source_root=root)
- for mutant in ({'libraries': {'FS.GG.Coord.Cli/0.99.0': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.17.0': {'dependencies': {'FS.GG.Coord.Cli': '0.99.0'}}, 'FS.GG.Coord.Cli/0.99.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
- {'libraries': {'FS.GG.Coord.Cli/0.97.1': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.17.0': {'dependencies': {'FS.GG.Coord.Cli': '0.97.1'}}, 'FS.GG.Coord.Cli/0.97.1': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
- {'libraries': {'FS.GG.Coord.Cli/0.97.0': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.17.0': {'dependencies': {'FS.GG.Coord.Cli': '0.97.0'}}, 'FS.GG.Coord.Cli/0.97.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
+ for mutant in ({'libraries': {'FS.GG.Coord.Cli/0.99.0': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.99.0'}}, 'FS.GG.Coord.Cli/0.99.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
+ {'libraries': {'FS.GG.Coord.Cli/0.97.1': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.97.1'}}, 'FS.GG.Coord.Cli/0.97.1': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
+ {'libraries': {'FS.GG.Coord.Cli/0.97.0': {'type': 'project'}}, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.97.0'}}, 'FS.GG.Coord.Cli/0.97.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
{'libraries': {'FS.GG.Coord.Cli/0.96.0': {}}},
{**deps, 'targets': {}},
- {**deps, 'targets': {'.NETCoreApp,Version=v10.0': {'FS.GG.Coord.Cli/0.107.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
- {**deps, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.17.0': {'dependencies': {'FS.GG.Coord.Cli': '0.107.0'}}}}}):
+ {**deps, 'targets': {'.NETCoreApp,Version=v10.0': {'FS.GG.Coord.Cli/0.108.0': {'runtime': {'fsgg-coord-engine.dll': {}}}}}},
+ {**deps, 'targets': {'.NETCoreApp,Version=v10.0': {'new-sdd-workspace/0.18.0': {'dependencies': {'FS.GG.Coord.Cli': '0.108.0'}}}}}):
old_deps = json.dumps(mutant).encode()
(output / 'new-sdd-workspace.deps.json').write_bytes(old_deps)
pack({**members, 'new-sdd-workspace.deps.json': old_deps})
@@ -526,7 +529,7 @@ def test_candidate_archive_identity_and_first_attempt_are_required(self):
root = pathlib.Path(temporary)
archive = root / "candidate.zip"
with zipfile.ZipFile(archive, "w") as zipped:
- zipped.writestr("manifest.json", json.dumps(manifest()))
+ zipped.writestr("manifest.json", json.dumps({**manifest(), "version": "0.17.0", "tag": "new-sdd-workspace/v0.17.0"}))
zipped.writestr("package-evidence.json", "{}")
zipped.writestr("FS.GG.NewSddWorkspace.0.17.0.nupkg", "fixture")
digest = hashlib.sha256(archive.read_bytes()).hexdigest()
@@ -539,7 +542,7 @@ def test_candidate_archive_identity_and_first_attempt_are_required(self):
"repository_id": verifier.REPOSITORY_ID,
"head_repository_id": verifier.REPOSITORY_ID}}
with patch.object(verifier.subprocess, "run"):
- self.assertEqual(verifier.verify(artifact, run, archive, root / "good", source)["version"], "0.17.0")
+ self.assertEqual(verifier.verify(artifact, run, archive, root / "good", source, release_binding=CURRENT_017)["version"], "0.17.0")
old_archive = root / "historical.zip"
with zipfile.ZipFile(old_archive, "w") as zipped:
zipped.writestr("manifest.json", json.dumps({**manifest(), "version": "0.13.0",
@@ -549,14 +552,14 @@ def test_candidate_archive_identity_and_first_attempt_are_required(self):
old_artifact = {**artifact, "digest": "sha256:" + hashlib.sha256(old_archive.read_bytes()).hexdigest()}
with patch.object(verifier.subprocess, "run") as package_check:
with self.assertRaises(ValueError):
- verifier.verify(old_artifact, run, old_archive, root / "old", source)
+ verifier.verify(old_artifact, run, old_archive, root / "old", source, release_binding=CURRENT_017)
package_check.assert_not_called()
altered = {**run, "run_attempt": 2}
with self.assertRaisesRegex(ValueError, "first-attempt"):
- verifier.verify(artifact, altered, archive, root / "rerun", source)
+ verifier.verify(artifact, altered, archive, root / "rerun", source, release_binding=CURRENT_017)
altered_artifact = {**artifact, "digest": "sha256:" + "0" * 64}
with self.assertRaisesRegex(ValueError, "digest differs"):
- verifier.verify(altered_artifact, run, archive, root / "tampered", source)
+ verifier.verify(altered_artifact, run, archive, root / "tampered", source, release_binding=CURRENT_017)
def test_prior_release_identity_and_wrong_payload_are_refused(self):
for key, value in (("version", "0.13.0"), ("tag", "new-sdd-workspace/v0.13.0"),
@@ -569,14 +572,14 @@ def test_prior_release_identity_and_wrong_payload_are_refused(self):
def test_predecessor_manifest_cannot_reuse_successor_effects(self):
prior = {**manifest(), "version": "0.12.0", "tag": "new-sdd-workspace/v0.12.0"}
- with self.assertRaisesRegex(Refused, "exact Wizard 0.17.0"):
+ with self.assertRaisesRegex(Refused, "exact Wizard 0.18.0"):
effects(prior)
def test_fresh_journal_and_version_cut_retain_the_existing_boundary(self):
publisher = (ROOT / "scripts/new-sdd-workspace-successor-publish.py").read_text()
- self.assertIn('REF = "refs/heads/fsgg/v2/journal/release/board-v2-product-creator-017"', publisher)
+ self.assertIn('REF = "refs/heads/fsgg/v2/journal/release/board-v2-product-creator-018"', publisher)
self.assertNotIn('REF = "refs/heads/fsgg/v2/journal/release/svg-d5-wizard-012"', publisher)
- self.assertIn('"version": "0.17.0"', publisher)
+ self.assertIn('"version": "0.18.0"', publisher)
self.assertEqual([e.identity for e in self.ordered],
['tag', 'draft', 'github', 'nuget', 'package-asset', 'manifest-asset',
'publication-journal-asset', 'promote'])
@@ -588,16 +591,16 @@ def test_fresh_journal_and_version_cut_retain_the_existing_boundary(self):
def test_source_cut_and_candidate_package_names_agree(self):
project = (ROOT / 'scripts/NewSddWorkspace/NewSddWorkspace.fsproj').read_text()
candidate = (ROOT / '.github/workflows/release-new-sdd-workspace-successor-candidate.yml').read_text()
- self.assertIn('0.17.0', project)
- self.assertIn('test "$version" = 0.17.0', candidate)
- self.assertIn('FS.GG.NewSddWorkspace.0.17.0.nupkg', candidate)
- self.assertIn('--tag new-sdd-workspace/v0.17.0', candidate)
+ self.assertIn('0.18.0', project)
+ self.assertIn('test "$version" = 0.18.0', candidate)
+ self.assertIn('FS.GG.NewSddWorkspace.0.18.0.nupkg', candidate)
+ self.assertIn('--tag new-sdd-workspace/v0.18.0', candidate)
props = ElementTree.parse(ROOT / 'Directory.Build.props')
- self.assertEqual(next(node.text for node in props.iter('FsggCoherentSetVersion')), '0.107.0')
- self.assertLess(candidate.index('Refuse mismatched Creator profiles before costly graph qualification'),
- candidate.index('Qualify wizard source'))
- self.assertNotIn('FsggFrozenCoordDependencies', candidate)
- self.assertNotIn('FsggFrozenCoordSource', candidate)
+ self.assertEqual(next(node.text for node in props.iter('FsggCoherentSetVersion')), '0.108.0')
+ self.assertLess(candidate.index("creator-current-coord-dependencies.py preflight"),
+ candidate.index("actions/setup-dotnet"))
+ self.assertIn('creator-current-coord-dependencies.py preflight', candidate)
+ self.assertIn('FSGG_CREATOR_DEPENDENCY_MODE: published-dependency', candidate)
def test_current_source_flows_keep_one_isolated_producer(self):
workflows = ROOT / '.github/workflows'
@@ -605,6 +608,7 @@ def test_current_source_flows_keep_one_isolated_producer(self):
if ('bash tests/new-sdd-workspace/run.sh' in path.read_text()
or '--exec tests/new-sdd-workspace/product-board.fsx' in path.read_text()
or 'dotnet pack scripts/NewSddWorkspace/NewSddWorkspace.fsproj' in path.read_text())}
+ actual.discard("release-new-sdd-workspace-successor-candidate.yml")
self.assertEqual(actual, set(SOURCE_FLOWS), 'unreviewed Creator source build consumer')
for name, steps in SOURCE_FLOWS.items():
original = (workflows / name).read_text()
@@ -631,8 +635,8 @@ def test_workflow_retains_exact_historical_title_and_isolates_current_mode(self)
workflow = (ROOT / '.github/workflows/release-new-sdd-workspace.yml').read_text()
self.assertIn("inputs.promotion_recovery != 'off' && format('Wizard 0.13 recovery {0} {1} {2}', "
"inputs.promotion_recovery, inputs.recovery_correlation, inputs.recovery_binding_sha256)", workflow)
- self.assertIn("format('Wizard 0.17 successor {0}', inputs.candidate_run_id)", workflow)
- self.assertIn("name: new-sdd-workspace-017-publisher", workflow)
+ self.assertIn("format('Wizard 0.18 successor {0}', inputs.candidate_run_id)", workflow)
+ self.assertIn("name: new-sdd-workspace-018-publisher", workflow)
self.assertIn("(inputs.promotion_recovery == 'diagnostic' || inputs.promotion_recovery == 'post-completion-readback') && !inputs.publish && !inputs.verify_nuget_login", workflow)
self.assertIn("inputs.promotion_recovery == 'complete' && !inputs.publish && !inputs.verify_nuget_login", workflow)
for mode in ('diagnostic', 'complete'):
@@ -648,19 +652,19 @@ def test_package_nuspec_must_bind_protected_source_commit(self):
checker = importlib.util.module_from_spec(spec)
spec.loader.exec_module(checker)
with tempfile.TemporaryDirectory() as temporary:
- package = pathlib.Path(temporary) / "FS.GG.NewSddWorkspace.0.17.0.nupkg"
+ package = pathlib.Path(temporary) / "FS.GG.NewSddWorkspace.0.18.0.nupkg"
def write_package(commit):
nuspec = ("FS.GG.NewSddWorkspace"
- "0.17.0")
+ "0.18.0")
with zipfile.ZipFile(package, "w") as archive:
archive.writestr("FS.GG.NewSddWorkspace.nuspec", nuspec)
write_package("a" * 40)
self.assertEqual(checker.package_identity(package),
- ("FS.GG.NewSddWorkspace", "0.17.0", "a" * 40))
+ ("FS.GG.NewSddWorkspace", "0.18.0", "a" * 40))
write_package("b" * 40)
with self.assertRaisesRegex(ValueError, "repository commit differs"):
checker.build_manifest(type("Args", (), {"package": str(package), "source_sha": "a" * 40,
- "version": "0.17.0", "tag": "new-sdd-workspace/v0.17.0"})())
+ "version": "0.18.0", "tag": "new-sdd-workspace/v0.18.0"})())
write_package("")
with self.assertRaisesRegex(ValueError, "repository commit"):
checker.package_identity(package)
@@ -719,9 +723,9 @@ def __init__(self):
self.assets = {}
self.writes = []
def get(self, path):
- if path.endswith("/git/ref/tags/new-sdd-workspace/v0.17.0") and self.tag:
+ if path.endswith("/git/ref/tags/new-sdd-workspace/v0.18.0") and self.tag:
return {"object": {"sha": self.tag}}
- if path.endswith("/releases/tags/new-sdd-workspace/v0.17.0") and self.release and not self.release["draft"]:
+ if path.endswith("/releases/tags/new-sdd-workspace/v0.18.0") and self.release and not self.release["draft"]:
return self.release
if path.endswith("/releases?per_page=100&page=1"):
return [self.release] if self.release else []
@@ -745,7 +749,7 @@ def download_asset(self, asset_id):
with tempfile.TemporaryDirectory() as temporary:
root = pathlib.Path(temporary)
row = manifest()
- package = root / "FS.GG.NewSddWorkspace.0.17.0.nupkg"
+ package = root / "FS.GG.NewSddWorkspace.0.18.0.nupkg"
package.write_bytes(b"exact original Wizard archive")
row["archiveSha256"] = hashlib.sha256(package.read_bytes()).hexdigest()
manifest_path = root / "manifest.json"
@@ -773,10 +777,10 @@ class API:
def __init__(self, raw):
self.raw = raw
def get(self, path):
- if path.endswith("/releases/tags/new-sdd-workspace/v0.17.0"):
+ if path.endswith("/releases/tags/new-sdd-workspace/v0.18.0"):
raise NotFound(path)
if path.endswith("/releases?per_page=100&page=1"):
- return [{"id": 1, "tag_name": "new-sdd-workspace/v0.17.0", "draft": True}]
+ return [{"id": 1, "tag_name": "new-sdd-workspace/v0.18.0", "draft": True}]
if path.endswith("/releases/1/assets?per_page=100"):
return [{"id": 1, "name": "publication-journal.json"}]
raise AssertionError(path)
@@ -944,7 +948,7 @@ def test_existing_open_promote_readback_logs_draft_without_install_or_write(self
def creator_caller():
- spec = importlib.util.spec_from_file_location("tested_creator017_publisher", ROOT / "scripts/new-sdd-workspace-successor-publish.py")
+ spec = importlib.util.spec_from_file_location("tested_creator018_publisher", ROOT / "scripts/new-sdd-workspace-successor-publish.py")
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module)
return module
@@ -976,7 +980,7 @@ def setUpClass(cls):
def setUp(self):
self.content, self.ordered = effects(manifest())
- self.intent = {"contentId": self.content, "sourceSha": "a" * 40, "version": "0.17.0",
+ self.intent = {"contentId": self.content, "sourceSha": "a" * 40, "version": "0.18.0",
"candidateArchiveSha256": "d" * 64, "operator": "EHotwagner"}
self.report = self.caller.publication_report(1, 2, "d" * 64, "publish")
@@ -1095,7 +1099,7 @@ def categories(calls):
return result
total = sum(counted.attempted.values())
self.assertLess(total, 4200)
- print("Creator017 actual all-eight Authority profile: " + json.dumps(
+ print("Creator018 actual all-eight Authority profile: " + json.dumps(
{"coldPreparationByMethod": cold, "warmReadByMethod": warm,
"coldPreparationCategories": categories(cold_calls), "warmReadCategories": categories(warm_calls),
"categories": categories(native.calls),
@@ -1292,6 +1296,7 @@ def subprocess_fixture(command, **kwargs):
if command[0] == "gh": return subprocess.CompletedProcess(command, 0)
output = pathlib.Path(command[command.index("--output")+1]); output.mkdir()
(output/"manifest.json").write_text(json.dumps(manifest()))
+ (output/"package-evidence.json").write_text("{}")
return subprocess.CompletedProcess(command, 0)
argv = ["creator", "--preflight-only", "--candidate-run-id", "1", "--candidate-artifact-id", "2",
"--candidate-archive-sha256", "d"*64, "--workdir", str(root/"candidate-work")]
@@ -1306,8 +1311,16 @@ def retain(path, report, counted):
return original(path, report, counted)
def api(token): return native if token == "SECRET-LEDGER" else publisher_api
if failure in ("first", "both"): native.quota_remaining = 1
+ real_run_path = runpy.run_path
+ def injected_run_path(path, *args, **kwargs):
+ if str(path).endswith("creator-current-coord-dependencies.py"):
+ return {"load_pin": lambda: {"explicitSyntheticUnitFixture": True},
+ "protected_pin": lambda source: {"explicitSyntheticUnitFixture": True},
+ "read_json": lambda body: {}, "verify_evidence": lambda *args: None}
+ return real_run_path(path, *args, **kwargs)
with patch.object(sys, "argv", argv), patch.dict(os.environ, env, clear=True), \
patch.object(self.caller, "GitHubAPI", side_effect=api), \
+ patch("runpy.run_path", side_effect=injected_run_path), \
patch.object(self.caller.subprocess, "run", side_effect=subprocess_fixture), \
patch.object(self.caller, "WizardProvider", return_value=Provider()), \
patch.object(self.caller, "retain_summary", side_effect=retain), contextlib.redirect_stderr(output):
@@ -1321,7 +1334,7 @@ def read(path):
native.get = read
actual = self.caller.main()
self.assertEqual(actual, 0 if failure is None else 1)
- summary = root/"creator017-publication-summary.json"
+ summary = root/"creator018-publication-summary.json"
if failure not in ("report", "both"):
row = json.loads(summary.read_text())
self.assertEqual(row["preflightPassed"], failure is None)
@@ -1335,10 +1348,10 @@ def read(path):
def test_workflow_summary_exact_path_and_historical_job_isolation(self):
workflow = (ROOT / ".github/workflows/release-new-sdd-workspace.yml").read_text()
ordinary, historical = workflow.split(" recovery-diagnostic:", 1)
- self.assertIn("name: creator017-publication-summary-${{ github.run_id }}", ordinary)
- self.assertIn("path: ${{ runner.temp }}/creator017-publication-summary.json", ordinary)
+ self.assertIn("name: creator018-publication-summary-${{ github.run_id }}", ordinary)
+ self.assertIn("path: ${{ runner.temp }}/creator018-publication-summary.json", ordinary)
self.assertIn("if-no-files-found: error", ordinary)
- self.assertNotIn("creator017-publication-summary", historical)
+ self.assertNotIn("creator018-publication-summary", historical)
self.assertIn("timeout-minutes: 60", ordinary)
self.assertIn("cancel-in-progress: false", workflow)
self.assertIn("promotion_recovery == 'off'", ordinary)
@@ -1358,6 +1371,10 @@ def load_tests(loader, tests, pattern):
readback_module = importlib.util.module_from_spec(readback_spec)
readback_spec.loader.exec_module(readback_module)
tests.addTests(loader.loadTestsFromModule(readback_module))
+ current_spec = importlib.util.spec_from_file_location("current_dependency_controls", pathlib.Path(__file__).with_name("current_dependencies.py"))
+ current_module = importlib.util.module_from_spec(current_spec)
+ current_spec.loader.exec_module(current_module)
+ tests.addTests(loader.loadTestsFromModule(current_module))
return tests
@@ -1371,7 +1388,32 @@ def load_tests(loader, tests, pattern):
parser.add_argument("--build-artifacts", type=pathlib.Path)
parser.add_argument("--frozen-coord-dependencies", type=pathlib.Path)
parser.add_argument("--frozen-coord-source", type=pathlib.Path)
+ parser.add_argument("--published-coord-source", type=pathlib.Path)
+ parser.add_argument("--published-coord-dependencies", type=pathlib.Path)
+ parser.add_argument("--creator-source", type=pathlib.Path)
args = parser.parse_args()
+ if args.published_coord_source is not None or args.published_coord_dependencies is not None:
+ if args.creator_source is None or args.published_coord_source is None or args.published_coord_dependencies is None or args.build_artifacts is not None or args.frozen_coord_source is not None or args.frozen_coord_dependencies is not None:
+ parser.error('published mode requires isolated creator, producer and dependency roots only')
+ current = runpy.run_path(str(ROOT / 'scripts/creator-current-coord-dependencies.py'))
+ pin = current['protected_pin'](args.source_sha)
+ current['old']['layout'](args.creator_source, args.published_coord_dependencies, pin, args.published_coord_source)
+ # The normal own-build/package comparison also applies to this conventional staged layout.
+ output = args.creator_source / 'scripts/NewSddWorkspace/bin/Release/net10.0'
+ with zipfile.ZipFile(args.board_package) as archive:
+ for path in output.rglob('*'):
+ if path.is_file() and 'publish' not in path.relative_to(output).parts and path.suffix in ('.dll', '.pdb', '.json', '.xml', '.so', '.dylib'):
+ name = path.relative_to(output).as_posix()
+ if archive.read(current['PREFIX'] + name) != path.read_bytes():
+ raise ValueError('published Creator build/package mismatch: ' + name)
+ if not args.release_manifest:
+ parser.error('published mode requires manifest')
+ checker = runpy.run_path(str(ROOT / 'scripts/new-sdd-workspace-release.py'))
+ checker['verify_artifact'](args.release_manifest, args.board_package)
+ print(json.dumps(current['evidence'](args.board_package, args.source_sha, pin, fixtures_passed=True), sort_keys=True))
+ raise SystemExit(0)
+ if args.creator_source is not None:
+ parser.error('creator source root is exclusive to published mode')
closure = board_package_closure(args.board_package, args.source_sha,
frozen_dependencies=args.frozen_coord_dependencies,
frozen_source=args.frozen_coord_source,
diff --git a/tests/new-sdd-workspace/build-artifact-state.py b/tests/new-sdd-workspace/build-artifact-state.py
index 15a93827b..a8e43501f 100644
--- a/tests/new-sdd-workspace/build-artifact-state.py
+++ b/tests/new-sdd-workspace/build-artifact-state.py
@@ -26,9 +26,11 @@ def file_identity(path):
def capture(root, caller):
artifacts = {}
- for project in ("Cli", "Core", "GitHub"):
+ projects = {p.parent for p in root.glob("src/**/*.fsproj")} | {p.parent for p in root.glob("scripts/NewSddWorkspace/*.fsproj")}
+ projects |= {root / f"src/FS.GG.Coord.{name}" for name in ("Cli", "Core", "GitHub")}
+ for project in sorted(projects):
for kind in ("bin", "obj"):
- directory = root / f"src/FS.GG.Coord.{project}" / kind
+ directory = project / kind
key = str(directory.relative_to(root))
artifacts[key] = None if not directory.exists() else file_identity(directory)
if directory.is_dir() and not directory.is_symlink():
@@ -45,6 +47,7 @@ def capture(root, caller):
if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument("--output", type=Path, required=True)
+ parser.add_argument("--root", type=Path, default=ROOT)
args = parser.parse_args()
found = shutil.which("fsgg-coord-engine")
- args.output.write_text(json.dumps(capture(ROOT, Path(found) if found else None), sort_keys=True) + "\n")
+ args.output.write_text(json.dumps(capture(args.root, Path(found) if found else None), sort_keys=True) + "\n")
diff --git a/tests/new-sdd-workspace/run.sh b/tests/new-sdd-workspace/run.sh
index 420a3db83..386b14340 100755
--- a/tests/new-sdd-workspace/run.sh
+++ b/tests/new-sdd-workspace/run.sh
@@ -56,21 +56,68 @@ PY_BOUND
[ "$BUILD_ROOT_OWNED" -eq 1 ] || mkdir -m 700 "$BUILD_ROOT"
python3 -B "$HERE/test-build-artifact-state.py"
python3 -B "$HERE/build-artifact-state.py" --output "$BUILD_ROOT/caller-before.json"
-echo "new-sdd-workspace parse fixture — building the CLI (Release, isolated project outputs)…"
+MODE="${FSGG_CREATOR_DEPENDENCY_MODE:-source-only}"
+case "$MODE" in
+ source-only)
+ echo "Creator source-only qualification (not release evidence)" >&2
+ DLL="$BUILD_ROOT/bin/NewSddWorkspace/release/new-sdd-workspace.dll"
+ ;;
+ published-dependency)
+ : "${FSGG_CREATOR_PRODUCER_SOURCE:?isolated producer checkout required}"
+ : "${FSGG_CREATOR_DEPENDENCIES:?verified staged dependency directory required}"
+ : "${FSGG_CREATOR_CALLER_ROOT:?active caller root required}"
+ python3 - "$REPO_ROOT" "$FSGG_CREATOR_PRODUCER_SOURCE" "$FSGG_CREATOR_CALLER_ROOT" <<'PY_ISOLATION'
+import pathlib, sys
+creator, producer, caller = map(pathlib.Path, sys.argv[1:])
+roots = [creator, producer, caller]
+if any(not p.is_absolute() or not p.is_dir() or any(parent.is_symlink() for parent in (p, *p.parents)) for p in roots):
+ raise SystemExit('Creator, producer and active caller require unlinked absolute checkout roots')
+canonical = [p.resolve(strict=True) for p in roots]
+if roots != canonical or any(a == b or a.is_relative_to(b) for i, a in enumerate(canonical) for j, b in enumerate(canonical) if i != j):
+ raise SystemExit('Creator, producer and active caller must be canonical distinct isolated checkout roots')
+if any(p.exists() for p in (creator / 'scripts/NewSddWorkspace/bin', creator / 'scripts/NewSddWorkspace/obj')):
+ raise SystemExit('Published mode refuses stale Creator output')
+PY_ISOLATION
+ python3 "$REPO_ROOT/scripts/creator-current-coord-dependencies.py" verify-layout \
+ --producer-source "$FSGG_CREATOR_PRODUCER_SOURCE" --dependencies "$FSGG_CREATOR_DEPENDENCIES"
+ DLL="$REPO_ROOT/scripts/NewSddWorkspace/bin/Release/net10.0/new-sdd-workspace.dll"
+ # Restore metadata in these disposable checkouts before freezing producer state.
+ # Compile and pack then consume only the already staged implementation bodies.
+ dotnet restore "$PROJ" --nologo -v quiet -m:1 -nr:false \
+ -p:FsggCurrentCoordDependencies=true -p:BuildProjectReferences=false \
+ -p:CompileUsingReferenceAssemblies=false \
+ "-p:FsggFrozenCoordSource=$FSGG_CREATOR_PRODUCER_SOURCE" \
+ "-p:FsggFrozenCoordDependencies=$FSGG_CREATOR_DEPENDENCIES" 1>&2
+ python3 -B "$HERE/build-artifact-state.py" --root "$FSGG_CREATOR_PRODUCER_SOURCE" --output "$BUILD_ROOT/producer-before.json"
+ python3 -B "$HERE/build-artifact-state.py" --root "$FSGG_CREATOR_CALLER_ROOT" --output "$BUILD_ROOT/active-before.json"
+ ;;
+ *) echo "::error::unknown Creator dependency mode"; exit 1 ;;
+esac
build_rc=0
-dotnet build "$PROJ" -c Release --artifacts-path "$BUILD_ROOT" --nologo -v quiet \
- -m:1 -nr:false -p:UseSharedCompilation=false 1>&2 || build_rc=$?
-python3 -B "$HERE/build-artifact-state.py" --output "$BUILD_ROOT/caller-after.json"
-if ! cmp -s "$BUILD_ROOT/caller-before.json" "$BUILD_ROOT/caller-after.json"; then
- echo "::error::Creator fixture changed caller workspace artifacts or selected installed entry" >&2
- [ "$build_rc" -ne 0 ] || build_rc=1
+if [ "$MODE" = published-dependency ]; then
+ dotnet build "$PROJ" -c Release --no-restore --nologo -v quiet \
+ -p:FsggCurrentCoordDependencies=true -p:BuildProjectReferences=false \
+ -p:CompileUsingReferenceAssemblies=false \
+ "-p:FsggFrozenCoordSource=$FSGG_CREATOR_PRODUCER_SOURCE" \
+ "-p:FsggFrozenCoordDependencies=$FSGG_CREATOR_DEPENDENCIES" \
+ -m:1 -nr:false -p:UseSharedCompilation=false 1>&2 || build_rc=$?
+else
+ dotnet build "$PROJ" -c Release --artifacts-path "$BUILD_ROOT" --nologo -v quiet \
+ -m:1 -nr:false -p:UseSharedCompilation=false 1>&2 || build_rc=$?
+fi
+if [ "$MODE" = published-dependency ]; then
+ python3 -B "$HERE/build-artifact-state.py" --root "$FSGG_CREATOR_PRODUCER_SOURCE" --output "$BUILD_ROOT/producer-after.json"
+ python3 -B "$HERE/build-artifact-state.py" --root "$FSGG_CREATOR_CALLER_ROOT" --output "$BUILD_ROOT/active-after.json"
+ cmp "$BUILD_ROOT/producer-before.json" "$BUILD_ROOT/producer-after.json" || build_rc=1
+ cmp "$BUILD_ROOT/active-before.json" "$BUILD_ROOT/active-after.json" || build_rc=1
+ python3 "$REPO_ROOT/scripts/creator-current-coord-dependencies.py" verify-layout \
+ --producer-source "$FSGG_CREATOR_PRODUCER_SOURCE" --dependencies "$FSGG_CREATOR_DEPENDENCIES"
+else
+ python3 -B "$HERE/build-artifact-state.py" --output "$BUILD_ROOT/caller-after.json"
+ cmp "$BUILD_ROOT/caller-before.json" "$BUILD_ROOT/caller-after.json" || build_rc=1
fi
[ "$build_rc" -eq 0 ] || exit "$build_rc"
-echo "PASS isolated Creator build preserved workspace artifacts and selected caller identity"
-
-# Exact fresh output wins; never search a stale source bin/publish tree.
-DLL="$BUILD_ROOT/bin/NewSddWorkspace/release/new-sdd-workspace.dll"
-[ -f "$DLL" ] || { echo "::error::missing freshly built Creator DLL in isolated artifacts"; exit 1; }
+[ -f "$DLL" ] || { echo "::error::missing freshly built Creator DLL"; exit 1; }
echo "new-sdd-workspace parse fixture — dll='$DLL'"
# Exercise the wizard's pure decision boundary directly. The normal interactive path intentionally
diff --git a/tests/new-sdd-workspace/test-build-artifact-state.py b/tests/new-sdd-workspace/test-build-artifact-state.py
index ab0f913b3..4887f70af 100644
--- a/tests/new-sdd-workspace/test-build-artifact-state.py
+++ b/tests/new-sdd-workspace/test-build-artifact-state.py
@@ -34,6 +34,19 @@ def test_same_size_same_time_changed_engine_bytes_are_detected(self):
os.utime(target, ns=(info.st_atime_ns, info.st_mtime_ns))
self.assertNotEqual(first, state.capture(root, None))
+ def test_declared_transitive_and_creator_artifacts_are_preserved(self):
+ with tempfile.TemporaryDirectory() as temporary:
+ root = Path(temporary)
+ for project in ("src/FS.GG.Telemetry.Contracts", "scripts/NewSddWorkspace"):
+ directory = root / project
+ directory.mkdir(parents=True)
+ (directory / "fixture.fsproj").write_text("")
+ first = state.capture(root, None)
+ target = directory / "obj/project.assets.json"
+ target.parent.mkdir()
+ target.write_bytes(b"synthetic restore metadata")
+ self.assertNotEqual(first, state.capture(root, None))
+
def test_selected_caller_change_is_detected_without_execution(self):
with tempfile.TemporaryDirectory() as temporary:
root = Path(temporary)
diff --git a/tests/paths-coherence/run.sh b/tests/paths-coherence/run.sh
index 5159aa3dc..df3d5d883 100755
--- a/tests/paths-coherence/run.sh
+++ b/tests/paths-coherence/run.sh
@@ -699,8 +699,8 @@ wf "$RBP/.github/workflows/w.yml" ' - "src/A/**"
expect "property-valued Include cannot become a literal graph edge" \
3 "requires MSBuild evaluation" "$RBP"
-# The frozen Creator route is a closed immutable external closure, not an arbitrary property
-# graph. Cover the ordinary local reference; every altered selector/guard stays no-verdict.
+# The retained and current Creator routes use closed external selectors, not arbitrary
+# property evaluation. Current release readiness is independent of static local coverage.
RBF="$(root "$WORK/cover-closed-frozen-creator")"
mkdir -p "$RBF/scripts/NewSddWorkspace"
cp "$REPO_ROOT/scripts/NewSddWorkspace/NewSddWorkspace.fsproj" "$RBF/scripts/NewSddWorkspace/"
@@ -709,8 +709,18 @@ proj "$RBF" "src/FS.GG.Coord.Cli"
wf "$RBF/.github/workflows/w.yml" ' - "scripts/NewSddWorkspace/**"
- "src/FS.GG.Coord.Cli/**"' ' - "scripts/NewSddWorkspace/**"
- "src/FS.GG.Coord.Cli/**"'
-expect "closed frozen Creator route retains ordinary local closure" 0 "ok:" "$RBF"
-for mutation in root condition ordinary parent pair error-continue content-child build copy verify pin malformed-pin; do
+expect "closed current Creator route retains ordinary local closure without future pin" 0 "ok:" "$RBF"
+# The original single-Exec recognizer remains usable by historical source fixtures.
+RBFH="$WORK/closed-historical-creator";cp -R "$RBF" "$RBFH"
+python3 - "$RBFH/scripts/NewSddWorkspace/NewSddWorkspace.fsproj" <<'PYHISTORICAL'
+import sys,xml.etree.ElementTree as ET
+path=sys.argv[1];tree=ET.parse(path);target=next(t for t in tree.getroot().findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies')
+retained=target[0];retained.attrib.pop('Condition')
+for child in list(target)[1:]:target.remove(child)
+tree.write(path,encoding='unicode')
+PYHISTORICAL
+expect "closed historical single-selector Creator route retains ordinary local closure" 0 "ok:" "$RBFH"
+for mutation in root condition ordinary parent pair error-continue content-child build copy verify current-verify current-condition retained-condition duplicate-selector pin malformed-pin; do
RBFC="$WORK/closed-frozen-$mutation"
cp -R "$RBF" "$RBFC"
python3 - "$RBFC" "$mutation" <<'PYCONTROL'
@@ -731,6 +741,11 @@ elif mode=='content-child':ET.SubElement(next(n for g in project.findall('ItemGr
elif mode=='build':next(project.iter('BuildProjectReferences')).text='true'
elif mode=='copy':next(project.iter('_GetChildProjectCopyToOutputDirectoryItems')).text='true'
elif mode=='verify':next(t for t in project.findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies')[0].set('Command','echo unverified')
+elif mode=='current-verify':next(t for t in project.findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies')[1].set('Command','echo unverified')
+elif mode=='current-condition':next(t for t in project.findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies')[1].set('Condition',"'$(FsggCurrentCoordDependencies)' != 'true'")
+elif mode=='retained-condition':next(t for t in project.findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies')[0].attrib.pop('Condition')
+elif mode=='duplicate-selector':
+ target=next(t for t in project.findall('Target') if t.get('Name')=='VerifyFrozenCoordDependencies');ET.SubElement(target,'Exec',target[1].attrib)
elif mode=='malformed-pin':
pin=root/'scripts/creator-frozen-coord-dependencies.json';value=json.loads(pin.read_text());value['projects']=list(value['projects']);pin.write_text(json.dumps(value))
elif mode=='pin':
diff --git a/tests/release-effect-sealing/run.py b/tests/release-effect-sealing/run.py
index 8cf8248a9..c3d8a87ad 100644
--- a/tests/release-effect-sealing/run.py
+++ b/tests/release-effect-sealing/run.py
@@ -89,8 +89,8 @@ def executable_text(path: pathlib.Path) -> str:
assert route["sha256"] == digest(ROOT / WIZARD_SUCCESSOR)
assert route["disposition"] == "exact-source-protected-journal-successor-only"
amendment = route["successorAmendment"]
-assert amendment["unit"] == "COORD-BOARD-V2-01.11" and amendment["version"] == "0.17.0"
-assert amendment["operationAcceptance"] == "candidate, journal initialization, protected preflight and 0.17 publication not performed"
+assert amendment["unit"] == "CBC-01" and amendment["version"] == "0.18.0"
+assert amendment["operationAcceptance"] == "Source only; no108/018 candidate, pin, journal initialization, protected preflight, publication, installation or native adoption acceptance."
history = next(row for row in report["historicalRouteAttestations"]
if row["acceptedSource"] == amendment["previousAcceptedSource"])
assert history["status"] == "non-current-history"
@@ -98,6 +98,9 @@ def executable_text(path: pathlib.Path) -> str:
for key in ("forwardRecoveryAmendment", "capabilityLoss", "historicalCapabilityLoss", "historicalDisposition"):
assert route[key] == history["route"][key], f"retained recovery/retirement boundary changed: {key}"
proof = route["bindingIsolationProof"]
+creator017_predecessor = next(row for row in report["historicalRouteAttestations"]
+ if row["acceptedSource"] == proof["creator017ProfileAmendment"]["previousAcceptedSource"])
+assert history["route"]["bindingIsolationProof"]["currentBinding"] == "CURRENT_017"
for name, expected in proof["currentRecoveryJobSha256"].items():
raw_workflow = (ROOT / WIZARD_SUCCESSOR).read_text()
start = raw_workflow.index(" " + name + ":\n")
@@ -146,9 +149,9 @@ def verify_creator017_publish_job(job, amendment):
assert set(amendment) == {"unit", "scope", "previousAcceptedSource", "previousSuccessorWorkflowSha256", "previousPublishJobSourceSha256", "currentPublishJobSourceSha256", "currentBinding", "retainedBinding", "coherentSourceVersion", "freshLogicalJournal", "originalH4Accepted", "oldEffectGrantRenewed", "operationAcceptance"}
assert amendment["unit"] == "COORD-BOARD-V2-01.11"
assert amendment["previousAcceptedSource"] == "2e60210be1e04d52fe0735a56333b3e3aef42284"
- assert amendment["previousSuccessorWorkflowSha256"] == history["route"]["sha256"]
+ assert amendment["previousSuccessorWorkflowSha256"] == creator017_predecessor["route"]["sha256"]
assert amendment["previousPublishJobSourceSha256"] == proof["creator016PublicationSummaryAmendment"]["currentPublishJobSourceSha256"]
- assert amendment["currentBinding"] == proof["currentBinding"] == "CURRENT_017"
+ assert amendment["currentBinding"] == "CURRENT_017"
assert amendment["retainedBinding"] == "CURRENT_016"
assert amendment["coherentSourceVersion"] == "0.107.0"
assert amendment["freshLogicalJournal"] == "board-v2-product-creator-017"
@@ -167,6 +170,34 @@ def verify_creator017_publish_job(job, amendment):
assert hashlib.sha256(retained.encode()).hexdigest() == amendment["previousPublishJobSourceSha256"]
verify_creator_publish_job(retained, proof["creator016PublicationSummaryAmendment"])
+CREATOR018_SUMMARY_STEP = CREATOR_SUMMARY_STEP.replace("creator016-", "creator018-")
+CURRENT_PIN_PREFLIGHT_STEP = """ - name: Refuse absent promoted dependency pin before credentials or effects
+ run: python3 scripts/creator-current-coord-dependencies.py preflight
+"""
+
+def verify_creator018_publish_job(job, amendment):
+ assert amendment["unit"] == "CBC-01"
+ assert amendment["currentBinding"] == proof["currentBinding"] == "CURRENT_018"
+ assert amendment["retainedBindings"] == ["CURRENT_017", "CURRENT_016", "HISTORICAL_013"]
+ assert amendment["coherentSourceVersion"] == "0.108.0"
+ assert amendment["freshLogicalJournal"] == "board-v2-product-creator-018"
+ assert amendment["dependencyMode"] == "published-dependency"
+ assert amendment["realPinPresent"] is False and amendment["oldEffectGrantRenewed"] is False
+ assert amendment["previousAcceptedSource"] == history["acceptedSource"]
+ assert amendment["previousSuccessorWorkflowSha256"] == history["route"]["sha256"]
+ assert amendment["previousPublishJobSourceSha256"] == proof["creator017ProfileAmendment"]["currentPublishJobSourceSha256"]
+ assert hashlib.sha256(job.encode()).hexdigest() == amendment["currentPublishJobSourceSha256"]
+ assert job.count(CURRENT_PIN_PREFLIGHT_STEP) == 1
+ assert job.index(CURRENT_PIN_PREFLIGHT_STEP) < job.index("actions/setup-dotnet") < job.index("Mint the ordinary")
+ retained = job.replace(CURRENT_PIN_PREFLIGHT_STEP, "", 1)
+ for current, previous in (("new-sdd-workspace-018-publisher", "new-sdd-workspace-017-publisher"),
+ ("creator018-publication-summary-", "creator017-publication-summary-"),
+ ("creator018-publication-summary.json", "creator017-publication-summary.json")):
+ assert retained.count(current) == 1
+ retained = retained.replace(current, previous, 1)
+ assert hashlib.sha256(retained.encode()).hexdigest() == amendment["previousPublishJobSourceSha256"]
+ verify_creator017_publish_job(retained, proof["creator017ProfileAmendment"])
+
def verify_diagnostic_job(source):
global_permissions = source.split("\npermissions:\n", 1)[1].split("\nconcurrency:\n", 1)[0]
assert global_permissions == " actions: read\n contents: write\n packages: write\n id-token: write\n"
@@ -194,7 +225,7 @@ def verify_diagnostic_job(source):
assert "python3 scripts/new_sdd_workspace_promote_recovery.py \\\n --post-completion-readback \"$RECOVERY_BINDING\"" in job
for name, expected in proof["postCompletionReadbackAmendment"]["currentJobSourceSha256"].items():
if name == "publish":
- verify_creator017_publish_job(jobs[name], proof["creator017ProfileAmendment"])
+ verify_creator018_publish_job(jobs[name], proof["creator018ProfileAmendment"])
else:
assert hashlib.sha256(jobs[name].encode()).hexdigest() == expected, name
@@ -217,12 +248,13 @@ def verify_diagnostic_job(source):
# changes still fail the reconstructed historical seal, rather than being
# excused by a new current hash. Recovery jobs retain their original full seals.
publish_job = workflow_jobs(raw_workflow)["publish"]
-summary_amendment = proof["creator017ProfileAmendment"]
+summary_amendment = proof["creator018ProfileAmendment"]
publish_mutations = (
(" if: always()", " if: success()"),
(" retention-days: 7", " retention-days: 8"),
- ("creator017-publication-summary.json", "unbounded-directory/"),
+ ("creator018-publication-summary.json", "unbounded-directory/"),
("inputs.promotion_recovery == 'off'", "true"),
+ ("creator-current-coord-dependencies.py preflight", "creator-frozen-coord-dependencies.py preflight"),
(" persist-credentials: false", " persist-credentials: true"),
)
for original, changed in publish_mutations:
@@ -230,14 +262,14 @@ def verify_diagnostic_job(source):
mutant = publish_job.replace(original, changed, 1)
repinned = {**summary_amendment, "currentPublishJobSourceSha256": hashlib.sha256(mutant.encode()).hexdigest()}
try:
- verify_creator017_publish_job(mutant, repinned)
+ verify_creator018_publish_job(mutant, repinned)
except AssertionError:
pass
else:
raise AssertionError("repinned Creator ordinary-job mutant accepted: " + original)
-for mutant in (publish_job.replace(CREATOR017_SUMMARY_STEP, "", 1), publish_job + CREATOR017_SUMMARY_STEP):
+for mutant in (publish_job.replace(CREATOR018_SUMMARY_STEP, "", 1), publish_job + CREATOR018_SUMMARY_STEP):
try:
- verify_creator017_publish_job(mutant, {**summary_amendment, "currentPublishJobSourceSha256": hashlib.sha256(mutant.encode()).hexdigest()})
+ verify_creator018_publish_job(mutant, {**summary_amendment, "currentPublishJobSourceSha256": hashlib.sha256(mutant.encode()).hexdigest()})
except AssertionError:
pass
else:
@@ -250,7 +282,7 @@ def verify_diagnostic_job(source):
pass
else:
raise AssertionError("historical recovery-job drift accepted: " + job_name)
-print(f"Creator017 ordinary profile and retained016 summary seal: {len(publish_mutations) + 4} repinned job/summary and recovery mutants refused")
+print(f"Creator018 current preflight/profile and retained017/016 summary seals: {len(publish_mutations) + 4} repinned job/summary and recovery mutants refused")
diagnostic = workflow_jobs(raw_workflow)["recovery-diagnostic"]
permission_mutations = (
(" contents: write", " contents: read"),
@@ -396,7 +428,7 @@ def verify_readback_source_spans(source):
assert len(selected) == count
assert all(any(arg.arg == keyword and isinstance(arg.value, ast.Name) and arg.value.id == "HISTORICAL_013"
for arg in call.keywords) for call in selected)
-assert "self.release_binding is not CURRENT_017" in admission
+assert "self.release_binding is not CURRENT_018" in admission
assert "self.release_binding is not HISTORICAL_013" in admission
execution = (ROOT / "scripts/new_sdd_workspace_successor_execution.py").read_text()
assert 'CURRENT_014 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.14.0", "new-sdd-workspace/v0.14.0")' in execution
@@ -404,7 +436,8 @@ def verify_readback_source_spans(source):
assert 'CURRENT_016 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.16.0", "new-sdd-workspace/v0.16.0")' in execution
assert 'HISTORICAL_013 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.13.0", "new-sdd-workspace/v0.13.0")' in execution
assert 'CURRENT_017 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.17.0", "new-sdd-workspace/v0.17.0")' in execution
-assert "binding is not CURRENT_017 and binding is not CURRENT_016 and binding is not HISTORICAL_013" in execution
+assert 'CURRENT_018 = ReleaseBinding("FS.GG.NewSddWorkspace", "0.18.0", "new-sdd-workspace/v0.18.0")' in execution
+assert "binding is not CURRENT_018 and binding is not CURRENT_017 and binding is not CURRENT_016 and binding is not HISTORICAL_013" in execution
with tempfile.TemporaryDirectory(prefix="gs2-08-9-release-seal.") as temporary:
work = pathlib.Path(temporary)
diff --git a/tests/release-successor-candidate/run.py b/tests/release-successor-candidate/run.py
index 0d93219dc..a83ef4c9e 100644
--- a/tests/release-successor-candidate/run.py
+++ b/tests/release-successor-candidate/run.py
@@ -222,7 +222,7 @@ def test_prospective_feed_probe_has_only_main_read_permissions_and_no_release_ef
self.assertIn('test "$(git ls-remote origin refs/heads/main | cut -f1)" = "$SOURCE_SHA"', workflow)
self.assertIn("python3 tests/release-successor-candidate/run.py", workflow)
self.assertIn("python3 scripts/check-release-candidate-uniqueness.py", workflow)
- self.assertIn("--version 0.107.0 --predecessor 0.106.0", workflow)
+ self.assertIn("--version 0.108.0 --predecessor 0.107.0", workflow)
for forbidden in (
"packages: write", "contents: write", "id-token:", "environment:", "secrets.",
"release-successor-publish.py", "release-saga.py", "dotnet pack",
@@ -233,21 +233,21 @@ def test_prospective_feed_probe_has_only_main_read_permissions_and_no_release_ef
def test_candidate_binds_the_next_version_and_exact_predecessor(self) -> None:
workflow = (ROOT / ".github/workflows/release-successor-candidate.yml").read_text()
- self.assertIn('test "$version" = 0.107.0', workflow)
- self.assertIn("gh release download coherent-set/v0.106.0", workflow)
- self.assertIn("--tag-source 2e42faaa994367b9f50be87439e8fd973ad21501", workflow)
- self.assertEqual(workflow.count("--predecessor 0.106.0"), 2)
- self.assertIn("--release-tag coherent-set/v0.106.0", workflow)
+ self.assertIn('test "$version" = 0.108.0', workflow)
+ self.assertIn("gh release download coherent-set/v0.107.0", workflow)
+ self.assertIn("--tag-source 75ab98dd28b1a818cc3986d595bf21e0fe691ec6", workflow)
+ self.assertEqual(workflow.count("--predecessor 0.107.0"), 2)
+ self.assertIn("--release-tag coherent-set/v0.107.0", workflow)
for namespace in ("coherent-set", "kit", "drivers", "coord-engine"):
- self.assertIn(f"refs/tags/{namespace}/v0.107.0", workflow)
+ self.assertIn(f"refs/tags/{namespace}/v0.108.0", workflow)
for project in ("FS.GG.Coord.Cli", "FS.GG.Kit", "FS.GG.Drivers"):
self.assertEqual(workflow.count(f"dotnet pack src/{project}/"), 1)
initial=workflow.split(' - name: Verify the stable predecessor and unused package version',1)[1].split(' - name: Test the telemetry producer',1)[0]
retention=workflow.split(' - name: Refuse a changed main or newly occupied version before retention',1)[1].split(' - uses: actions/upload-artifact',1)[0]
- self.assertIn('releases/tags/coherent-set/v0.107.0',initial)
+ self.assertIn('releases/tags/coherent-set/v0.108.0',initial)
self.assertIn('git ls-remote',initial)
self.assertIn('refs/heads/main',retention)
- self.assertIn('--predecessor 0.106.0',retention)
+ self.assertIn('--predecessor 0.107.0',retention)
self.assertNotIn('releases/tags/',retention)
self.assertNotIn('refs/tags/',retention)
self.assertIn('timeout-minutes: 45',workflow)
diff --git a/tests/release-successor-recovery/run.py b/tests/release-successor-recovery/run.py
index f45abe4e9..1bd1a5aa7 100644
--- a/tests/release-successor-recovery/run.py
+++ b/tests/release-successor-recovery/run.py
@@ -1613,13 +1613,13 @@ def test_current_default_has_107_106_and_distinct25(self):
args = types.SimpleNamespace(recovery_checkpoint=False, repeat_original_nuget_kit_intent=False,
recover_original_runtime_intent=False)
self.assertEqual(publisher.selected_release_binding(args),
- ("0.107.0", "0.106.0", "refs/heads/fsgg/v2/journal/release/utel-rel-25"))
+ ("0.108.0", "0.107.0", "refs/heads/fsgg/v2/journal/release/utel-rel-26"))
- def test_current_profile_binds_promoted106_and_cannot_claim_old_journals(self):
- self.assertEqual(publisher.CURRENT_RELEASE['predecessorSource'],'2e42faaa994367b9f50be87439e8fd973ad21501')
- self.assertEqual(publisher.CURRENT_RELEASE['predecessorContentId'],'sha256:351a435c1f162f3ff8ca8e6722d58b34b193b44744a6a207f9bb57f015f8204d')
- self.assertEqual(publisher.CURRENT_RELEASE['directory'],'state/releases/utel-rel-25')
- for suffix in ('utel-rel-23','utel-rel-24'):
+ def test_current_profile_binds_promoted107_and_cannot_claim_old_journals(self):
+ self.assertEqual(publisher.CURRENT_RELEASE['predecessorSource'],'75ab98dd28b1a818cc3986d595bf21e0fe691ec6')
+ self.assertEqual(publisher.CURRENT_RELEASE['predecessorContentId'],'sha256:c193dbf487f643a8b78300b568e4bfd09f8c56086ce96dc52865e219e8f98c9b')
+ self.assertEqual(publisher.CURRENT_RELEASE['directory'],'state/releases/utel-rel-26')
+ for suffix in ('utel-rel-23','utel-rel-24','utel-rel-25'):
authority=MemoryAuthority()
with self.subTest(prior=suffix),self.assertRaisesRegex(JournalRefused,'different owner or profile'):
ProtectedReleaseJournal(authority,'refs/heads/fsgg/v2/journal/release/'+suffix,
@@ -2402,7 +2402,7 @@ def test_precredential_workflow_order_and_candidate_binding(self):
self.assertLess(fence,workflow.index(name))
self.assertNotIn('disposition_json:',workflow)
candidate = (ROOT/'.github/workflows/release-successor-candidate.yml').read_text()
- self.assertIn('test "$version" = 0.107.0',candidate)
+ self.assertIn('test "$version" = 0.108.0',candidate)
self.assertNotIn('-p:Version=',candidate)
self.assertIn('name: release-successor-candidate-${{ github.sha }}-${{ github.run_id }}',candidate)
self.assertIn('Separate evidence: never add a member to the exact seven-member publisher archive.',candidate)
@@ -2413,8 +2413,8 @@ class LiteralForwardControls(SuspensionFixture):
def context(self):
if not hasattr(self,'_forward_base'):self._forward_base=copy.deepcopy(self.authority)
self.authority=copy.deepcopy(self._forward_base)
- self.install();self.authority.logical_ref=publisher.CURRENT_RELEASE['logicalRef'];self.authority.directory_suffix='utel-rel-25';self.authority.calls.clear()
- candidate=manifest();candidate['descriptor'].update(version='0.107.0',previousStableVersion='0.106.0')
+ self.install();self.authority.logical_ref=publisher.CURRENT_RELEASE['logicalRef'];self.authority.directory_suffix='utel-rel-26';self.authority.calls.clear()
+ candidate=manifest();candidate['descriptor'].update(version='0.108.0',previousStableVersion='0.107.0')
candidate['contentId']='sha256:'+hashlib.sha256(json.dumps(candidate['descriptor'],sort_keys=True,separators=(',',':')).encode()).hexdigest()
counted=publisher.CountedAuthorityAPI(self.authority,ceiling=1500,quota_floor=1800);counted.admit_quota()
shared=self.mod.ReleaseSuspension(counted);rows=report();native=MemoryPublisher()
@@ -2431,7 +2431,7 @@ def visibility(effect):
if observation.state=='matched' and observation.observed_digest==effect.target_digest:return 'potential'
raise publisher.Refused('inert pending witness '+observation.state)
provider.ordinary_visibility=visibility
- intent={'contentId':candidate['contentId'],'sourceSha':'b'*40,'version':'0.107.0','candidateArchiveSha256':'c'*64,'operator':'EHotwagner'}
+ intent={'contentId':candidate['contentId'],'sourceSha':'b'*40,'version':'0.108.0','candidateArchiveSha256':'c'*64,'operator':'EHotwagner'}
publisher.prepare_release_journal(journal,counted,admission,provider,native,candidate,intent,'b'*40,'b'*40,False,lambda:None)
journal.capture();ticks=[0];sleeps=[]
def sleep(seconds):sleeps.append(seconds);ticks[0]+=seconds
@@ -2499,7 +2499,7 @@ def get(path):
if '/actions/runs/' in path:row['status']='cancelled'
return row
native.get=get
- elif mode=='suspension':self.add_file('state/releases/utel-rel-25/release-state.json',canonical(journal._observed.state)+b' ')
+ elif mode=='suspension':self.add_file('state/releases/utel-rel-26/release-state.json',canonical(journal._observed.state)+b' ')
else:next(iter(self.authority.controls.values()))['enforcement']='disabled'
with self.assertRaises(RuntimeError):run(sleep=sleep)
self.assertEqual(provider.dispatched,['tag']);self.assertEqual(sleeps,[5])
@@ -3493,12 +3493,15 @@ def prepare_caller(self, *, history=0, delays=0, target='channel-asset', ceiling
self.promoted106_fixture=b'preserved synthetic consumed106 journal bytes\n'
self.add_file('state/releases/utel-rel-24/release-state.json',self.promoted106_fixture)
self.add_file('state/releases/utel-rel-24/release-head.txt',b'preserved prior106 logical head\n')
- self.authority.directory_suffix='utel-rel-25';self.authority.logical_ref=publisher.CURRENT_RELEASE['logicalRef']
+ self.promoted107_fixture=b'preserved synthetic consumed107 journal bytes\n'
+ self.add_file('state/releases/utel-rel-25/release-state.json',self.promoted107_fixture)
+ self.add_file('state/releases/utel-rel-25/release-head.txt',b'preserved prior107 logical head\n')
+ self.authority.directory_suffix='utel-rel-26';self.authority.logical_ref=publisher.CURRENT_RELEASE['logicalRef']
for n in range(history):self.add_file('state/ordinary/cold-history.json',canonical({'generation':n}))
- self.native=Literal104ProviderFixture(self.root,None,version="0.107.0")
+ self.native=Literal104ProviderFixture(self.root,None,version="0.108.0")
stream=io.BytesIO()
with zipfile.ZipFile(stream,'w') as archive:
- for name in [*(f'{package}.0.107.0.nupkg' for package in PACKAGES),
+ for name in [*(f'{package}.0.108.0.nupkg' for package in PACKAGES),
'release-manifest.json','previous-stable-channel.json',
'standalone-telemetry-evidence.json','standalone-telemetry-runtime-evidence.json']:
archive.writestr(name,(self.root/name).read_bytes())
@@ -3535,7 +3538,7 @@ def get(path,_original_get=original):
if '/releases?' in path:return []
if hidden=='promote' and '/releases/tags/' in path:value['draft']=True
if hidden and '/assets?per_page=100' in path:
- name={**{f'archive-asset:{package}':f'{package}.0.107.0.nupkg' for package in PACKAGES},
+ name={**{f'archive-asset:{package}':f'{package}.0.108.0.nupkg' for package in PACKAGES},
'qualification-asset:evidence':'standalone-telemetry-evidence.json',
'qualification-asset:runtime':'standalone-telemetry-runtime-evidence.json',
'channel-asset':'stable-channel.json','manifest-asset':'release-manifest.json'}.get(hidden)
@@ -3605,7 +3608,7 @@ def process(argv,**kwargs):
return types.SimpleNamespace(returncode=0)
if len(argv)>1 and argv[1].endswith('check-release-candidate-uniqueness.py'):
self.local_ports.append('uniqueness-external-port')
- self.assertEqual(argv[2:],['--version','0.107.0','--predecessor','0.106.0'])
+ self.assertEqual(argv[2:],['--version','0.108.0','--predecessor','0.107.0'])
self.assertFalse(self.native.feeds);self.assertIsNone(self.native.release)
return types.SimpleNamespace(returncode=0)
self.local_ports.append('inert-nuget-send' if argv[:3]==['dotnet','nuget','push'] else 'saga:'+argv[2])
@@ -3670,6 +3673,7 @@ def assert_complete(self):
self.assertEqual(reader.file(self.authority.head,'state/releases/utel-rel-22/release-head.txt'),self.claimed104_head)
self.assertEqual(reader.file(self.authority.head,'state/ordinary/sibling.json'),b'original sibling bytes\n')
self.assertEqual(reader.file(self.authority.head,'state/releases/utel-rel-24/release-state.json'),self.promoted106_fixture)
+ self.assertEqual(reader.file(self.authority.head,'state/releases/utel-rel-25/release-state.json'),self.promoted107_fixture)
self.assertEqual(reader.file(self.authority.head,'state/releases/utel-rel-24/release-head.txt'),b'preserved prior106 logical head\n')
if self.history:self.assertEqual(reader.file(self.authority.head,'state/ordinary/cold-history.json'),canonical({'generation':self.history-1}))
self.assertEqual(sum(self.rows['authorityCounter'].attempted.values()),counted_entries)
@@ -3795,7 +3799,7 @@ def get(path):
return row
self.native.get=get
elif mode=='protection':next(iter(self.authority.controls.values()))['enforcement']='disabled'
- else:self.external_file('state/releases/utel-rel-25/release-state.json',canonical(self.rows['lastObservedJournal'])+b' ')
+ else:self.external_file('state/releases/utel-rel-26/release-state.json',canonical(self.rows['lastObservedJournal'])+b' ')
self.on_sleep=change
with self.assertRaises(RuntimeError):self.invoke_caller()
self.assertEqual(self.dispatches,['tag'])
@@ -3889,7 +3893,7 @@ def prepare(effect):
name='release-state.json' if mode=='state' else 'release-head.txt'
expected=self.providers[0]._ordinary_expected_journal
raw=expected[1]+b' ' if mode=='state' else ('e'*40+'\n').encode()
- self.external_file('state/releases/utel-rel-25/'+name,raw)
+ self.external_file('state/releases/utel-rel-26/'+name,raw)
self.on_prepare=prepare
with self.assertRaises(RuntimeError):self.invoke_caller()
self.assertIsNone(self.native.tag);self.assertEqual(self.publisher_ports.count('post'),0)