From 6e1b5b7a0c9875e7455734d2c1f7793fea06f053 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 11 Feb 2026 17:44:08 +0000 Subject: [PATCH 01/14] chore(deps): bump pillow from 11.3.0 to 12.1.1 Bumps [pillow](https://github.com/python-pillow/Pillow) from 11.3.0 to 12.1.1. - [Release notes](https://github.com/python-pillow/Pillow/releases) - [Changelog](https://github.com/python-pillow/Pillow/blob/main/CHANGES.rst) - [Commits](https://github.com/python-pillow/Pillow/compare/11.3.0...12.1.1) --- updated-dependencies: - dependency-name: pillow dependency-version: 12.1.1 dependency-type: indirect ... Signed-off-by: dependabot[bot] --- poetry.lock | 214 ++++++++++++++++++++++++---------------------------- 1 file changed, 99 insertions(+), 115 deletions(-) diff --git a/poetry.lock b/poetry.lock index e91e9dc..9cbdde7 100644 --- a/poetry.lock +++ b/poetry.lock @@ -4353,128 +4353,111 @@ ptyprocess = ">=0.5" [[package]] name = "pillow" -version = "11.3.0" -description = "Python Imaging Library (Fork)" -optional = true -python-versions = ">=3.9" +version = "12.1.1" +description = "Python Imaging Library (fork)" +optional = false +python-versions = ">=3.10" groups = ["main"] -markers = "extra == \"sandbox\"" files = [ - {file = "pillow-11.3.0-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:1b9c17fd4ace828b3003dfd1e30bff24863e0eb59b535e8f80194d9cc7ecf860"}, - {file = "pillow-11.3.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:65dc69160114cdd0ca0f35cb434633c75e8e7fad4cf855177a05bf38678f73ad"}, - {file = "pillow-11.3.0-cp310-cp310-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:7107195ddc914f656c7fc8e4a5e1c25f32e9236ea3ea860f257b0436011fddd0"}, - {file = "pillow-11.3.0-cp310-cp310-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:cc3e831b563b3114baac7ec2ee86819eb03caa1a2cef0b481a5675b59c4fe23b"}, - {file = "pillow-11.3.0-cp310-cp310-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:f1f182ebd2303acf8c380a54f615ec883322593320a9b00438eb842c1f37ae50"}, - {file = "pillow-11.3.0-cp310-cp310-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4445fa62e15936a028672fd48c4c11a66d641d2c05726c7ec1f8ba6a572036ae"}, - {file = "pillow-11.3.0-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:71f511f6b3b91dd543282477be45a033e4845a40278fa8dcdbfdb07109bf18f9"}, - {file = "pillow-11.3.0-cp310-cp310-musllinux_1_2_x86_64.whl", hash = "sha256:040a5b691b0713e1f6cbe222e0f4f74cd233421e105850ae3b3c0ceda520f42e"}, - {file = "pillow-11.3.0-cp310-cp310-win32.whl", hash = "sha256:89bd777bc6624fe4115e9fac3352c79ed60f3bb18651420635f26e643e3dd1f6"}, - {file = "pillow-11.3.0-cp310-cp310-win_amd64.whl", hash = "sha256:19d2ff547c75b8e3ff46f4d9ef969a06c30ab2d4263a9e287733aa8b2429ce8f"}, - {file = "pillow-11.3.0-cp310-cp310-win_arm64.whl", hash = "sha256:819931d25e57b513242859ce1876c58c59dc31587847bf74cfe06b2e0cb22d2f"}, - {file = "pillow-11.3.0-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:1cd110edf822773368b396281a2293aeb91c90a2db00d78ea43e7e861631b722"}, - {file = "pillow-11.3.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:9c412fddd1b77a75aa904615ebaa6001f169b26fd467b4be93aded278266b288"}, - {file = "pillow-11.3.0-cp311-cp311-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:7d1aa4de119a0ecac0a34a9c8bde33f34022e2e8f99104e47a3ca392fd60e37d"}, - {file = "pillow-11.3.0-cp311-cp311-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:91da1d88226663594e3f6b4b8c3c8d85bd504117d043740a8e0ec449087cc494"}, - {file = "pillow-11.3.0-cp311-cp311-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:643f189248837533073c405ec2f0bb250ba54598cf80e8c1e043381a60632f58"}, - {file = "pillow-11.3.0-cp311-cp311-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:106064daa23a745510dabce1d84f29137a37224831d88eb4ce94bb187b1d7e5f"}, - {file = "pillow-11.3.0-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:cd8ff254faf15591e724dc7c4ddb6bf4793efcbe13802a4ae3e863cd300b493e"}, - {file = "pillow-11.3.0-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:932c754c2d51ad2b2271fd01c3d121daaa35e27efae2a616f77bf164bc0b3e94"}, - {file = "pillow-11.3.0-cp311-cp311-win32.whl", hash = "sha256:b4b8f3efc8d530a1544e5962bd6b403d5f7fe8b9e08227c6b255f98ad82b4ba0"}, - {file = "pillow-11.3.0-cp311-cp311-win_amd64.whl", hash = "sha256:1a992e86b0dd7aeb1f053cd506508c0999d710a8f07b4c791c63843fc6a807ac"}, - {file = "pillow-11.3.0-cp311-cp311-win_arm64.whl", hash = "sha256:30807c931ff7c095620fe04448e2c2fc673fcbb1ffe2a7da3fb39613489b1ddd"}, - {file = "pillow-11.3.0-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:fdae223722da47b024b867c1ea0be64e0df702c5e0a60e27daad39bf960dd1e4"}, - {file = "pillow-11.3.0-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:921bd305b10e82b4d1f5e802b6850677f965d8394203d182f078873851dada69"}, - {file = "pillow-11.3.0-cp312-cp312-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:eb76541cba2f958032d79d143b98a3a6b3ea87f0959bbe256c0b5e416599fd5d"}, - {file = "pillow-11.3.0-cp312-cp312-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:67172f2944ebba3d4a7b54f2e95c786a3a50c21b88456329314caaa28cda70f6"}, - {file = "pillow-11.3.0-cp312-cp312-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:97f07ed9f56a3b9b5f49d3661dc9607484e85c67e27f3e8be2c7d28ca032fec7"}, - {file = "pillow-11.3.0-cp312-cp312-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:676b2815362456b5b3216b4fd5bd89d362100dc6f4945154ff172e206a22c024"}, - {file = "pillow-11.3.0-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:3e184b2f26ff146363dd07bde8b711833d7b0202e27d13540bfe2e35a323a809"}, - {file = "pillow-11.3.0-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:6be31e3fc9a621e071bc17bb7de63b85cbe0bfae91bb0363c893cbe67247780d"}, - {file = "pillow-11.3.0-cp312-cp312-win32.whl", hash = "sha256:7b161756381f0918e05e7cb8a371fff367e807770f8fe92ecb20d905d0e1c149"}, - {file = "pillow-11.3.0-cp312-cp312-win_amd64.whl", hash = "sha256:a6444696fce635783440b7f7a9fc24b3ad10a9ea3f0ab66c5905be1c19ccf17d"}, - {file = "pillow-11.3.0-cp312-cp312-win_arm64.whl", hash = "sha256:2aceea54f957dd4448264f9bf40875da0415c83eb85f55069d89c0ed436e3542"}, - {file = "pillow-11.3.0-cp313-cp313-ios_13_0_arm64_iphoneos.whl", hash = "sha256:1c627742b539bba4309df89171356fcb3cc5a9178355b2727d1b74a6cf155fbd"}, - {file = "pillow-11.3.0-cp313-cp313-ios_13_0_arm64_iphonesimulator.whl", hash = "sha256:30b7c02f3899d10f13d7a48163c8969e4e653f8b43416d23d13d1bbfdc93b9f8"}, - {file = "pillow-11.3.0-cp313-cp313-ios_13_0_x86_64_iphonesimulator.whl", hash = "sha256:7859a4cc7c9295f5838015d8cc0a9c215b77e43d07a25e460f35cf516df8626f"}, - {file = "pillow-11.3.0-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:ec1ee50470b0d050984394423d96325b744d55c701a439d2bd66089bff963d3c"}, - {file = "pillow-11.3.0-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:7db51d222548ccfd274e4572fdbf3e810a5e66b00608862f947b163e613b67dd"}, - {file = "pillow-11.3.0-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:2d6fcc902a24ac74495df63faad1884282239265c6839a0a6416d33faedfae7e"}, - {file = "pillow-11.3.0-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:f0f5d8f4a08090c6d6d578351a2b91acf519a54986c055af27e7a93feae6d3f1"}, - {file = "pillow-11.3.0-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:c37d8ba9411d6003bba9e518db0db0c58a680ab9fe5179f040b0463644bc9805"}, - {file = "pillow-11.3.0-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:13f87d581e71d9189ab21fe0efb5a23e9f28552d5be6979e84001d3b8505abe8"}, - {file = "pillow-11.3.0-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:023f6d2d11784a465f09fd09a34b150ea4672e85fb3d05931d89f373ab14abb2"}, - {file = "pillow-11.3.0-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:45dfc51ac5975b938e9809451c51734124e73b04d0f0ac621649821a63852e7b"}, - {file = "pillow-11.3.0-cp313-cp313-win32.whl", hash = "sha256:a4d336baed65d50d37b88ca5b60c0fa9d81e3a87d4a7930d3880d1624d5b31f3"}, - {file = "pillow-11.3.0-cp313-cp313-win_amd64.whl", hash = "sha256:0bce5c4fd0921f99d2e858dc4d4d64193407e1b99478bc5cacecba2311abde51"}, - {file = "pillow-11.3.0-cp313-cp313-win_arm64.whl", hash = "sha256:1904e1264881f682f02b7f8167935cce37bc97db457f8e7849dc3a6a52b99580"}, - {file = "pillow-11.3.0-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:4c834a3921375c48ee6b9624061076bc0a32a60b5532b322cc0ea64e639dd50e"}, - {file = "pillow-11.3.0-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:5e05688ccef30ea69b9317a9ead994b93975104a677a36a8ed8106be9260aa6d"}, - {file = "pillow-11.3.0-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:1019b04af07fc0163e2810167918cb5add8d74674b6267616021ab558dc98ced"}, - {file = "pillow-11.3.0-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:f944255db153ebb2b19c51fe85dd99ef0ce494123f21b9db4877ffdfc5590c7c"}, - {file = "pillow-11.3.0-cp313-cp313t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:1f85acb69adf2aaee8b7da124efebbdb959a104db34d3a2cb0f3793dbae422a8"}, - {file = "pillow-11.3.0-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:05f6ecbeff5005399bb48d198f098a9b4b6bdf27b8487c7f38ca16eeb070cd59"}, - {file = "pillow-11.3.0-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:a7bc6e6fd0395bc052f16b1a8670859964dbd7003bd0af2ff08342eb6e442cfe"}, - {file = "pillow-11.3.0-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:83e1b0161c9d148125083a35c1c5a89db5b7054834fd4387499e06552035236c"}, - {file = "pillow-11.3.0-cp313-cp313t-win32.whl", hash = "sha256:2a3117c06b8fb646639dce83694f2f9eac405472713fcb1ae887469c0d4f6788"}, - {file = "pillow-11.3.0-cp313-cp313t-win_amd64.whl", hash = "sha256:857844335c95bea93fb39e0fa2726b4d9d758850b34075a7e3ff4f4fa3aa3b31"}, - {file = "pillow-11.3.0-cp313-cp313t-win_arm64.whl", hash = "sha256:8797edc41f3e8536ae4b10897ee2f637235c94f27404cac7297f7b607dd0716e"}, - {file = "pillow-11.3.0-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:d9da3df5f9ea2a89b81bb6087177fb1f4d1c7146d583a3fe5c672c0d94e55e12"}, - {file = "pillow-11.3.0-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:0b275ff9b04df7b640c59ec5a3cb113eefd3795a8df80bac69646ef699c6981a"}, - {file = "pillow-11.3.0-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:0743841cabd3dba6a83f38a92672cccbd69af56e3e91777b0ee7f4dba4385632"}, - {file = "pillow-11.3.0-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:2465a69cf967b8b49ee1b96d76718cd98c4e925414ead59fdf75cf0fd07df673"}, - {file = "pillow-11.3.0-cp314-cp314-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:41742638139424703b4d01665b807c6468e23e699e8e90cffefe291c5832b027"}, - {file = "pillow-11.3.0-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:93efb0b4de7e340d99057415c749175e24c8864302369e05914682ba642e5d77"}, - {file = "pillow-11.3.0-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:7966e38dcd0fa11ca390aed7c6f20454443581d758242023cf36fcb319b1a874"}, - {file = "pillow-11.3.0-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:98a9afa7b9007c67ed84c57c9e0ad86a6000da96eaa638e4f8abe5b65ff83f0a"}, - {file = "pillow-11.3.0-cp314-cp314-win32.whl", hash = "sha256:02a723e6bf909e7cea0dac1b0e0310be9d7650cd66222a5f1c571455c0a45214"}, - {file = "pillow-11.3.0-cp314-cp314-win_amd64.whl", hash = "sha256:a418486160228f64dd9e9efcd132679b7a02a5f22c982c78b6fc7dab3fefb635"}, - {file = "pillow-11.3.0-cp314-cp314-win_arm64.whl", hash = "sha256:155658efb5e044669c08896c0c44231c5e9abcaadbc5cd3648df2f7c0b96b9a6"}, - {file = "pillow-11.3.0-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:59a03cdf019efbfeeed910bf79c7c93255c3d54bc45898ac2a4140071b02b4ae"}, - {file = "pillow-11.3.0-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:f8a5827f84d973d8636e9dc5764af4f0cf2318d26744b3d902931701b0d46653"}, - {file = "pillow-11.3.0-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:ee92f2fd10f4adc4b43d07ec5e779932b4eb3dbfbc34790ada5a6669bc095aa6"}, - {file = "pillow-11.3.0-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:c96d333dcf42d01f47b37e0979b6bd73ec91eae18614864622d9b87bbd5bbf36"}, - {file = "pillow-11.3.0-cp314-cp314t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:4c96f993ab8c98460cd0c001447bff6194403e8b1d7e149ade5f00594918128b"}, - {file = "pillow-11.3.0-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:41342b64afeba938edb034d122b2dda5db2139b9a4af999729ba8818e0056477"}, - {file = "pillow-11.3.0-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:068d9c39a2d1b358eb9f245ce7ab1b5c3246c7c8c7d9ba58cfa5b43146c06e50"}, - {file = "pillow-11.3.0-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:a1bc6ba083b145187f648b667e05a2534ecc4b9f2784c2cbe3089e44868f2b9b"}, - {file = "pillow-11.3.0-cp314-cp314t-win32.whl", hash = "sha256:118ca10c0d60b06d006be10a501fd6bbdfef559251ed31b794668ed569c87e12"}, - {file = "pillow-11.3.0-cp314-cp314t-win_amd64.whl", hash = "sha256:8924748b688aa210d79883357d102cd64690e56b923a186f35a82cbc10f997db"}, - {file = "pillow-11.3.0-cp314-cp314t-win_arm64.whl", hash = "sha256:79ea0d14d3ebad43ec77ad5272e6ff9bba5b679ef73375ea760261207fa8e0aa"}, - {file = "pillow-11.3.0-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:48d254f8a4c776de343051023eb61ffe818299eeac478da55227d96e241de53f"}, - {file = "pillow-11.3.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7aee118e30a4cf54fdd873bd3a29de51e29105ab11f9aad8c32123f58c8f8081"}, - {file = "pillow-11.3.0-cp39-cp39-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:23cff760a9049c502721bdb743a7cb3e03365fafcdfc2ef9784610714166e5a4"}, - {file = "pillow-11.3.0-cp39-cp39-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:6359a3bc43f57d5b375d1ad54a0074318a0844d11b76abccf478c37c986d3cfc"}, - {file = "pillow-11.3.0-cp39-cp39-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:092c80c76635f5ecb10f3f83d76716165c96f5229addbd1ec2bdbbda7d496e06"}, - {file = "pillow-11.3.0-cp39-cp39-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:cadc9e0ea0a2431124cde7e1697106471fc4c1da01530e679b2391c37d3fbb3a"}, - {file = "pillow-11.3.0-cp39-cp39-musllinux_1_2_aarch64.whl", hash = "sha256:6a418691000f2a418c9135a7cf0d797c1bb7d9a485e61fe8e7722845b95ef978"}, - {file = "pillow-11.3.0-cp39-cp39-musllinux_1_2_x86_64.whl", hash = "sha256:97afb3a00b65cc0804d1c7abddbf090a81eaac02768af58cbdcaaa0a931e0b6d"}, - {file = "pillow-11.3.0-cp39-cp39-win32.whl", hash = "sha256:ea944117a7974ae78059fcc1800e5d3295172bb97035c0c1d9345fca1419da71"}, - {file = "pillow-11.3.0-cp39-cp39-win_amd64.whl", hash = "sha256:e5c5858ad8ec655450a7c7df532e9842cf8df7cc349df7225c60d5d348c8aada"}, - {file = "pillow-11.3.0-cp39-cp39-win_arm64.whl", hash = "sha256:6abdbfd3aea42be05702a8dd98832329c167ee84400a1d1f61ab11437f1717eb"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-macosx_10_15_x86_64.whl", hash = "sha256:3cee80663f29e3843b68199b9d6f4f54bd1d4a6b59bdd91bceefc51238bcb967"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-macosx_11_0_arm64.whl", hash = "sha256:b5f56c3f344f2ccaf0dd875d3e180f631dc60a51b314295a3e681fe8cf851fbe"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:e67d793d180c9df62f1f40aee3accca4829d3794c95098887edc18af4b8b780c"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:d000f46e2917c705e9fb93a3606ee4a819d1e3aa7a9b442f6444f07e77cf5e25"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:527b37216b6ac3a12d7838dc3bd75208ec57c1c6d11ef01902266a5a0c14fc27"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:be5463ac478b623b9dd3937afd7fb7ab3d79dd290a28e2b6df292dc75063eb8a"}, - {file = "pillow-11.3.0-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:8dc70ca24c110503e16918a658b869019126ecfe03109b754c402daff12b3d9f"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-macosx_10_15_x86_64.whl", hash = "sha256:7c8ec7a017ad1bd562f93dbd8505763e688d388cde6e4a010ae1486916e713e6"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-macosx_11_0_arm64.whl", hash = "sha256:9ab6ae226de48019caa8074894544af5b53a117ccb9d3b3dcb2871464c829438"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:fe27fb049cdcca11f11a7bfda64043c37b30e6b91f10cb5bab275806c32f6ab3"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:465b9e8844e3c3519a983d58b80be3f668e2a7a5db97f2784e7079fbc9f9822c"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:5418b53c0d59b3824d05e029669efa023bbef0f3e92e75ec8428f3799487f361"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:504b6f59505f08ae014f724b6207ff6222662aab5cc9542577fb084ed0676ac7"}, - {file = "pillow-11.3.0-pp311-pypy311_pp73-win_amd64.whl", hash = "sha256:c84d689db21a1c397d001aa08241044aa2069e7587b398c8cc63020390b1c1b8"}, - {file = "pillow-11.3.0.tar.gz", hash = "sha256:3828ee7586cd0b2091b6209e5ad53e20d0649bbe87164a459d0676e035e8f523"}, + {file = "pillow-12.1.1-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:1f1625b72740fdda5d77b4def688eb8fd6490975d06b909fd19f13f391e077e0"}, + {file = "pillow-12.1.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:178aa072084bd88ec759052feca8e56cbb14a60b39322b99a049e58090479713"}, + {file = "pillow-12.1.1-cp310-cp310-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:b66e95d05ba806247aaa1561f080abc7975daf715c30780ff92a20e4ec546e1b"}, + {file = "pillow-12.1.1-cp310-cp310-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:89c7e895002bbe49cdc5426150377cbbc04767d7547ed145473f496dfa40408b"}, + {file = "pillow-12.1.1-cp310-cp310-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:3a5cbdcddad0af3da87cb16b60d23648bc3b51967eb07223e9fed77a82b457c4"}, + {file = "pillow-12.1.1-cp310-cp310-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:9f51079765661884a486727f0729d29054242f74b46186026582b4e4769918e4"}, + {file = "pillow-12.1.1-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:99c1506ea77c11531d75e3a412832a13a71c7ebc8192ab9e4b2e355555920e3e"}, + {file = "pillow-12.1.1-cp310-cp310-musllinux_1_2_x86_64.whl", hash = "sha256:36341d06738a9f66c8287cf8b876d24b18db9bd8740fa0672c74e259ad408cff"}, + {file = "pillow-12.1.1-cp310-cp310-win32.whl", hash = "sha256:6c52f062424c523d6c4db85518774cc3d50f5539dd6eed32b8f6229b26f24d40"}, + {file = "pillow-12.1.1-cp310-cp310-win_amd64.whl", hash = "sha256:c6008de247150668a705a6338156efb92334113421ceecf7438a12c9a12dab23"}, + {file = "pillow-12.1.1-cp310-cp310-win_arm64.whl", hash = "sha256:1a9b0ee305220b392e1124a764ee4265bd063e54a751a6b62eff69992f457fa9"}, + {file = "pillow-12.1.1-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:e879bb6cd5c73848ef3b2b48b8af9ff08c5b71ecda8048b7dd22d8a33f60be32"}, + {file = "pillow-12.1.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:365b10bb9417dd4498c0e3b128018c4a624dc11c7b97d8cc54effe3b096f4c38"}, + {file = "pillow-12.1.1-cp311-cp311-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:d4ce8e329c93845720cd2014659ca67eac35f6433fd3050393d85f3ecef0dad5"}, + {file = "pillow-12.1.1-cp311-cp311-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:fc354a04072b765eccf2204f588a7a532c9511e8b9c7f900e1b64e3e33487090"}, + {file = "pillow-12.1.1-cp311-cp311-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:7e7976bf1910a8116b523b9f9f58bf410f3e8aa330cd9a2bb2953f9266ab49af"}, + {file = "pillow-12.1.1-cp311-cp311-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:597bd9c8419bc7c6af5604e55847789b69123bbe25d65cc6ad3012b4f3c98d8b"}, + {file = "pillow-12.1.1-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:2c1fc0f2ca5f96a3c8407e41cca26a16e46b21060fe6d5b099d2cb01412222f5"}, + {file = "pillow-12.1.1-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:578510d88c6229d735855e1f278aa305270438d36a05031dfaae5067cc8eb04d"}, + {file = "pillow-12.1.1-cp311-cp311-win32.whl", hash = "sha256:7311c0a0dcadb89b36b7025dfd8326ecfa36964e29913074d47382706e516a7c"}, + {file = "pillow-12.1.1-cp311-cp311-win_amd64.whl", hash = "sha256:fbfa2a7c10cc2623f412753cddf391c7f971c52ca40a3f65dc5039b2939e8563"}, + {file = "pillow-12.1.1-cp311-cp311-win_arm64.whl", hash = "sha256:b81b5e3511211631b3f672a595e3221252c90af017e399056d0faabb9538aa80"}, + {file = "pillow-12.1.1-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:ab323b787d6e18b3d91a72fc99b1a2c28651e4358749842b8f8dfacd28ef2052"}, + {file = "pillow-12.1.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:adebb5bee0f0af4909c30db0d890c773d1a92ffe83da908e2e9e720f8edf3984"}, + {file = "pillow-12.1.1-cp312-cp312-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:bb66b7cc26f50977108790e2456b7921e773f23db5630261102233eb355a3b79"}, + {file = "pillow-12.1.1-cp312-cp312-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:aee2810642b2898bb187ced9b349e95d2a7272930796e022efaf12e99dccd293"}, + {file = "pillow-12.1.1-cp312-cp312-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:a0b1cd6232e2b618adcc54d9882e4e662a089d5768cd188f7c245b4c8c44a397"}, + {file = "pillow-12.1.1-cp312-cp312-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:7aac39bcf8d4770d089588a2e1dd111cbaa42df5a94be3114222057d68336bd0"}, + {file = "pillow-12.1.1-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:ab174cd7d29a62dd139c44bf74b698039328f45cb03b4596c43473a46656b2f3"}, + {file = "pillow-12.1.1-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:339ffdcb7cbeaa08221cd401d517d4b1fe7a9ed5d400e4a8039719238620ca35"}, + {file = "pillow-12.1.1-cp312-cp312-win32.whl", hash = "sha256:5d1f9575a12bed9e9eedd9a4972834b08c97a352bd17955ccdebfeca5913fa0a"}, + {file = "pillow-12.1.1-cp312-cp312-win_amd64.whl", hash = "sha256:21329ec8c96c6e979cd0dfd29406c40c1d52521a90544463057d2aaa937d66a6"}, + {file = "pillow-12.1.1-cp312-cp312-win_arm64.whl", hash = "sha256:af9a332e572978f0218686636610555ae3defd1633597be015ed50289a03c523"}, + {file = "pillow-12.1.1-cp313-cp313-ios_13_0_arm64_iphoneos.whl", hash = "sha256:d242e8ac078781f1de88bf823d70c1a9b3c7950a44cdf4b7c012e22ccbcd8e4e"}, + {file = "pillow-12.1.1-cp313-cp313-ios_13_0_arm64_iphonesimulator.whl", hash = "sha256:02f84dfad02693676692746df05b89cf25597560db2857363a208e393429f5e9"}, + {file = "pillow-12.1.1-cp313-cp313-ios_13_0_x86_64_iphonesimulator.whl", hash = "sha256:e65498daf4b583091ccbb2556c7000abf0f3349fcd57ef7adc9a84a394ed29f6"}, + {file = "pillow-12.1.1-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:6c6db3b84c87d48d0088943bf33440e0c42370b99b1c2a7989216f7b42eede60"}, + {file = "pillow-12.1.1-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:8b7e5304e34942bf62e15184219a7b5ad4ff7f3bb5cca4d984f37df1a0e1aee2"}, + {file = "pillow-12.1.1-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:18e5bddd742a44b7e6b1e773ab5db102bd7a94c32555ba656e76d319d19c3850"}, + {file = "pillow-12.1.1-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:fc44ef1f3de4f45b50ccf9136999d71abb99dca7706bc75d222ed350b9fd2289"}, + {file = "pillow-12.1.1-cp313-cp313-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:5a8eb7ed8d4198bccbd07058416eeec51686b498e784eda166395a23eb99138e"}, + {file = "pillow-12.1.1-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:47b94983da0c642de92ced1702c5b6c292a84bd3a8e1d1702ff923f183594717"}, + {file = "pillow-12.1.1-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:518a48c2aab7ce596d3bf79d0e275661b846e86e4d0e7dec34712c30fe07f02a"}, + {file = "pillow-12.1.1-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:a550ae29b95c6dc13cf69e2c9dc5747f814c54eeb2e32d683e5e93af56caa029"}, + {file = "pillow-12.1.1-cp313-cp313-win32.whl", hash = "sha256:a003d7422449f6d1e3a34e3dd4110c22148336918ddbfc6a32581cd54b2e0b2b"}, + {file = "pillow-12.1.1-cp313-cp313-win_amd64.whl", hash = "sha256:344cf1e3dab3be4b1fa08e449323d98a2a3f819ad20f4b22e77a0ede31f0faa1"}, + {file = "pillow-12.1.1-cp313-cp313-win_arm64.whl", hash = "sha256:5c0dd1636633e7e6a0afe7bf6a51a14992b7f8e60de5789018ebbdfae55b040a"}, + {file = "pillow-12.1.1-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:0330d233c1a0ead844fc097a7d16c0abff4c12e856c0b325f231820fee1f39da"}, + {file = "pillow-12.1.1-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:5dae5f21afb91322f2ff791895ddd8889e5e947ff59f71b46041c8ce6db790bc"}, + {file = "pillow-12.1.1-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:2e0c664be47252947d870ac0d327fea7e63985a08794758aa8af5b6cb6ec0c9c"}, + {file = "pillow-12.1.1-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:691ab2ac363b8217f7d31b3497108fb1f50faab2f75dfb03284ec2f217e87bf8"}, + {file = "pillow-12.1.1-cp313-cp313t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:e9e8064fb1cc019296958595f6db671fba95209e3ceb0c4734c9baf97de04b20"}, + {file = "pillow-12.1.1-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:472a8d7ded663e6162dafdf20015c486a7009483ca671cece7a9279b512fcb13"}, + {file = "pillow-12.1.1-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:89b54027a766529136a06cfebeecb3a04900397a3590fd252160b888479517bf"}, + {file = "pillow-12.1.1-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:86172b0831b82ce4f7877f280055892b31179e1576aa00d0df3bb1bbf8c3e524"}, + {file = "pillow-12.1.1-cp313-cp313t-win32.whl", hash = "sha256:44ce27545b6efcf0fdbdceb31c9a5bdea9333e664cda58a7e674bb74608b3986"}, + {file = "pillow-12.1.1-cp313-cp313t-win_amd64.whl", hash = "sha256:a285e3eb7a5a45a2ff504e31f4a8d1b12ef62e84e5411c6804a42197c1cf586c"}, + {file = "pillow-12.1.1-cp313-cp313t-win_arm64.whl", hash = "sha256:cc7d296b5ea4d29e6570dabeaed58d31c3fea35a633a69679fb03d7664f43fb3"}, + {file = "pillow-12.1.1-cp314-cp314-ios_13_0_arm64_iphoneos.whl", hash = "sha256:417423db963cb4be8bac3fc1204fe61610f6abeed1580a7a2cbb2fbda20f12af"}, + {file = "pillow-12.1.1-cp314-cp314-ios_13_0_arm64_iphonesimulator.whl", hash = "sha256:b957b71c6b2387610f556a7eb0828afbe40b4a98036fc0d2acfa5a44a0c2036f"}, + {file = "pillow-12.1.1-cp314-cp314-ios_13_0_x86_64_iphonesimulator.whl", hash = "sha256:097690ba1f2efdeb165a20469d59d8bb03c55fb6621eb2041a060ae8ea3e9642"}, + {file = "pillow-12.1.1-cp314-cp314-macosx_10_15_x86_64.whl", hash = "sha256:2815a87ab27848db0321fb78c7f0b2c8649dee134b7f2b80c6a45c6831d75ccd"}, + {file = "pillow-12.1.1-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:f7ed2c6543bad5a7d5530eb9e78c53132f93dfa44a28492db88b41cdab885202"}, + {file = "pillow-12.1.1-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:652a2c9ccfb556235b2b501a3a7cf3742148cd22e04b5625c5fe057ea3e3191f"}, + {file = "pillow-12.1.1-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:d6e4571eedf43af33d0fc233a382a76e849badbccdf1ac438841308652a08e1f"}, + {file = "pillow-12.1.1-cp314-cp314-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:b574c51cf7d5d62e9be37ba446224b59a2da26dc4c1bb2ecbe936a4fb1a7cb7f"}, + {file = "pillow-12.1.1-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:a37691702ed687799de29a518d63d4682d9016932db66d4e90c345831b02fb4e"}, + {file = "pillow-12.1.1-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:f95c00d5d6700b2b890479664a06e754974848afaae5e21beb4d83c106923fd0"}, + {file = "pillow-12.1.1-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:559b38da23606e68681337ad74622c4dbba02254fc9cb4488a305dd5975c7eeb"}, + {file = "pillow-12.1.1-cp314-cp314-win32.whl", hash = "sha256:03edcc34d688572014ff223c125a3f77fb08091e4607e7745002fc214070b35f"}, + {file = "pillow-12.1.1-cp314-cp314-win_amd64.whl", hash = "sha256:50480dcd74fa63b8e78235957d302d98d98d82ccbfac4c7e12108ba9ecbdba15"}, + {file = "pillow-12.1.1-cp314-cp314-win_arm64.whl", hash = "sha256:5cb1785d97b0c3d1d1a16bc1d710c4a0049daefc4935f3a8f31f827f4d3d2e7f"}, + {file = "pillow-12.1.1-cp314-cp314t-macosx_10_15_x86_64.whl", hash = "sha256:1f90cff8aa76835cba5769f0b3121a22bd4eb9e6884cfe338216e557a9a548b8"}, + {file = "pillow-12.1.1-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:1f1be78ce9466a7ee64bfda57bdba0f7cc499d9794d518b854816c41bf0aa4e9"}, + {file = "pillow-12.1.1-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:42fc1f4677106188ad9a55562bbade416f8b55456f522430fadab3cef7cd4e60"}, + {file = "pillow-12.1.1-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:98edb152429ab62a1818039744d8fbb3ccab98a7c29fc3d5fcef158f3f1f68b7"}, + {file = "pillow-12.1.1-cp314-cp314t-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:d470ab1178551dd17fdba0fef463359c41aaa613cdcd7ff8373f54be629f9f8f"}, + {file = "pillow-12.1.1-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:6408a7b064595afcab0a49393a413732a35788f2a5092fdc6266952ed67de586"}, + {file = "pillow-12.1.1-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:5d8c41325b382c07799a3682c1c258469ea2ff97103c53717b7893862d0c98ce"}, + {file = "pillow-12.1.1-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:c7697918b5be27424e9ce568193efd13d925c4481dd364e43f5dff72d33e10f8"}, + {file = "pillow-12.1.1-cp314-cp314t-win32.whl", hash = "sha256:d2912fd8114fc5545aa3a4b5576512f64c55a03f3ebcca4c10194d593d43ea36"}, + {file = "pillow-12.1.1-cp314-cp314t-win_amd64.whl", hash = "sha256:4ceb838d4bd9dab43e06c363cab2eebf63846d6a4aeaea283bbdfd8f1a8ed58b"}, + {file = "pillow-12.1.1-cp314-cp314t-win_arm64.whl", hash = "sha256:7b03048319bfc6170e93bd60728a1af51d3dd7704935feb228c4d4faab35d334"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-macosx_10_15_x86_64.whl", hash = "sha256:600fd103672b925fe62ed08e0d874ea34d692474df6f4bf7ebe148b30f89f39f"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-macosx_11_0_arm64.whl", hash = "sha256:665e1b916b043cef294bc54d47bf02d87e13f769bc4bc5fa225a24b3a6c5aca9"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:495c302af3aad1ca67420ddd5c7bd480c8867ad173528767d906428057a11f0e"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:8fd420ef0c52c88b5a035a0886f367748c72147b2b8f384c9d12656678dfdfa9"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-manylinux_2_27_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:f975aa7ef9684ce7e2c18a3aa8f8e2106ce1e46b94ab713d156b2898811651d3"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:8089c852a56c2966cf18835db62d9b34fef7ba74c726ad943928d494fa7f4735"}, + {file = "pillow-12.1.1-pp311-pypy311_pp73-win_amd64.whl", hash = "sha256:cb9bb857b2d057c6dfc72ac5f3b44836924ba15721882ef103cecb40d002d80e"}, + {file = "pillow-12.1.1.tar.gz", hash = "sha256:9ad8fa5937ab05218e2b6a4cff30295ad35afd2f83ac592e68c0d871bb0fdbc4"}, ] [package.extras] docs = ["furo", "olefile", "sphinx (>=8.2)", "sphinx-autobuild", "sphinx-copybutton", "sphinx-inline-tabs", "sphinxext-opengraph"] fpx = ["olefile"] mic = ["olefile"] -test-arrow = ["pyarrow"] -tests = ["check-manifest", "coverage (>=7.4.2)", "defusedxml", "markdown2", "olefile", "packaging", "pyroma", "pytest", "pytest-cov", "pytest-timeout", "pytest-xdist", "trove-classifiers (>=2024.10.12)"] -typing = ["typing-extensions ; python_version < \"3.10\""] +test-arrow = ["arro3-compute", "arro3-core", "nanoarrow", "pyarrow"] +tests = ["check-manifest", "coverage (>=7.4.2)", "defusedxml", "markdown2", "olefile", "packaging", "pyroma (>=5)", "pytest", "pytest-cov", "pytest-timeout", "pytest-xdist", "trove-classifiers (>=2024.10.12)"] xmp = ["defusedxml"] [[package]] @@ -5237,9 +5220,10 @@ diagrams = ["jinja2", "railroad-diagrams"] name = "pypdf" version = "6.6.2" description = "A pure-python PDF library capable of splitting, merging, cropping, and transforming PDF files" -optional = false +optional = true python-versions = ">=3.9" groups = ["main"] +markers = "extra == \"sandbox\"" files = [ {file = "pypdf-6.6.2-py3-none-any.whl", hash = "sha256:44c0c9811cfb3b83b28f1c3d054531d5b8b81abaedee0d8cb403650d023832ba"}, {file = "pypdf-6.6.2.tar.gz", hash = "sha256:0a3ea3b3303982333404e22d8f75d7b3144f9cf4b2970b96856391a516f9f016"}, From 846f8c02b4a169492bee92b217446d9aca7b6422 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 11 Feb 2026 01:53:46 +0000 Subject: [PATCH 02/14] chore(deps): bump cryptography from 44.0.1 to 46.0.5 Bumps [cryptography](https://github.com/pyca/cryptography) from 44.0.1 to 46.0.5. - [Changelog](https://github.com/pyca/cryptography/blob/main/CHANGELOG.rst) - [Commits](https://github.com/pyca/cryptography/compare/44.0.1...46.0.5) --- updated-dependencies: - dependency-name: cryptography dependency-version: 46.0.5 dependency-type: indirect ... Signed-off-by: dependabot[bot] --- poetry.lock | 94 +++++++++++++++++++++++++++++++---------------------- 1 file changed, 56 insertions(+), 38 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9cbdde7..43b5341 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1104,56 +1104,74 @@ pytz = ">2021.1" [[package]] name = "cryptography" -version = "44.0.1" +version = "46.0.5" description = "cryptography is a package which provides cryptographic recipes and primitives to Python developers." optional = false -python-versions = "!=3.9.0,!=3.9.1,>=3.7" +python-versions = "!=3.9.0,!=3.9.1,>=3.8" groups = ["main"] files = [ - {file = "cryptography-44.0.1-cp37-abi3-macosx_10_9_universal2.whl", hash = "sha256:bf688f615c29bfe9dfc44312ca470989279f0e94bb9f631f85e3459af8efc009"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dd7c7e2d71d908dc0f8d2027e1604102140d84b155e658c20e8ad1304317691f"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:887143b9ff6bad2b7570da75a7fe8bbf5f65276365ac259a5d2d5147a73775f2"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:322eb03ecc62784536bc173f1483e76747aafeb69c8728df48537eb431cd1911"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_28_armv7l.manylinux_2_31_armv7l.whl", hash = "sha256:21377472ca4ada2906bc313168c9dc7b1d7ca417b63c1c3011d0c74b7de9ae69"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:df978682c1504fc93b3209de21aeabf2375cb1571d4e61907b3e7a2540e83026"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_34_aarch64.whl", hash = "sha256:eb3889330f2a4a148abead555399ec9a32b13b7c8ba969b72d8e500eb7ef84cd"}, - {file = "cryptography-44.0.1-cp37-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:8e6a85a93d0642bd774460a86513c5d9d80b5c002ca9693e63f6e540f1815ed0"}, - {file = "cryptography-44.0.1-cp37-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:6f76fdd6fd048576a04c5210d53aa04ca34d2ed63336d4abd306d0cbe298fddf"}, - {file = "cryptography-44.0.1-cp37-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:6c8acf6f3d1f47acb2248ec3ea261171a671f3d9428e34ad0357148d492c7864"}, - {file = "cryptography-44.0.1-cp37-abi3-win32.whl", hash = "sha256:24979e9f2040c953a94bf3c6782e67795a4c260734e5264dceea65c8f4bae64a"}, - {file = "cryptography-44.0.1-cp37-abi3-win_amd64.whl", hash = "sha256:fd0ee90072861e276b0ff08bd627abec29e32a53b2be44e41dbcdf87cbee2b00"}, - {file = "cryptography-44.0.1-cp39-abi3-macosx_10_9_universal2.whl", hash = "sha256:a2d8a7045e1ab9b9f803f0d9531ead85f90c5f2859e653b61497228b18452008"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b8272f257cf1cbd3f2e120f14c68bff2b6bdfcc157fafdee84a1b795efd72862"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1e8d181e90a777b63f3f0caa836844a1182f1f265687fac2115fcf245f5fbec3"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:436df4f203482f41aad60ed1813811ac4ab102765ecae7a2bbb1dbb66dcff5a7"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_28_armv7l.manylinux_2_31_armv7l.whl", hash = "sha256:4f422e8c6a28cf8b7f883eb790695d6d45b0c385a2583073f3cec434cc705e1a"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:72198e2b5925155497a5a3e8c216c7fb3e64c16ccee11f0e7da272fa93b35c4c"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_34_aarch64.whl", hash = "sha256:2a46a89ad3e6176223b632056f321bc7de36b9f9b93b2cc1cccf935a3849dc62"}, - {file = "cryptography-44.0.1-cp39-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:53f23339864b617a3dfc2b0ac8d5c432625c80014c25caac9082314e9de56f41"}, - {file = "cryptography-44.0.1-cp39-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:888fcc3fce0c888785a4876ca55f9f43787f4c5c1cc1e2e0da71ad481ff82c5b"}, - {file = "cryptography-44.0.1-cp39-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:00918d859aa4e57db8299607086f793fa7813ae2ff5a4637e318a25ef82730f7"}, - {file = "cryptography-44.0.1-cp39-abi3-win32.whl", hash = "sha256:9b336599e2cb77b1008cb2ac264b290803ec5e8e89d618a5e978ff5eb6f715d9"}, - {file = "cryptography-44.0.1-cp39-abi3-win_amd64.whl", hash = "sha256:e403f7f766ded778ecdb790da786b418a9f2394f36e8cc8b796cc056ab05f44f"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-macosx_10_9_x86_64.whl", hash = "sha256:1f9a92144fa0c877117e9748c74501bea842f93d21ee00b0cf922846d9d0b183"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:610a83540765a8d8ce0f351ce42e26e53e1f774a6efb71eb1b41eb01d01c3d12"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:5fed5cd6102bb4eb843e3315d2bf25fede494509bddadb81e03a859c1bc17b83"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-manylinux_2_34_aarch64.whl", hash = "sha256:f4daefc971c2d1f82f03097dc6f216744a6cd2ac0f04c68fb935ea2ba2a0d420"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-manylinux_2_34_x86_64.whl", hash = "sha256:94f99f2b943b354a5b6307d7e8d19f5c423a794462bde2bf310c770ba052b1c4"}, - {file = "cryptography-44.0.1-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:d9c5b9f698a83c8bd71e0f4d3f9f839ef244798e5ffe96febfa9714717db7af7"}, - {file = "cryptography-44.0.1.tar.gz", hash = "sha256:f51f5705ab27898afda1aaa430f34ad90dc117421057782022edf0600bec5f14"}, + {file = "cryptography-46.0.5-cp311-abi3-macosx_10_9_universal2.whl", hash = "sha256:351695ada9ea9618b3500b490ad54c739860883df6c1f555e088eaf25b1bbaad"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:c18ff11e86df2e28854939acde2d003f7984f721eba450b56a200ad90eeb0e6b"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:4d7e3d356b8cd4ea5aff04f129d5f66ebdc7b6f8eae802b93739ed520c47c79b"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:50bfb6925eff619c9c023b967d5b77a54e04256c4281b0e21336a130cd7fc263"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_28_ppc64le.whl", hash = "sha256:803812e111e75d1aa73690d2facc295eaefd4439be1023fefc4995eaea2af90d"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:3ee190460e2fbe447175cda91b88b84ae8322a104fc27766ad09428754a618ed"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_31_armv7l.whl", hash = "sha256:f145bba11b878005c496e93e257c1e88f154d278d2638e6450d17e0f31e558d2"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_34_aarch64.whl", hash = "sha256:e9251e3be159d1020c4030bd2e5f84d6a43fe54b6c19c12f51cde9542a2817b2"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_34_ppc64le.whl", hash = "sha256:47fb8a66058b80e509c47118ef8a75d14c455e81ac369050f20ba0d23e77fee0"}, + {file = "cryptography-46.0.5-cp311-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:4c3341037c136030cb46e4b1e17b7418ea4cbd9dd207e4a6f3b2b24e0d4ac731"}, + {file = "cryptography-46.0.5-cp311-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:890bcb4abd5a2d3f852196437129eb3667d62630333aacc13dfd470fad3aaa82"}, + {file = "cryptography-46.0.5-cp311-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:80a8d7bfdf38f87ca30a5391c0c9ce4ed2926918e017c29ddf643d0ed2778ea1"}, + {file = "cryptography-46.0.5-cp311-abi3-win32.whl", hash = "sha256:60ee7e19e95104d4c03871d7d7dfb3d22ef8a9b9c6778c94e1c8fcc8365afd48"}, + {file = "cryptography-46.0.5-cp311-abi3-win_amd64.whl", hash = "sha256:38946c54b16c885c72c4f59846be9743d699eee2b69b6988e0a00a01f46a61a4"}, + {file = "cryptography-46.0.5-cp314-cp314t-macosx_10_9_universal2.whl", hash = "sha256:94a76daa32eb78d61339aff7952ea819b1734b46f73646a07decb40e5b3448e2"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:5be7bf2fb40769e05739dd0046e7b26f9d4670badc7b032d6ce4db64dddc0678"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:fe346b143ff9685e40192a4960938545c699054ba11d4f9029f94751e3f71d87"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_28_aarch64.whl", hash = "sha256:c69fd885df7d089548a42d5ec05be26050ebcd2283d89b3d30676eb32ff87dee"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_28_ppc64le.whl", hash = "sha256:8293f3dea7fc929ef7240796ba231413afa7b68ce38fd21da2995549f5961981"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_28_x86_64.whl", hash = "sha256:1abfdb89b41c3be0365328a410baa9df3ff8a9110fb75e7b52e66803ddabc9a9"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_31_armv7l.whl", hash = "sha256:d66e421495fdb797610a08f43b05269e0a5ea7f5e652a89bfd5a7d3c1dee3648"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_34_aarch64.whl", hash = "sha256:4e817a8920bfbcff8940ecfd60f23d01836408242b30f1a708d93198393a80b4"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_34_ppc64le.whl", hash = "sha256:68f68d13f2e1cb95163fa3b4db4bf9a159a418f5f6e7242564fc75fcae667fd0"}, + {file = "cryptography-46.0.5-cp314-cp314t-manylinux_2_34_x86_64.whl", hash = "sha256:a3d1fae9863299076f05cb8a778c467578262fae09f9dc0ee9b12eb4268ce663"}, + {file = "cryptography-46.0.5-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:c4143987a42a2397f2fc3b4d7e3a7d313fbe684f67ff443999e803dd75a76826"}, + {file = "cryptography-46.0.5-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:7d731d4b107030987fd61a7f8ab512b25b53cef8f233a97379ede116f30eb67d"}, + {file = "cryptography-46.0.5-cp314-cp314t-win32.whl", hash = "sha256:c3bcce8521d785d510b2aad26ae2c966092b7daa8f45dd8f44734a104dc0bc1a"}, + {file = "cryptography-46.0.5-cp314-cp314t-win_amd64.whl", hash = "sha256:4d8ae8659ab18c65ced284993c2265910f6c9e650189d4e3f68445ef82a810e4"}, + {file = "cryptography-46.0.5-cp38-abi3-macosx_10_9_universal2.whl", hash = "sha256:4108d4c09fbbf2789d0c926eb4152ae1760d5a2d97612b92d508d96c861e4d31"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:7d1f30a86d2757199cb2d56e48cce14deddf1f9c95f1ef1b64ee91ea43fe2e18"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:039917b0dc418bb9f6edce8a906572d69e74bd330b0b3fea4f79dab7f8ddd235"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:ba2a27ff02f48193fc4daeadf8ad2590516fa3d0adeeb34336b96f7fa64c1e3a"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_28_ppc64le.whl", hash = "sha256:61aa400dce22cb001a98014f647dc21cda08f7915ceb95df0c9eaf84b4b6af76"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:3ce58ba46e1bc2aac4f7d9290223cead56743fa6ab94a5d53292ffaac6a91614"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_31_armv7l.whl", hash = "sha256:420d0e909050490d04359e7fdb5ed7e667ca5c3c402b809ae2563d7e66a92229"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_34_aarch64.whl", hash = "sha256:582f5fcd2afa31622f317f80426a027f30dc792e9c80ffee87b993200ea115f1"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_34_ppc64le.whl", hash = "sha256:bfd56bb4b37ed4f330b82402f6f435845a5f5648edf1ad497da51a8452d5d62d"}, + {file = "cryptography-46.0.5-cp38-abi3-manylinux_2_34_x86_64.whl", hash = "sha256:a3d507bb6a513ca96ba84443226af944b0f7f47dcc9a399d110cd6146481d24c"}, + {file = "cryptography-46.0.5-cp38-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:9f16fbdf4da055efb21c22d81b89f155f02ba420558db21288b3d0035bafd5f4"}, + {file = "cryptography-46.0.5-cp38-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:ced80795227d70549a411a4ab66e8ce307899fad2220ce5ab2f296e687eacde9"}, + {file = "cryptography-46.0.5-cp38-abi3-win32.whl", hash = "sha256:02f547fce831f5096c9a567fd41bc12ca8f11df260959ecc7c3202555cc47a72"}, + {file = "cryptography-46.0.5-cp38-abi3-win_amd64.whl", hash = "sha256:556e106ee01aa13484ce9b0239bca667be5004efb0aabbed28d353df86445595"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-macosx_11_0_arm64.whl", hash = "sha256:3b4995dc971c9fb83c25aa44cf45f02ba86f71ee600d81091c2f0cbae116b06c"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:bc84e875994c3b445871ea7181d424588171efec3e185dced958dad9e001950a"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:2ae6971afd6246710480e3f15824ed3029a60fc16991db250034efd0b9fb4356"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-manylinux_2_34_aarch64.whl", hash = "sha256:d861ee9e76ace6cf36a6a89b959ec08e7bc2493ee39d07ffe5acb23ef46d27da"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-manylinux_2_34_x86_64.whl", hash = "sha256:2b7a67c9cd56372f3249b39699f2ad479f6991e62ea15800973b956f4b73e257"}, + {file = "cryptography-46.0.5-pp311-pypy311_pp73-win_amd64.whl", hash = "sha256:8456928655f856c6e1533ff59d5be76578a7157224dbd9ce6872f25055ab9ab7"}, + {file = "cryptography-46.0.5.tar.gz", hash = "sha256:abace499247268e3757271b2f1e244b36b06f8515cf27c4d49468fc9eb16e93d"}, ] [package.dependencies] -cffi = {version = ">=1.12", markers = "platform_python_implementation != \"PyPy\""} +cffi = {version = ">=2.0.0", markers = "python_full_version >= \"3.9.0\" and platform_python_implementation != \"PyPy\""} [package.extras] -docs = ["sphinx (>=5.3.0)", "sphinx-rtd-theme (>=3.0.0) ; python_version >= \"3.8\""] +docs = ["sphinx (>=5.3.0)", "sphinx-inline-tabs", "sphinx-rtd-theme (>=3.0.0)"] docstest = ["pyenchant (>=3)", "readme-renderer (>=30.0)", "sphinxcontrib-spelling (>=7.3.1)"] -nox = ["nox (>=2024.4.15)", "nox[uv] (>=2024.3.2) ; python_version >= \"3.8\""] -pep8test = ["check-sdist ; python_version >= \"3.8\"", "click (>=8.0.1)", "mypy (>=1.4)", "ruff (>=0.3.6)"] +nox = ["nox[uv] (>=2024.4.15)"] +pep8test = ["check-sdist", "click (>=8.0.1)", "mypy (>=1.14)", "ruff (>=0.11.11)"] sdist = ["build (>=1.0.0)"] ssh = ["bcrypt (>=3.1.5)"] -test = ["certifi (>=2024)", "cryptography-vectors (==44.0.1)", "pretend (>=0.7)", "pytest (>=7.4.0)", "pytest-benchmark (>=4.0)", "pytest-cov (>=2.10.1)", "pytest-xdist (>=3.5.0)"] +test = ["certifi (>=2024)", "cryptography-vectors (==46.0.5)", "pretend (>=0.7)", "pytest (>=7.4.0)", "pytest-benchmark (>=4.0)", "pytest-cov (>=2.10.1)", "pytest-xdist (>=3.5.0)"] test-randomorder = ["pytest-randomly"] [[package]] From 2b94633212995bd209241f5af7d009dc3df7ee3c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 1 Feb 2026 07:19:33 +0000 Subject: [PATCH 03/14] chore(deps): bump protobuf from 6.33.4 to 6.33.5 Bumps [protobuf](https://github.com/protocolbuffers/protobuf) from 6.33.4 to 6.33.5. - [Release notes](https://github.com/protocolbuffers/protobuf/releases) - [Commits](https://github.com/protocolbuffers/protobuf/commits) --- updated-dependencies: - dependency-name: protobuf dependency-version: 6.33.5 dependency-type: indirect ... Signed-off-by: dependabot[bot] --- poetry.lock | 25 ++++++++++++------------- 1 file changed, 12 insertions(+), 13 deletions(-) diff --git a/poetry.lock b/poetry.lock index 43b5341..37a393c 100644 --- a/poetry.lock +++ b/poetry.lock @@ -4742,23 +4742,22 @@ testing = ["google-api-core (>=1.31.5)"] [[package]] name = "protobuf" -version = "6.33.4" +version = "6.33.5" description = "" -optional = true +optional = false python-versions = ">=3.9" groups = ["main"] -markers = "extra == \"vertex\"" files = [ - {file = "protobuf-6.33.4-cp310-abi3-win32.whl", hash = "sha256:918966612c8232fc6c24c78e1cd89784307f5814ad7506c308ee3cf86662850d"}, - {file = "protobuf-6.33.4-cp310-abi3-win_amd64.whl", hash = "sha256:8f11ffae31ec67fc2554c2ef891dcb561dae9a2a3ed941f9e134c2db06657dbc"}, - {file = "protobuf-6.33.4-cp39-abi3-macosx_10_9_universal2.whl", hash = "sha256:2fe67f6c014c84f655ee06f6f66213f9254b3a8b6bda6cda0ccd4232c73c06f0"}, - {file = "protobuf-6.33.4-cp39-abi3-manylinux2014_aarch64.whl", hash = "sha256:757c978f82e74d75cba88eddec479df9b99a42b31193313b75e492c06a51764e"}, - {file = "protobuf-6.33.4-cp39-abi3-manylinux2014_s390x.whl", hash = "sha256:c7c64f259c618f0bef7bee042075e390debbf9682334be2b67408ec7c1c09ee6"}, - {file = "protobuf-6.33.4-cp39-abi3-manylinux2014_x86_64.whl", hash = "sha256:3df850c2f8db9934de4cf8f9152f8dc2558f49f298f37f90c517e8e5c84c30e9"}, - {file = "protobuf-6.33.4-cp39-cp39-win32.whl", hash = "sha256:955478a89559fa4568f5a81dce77260eabc5c686f9e8366219ebd30debf06aa6"}, - {file = "protobuf-6.33.4-cp39-cp39-win_amd64.whl", hash = "sha256:0f12ddbf96912690c3582f9dffb55530ef32015ad8e678cd494312bd78314c4f"}, - {file = "protobuf-6.33.4-py3-none-any.whl", hash = "sha256:1fe3730068fcf2e595816a6c34fe66eeedd37d51d0400b72fabc848811fdc1bc"}, - {file = "protobuf-6.33.4.tar.gz", hash = "sha256:dc2e61bca3b10470c1912d166fe0af67bfc20eb55971dcef8dfa48ce14f0ed91"}, + {file = "protobuf-6.33.5-cp310-abi3-win32.whl", hash = "sha256:d71b040839446bac0f4d162e758bea99c8251161dae9d0983a3b88dee345153b"}, + {file = "protobuf-6.33.5-cp310-abi3-win_amd64.whl", hash = "sha256:3093804752167bcab3998bec9f1048baae6e29505adaf1afd14a37bddede533c"}, + {file = "protobuf-6.33.5-cp39-abi3-macosx_10_9_universal2.whl", hash = "sha256:a5cb85982d95d906df1e2210e58f8e4f1e3cdc088e52c921a041f9c9a0386de5"}, + {file = "protobuf-6.33.5-cp39-abi3-manylinux2014_aarch64.whl", hash = "sha256:9b71e0281f36f179d00cbcb119cb19dec4d14a81393e5ea220f64b286173e190"}, + {file = "protobuf-6.33.5-cp39-abi3-manylinux2014_s390x.whl", hash = "sha256:8afa18e1d6d20af15b417e728e9f60f3aa108ee76f23c3b2c07a2c3b546d3afd"}, + {file = "protobuf-6.33.5-cp39-abi3-manylinux2014_x86_64.whl", hash = "sha256:cbf16ba3350fb7b889fca858fb215967792dc125b35c7976ca4818bee3521cf0"}, + {file = "protobuf-6.33.5-cp39-cp39-win32.whl", hash = "sha256:a3157e62729aafb8df6da2c03aa5c0937c7266c626ce11a278b6eb7963c4e37c"}, + {file = "protobuf-6.33.5-cp39-cp39-win_amd64.whl", hash = "sha256:8f04fa32763dcdb4973d537d6b54e615cc61108c7cb38fe59310c3192d29510a"}, + {file = "protobuf-6.33.5-py3-none-any.whl", hash = "sha256:69915a973dd0f60f31a08b8318b73eab2bd6a392c79184b3612226b0a3f8ec02"}, + {file = "protobuf-6.33.5.tar.gz", hash = "sha256:6ddcac2a081f8b7b9642c09406bc6a4290128fce5f471cddd165960bb9119e5c"}, ] [[package]] From d6e9b3b7cfdcf29281b4ff9310f75964bccc25aa Mon Sep 17 00:00:00 2001 From: 0xallam Date: Sun, 15 Feb 2026 16:40:26 -0800 Subject: [PATCH 04/14] feat: Redesign vulnerability reporting with nested XML code locations and CVSS Replace 12 flat parameters (code_file, code_before, code_after, code_diff, and 8 CVSS fields) with structured nested XML fields: code_locations with co-located fix_before/fix_after per location, cvss_breakdown, and cwe. This enables multi-file vulnerability locations, per-location fixes with precise line numbers, data flow representation (source/sink), CWE classification, and compatibility with GitHub/GitLab PR review APIs. --- .../tool_components/reporting_renderer.py | 107 ++++++---- strix/interface/tui.py | 30 ++- strix/interface/utils.py | 52 ++--- strix/telemetry/tracer.py | 53 +++-- strix/tools/reporting/reporting_actions.py | 194 +++++++++++++----- .../reporting/reporting_actions_schema.xml | 178 ++++++++++------ 6 files changed, 404 insertions(+), 210 deletions(-) diff --git a/strix/interface/tool_components/reporting_renderer.py b/strix/interface/tool_components/reporting_renderer.py index 98cc85d..898157d 100644 --- a/strix/interface/tool_components/reporting_renderer.py +++ b/strix/interface/tool_components/reporting_renderer.py @@ -6,6 +6,11 @@ from pygments.styles import get_style_by_name from rich.text import Text from textual.widgets import Static +from strix.tools.reporting.reporting_actions import ( + parse_code_locations_xml, + parse_cvss_xml, +) + from .base_renderer import BaseToolRenderer from .registry import register_tool_renderer @@ -17,6 +22,13 @@ def _get_style_colors() -> dict[Any, str]: FIELD_STYLE = "bold #4ade80" +DIM_STYLE = "dim" +FILE_STYLE = "bold #60a5fa" +LINE_STYLE = "#facc15" +LABEL_STYLE = "italic #a1a1aa" +CODE_STYLE = "#e2e8f0" +BEFORE_STYLE = "#ef4444" +AFTER_STYLE = "#22c55e" @register_tool_renderer @@ -80,18 +92,13 @@ class CreateVulnerabilityReportRenderer(BaseToolRenderer): poc_script_code = args.get("poc_script_code", "") remediation_steps = args.get("remediation_steps", "") - attack_vector = args.get("attack_vector", "") - attack_complexity = args.get("attack_complexity", "") - privileges_required = args.get("privileges_required", "") - user_interaction = args.get("user_interaction", "") - scope = args.get("scope", "") - confidentiality = args.get("confidentiality", "") - integrity = args.get("integrity", "") - availability = args.get("availability", "") + cvss_breakdown_xml = args.get("cvss_breakdown", "") + code_locations_xml = args.get("code_locations", "") endpoint = args.get("endpoint", "") method = args.get("method", "") cve = args.get("cve", "") + cwe = args.get("cwe", "") severity = "" cvss_score = None @@ -140,38 +147,30 @@ class CreateVulnerabilityReportRenderer(BaseToolRenderer): text.append("CVE: ", style=FIELD_STYLE) text.append(cve) - if any( - [ - attack_vector, - attack_complexity, - privileges_required, - user_interaction, - scope, - confidentiality, - integrity, - availability, - ] - ): + if cwe: + text.append("\n\n") + text.append("CWE: ", style=FIELD_STYLE) + text.append(cwe) + + parsed_cvss = parse_cvss_xml(cvss_breakdown_xml) if cvss_breakdown_xml else None + if parsed_cvss: text.append("\n\n") cvss_parts = [] - if attack_vector: - cvss_parts.append(f"AV:{attack_vector}") - if attack_complexity: - cvss_parts.append(f"AC:{attack_complexity}") - if privileges_required: - cvss_parts.append(f"PR:{privileges_required}") - if user_interaction: - cvss_parts.append(f"UI:{user_interaction}") - if scope: - cvss_parts.append(f"S:{scope}") - if confidentiality: - cvss_parts.append(f"C:{confidentiality}") - if integrity: - cvss_parts.append(f"I:{integrity}") - if availability: - cvss_parts.append(f"A:{availability}") + for key, prefix in [ + ("attack_vector", "AV"), + ("attack_complexity", "AC"), + ("privileges_required", "PR"), + ("user_interaction", "UI"), + ("scope", "S"), + ("confidentiality", "C"), + ("integrity", "I"), + ("availability", "A"), + ]: + val = parsed_cvss.get(key) + if val: + cvss_parts.append(f"{prefix}:{val}") text.append("CVSS Vector: ", style=FIELD_STYLE) - text.append("/".join(cvss_parts), style="dim") + text.append("/".join(cvss_parts), style=DIM_STYLE) if description: text.append("\n\n") @@ -191,6 +190,40 @@ class CreateVulnerabilityReportRenderer(BaseToolRenderer): text.append("\n") text.append(technical_analysis) + parsed_locations = ( + parse_code_locations_xml(code_locations_xml) if code_locations_xml else None + ) + if parsed_locations: + text.append("\n\n") + text.append("Code Locations", style=FIELD_STYLE) + for i, loc in enumerate(parsed_locations): + text.append("\n\n") + text.append(f" Location {i + 1}: ", style=DIM_STYLE) + text.append(loc.get("file", "unknown"), style=FILE_STYLE) + start = loc.get("start_line") + end = loc.get("end_line") + if start is not None: + if end and end != start: + text.append(f":{start}-{end}", style=LINE_STYLE) + else: + text.append(f":{start}", style=LINE_STYLE) + if loc.get("label"): + text.append(f"\n {loc['label']}", style=LABEL_STYLE) + if loc.get("snippet"): + text.append("\n ") + text.append(loc["snippet"], style=CODE_STYLE) + if loc.get("fix_before") or loc.get("fix_after"): + text.append("\n ") + text.append("Fix:", style=DIM_STYLE) + if loc.get("fix_before"): + text.append("\n ") + text.append("- ", style=BEFORE_STYLE) + text.append(loc["fix_before"], style=BEFORE_STYLE) + if loc.get("fix_after"): + text.append("\n ") + text.append("+ ", style=AFTER_STYLE) + text.append(loc["fix_after"], style=AFTER_STYLE) + if poc_description: text.append("\n\n") text.append("PoC Description", style=FIELD_STYLE) diff --git a/strix/interface/tui.py b/strix/interface/tui.py index 49a0489..cb1adff 100644 --- a/strix/interface/tui.py +++ b/strix/interface/tui.py @@ -531,16 +531,30 @@ class VulnerabilityDetailScreen(ModalScreen): # type: ignore[misc] lines.append("```") # Code Analysis - if vuln.get("code_file") or vuln.get("code_diff"): + if vuln.get("code_locations"): lines.extend(["", "## Code Analysis", ""]) - if vuln.get("code_file"): - lines.append(f"**File:** {vuln['code_file']}") + for i, loc in enumerate(vuln["code_locations"]): + file_ref = loc.get("file", "unknown") + line_ref = "" + if loc.get("start_line") is not None: + if loc.get("end_line") and loc["end_line"] != loc["start_line"]: + line_ref = f" (lines {loc['start_line']}-{loc['end_line']})" + else: + line_ref = f" (line {loc['start_line']})" + lines.append(f"**Location {i + 1}:** `{file_ref}`{line_ref}") + if loc.get("label"): + lines.append(f" {loc['label']}") + if loc.get("snippet"): + lines.append(f"```\n{loc['snippet']}\n```") + if loc.get("fix_before") or loc.get("fix_after"): + lines.append("**Suggested Fix:**") + lines.append("```diff") + if loc.get("fix_before"): + lines.extend(f"- {line}" for line in loc["fix_before"].splitlines()) + if loc.get("fix_after"): + lines.extend(f"+ {line}" for line in loc["fix_after"].splitlines()) + lines.append("```") lines.append("") - if vuln.get("code_diff"): - lines.append("**Changes:**") - lines.append("```diff") - lines.append(vuln["code_diff"]) - lines.append("```") # Remediation if vuln.get("remediation_steps"): diff --git a/strix/interface/utils.py b/strix/interface/utils.py index 8dbaebb..fe5bdfc 100644 --- a/strix/interface/utils.py +++ b/strix/interface/utils.py @@ -163,32 +163,34 @@ def format_vulnerability_report(report: dict[str, Any]) -> Text: # noqa: PLR091 text.append("\n") text.append(poc_script_code, style="dim") - code_file = report.get("code_file") - if code_file: + code_locations = report.get("code_locations") + if code_locations: text.append("\n\n") - text.append("Code File: ", style=field_style) - text.append(code_file) - - code_before = report.get("code_before") - if code_before: - text.append("\n\n") - text.append("Code Before", style=field_style) - text.append("\n") - text.append(code_before, style="dim") - - code_after = report.get("code_after") - if code_after: - text.append("\n\n") - text.append("Code After", style=field_style) - text.append("\n") - text.append(code_after, style="dim") - - code_diff = report.get("code_diff") - if code_diff: - text.append("\n\n") - text.append("Code Diff", style=field_style) - text.append("\n") - text.append(code_diff, style="dim") + text.append("Code Locations", style=field_style) + for i, loc in enumerate(code_locations): + text.append("\n\n") + text.append(f" Location {i + 1}: ", style="dim") + text.append(loc.get("file", "unknown"), style="bold") + start = loc.get("start_line") + end = loc.get("end_line") + if start is not None: + if end and end != start: + text.append(f":{start}-{end}") + else: + text.append(f":{start}") + if loc.get("label"): + text.append(f"\n {loc['label']}", style="italic dim") + if loc.get("snippet"): + text.append("\n ") + text.append(loc["snippet"], style="dim") + if loc.get("fix_before") or loc.get("fix_after"): + text.append("\n Fix:") + if loc.get("fix_before"): + text.append("\n - ", style="dim") + text.append(loc["fix_before"], style="dim") + if loc.get("fix_after"): + text.append("\n + ", style="dim") + text.append(loc["fix_after"], style="dim") remediation_steps = report.get("remediation_steps") if remediation_steps: diff --git a/strix/telemetry/tracer.py b/strix/telemetry/tracer.py index 25af62c..ecf3ce8 100644 --- a/strix/telemetry/tracer.py +++ b/strix/telemetry/tracer.py @@ -89,10 +89,8 @@ class Tracer: endpoint: str | None = None, method: str | None = None, cve: str | None = None, - code_file: str | None = None, - code_before: str | None = None, - code_after: str | None = None, - code_diff: str | None = None, + cwe: str | None = None, + code_locations: list[dict[str, Any]] | None = None, ) -> str: report_id = f"vuln-{len(self.vulnerability_reports) + 1:04d}" @@ -127,14 +125,10 @@ class Tracer: report["method"] = method.strip() if cve: report["cve"] = cve.strip() - if code_file: - report["code_file"] = code_file.strip() - if code_before: - report["code_before"] = code_before.strip() - if code_after: - report["code_after"] = code_after.strip() - if code_diff: - report["code_diff"] = code_diff.strip() + if cwe: + report["cwe"] = cwe.strip() + if code_locations: + report["code_locations"] = code_locations self.vulnerability_reports.append(report) logger.info(f"Added vulnerability report: {report_id} - {title}") @@ -323,6 +317,7 @@ class Tracer: ("Endpoint", report.get("endpoint")), ("Method", report.get("method")), ("CVE", report.get("cve")), + ("CWE", report.get("cwe")), ] cvss_score = report.get("cvss") if cvss_score is not None: @@ -353,15 +348,33 @@ class Tracer: f.write(f"{report['poc_script_code']}\n") f.write("```\n\n") - if report.get("code_file") or report.get("code_diff"): + if report.get("code_locations"): f.write("## Code Analysis\n\n") - if report.get("code_file"): - f.write(f"**File:** {report['code_file']}\n\n") - if report.get("code_diff"): - f.write("**Changes:**\n") - f.write("```diff\n") - f.write(f"{report['code_diff']}\n") - f.write("```\n\n") + for i, loc in enumerate(report["code_locations"]): + prefix = f"**Location {i + 1}:**" + file_ref = loc.get("file", "unknown") + line_ref = "" + if loc.get("start_line") is not None: + if loc.get("end_line") and loc["end_line"] != loc["start_line"]: + line_ref = f" (lines {loc['start_line']}-{loc['end_line']})" + else: + line_ref = f" (line {loc['start_line']})" + f.write(f"{prefix} `{file_ref}`{line_ref}\n") + if loc.get("label"): + f.write(f" {loc['label']}\n") + if loc.get("snippet"): + f.write(f" ```\n {loc['snippet']}\n ```\n") + if loc.get("fix_before") or loc.get("fix_after"): + f.write("\n **Suggested Fix:**\n") + f.write(" ```diff\n") + if loc.get("fix_before"): + for line in loc["fix_before"].splitlines(): + f.write(f" - {line}\n") + if loc.get("fix_after"): + for line in loc["fix_after"].splitlines(): + f.write(f" + {line}\n") + f.write(" ```\n") + f.write("\n") if report.get("remediation_steps"): f.write("## Remediation\n\n") diff --git a/strix/tools/reporting/reporting_actions.py b/strix/tools/reporting/reporting_actions.py index c307d93..b84797f 100644 --- a/strix/tools/reporting/reporting_actions.py +++ b/strix/tools/reporting/reporting_actions.py @@ -1,8 +1,120 @@ +import contextlib +import re +from pathlib import PurePosixPath from typing import Any from strix.tools.registry import register_tool +_CVSS_FIELDS = ( + "attack_vector", + "attack_complexity", + "privileges_required", + "user_interaction", + "scope", + "confidentiality", + "integrity", + "availability", +) + + +def parse_cvss_xml(xml_str: str) -> dict[str, str] | None: + if not xml_str or not xml_str.strip(): + return None + result = {} + for field in _CVSS_FIELDS: + match = re.search(rf"<{field}>(.*?)", xml_str, re.DOTALL) + if match: + result[field] = match.group(1).strip() + return result if result else None + + +def parse_code_locations_xml(xml_str: str) -> list[dict[str, Any]] | None: + if not xml_str or not xml_str.strip(): + return None + locations = [] + for loc_match in re.finditer(r"(.*?)", xml_str, re.DOTALL): + loc: dict[str, Any] = {} + loc_content = loc_match.group(1) + for field in ( + "file", + "start_line", + "end_line", + "snippet", + "label", + "fix_before", + "fix_after", + ): + field_match = re.search(rf"<{field}>(.*?)", loc_content, re.DOTALL) + if field_match: + raw = field_match.group(1) + value = ( + raw.strip("\n") + if field in ("snippet", "fix_before", "fix_after") + else raw.strip() + ) + if field in ("start_line", "end_line"): + with contextlib.suppress(ValueError, TypeError): + loc[field] = int(value) + elif value: + loc[field] = value + if loc.get("file") and loc.get("start_line") is not None: + locations.append(loc) + return locations if locations else None + + +def _validate_file_path(path: str) -> str | None: + if not path or not path.strip(): + return "file path cannot be empty" + p = PurePosixPath(path) + if p.is_absolute(): + return f"file path must be relative, got absolute: '{path}'" + if ".." in p.parts: + return f"file path must not contain '..': '{path}'" + return None + + +def _validate_code_locations(locations: list[dict[str, Any]]) -> list[str]: + errors = [] + for i, loc in enumerate(locations): + path_err = _validate_file_path(loc.get("file", "")) + if path_err: + errors.append(f"code_locations[{i}]: {path_err}") + start = loc.get("start_line") + if not isinstance(start, int) or start < 1: + errors.append(f"code_locations[{i}]: start_line must be a positive integer") + end = loc.get("end_line") + if end is None: + errors.append(f"code_locations[{i}]: end_line is required") + elif not isinstance(end, int) or end < 1: + errors.append(f"code_locations[{i}]: end_line must be a positive integer") + elif isinstance(start, int) and end < start: + errors.append(f"code_locations[{i}]: end_line ({end}) must be >= start_line ({start})") + return errors + + +def _extract_cve(cve: str) -> str: + match = re.search(r"CVE-\d{4}-\d{4,}", cve) + return match.group(0) if match else cve.strip() + + +def _validate_cve(cve: str) -> str | None: + if not re.match(r"^CVE-\d{4}-\d{4,}$", cve): + return f"invalid CVE format: '{cve}' (expected 'CVE-YYYY-NNNNN')" + return None + + +def _extract_cwe(cwe: str) -> str: + match = re.search(r"CWE-\d+", cwe) + return match.group(0) if match else cwe.strip() + + +def _validate_cwe(cwe: str) -> str | None: + if not re.match(r"^CWE-\d+$", cwe): + return f"invalid CWE format: '{cwe}' (expected 'CWE-NNN')" + return None + + def calculate_cvss_and_severity( attack_vector: str, attack_complexity: str, @@ -87,7 +199,7 @@ def _validate_cvss_parameters(**kwargs: str) -> list[str]: @register_tool(sandbox_execution=False) -def create_vulnerability_report( +def create_vulnerability_report( # noqa: PLR0912 title: str, description: str, impact: str, @@ -96,23 +208,12 @@ def create_vulnerability_report( poc_description: str, poc_script_code: str, remediation_steps: str, - # CVSS Breakdown Components - attack_vector: str, - attack_complexity: str, - privileges_required: str, - user_interaction: str, - scope: str, - confidentiality: str, - integrity: str, - availability: str, - # Optional fields + cvss_breakdown: str, endpoint: str | None = None, method: str | None = None, cve: str | None = None, - code_file: str | None = None, - code_before: str | None = None, - code_after: str | None = None, - code_diff: str | None = None, + cwe: str | None = None, + code_locations: str | None = None, ) -> dict[str, Any]: validation_errors = _validate_required_fields( title=title, @@ -125,32 +226,32 @@ def create_vulnerability_report( remediation_steps=remediation_steps, ) - validation_errors.extend( - _validate_cvss_parameters( - attack_vector=attack_vector, - attack_complexity=attack_complexity, - privileges_required=privileges_required, - user_interaction=user_interaction, - scope=scope, - confidentiality=confidentiality, - integrity=integrity, - availability=availability, - ) - ) + parsed_cvss = parse_cvss_xml(cvss_breakdown) + if not parsed_cvss: + validation_errors.append("cvss: could not parse CVSS breakdown XML") + else: + validation_errors.extend(_validate_cvss_parameters(**parsed_cvss)) + + parsed_locations = parse_code_locations_xml(code_locations) if code_locations else None + + if parsed_locations: + validation_errors.extend(_validate_code_locations(parsed_locations)) + if cve: + cve = _extract_cve(cve) + cve_err = _validate_cve(cve) + if cve_err: + validation_errors.append(cve_err) + if cwe: + cwe = _extract_cwe(cwe) + cwe_err = _validate_cwe(cwe) + if cwe_err: + validation_errors.append(cwe_err) if validation_errors: return {"success": False, "message": "Validation failed", "errors": validation_errors} - cvss_score, severity, cvss_vector = calculate_cvss_and_severity( - attack_vector, - attack_complexity, - privileges_required, - user_interaction, - scope, - confidentiality, - integrity, - availability, - ) + assert parsed_cvss is not None + cvss_score, severity, cvss_vector = calculate_cvss_and_severity(**parsed_cvss) try: from strix.telemetry.tracer import get_global_tracer @@ -196,17 +297,6 @@ def create_vulnerability_report( "reason": dedupe_result.get("reason", ""), } - cvss_breakdown = { - "attack_vector": attack_vector, - "attack_complexity": attack_complexity, - "privileges_required": privileges_required, - "user_interaction": user_interaction, - "scope": scope, - "confidentiality": confidentiality, - "integrity": integrity, - "availability": availability, - } - report_id = tracer.add_vulnerability_report( title=title, description=description, @@ -218,14 +308,12 @@ def create_vulnerability_report( poc_script_code=poc_script_code, remediation_steps=remediation_steps, cvss=cvss_score, - cvss_breakdown=cvss_breakdown, + cvss_breakdown=parsed_cvss, endpoint=endpoint, method=method, cve=cve, - code_file=code_file, - code_before=code_before, - code_after=code_after, - code_diff=code_diff, + cwe=cwe, + code_locations=parsed_locations, ) return { diff --git a/strix/tools/reporting/reporting_actions_schema.xml b/strix/tools/reporting/reporting_actions_schema.xml index 56c6cc0..39e6a77 100644 --- a/strix/tools/reporting/reporting_actions_schema.xml +++ b/strix/tools/reporting/reporting_actions_schema.xml @@ -14,7 +14,7 @@ DO NOT USE: - For reporting multiple vulnerabilities at once. Use a separate create_vulnerability_report for each vulnerability. - To re-report a vulnerability that was already reported (even with different details) -White-box requirement (when you have access to the code): You MUST include code_file, code_before, code_after, and code_diff. These must contain the actual code (before/after) and a complete, apply-able unified diff. +White-box requirement (when you have access to the code): You MUST include code_locations with nested XML, including fix_before/fix_after on locations where a fix is proposed. DEDUPLICATION: If this tool returns with success=false and mentions a duplicate, DO NOT attempt to re-submit. The vulnerability has already been reported. Move on to testing other areas. @@ -30,7 +30,7 @@ Professional, customer-facing report rules (PDF-ready): 6) Impact 7) Remediation 8) Evidence (optional request/response excerpts, etc.) in the technical analysis field. -- Numbered steps are allowed ONLY within the proof of concept. Elsewhere, use clear, concise paragraphs suitable for customer-facing reports. +- Numbered steps are allowed ONLY within the proof of concept and remediation sections. Elsewhere, use clear, concise paragraphs suitable for customer-facing reports. - Language must be precise and non-vague; avoid hedging. @@ -58,51 +58,28 @@ Professional, customer-facing report rules (PDF-ready): Specific, actionable steps to fix the vulnerability - - CVSS Attack Vector - How the vulnerability is exploited: -N = Network (remotely exploitable) -A = Adjacent (same network segment) -L = Local (local access required) -P = Physical (physical access required) - - - CVSS Attack Complexity - Conditions beyond attacker's control: -L = Low (no special conditions) -H = High (special conditions must exist) - - - CVSS Privileges Required - Level of privileges needed: -N = None (no privileges needed) -L = Low (basic user privileges) -H = High (admin privileges) - - - CVSS User Interaction - Does exploit require user action: -N = None (no user interaction needed) -R = Required (user must perform some action) - - - CVSS Scope - Can the vulnerability affect resources beyond its security scope: -U = Unchanged (only affects the vulnerable component) -C = Changed (affects resources beyond vulnerable component) - - - CVSS Confidentiality Impact - Impact to confidentiality: -N = None (no impact) -L = Low (some information disclosure) -H = High (all information disclosed) - - - CVSS Integrity Impact - Impact to integrity: -N = None (no impact) -L = Low (data can be modified but scope is limited) -H = High (total loss of integrity) - - - CVSS Availability Impact - Impact to availability: -N = None (no impact) -L = Low (reduced performance or interruptions) -H = High (total loss of availability) + + CVSS 3.1 base score breakdown as nested XML. All 8 metrics are required. + +Each metric element contains a single uppercase letter value: +- attack_vector: N (Network), A (Adjacent), L (Local), P (Physical) +- attack_complexity: L (Low), H (High) +- privileges_required: N (None), L (Low), H (High) +- user_interaction: N (None), R (Required) +- scope: U (Unchanged), C (Changed) +- confidentiality: N (None), L (Low), H (High) +- integrity: N (None), L (Low), H (High) +- availability: N (None), L (Low), H (High) + + N + L + N + N + U + H + H + N + API endpoint(s) or URL path(s) (e.g., "/api/login") - for web vulnerabilities, or Git repository path(s) - for code vulnerabilities @@ -111,19 +88,64 @@ H = High (total loss of availability) HTTP method(s) (GET, POST, etc.) - for web vulnerabilities. - CVE identifier (e.g., "CVE-2024-1234"). Make sure it's a valid CVE. Use web search or vulnerability databases to make sure it's a valid CVE number. + CVE identifier. ONLY the ID, e.g. "CVE-2024-1234" — do NOT include the name or description. +You must be 100% certain of the exact CVE number. Do NOT guess, approximate, or hallucinate CVE IDs. +If web_search is available, use it to verify the CVE exists and matches this vulnerability. If you cannot verify it, omit this field entirely. - - MANDATORY for white-box testing: exact affected source file path(s). + + CWE identifier. ONLY the ID, e.g. "CWE-89" — do NOT include the name or parenthetical (wrong: "CWE-89 (SQL Injection)"). + +You must be 100% certain of the exact CWE number. Do NOT guess or approximate. +If web_search is available and you are unsure, use it to look up the correct CWE. If you cannot be certain, omit this field entirely. +Always prefer the most specific child CWE over a broad parent. +For example, use CWE-89 instead of CWE-74, or CWE-78 instead of CWE-77. + +Reference (ID only — names here are just for your reference, do NOT include them in the value): +- Injection: CWE-79 XSS, CWE-89 SQLi, CWE-78 OS Command Injection, CWE-94 Code Injection, CWE-77 Command Injection +- Auth/Access: CWE-287 Improper Authentication, CWE-862 Missing Authorization, CWE-863 Incorrect Authorization, CWE-306 Missing Authentication for Critical Function, CWE-639 Authorization Bypass Through User-Controlled Key +- Web: CWE-352 CSRF, CWE-918 SSRF, CWE-601 Open Redirect, CWE-434 Unrestricted Upload of File with Dangerous Type +- Memory: CWE-787 Out-of-bounds Write, CWE-125 Out-of-bounds Read, CWE-416 Use After Free, CWE-120 Classic Buffer Overflow +- Data: CWE-502 Deserialization of Untrusted Data, CWE-22 Path Traversal, CWE-611 XXE +- Crypto/Config: CWE-798 Use of Hard-coded Credentials, CWE-327 Use of Broken or Risky Cryptographic Algorithm, CWE-311 Missing Encryption of Sensitive Data, CWE-916 Password Hash With Insufficient Computational Effort + +Do NOT use broad/parent CWEs like CWE-74, CWE-20, CWE-200, CWE-284, or CWE-693. - - MANDATORY for white-box testing: actual vulnerable code snippet(s) copied verbatim from the repository. - - - MANDATORY for white-box testing: corrected code snippet(s) exactly as they should appear after the fix. - - - MANDATORY for white-box testing: unified diff showing the code changes. Must be a complete, apply-able unified diff (git format) covering all affected files, with proper file headers, line numbers, and sufficient context. + + Nested XML list of code locations where the vulnerability exists. MANDATORY for white-box testing. + +Order: first location is where the issue manifests (typically the sink). Additional locations provide data flow context (source → propagation → sink). + +Each location element fields: +- file (REQUIRED): Path relative to repository root. No leading slash, no absolute paths, no ".." traversal. + Correct: "src/db/queries.ts" or "app/routes/users.py" + Wrong: "/workspace/repo/src/db/queries.ts", "./src/db/queries.ts", "../../etc/passwd" +- start_line (REQUIRED): Exact 1-based line number where the vulnerable code begins. Must be a positive integer. You must be certain of this number — do not guess or approximate. Go back and verify against the actual file content if needed. +- end_line (REQUIRED): Exact 1-based line number where the vulnerable code ends. Must be >= start_line. Set equal to start_line if the vulnerability is on a single line. +- snippet (optional): The actual source code at this location, copied verbatim from the file. Do not paraphrase or summarize code — paste it exactly as it appears. +- label (optional): Short role description for this location in the data flow, e.g. "User input from request parameter (source)", "Unsanitized input passed to SQL query (sink)". +- fix_before (optional): The vulnerable code to be replaced, copied verbatim. Must match the actual source exactly — do not paraphrase, summarize, or add/remove whitespace. Only include on locations where a fix is proposed. +- fix_after (optional): The corrected code that should replace fix_before. Must be syntactically valid and ready to apply as a direct replacement. Only include on locations where a fix is proposed. + +Locations without fix_before/fix_after are informational context (e.g. showing the source of tainted data). +Locations with fix_before/fix_after are actionable fixes (used for PR review suggestions). + + + src/db/queries.ts + 42 + 42 + db.query(`SELECT * FROM users WHERE id = ${id}`) + + db.query(`SELECT * FROM users WHERE id = ${id}`) + db.query('SELECT * FROM users WHERE id = $1', [id]) + + + src/routes/users.ts + 15 + 15 + const id = req.params.id + + + @@ -177,7 +199,6 @@ Impact validation: - Use a controlled internal endpoint (or a benign endpoint that returns a distinct marker) to demonstrate that the request is performed by the server, not the client. - If the application follows redirects, validate whether an allowlisted URL can redirect to a disallowed destination, and whether the redirected-to destination is still fetched. import json -import sys import time from urllib.parse import urljoin @@ -262,16 +283,39 @@ if __name__ == "__main__": 6. Monitoring and alerting - Log and alert on preview attempts to unusual destinations, repeated failures, high-frequency requests, or attempts to access blocked ranges. -N -L -L -N -C -H -H -L + + N + L + L + N + C + H + H + L + /api/v1/link-preview POST +CWE-918 + + + src/services/link-preview.ts + 47 + 47 + const response = await fetch(userUrl) + + const response = await fetch(userUrl) + const validated = await validateAndResolveUrl(userUrl) +if (!validated) throw new ForbiddenError('URL not allowed') +const response = await fetch(validated) + + + src/routes/api/v1/links.ts + 12 + 12 + const userUrl = req.body.url + + + From 305ae2f69906cb1a066493d25d0c91efefc0afe7 Mon Sep 17 00:00:00 2001 From: 0xallam Date: Sun, 15 Feb 2026 17:16:58 -0800 Subject: [PATCH 05/14] fix: Remove indentation prefix from diff code block markers for syntax highlighting --- strix/telemetry/tracer.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/strix/telemetry/tracer.py b/strix/telemetry/tracer.py index ecf3ce8..8bbb412 100644 --- a/strix/telemetry/tracer.py +++ b/strix/telemetry/tracer.py @@ -366,14 +366,14 @@ class Tracer: f.write(f" ```\n {loc['snippet']}\n ```\n") if loc.get("fix_before") or loc.get("fix_after"): f.write("\n **Suggested Fix:**\n") - f.write(" ```diff\n") + f.write("```diff\n") if loc.get("fix_before"): for line in loc["fix_before"].splitlines(): - f.write(f" - {line}\n") + f.write(f"- {line}\n") if loc.get("fix_after"): for line in loc["fix_after"].splitlines(): - f.write(f" + {line}\n") - f.write(" ```\n") + f.write(f"+ {line}\n") + f.write("```\n") f.write("\n") if report.get("remediation_steps"): From 365d51f52fea1908a4b6663f58ca7e0f4fd615ca Mon Sep 17 00:00:00 2001 From: TaeBbong Date: Tue, 3 Feb 2026 18:34:54 +0900 Subject: [PATCH 06/14] fix: Add explicit UTF-8 encoding to read_text() calls - Specify encoding="utf-8" in registry.py _load_xml_schema() - Specify encoding="utf-8" in skills/__init__.py load_skills() - Prevents cp949/shift_jis/cp1252 decoding errors on non-English Windows --- strix/skills/__init__.py | 2 +- strix/tools/registry.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/strix/skills/__init__.py b/strix/skills/__init__.py index c3ac391..c9cdf03 100644 --- a/strix/skills/__init__.py +++ b/strix/skills/__init__.py @@ -130,7 +130,7 @@ def load_skills(skill_names: list[str]) -> dict[str, str]: if skill_path and (skills_dir / skill_path).exists(): full_path = skills_dir / skill_path var_name = skill_name.split("/")[-1] - content = full_path.read_text() + content = full_path.read_text(encoding="utf-8") content = _FRONTMATTER_PATTERN.sub("", content).lstrip() skill_content[var_name] = content logger.info(f"Loaded skill: {skill_name} -> {var_name}") diff --git a/strix/tools/registry.py b/strix/tools/registry.py index ac6e15f..7313bc3 100644 --- a/strix/tools/registry.py +++ b/strix/tools/registry.py @@ -48,7 +48,7 @@ def _load_xml_schema(path: Path) -> Any: if not path.exists(): return None try: - content = path.read_text() + content = path.read_text(encoding="utf-8") content = _process_dynamic_content(content) From 154040f9fb76dcdfcb55d13e2405daa11bac9031 Mon Sep 17 00:00:00 2001 From: 0xallam Date: Tue, 17 Feb 2026 14:11:58 -0800 Subject: [PATCH 07/14] fix: Improve code_locations schema for accurate block-level fixes and multi-part suggestions Rewrote the code_locations parameter description to make fix_before/fix_after semantics explicit: they are literal block-level replacements mapped directly to GitHub/GitLab PR suggestion blocks. Added guidance for multi-part fixes (separate locations for non-contiguous changes like imports + code), common mistakes to avoid, and updated all examples to demonstrate multi-line ranges. --- .../reporting/reporting_actions_schema.xml | 85 ++++++++++++++----- 1 file changed, 66 insertions(+), 19 deletions(-) diff --git a/strix/tools/reporting/reporting_actions_schema.xml b/strix/tools/reporting/reporting_actions_schema.xml index 39e6a77..b0b9afb 100644 --- a/strix/tools/reporting/reporting_actions_schema.xml +++ b/strix/tools/reporting/reporting_actions_schema.xml @@ -113,30 +113,58 @@ Do NOT use broad/parent CWEs like CWE-74, CWE-20, CWE-200, CWE-284, or CWE-693.< Nested XML list of code locations where the vulnerability exists. MANDATORY for white-box testing. -Order: first location is where the issue manifests (typically the sink). Additional locations provide data flow context (source → propagation → sink). +CRITICAL — HOW fix_before/fix_after WORK: +fix_before and fix_after are LITERAL BLOCK-LEVEL REPLACEMENTS used directly for GitHub/GitLab PR suggestion blocks. When a reviewer clicks "Accept suggestion", the platform replaces the EXACT lines from start_line to end_line with the fix_after content. This means: + +1. fix_before MUST be an EXACT, VERBATIM copy of the source code at lines start_line through end_line. Same whitespace, same indentation, same line breaks. If fix_before does not match the actual file content character-for-character, the suggestion will be wrong or will corrupt the code when accepted. + +2. fix_after is the COMPLETE replacement for that entire block. It replaces ALL lines from start_line to end_line. It can be more lines, fewer lines, or the same number of lines as fix_before. + +3. start_line and end_line define the EXACT line range being replaced. They must precisely cover the lines in fix_before — no more, no less. If the vulnerable code spans lines 45-48, then start_line=45 and end_line=48, and fix_before must contain all 4 lines exactly as they appear in the file. + +MULTI-PART FIXES: +Many fixes require changes in multiple non-contiguous parts of a file (e.g., adding an import at the top AND changing code lower down), or across multiple files. Since each fix_before/fix_after pair covers ONE contiguous block, you MUST create SEPARATE location entries for each part of the fix: + +- Each location covers one contiguous block of lines to change +- Use the label field to describe how each part relates to the overall fix (e.g., "Add import for parameterized query library", "Replace string interpolation with parameterized query") +- Order fix locations logically: primary fix first (where the vulnerability manifests), then supporting changes (imports, config, etc.) + +COMMON MISTAKES TO AVOID: +- Do NOT guess line numbers. Read the file and verify the exact lines before reporting. +- Do NOT paraphrase or reformat code in fix_before. It must be a verbatim copy. +- Do NOT set start_line=end_line when the vulnerable code spans multiple lines. Cover the full range. +- Do NOT put an import addition and a code change in the same fix_before/fix_after if they are not on adjacent lines. Split them into separate locations. +- Do NOT include lines outside the vulnerable/fixed code in fix_before just to "pad" the range. Each location element fields: - file (REQUIRED): Path relative to repository root. No leading slash, no absolute paths, no ".." traversal. Correct: "src/db/queries.ts" or "app/routes/users.py" Wrong: "/workspace/repo/src/db/queries.ts", "./src/db/queries.ts", "../../etc/passwd" -- start_line (REQUIRED): Exact 1-based line number where the vulnerable code begins. Must be a positive integer. You must be certain of this number — do not guess or approximate. Go back and verify against the actual file content if needed. -- end_line (REQUIRED): Exact 1-based line number where the vulnerable code ends. Must be >= start_line. Set equal to start_line if the vulnerability is on a single line. -- snippet (optional): The actual source code at this location, copied verbatim from the file. Do not paraphrase or summarize code — paste it exactly as it appears. -- label (optional): Short role description for this location in the data flow, e.g. "User input from request parameter (source)", "Unsanitized input passed to SQL query (sink)". -- fix_before (optional): The vulnerable code to be replaced, copied verbatim. Must match the actual source exactly — do not paraphrase, summarize, or add/remove whitespace. Only include on locations where a fix is proposed. -- fix_after (optional): The corrected code that should replace fix_before. Must be syntactically valid and ready to apply as a direct replacement. Only include on locations where a fix is proposed. +- start_line (REQUIRED): Exact 1-based line number where the vulnerable/affected code begins. Must be a positive integer. You must be certain of this number — go back and verify against the actual file content if needed. +- end_line (REQUIRED): Exact 1-based line number where the vulnerable/affected code ends. Must be >= start_line. Set equal to start_line ONLY if the code is truly on a single line. +- snippet (optional): The actual source code at this location, copied verbatim from the file. +- label (optional): Short role description for this location. For multi-part fixes, use this to explain the purpose of each change (e.g., "Add import for escape utility", "Sanitize user input before SQL query"). +- fix_before (optional): The vulnerable code to be replaced — VERBATIM copy of lines start_line through end_line. Must match the actual source character-for-character including whitespace and indentation. +- fix_after (optional): The corrected code that replaces the entire fix_before block. Must be syntactically valid and ready to apply as a direct replacement. Locations without fix_before/fix_after are informational context (e.g. showing the source of tainted data). -Locations with fix_before/fix_after are actionable fixes (used for PR review suggestions). +Locations with fix_before/fix_after are actionable fixes (used directly for PR suggestion blocks). src/db/queries.ts 42 - 42 - db.query(`SELECT * FROM users WHERE id = ${id}`) + 45 + const query = ( + `SELECT * FROM users ` + + `WHERE id = ${id}` +); - db.query(`SELECT * FROM users WHERE id = ${id}`) - db.query('SELECT * FROM users WHERE id = $1', [id]) + const query = ( + `SELECT * FROM users ` + + `WHERE id = ${id}` +); + const query = 'SELECT * FROM users WHERE id = $1'; +const result = await db.query(query, [id]); src/routes/users.ts @@ -299,14 +327,33 @@ if __name__ == "__main__": src/services/link-preview.ts - 47 - 47 - const response = await fetch(userUrl) + 45 + 48 + const options = { timeout: 5000 }; + const response = await fetch(userUrl, options); + const html = await response.text(); + return extractMetadata(html); - const response = await fetch(userUrl) - const validated = await validateAndResolveUrl(userUrl) -if (!validated) throw new ForbiddenError('URL not allowed') -const response = await fetch(validated) + const options = { timeout: 5000 }; + const response = await fetch(userUrl, options); + const html = await response.text(); + return extractMetadata(html); + const validated = await validateAndResolveUrl(userUrl); + if (!validated) throw new ForbiddenError('URL not allowed'); + const options = { timeout: 5000 }; + const response = await fetch(validated, options); + const html = await response.text(); + return extractMetadata(html); + + + src/services/link-preview.ts + 2 + 2 + import { extractMetadata } from '../utils/html'; + + import { extractMetadata } from '../utils/html'; + import { extractMetadata } from '../utils/html'; +import { validateAndResolveUrl } from '../utils/url-validator'; src/routes/api/v1/links.ts From 30550dd189743aacb9c564b6ba861ad04a27d9e1 Mon Sep 17 00:00:00 2001 From: 0xallam Date: Tue, 17 Feb 2026 14:59:13 -0800 Subject: [PATCH 08/14] fix: Add rule against duplicating changes across code_locations --- strix/tools/reporting/reporting_actions_schema.xml | 1 + 1 file changed, 1 insertion(+) diff --git a/strix/tools/reporting/reporting_actions_schema.xml b/strix/tools/reporting/reporting_actions_schema.xml index b0b9afb..0f4780a 100644 --- a/strix/tools/reporting/reporting_actions_schema.xml +++ b/strix/tools/reporting/reporting_actions_schema.xml @@ -135,6 +135,7 @@ COMMON MISTAKES TO AVOID: - Do NOT set start_line=end_line when the vulnerable code spans multiple lines. Cover the full range. - Do NOT put an import addition and a code change in the same fix_before/fix_after if they are not on adjacent lines. Split them into separate locations. - Do NOT include lines outside the vulnerable/fixed code in fix_before just to "pad" the range. +- Do NOT duplicate changes across locations. Each location's fix_after must ONLY contain changes for its own line range. Never repeat a change that is already covered by another location. Each location element fields: - file (REQUIRED): Path relative to repository root. No leading slash, no absolute paths, no ".." traversal. From e38f523a458274e5731521c9bc5ea2f141c00872 Mon Sep 17 00:00:00 2001 From: octovimmer Date: Thu, 19 Feb 2026 13:43:18 -0800 Subject: [PATCH 09/14] Strix LLM Documentation and Config Changes (#315) * feat: add to readme new keys * feat: shoutout strix models, docs * fix: mypy error * fix: base api * docs: update quickstart and models * fixes: changes to docs uniform api_key variable naming * test: git commit hook * nevermind it was nothing * docs: Update default model to claude-sonnet-4.6 and improve Strix Router docs - Replace gpt-5 and opus-4.6 defaults with claude-sonnet-4.6 across all docs and code - Rewrite Strix Router (models.mdx) page with clearer structure and messaging - Add Strix Router as recommended option in overview.mdx and quickstart prerequisites - Update stale Claude 4.5 references to 4.6 in anthropic.mdx, openrouter.mdx, bug_report.md - Fix install.sh links to point to models.strix.ai and correct docs URLs - Update error message examples in main.py to use claude-sonnet-4-6 --------- Co-authored-by: 0xallam --- .github/ISSUE_TEMPLATE/bug_report.md | 2 +- CONTRIBUTING.md | 2 +- README.md | 10 ++-- docs/advanced/configuration.mdx | 6 +-- docs/contributing.mdx | 2 +- docs/index.mdx | 2 +- docs/integrations/github-actions.mdx | 2 +- docs/llm-providers/anthropic.mdx | 6 +-- docs/llm-providers/models.mdx | 80 ++++++++++++++++++++++++++++ docs/llm-providers/openrouter.mdx | 2 +- docs/llm-providers/overview.mdx | 41 ++++++++++---- docs/quickstart.mdx | 22 +++++--- scripts/install.sh | 12 +++-- strix/config/config.py | 30 +++++++++++ strix/interface/main.py | 25 ++++----- strix/llm/config.py | 4 +- strix/llm/dedupe.py | 11 +--- strix/llm/llm.py | 13 ++--- strix/llm/memory_compressor.py | 10 +--- 19 files changed, 208 insertions(+), 74 deletions(-) create mode 100644 docs/llm-providers/models.mdx diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md index f9b9106..85919ce 100644 --- a/.github/ISSUE_TEMPLATE/bug_report.md +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -27,7 +27,7 @@ If applicable, add screenshots to help explain your problem. - OS: [e.g. Ubuntu 22.04] - Strix Version or Commit: [e.g. 0.1.18] - Python Version: [e.g. 3.12] -- LLM Used: [e.g. GPT-5, Claude Sonnet 4] +- LLM Used: [e.g. GPT-5, Claude Sonnet 4.6] **Additional context** Add any other context about the problem here. diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index d6b9a64..e272e0b 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -30,7 +30,7 @@ Thank you for your interest in contributing to Strix! This guide will help you g 3. **Configure your LLM provider** ```bash - export STRIX_LLM="openai/gpt-5" + export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="your-api-key" ``` diff --git a/README.md b/README.md index 5e2a0be..fd79f86 100644 --- a/README.md +++ b/README.md @@ -72,7 +72,9 @@ Strix are autonomous AI agents that act just like real hackers - they run your c **Prerequisites:** - Docker (running) -- An LLM provider key (e.g. [get OpenAI API key](https://platform.openai.com/api-keys) or use a local LLM) +- An LLM API key: + - Any [supported provider](https://docs.strix.ai/llm-providers/overview) (OpenAI, Anthropic, Google, etc.) + - Or [Strix Router](https://models.strix.ai) — single API key for multiple providers with $10 free credit on signup ### Installation & First Scan @@ -84,7 +86,7 @@ curl -sSL https://strix.ai/install | bash pipx install strix-agent # Configure your AI provider -export STRIX_LLM="openai/gpt-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" # or "strix/claude-sonnet-4.6" via Strix Router (https://models.strix.ai) export LLM_API_KEY="your-api-key" # Run your first security assessment @@ -201,7 +203,7 @@ jobs: ### Configuration ```bash -export STRIX_LLM="openai/gpt-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="your-api-key" # Optional @@ -215,8 +217,8 @@ export STRIX_REASONING_EFFORT="high" # control thinking effort (default: high, **Recommended models for best results:** +- [Anthropic Claude Sonnet 4.6](https://claude.com/platform/api) — `anthropic/claude-sonnet-4-6` - [OpenAI GPT-5](https://openai.com/api/) — `openai/gpt-5` -- [Anthropic Claude Sonnet 4.5](https://claude.com/platform/api) — `anthropic/claude-sonnet-4-5` - [Google Gemini 3 Pro Preview](https://cloud.google.com/vertex-ai) — `vertex_ai/gemini-3-pro-preview` See the [LLM Providers documentation](https://docs.strix.ai/llm-providers/overview) for all supported providers including Vertex AI, Bedrock, Azure, and local models. diff --git a/docs/advanced/configuration.mdx b/docs/advanced/configuration.mdx index 9a6d9e4..bd71c68 100644 --- a/docs/advanced/configuration.mdx +++ b/docs/advanced/configuration.mdx @@ -8,7 +8,7 @@ Configure Strix using environment variables or a config file. ## LLM Configuration - Model name in LiteLLM format (e.g., `openai/gpt-5`, `anthropic/claude-sonnet-4-5`). + Model name in LiteLLM format (e.g., `anthropic/claude-sonnet-4-6`, `openai/gpt-5`). @@ -86,7 +86,7 @@ strix --target ./app --config /path/to/config.json ```json { "env": { - "STRIX_LLM": "openai/gpt-5", + "STRIX_LLM": "anthropic/claude-sonnet-4-6", "LLM_API_KEY": "sk-...", "STRIX_REASONING_EFFORT": "high" } @@ -97,7 +97,7 @@ strix --target ./app --config /path/to/config.json ```bash # Required -export STRIX_LLM="openai/gpt-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="sk-..." # Optional: Enable web search diff --git a/docs/contributing.mdx b/docs/contributing.mdx index b2e50a0..ffa3192 100644 --- a/docs/contributing.mdx +++ b/docs/contributing.mdx @@ -32,7 +32,7 @@ description: "Contribute to Strix development" ```bash - export STRIX_LLM="openai/gpt-5" + export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="your-api-key" ``` diff --git a/docs/index.mdx b/docs/index.mdx index ef5ab9a..14de192 100644 --- a/docs/index.mdx +++ b/docs/index.mdx @@ -78,7 +78,7 @@ Strix uses a graph of specialized agents for comprehensive security testing: curl -sSL https://strix.ai/install | bash # Configure -export STRIX_LLM="openai/gpt-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="your-api-key" # Scan diff --git a/docs/integrations/github-actions.mdx b/docs/integrations/github-actions.mdx index 827dce0..fcc5eb9 100644 --- a/docs/integrations/github-actions.mdx +++ b/docs/integrations/github-actions.mdx @@ -35,7 +35,7 @@ Add these secrets to your repository: | Secret | Description | |--------|-------------| -| `STRIX_LLM` | Model name (e.g., `openai/gpt-5`) | +| `STRIX_LLM` | Model name (e.g., `anthropic/claude-sonnet-4-6`) | | `LLM_API_KEY` | API key for your LLM provider | ## Exit Codes diff --git a/docs/llm-providers/anthropic.mdx b/docs/llm-providers/anthropic.mdx index 81680a1..b7b3085 100644 --- a/docs/llm-providers/anthropic.mdx +++ b/docs/llm-providers/anthropic.mdx @@ -6,7 +6,7 @@ description: "Configure Strix with Claude models" ## Setup ```bash -export STRIX_LLM="anthropic/claude-sonnet-4-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="sk-ant-..." ``` @@ -14,8 +14,8 @@ export LLM_API_KEY="sk-ant-..." | Model | Description | |-------|-------------| -| `anthropic/claude-sonnet-4-5` | Best balance of intelligence and speed (recommended) | -| `anthropic/claude-opus-4-5` | Maximum capability for deep analysis | +| `anthropic/claude-sonnet-4-6` | Best balance of intelligence and speed (recommended) | +| `anthropic/claude-opus-4-6` | Maximum capability for deep analysis | ## Get API Key diff --git a/docs/llm-providers/models.mdx b/docs/llm-providers/models.mdx new file mode 100644 index 0000000..54007a9 --- /dev/null +++ b/docs/llm-providers/models.mdx @@ -0,0 +1,80 @@ +--- +title: "Strix Router" +description: "Access top LLMs through a single API with high rate limits and zero data retention" +--- + +Strix Router gives you access to the best LLMs through a single API key. + + +Strix Router is currently in **beta**. It's completely optional — Strix works with any [LiteLLM-compatible provider](/llm-providers/overview) using your own API keys, or with [local models](/llm-providers/local). Strix Router is just the setup we test and optimize for. + + +## Why Use Strix Router? + +- **High rate limits** — No throttling during long-running scans +- **Zero data retention** — Routes to providers with zero data retention policies enabled +- **Failover & load balancing** — Automatic fallback across providers for reliability +- **Simple setup** — One API key, one environment variable, no provider accounts needed +- **No markup** — Same token pricing as the underlying providers, no extra fees +- **$10 free credit** — Try it free on signup, no credit card required + +## Quick Start + +1. Get your API key at [models.strix.ai](https://models.strix.ai) +2. Set your environment: + +```bash +export LLM_API_KEY='your-strix-api-key' +export STRIX_LLM='strix/claude-sonnet-4.6' +``` + +3. Run a scan: + +```bash +strix --target ./your-app +``` + +## Available Models + +### Anthropic + +| Model | ID | +|-------|-----| +| Claude Sonnet 4.6 | `strix/claude-sonnet-4.6` | +| Claude Opus 4.6 | `strix/claude-opus-4.6` | + +### OpenAI + +| Model | ID | +|-------|-----| +| GPT-5.2 | `strix/gpt-5.2` | +| GPT-5.1 | `strix/gpt-5.1` | +| GPT-5 | `strix/gpt-5` | +| GPT-5.2 Codex | `strix/gpt-5.2-codex` | +| GPT-5.1 Codex Max | `strix/gpt-5.1-codex-max` | +| GPT-5.1 Codex | `strix/gpt-5.1-codex` | +| GPT-5 Codex | `strix/gpt-5-codex` | + +### Google + +| Model | ID | +|-------|-----| +| Gemini 3 Pro | `strix/gemini-3-pro-preview` | +| Gemini 3 Flash | `strix/gemini-3-flash-preview` | + +### Other + +| Model | ID | +|-------|-----| +| GLM-5 | `strix/glm-5` | +| GLM-4.7 | `strix/glm-4.7` | + +## Configuration Reference + + + Your Strix API key from [models.strix.ai](https://models.strix.ai). + + + + Model ID from the tables above. Must be prefixed with `strix/`. + diff --git a/docs/llm-providers/openrouter.mdx b/docs/llm-providers/openrouter.mdx index 31919c1..d4d36bf 100644 --- a/docs/llm-providers/openrouter.mdx +++ b/docs/llm-providers/openrouter.mdx @@ -19,7 +19,7 @@ Access any model on OpenRouter using the format `openrouter//`: | Model | Configuration | |-------|---------------| | GPT-5 | `openrouter/openai/gpt-5` | -| Claude 4.5 Sonnet | `openrouter/anthropic/claude-sonnet-4.5` | +| Claude Sonnet 4.6 | `openrouter/anthropic/claude-sonnet-4.6` | | Gemini 3 Pro | `openrouter/google/gemini-3-pro-preview` | | GLM-4.7 | `openrouter/z-ai/glm-4.7` | diff --git a/docs/llm-providers/overview.mdx b/docs/llm-providers/overview.mdx index 9027aac..567af50 100644 --- a/docs/llm-providers/overview.mdx +++ b/docs/llm-providers/overview.mdx @@ -5,31 +5,54 @@ description: "Configure your AI model for Strix" Strix uses [LiteLLM](https://docs.litellm.ai/docs/providers) for model compatibility, supporting 100+ LLM providers. -## Recommended Models +## Strix Router (Recommended) -For best results, use one of these models: +The fastest way to get started. [Strix Router](/llm-providers/models) gives you access to tested models with the highest rate limits and zero data retention. + +```bash +export STRIX_LLM="strix/claude-sonnet-4.6" +export LLM_API_KEY="your-strix-api-key" +``` + +Get your API key at [models.strix.ai](https://models.strix.ai). + +## Bring Your Own Key + +You can also use any LiteLLM-compatible provider with your own API keys: | Model | Provider | Configuration | | ----------------- | ------------- | -------------------------------- | +| Claude Sonnet 4.6 | Anthropic | `anthropic/claude-sonnet-4-6` | | GPT-5 | OpenAI | `openai/gpt-5` | -| Claude 4.5 Sonnet | Anthropic | `anthropic/claude-sonnet-4-5` | | Gemini 3 Pro | Google Vertex | `vertex_ai/gemini-3-pro-preview` | -## Quick Setup - ```bash -export STRIX_LLM="openai/gpt-5" +export STRIX_LLM="anthropic/claude-sonnet-4-6" export LLM_API_KEY="your-api-key" ``` +## Local Models + +Run models locally with [Ollama](https://ollama.com), [LM Studio](https://lmstudio.ai), or any OpenAI-compatible server: + +```bash +export STRIX_LLM="ollama/llama4" +export LLM_API_BASE="http://localhost:11434" +``` + +See the [Local Models guide](/llm-providers/local) for setup instructions and recommended models. + ## Provider Guides + + Recommended models router with high rate limits. + GPT-5 and Codex models. - Claude 4.5 Sonnet, Opus, and Haiku. + Claude Sonnet 4.6, Opus, and Haiku. Access 100+ models through a single API. @@ -38,7 +61,7 @@ export LLM_API_KEY="your-api-key" Gemini 3 models via Google Cloud. - Claude 4.5 and Titan models via AWS. + Claude and Titan models via AWS. GPT-5 via Azure. @@ -53,8 +76,8 @@ export LLM_API_KEY="your-api-key" Use LiteLLM's `provider/model-name` format: ``` +anthropic/claude-sonnet-4-6 openai/gpt-5 -anthropic/claude-sonnet-4-5 vertex_ai/gemini-3-pro-preview bedrock/anthropic.claude-4-5-sonnet-20251022-v1:0 ollama/llama4 diff --git a/docs/quickstart.mdx b/docs/quickstart.mdx index 487caae..32eac3d 100644 --- a/docs/quickstart.mdx +++ b/docs/quickstart.mdx @@ -6,7 +6,7 @@ description: "Install Strix and run your first security scan" ## Prerequisites - Docker (running) -- An LLM provider API key (OpenAI, Anthropic, or local model) +- An LLM API key — use [Strix Router](/llm-providers/models) for the easiest setup, or bring your own key from any [supported provider](/llm-providers/overview) ## Installation @@ -27,13 +27,23 @@ description: "Install Strix and run your first security scan" Set your LLM provider: -```bash -export STRIX_LLM="openai/gpt-5" -export LLM_API_KEY="your-api-key" -``` + + + ```bash + export STRIX_LLM="strix/claude-sonnet-4.6" + export LLM_API_KEY="your-strix-api-key" + ``` + + + ```bash + export STRIX_LLM="anthropic/claude-sonnet-4-6" + export LLM_API_KEY="your-api-key" + ``` + + -For best results, use `openai/gpt-5`, `anthropic/claude-sonnet-4-5`, or `vertex_ai/gemini-3-pro-preview`. +For best results, use `strix/claude-sonnet-4.6`, `strix/claude-opus-4.6`, or `strix/gpt-5.2`. ## Run Your First Scan diff --git a/scripts/install.sh b/scripts/install.sh index ae5b11d..7fb158b 100755 --- a/scripts/install.sh +++ b/scripts/install.sh @@ -335,14 +335,18 @@ echo -e "${MUTED} AI Penetration Testing Agent${NC}" echo "" echo -e "${MUTED}To get started:${NC}" echo "" -echo -e " ${CYAN}1.${NC} Set your LLM provider:" -echo -e " ${MUTED}export STRIX_LLM='openai/gpt-5'${NC}" -echo -e " ${MUTED}export LLM_API_KEY='your-api-key'${NC}" +echo -e " ${CYAN}1.${NC} Get your Strix API key:" +echo -e " ${MUTED}https://models.strix.ai${NC}" echo "" -echo -e " ${CYAN}2.${NC} Run a penetration test:" +echo -e " ${CYAN}2.${NC} Set your environment:" +echo -e " ${MUTED}export LLM_API_KEY='your-api-key'${NC}" +echo -e " ${MUTED}export STRIX_LLM='strix/claude-sonnet-4.6'${NC}" +echo "" +echo -e " ${CYAN}3.${NC} Run a penetration test:" echo -e " ${MUTED}strix --target https://example.com${NC}" echo "" echo -e "${MUTED}For more information visit ${NC}https://strix.ai" +echo -e "${MUTED}Supported models ${NC}https://docs.strix.ai/llm-providers/overview" echo -e "${MUTED}Join our community ${NC}https://discord.gg/strix-ai" echo "" diff --git a/strix/config/config.py b/strix/config/config.py index 387834b..53a3726 100644 --- a/strix/config/config.py +++ b/strix/config/config.py @@ -5,6 +5,9 @@ from pathlib import Path from typing import Any +STRIX_API_BASE = "https://models.strix.ai/api/v1" + + class Config: """Configuration Manager for Strix.""" @@ -177,3 +180,30 @@ def apply_saved_config(force: bool = False) -> dict[str, str]: def save_current_config() -> bool: return Config.save_current() + + +def resolve_llm_config() -> tuple[str | None, str | None, str | None]: + """Resolve LLM model, api_key, and api_base based on STRIX_LLM prefix. + + Returns: + tuple: (model_name, api_key, api_base) + """ + model = Config.get("strix_llm") + if not model: + return None, None, None + + api_key = Config.get("llm_api_key") + + if model.startswith("strix/"): + model_name = "openai/" + model[6:] + api_base: str | None = STRIX_API_BASE + else: + model_name = model + api_base = ( + Config.get("llm_api_base") + or Config.get("openai_api_base") + or Config.get("litellm_base_url") + or Config.get("ollama_api_base") + ) + + return model_name, api_key, api_base diff --git a/strix/interface/main.py b/strix/interface/main.py index edd7dd5..e7ab6c0 100644 --- a/strix/interface/main.py +++ b/strix/interface/main.py @@ -51,10 +51,13 @@ def validate_environment() -> None: # noqa: PLR0912, PLR0915 missing_required_vars = [] missing_optional_vars = [] - if not Config.get("strix_llm"): + strix_llm = Config.get("strix_llm") + uses_strix_models = strix_llm and strix_llm.startswith("strix/") + + if not strix_llm: missing_required_vars.append("STRIX_LLM") - has_base_url = any( + has_base_url = uses_strix_models or any( [ Config.get("llm_api_base"), Config.get("openai_api_base"), @@ -96,7 +99,7 @@ def validate_environment() -> None: # noqa: PLR0912, PLR0915 error_text.append("• ", style="white") error_text.append("STRIX_LLM", style="bold cyan") error_text.append( - " - Model name to use with litellm (e.g., 'openai/gpt-5')\n", + " - Model name to use with litellm (e.g., 'anthropic/claude-sonnet-4-6')\n", style="white", ) @@ -135,7 +138,10 @@ def validate_environment() -> None: # noqa: PLR0912, PLR0915 ) error_text.append("\nExample setup:\n", style="white") - error_text.append("export STRIX_LLM='openai/gpt-5'\n", style="dim white") + if uses_strix_models: + error_text.append("export STRIX_LLM='strix/claude-sonnet-4.6'\n", style="dim white") + else: + error_text.append("export STRIX_LLM='anthropic/claude-sonnet-4-6'\n", style="dim white") if missing_optional_vars: for var in missing_optional_vars: @@ -198,17 +204,12 @@ def check_docker_installed() -> None: async def warm_up_llm() -> None: + from strix.config.config import resolve_llm_config + console = Console() try: - model_name = Config.get("strix_llm") - api_key = Config.get("llm_api_key") - api_base = ( - Config.get("llm_api_base") - or Config.get("openai_api_base") - or Config.get("litellm_base_url") - or Config.get("ollama_api_base") - ) + model_name, api_key, api_base = resolve_llm_config() test_messages = [ {"role": "system", "content": "You are a helpful assistant."}, diff --git a/strix/llm/config.py b/strix/llm/config.py index 3426327..1ee2ddd 100644 --- a/strix/llm/config.py +++ b/strix/llm/config.py @@ -1,4 +1,5 @@ from strix.config import Config +from strix.config.config import resolve_llm_config class LLMConfig: @@ -10,7 +11,8 @@ class LLMConfig: timeout: int | None = None, scan_mode: str = "deep", ): - self.model_name = model_name or Config.get("strix_llm") + resolved_model, self.api_key, self.api_base = resolve_llm_config() + self.model_name = model_name or resolved_model if not self.model_name: raise ValueError("STRIX_LLM environment variable must be set and not empty") diff --git a/strix/llm/dedupe.py b/strix/llm/dedupe.py index 9edd6b7..ec15192 100644 --- a/strix/llm/dedupe.py +++ b/strix/llm/dedupe.py @@ -5,7 +5,7 @@ from typing import Any import litellm -from strix.config import Config +from strix.config.config import resolve_llm_config logger = logging.getLogger(__name__) @@ -155,14 +155,7 @@ def check_duplicate( comparison_data = {"candidate": candidate_cleaned, "existing_reports": existing_cleaned} - model_name = Config.get("strix_llm") - api_key = Config.get("llm_api_key") - api_base = ( - Config.get("llm_api_base") - or Config.get("openai_api_base") - or Config.get("litellm_base_url") - or Config.get("ollama_api_base") - ) + model_name, api_key, api_base = resolve_llm_config() messages = [ {"role": "system", "content": DEDUPE_SYSTEM_PROMPT}, diff --git a/strix/llm/llm.py b/strix/llm/llm.py index 311de35..8133fe3 100644 --- a/strix/llm/llm.py +++ b/strix/llm/llm.py @@ -200,15 +200,10 @@ class LLM: "stream_options": {"include_usage": True}, } - if api_key := Config.get("llm_api_key"): - args["api_key"] = api_key - if api_base := ( - Config.get("llm_api_base") - or Config.get("openai_api_base") - or Config.get("litellm_base_url") - or Config.get("ollama_api_base") - ): - args["api_base"] = api_base + if self.config.api_key: + args["api_key"] = self.config.api_key + if self.config.api_base: + args["api_base"] = self.config.api_base if self._supports_reasoning(): args["reasoning_effort"] = self._reasoning_effort diff --git a/strix/llm/memory_compressor.py b/strix/llm/memory_compressor.py index ef0b9ab..f5981f6 100644 --- a/strix/llm/memory_compressor.py +++ b/strix/llm/memory_compressor.py @@ -3,7 +3,7 @@ from typing import Any import litellm -from strix.config import Config +from strix.config.config import Config, resolve_llm_config logger = logging.getLogger(__name__) @@ -104,13 +104,7 @@ def _summarize_messages( conversation = "\n".join(formatted) prompt = SUMMARY_PROMPT_TEMPLATE.format(conversation=conversation) - api_key = Config.get("llm_api_key") - api_base = ( - Config.get("llm_api_base") - or Config.get("openai_api_base") - or Config.get("litellm_base_url") - or Config.get("ollama_api_base") - ) + _, api_key, api_base = resolve_llm_config() try: completion_args: dict[str, Any] = { From 62bb47a88170f94712e2d275b45df80efb915af8 Mon Sep 17 00:00:00 2001 From: 0xallam Date: Thu, 19 Feb 2026 13:46:44 -0800 Subject: [PATCH 10/14] docs: Add Strix Router page to navigation sidebar --- docs/docs.json | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/docs.json b/docs/docs.json index e15b496..27ee5dc 100644 --- a/docs/docs.json +++ b/docs/docs.json @@ -32,6 +32,7 @@ "group": "LLM Providers", "pages": [ "llm-providers/overview", + "llm-providers/models", "llm-providers/openai", "llm-providers/anthropic", "llm-providers/openrouter", From cec741758250ebe8ac72c16138fbf7de2e777f4c Mon Sep 17 00:00:00 2001 From: 0xallam Date: Thu, 19 Feb 2026 13:52:13 -0800 Subject: [PATCH 11/14] docs: Cache bust discord badge --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index fd79f86..3cb4c9f 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,7 @@ Docs Website -[![](https://dcbadge.limes.pink/api/server/8Suzzd9z)](https://discord.gg/strix-ai) +[![](https://dcbadge.limes.pink/api/server/8Suzzd9z?v=2)](https://discord.gg/strix-ai) Ask DeepWiki GitHub Stars From 8cb026b1beffafe0c99b898c25211c774ec9f43e Mon Sep 17 00:00:00 2001 From: 0xallam Date: Thu, 19 Feb 2026 13:53:27 -0800 Subject: [PATCH 12/14] docs: Revert discord badge cache bust --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 3cb4c9f..fd79f86 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,7 @@ Docs Website -[![](https://dcbadge.limes.pink/api/server/8Suzzd9z?v=2)](https://discord.gg/strix-ai) +[![](https://dcbadge.limes.pink/api/server/8Suzzd9z)](https://discord.gg/strix-ai) Ask DeepWiki GitHub Stars From cc6d46a838b749c51c0a0e7889bf881e616c9b9f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 19 Feb 2026 19:42:25 +0000 Subject: [PATCH 13/14] chore(deps): bump pypdf from 6.6.2 to 6.7.1 Bumps [pypdf](https://github.com/py-pdf/pypdf) from 6.6.2 to 6.7.1. - [Release notes](https://github.com/py-pdf/pypdf/releases) - [Changelog](https://github.com/py-pdf/pypdf/blob/main/CHANGELOG.md) - [Commits](https://github.com/py-pdf/pypdf/compare/6.6.2...6.7.1) --- updated-dependencies: - dependency-name: pypdf dependency-version: 6.7.1 dependency-type: indirect ... Signed-off-by: dependabot[bot] --- poetry.lock | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/poetry.lock b/poetry.lock index 37a393c..9367ef4 100644 --- a/poetry.lock +++ b/poetry.lock @@ -4373,9 +4373,10 @@ ptyprocess = ">=0.5" name = "pillow" version = "12.1.1" description = "Python Imaging Library (fork)" -optional = false +optional = true python-versions = ">=3.10" groups = ["main"] +markers = "extra == \"sandbox\"" files = [ {file = "pillow-12.1.1-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:1f1625b72740fdda5d77b4def688eb8fd6490975d06b909fd19f13f391e077e0"}, {file = "pillow-12.1.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:178aa072084bd88ec759052feca8e56cbb14a60b39322b99a049e58090479713"}, @@ -4744,9 +4745,10 @@ testing = ["google-api-core (>=1.31.5)"] name = "protobuf" version = "6.33.5" description = "" -optional = false +optional = true python-versions = ">=3.9" groups = ["main"] +markers = "extra == \"vertex\"" files = [ {file = "protobuf-6.33.5-cp310-abi3-win32.whl", hash = "sha256:d71b040839446bac0f4d162e758bea99c8251161dae9d0983a3b88dee345153b"}, {file = "protobuf-6.33.5-cp310-abi3-win_amd64.whl", hash = "sha256:3093804752167bcab3998bec9f1048baae6e29505adaf1afd14a37bddede533c"}, @@ -5235,21 +5237,20 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pypdf" -version = "6.6.2" +version = "6.7.1" description = "A pure-python PDF library capable of splitting, merging, cropping, and transforming PDF files" -optional = true +optional = false python-versions = ">=3.9" groups = ["main"] -markers = "extra == \"sandbox\"" files = [ - {file = "pypdf-6.6.2-py3-none-any.whl", hash = "sha256:44c0c9811cfb3b83b28f1c3d054531d5b8b81abaedee0d8cb403650d023832ba"}, - {file = "pypdf-6.6.2.tar.gz", hash = "sha256:0a3ea3b3303982333404e22d8f75d7b3144f9cf4b2970b96856391a516f9f016"}, + {file = "pypdf-6.7.1-py3-none-any.whl", hash = "sha256:a02ccbb06463f7c334ce1612e91b3e68a8e827f3cee100b9941771e6066b094e"}, + {file = "pypdf-6.7.1.tar.gz", hash = "sha256:6b7a63be5563a0a35d54c6d6b550d75c00b8ccf36384be96365355e296e6b3b0"}, ] [package.extras] crypto = ["cryptography"] cryptodome = ["PyCryptodome"] -dev = ["black", "flit", "pip-tools", "pre-commit", "pytest-cov", "pytest-socket", "pytest-timeout", "pytest-xdist", "wheel"] +dev = ["flit", "pip-tools", "pre-commit", "pytest-cov", "pytest-socket", "pytest-timeout", "pytest-xdist", "wheel"] docs = ["myst_parser", "sphinx", "sphinx_rtd_theme"] full = ["Pillow (>=8.0.0)", "cryptography"] image = ["Pillow (>=8.0.0)"] From 1833f1a021eca77e1a83cc3c8e4424a06da5666c Mon Sep 17 00:00:00 2001 From: 0xallam Date: Thu, 19 Feb 2026 14:12:59 -0800 Subject: [PATCH 14/14] chore: Bump version to 0.8.0 --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 6c32647..ab8ca11 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [tool.poetry] name = "strix-agent" -version = "0.7.0" +version = "0.8.0" description = "Open-source AI Hackers for your apps" authors = ["Strix "] readme = "README.md"