From 886b1abfa58fb68a72efda279102da5853709764 Mon Sep 17 00:00:00 2001 From: Cristian Magherusan-Stanciu Date: Thu, 5 Nov 2026 19:26:27 +0100 Subject: [PATCH 1/2] fix(deps): adopt the latest reviewed cloud-commitments-go purchase safeguards Bumps all four cloud-commitments-go modules together to go main, which adds the purchase-safety fixes reviewed since the previous pin: RI quantities from Cost Explorer are rounded down with their costs scaled (#682), GCP lists only live commitments (#685), exchange targets keep the source RI's offering type (#688), and purchase counts that do not fit int32 are refused before any AWS call (#684). The MCP server does no RI exchange lookups, so the offering-type requirement does not affect it. No replace directives; go mod verify passes. Closes #35 Co-Authored-By: Claude Opus 5.5 --- go.mod | 34 ++++++++++++++--------------- go.sum | 68 +++++++++++++++++++++++++++++----------------------------- 2 files changed, 51 insertions(+), 51 deletions(-) diff --git a/go.mod b/go.mod index a422444..dcabeae 100644 --- a/go.mod +++ b/go.mod @@ -4,8 +4,8 @@ go 1.26.10 require ( github.com/aws/aws-sdk-go-v2 v1.47.5 - github.com/aws/aws-sdk-go-v2/config v1.33.10 // indirect - github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.3 // indirect + github.com/aws/aws-sdk-go-v2/config v1.33.13 // indirect + github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.5 // indirect github.com/aws/aws-sdk-go-v2/service/ec2 v1.343.0 github.com/aws/aws-sdk-go-v2/service/elasticache v1.64.2 github.com/aws/aws-sdk-go-v2/service/memorydb v1.42.8 @@ -22,7 +22,7 @@ require ( cloud.google.com/go/iam v1.14.0 // indirect cloud.google.com/go/longrunning v1.3.0 // indirect cloud.google.com/go/recommender v1.20.0 // indirect - cloud.google.com/go/resourcemanager v1.16.0 // indirect + cloud.google.com/go/resourcemanager v1.18.1 // indirect github.com/Azure/azure-sdk-for-go/sdk/azcore v1.23.3 github.com/Azure/azure-sdk-for-go/sdk/azidentity v1.15.0 // indirect github.com/Azure/azure-sdk-for-go/sdk/internal v1.13.0 // indirect @@ -33,15 +33,15 @@ require ( github.com/Azure/azure-sdk-for-go/sdk/resourcemanager/resources/armsubscriptions v1.3.0 // indirect github.com/Azure/azure-sdk-for-go/sdk/resourcemanager/sql/armsql v1.2.0 // indirect github.com/AzureAD/microsoft-authentication-library-for-go v1.10.1 // indirect - github.com/aws/aws-sdk-go-v2/credentials v1.20.10 // indirect - github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.4 // indirect + github.com/aws/aws-sdk-go-v2/credentials v1.20.13 // indirect + github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.5 // indirect github.com/aws/aws-sdk-go-v2/internal/configsources v1.5.8 // indirect github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.8.8 // indirect github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.23 // indirect github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.14.8 // indirect github.com/aws/aws-sdk-go-v2/service/savingsplans v1.41.1 - github.com/aws/aws-sdk-go-v2/service/sso v1.38.5 // indirect - github.com/aws/aws-sdk-go-v2/service/ssooidc v1.43.5 // indirect + github.com/aws/aws-sdk-go-v2/service/sso v1.39.1 // indirect + github.com/aws/aws-sdk-go-v2/service/ssooidc v1.44.1 // indirect github.com/aws/smithy-go v1.28.7 github.com/felixge/httpsnoop v1.1.0 // indirect github.com/go-logr/logr v1.4.4 // indirect @@ -68,15 +68,15 @@ require ( google.golang.org/genproto v0.0.0-20261012220534-4341edf3f941 // indirect google.golang.org/genproto/googleapis/api v0.0.0-20261012220534-4341edf3f941 // indirect google.golang.org/genproto/googleapis/rpc v0.0.0-20261019180522-ce908d29299b // indirect - google.golang.org/grpc v1.84.0 // indirect + google.golang.org/grpc v1.85.0 // indirect google.golang.org/protobuf v1.36.12 ) require ( - github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261104073158-39dc6e76ed43 - github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261104073158-39dc6e76ed43 - github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261104073158-39dc6e76ed43 - github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261104073158-39dc6e76ed43 + github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261105181516-07b7b48d9463 + github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261105181516-07b7b48d9463 + github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261105181516-07b7b48d9463 + github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261105181516-07b7b48d9463 github.com/aws/aws-sdk-go-v2/service/sts v1.51.6 github.com/google/jsonschema-go v0.4.3 github.com/google/uuid v1.6.0 @@ -84,11 +84,11 @@ require ( ) require ( - cel.dev/expr v0.25.2 // indirect + cel.dev/expr v0.25.3 // indirect cloud.google.com/go/auth v0.24.1 // indirect cloud.google.com/go/auth/oauth2adapt v0.3.0 // indirect cloud.google.com/go/monitoring v1.30.0 // indirect - cloud.google.com/go/redis v1.24.0 // indirect + cloud.google.com/go/redis v1.29.0 // indirect cloud.google.com/go/storage v1.70.0 // indirect github.com/Azure/azure-sdk-for-go/sdk/resourcemanager/billingbenefits/armbillingbenefits v1.0.0 // indirect github.com/Azure/azure-sdk-for-go/sdk/resourcemanager/cosmos/armcosmos/v2 v2.7.0 // indirect @@ -98,11 +98,11 @@ require ( github.com/GoogleCloudPlatform/opentelemetry-operations-go/exporter/metric v0.57.0 // indirect github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/resourcemapping v0.57.0 // indirect github.com/aws/aws-sdk-go-v2/internal/v4a v1.5.8 // indirect - github.com/aws/aws-sdk-go-v2/service/organizations v1.62.2 // indirect - github.com/aws/aws-sdk-go-v2/service/signin v1.10.5 // indirect + github.com/aws/aws-sdk-go-v2/service/organizations v1.62.4 // indirect + github.com/aws/aws-sdk-go-v2/service/signin v1.12.1 // indirect github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/cncf/xds/go v0.0.0-20260202195803-dba9d589def2 // indirect - github.com/envoyproxy/go-control-plane/envoy v1.37.0 // indirect + github.com/envoyproxy/go-control-plane/envoy v1.39.1-0.20260819172001-e6e3fd93e4be // indirect github.com/envoyproxy/protoc-gen-validate v1.3.3 // indirect github.com/go-jose/go-jose/v4 v4.1.4 // indirect github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 // indirect diff --git a/go.sum b/go.sum index 3eff9f4..82e6373 100644 --- a/go.sum +++ b/go.sum @@ -1,5 +1,5 @@ -cel.dev/expr v0.25.2 h1:K6j46C81hXtZQfuX60cVWQFBJahKSE2gfRbNuvr5bFs= -cel.dev/expr v0.25.2/go.mod h1:hrXvqGP6G6gyx8UAHSHJ5RGk//1Oj5nXQ2NI02Nrsg4= +cel.dev/expr v0.25.3 h1:A2jO8jwOugrrovveCWfj0KEZOfqiLgAcwjpHPhzIGw0= +cel.dev/expr v0.25.3/go.mod h1:hrXvqGP6G6gyx8UAHSHJ5RGk//1Oj5nXQ2NI02Nrsg4= cloud.google.com/go v0.123.0 h1:2NAUJwPR47q+E35uaJeYoNhuNEM9kM8SjgRgdeOJUSE= cloud.google.com/go v0.123.0/go.mod h1:xBoMV08QcqUGuPW65Qfm1o9Y4zKZBpGS+7bImXLTAZU= cloud.google.com/go/auth v0.24.1 h1:NTmd2iJb4DsGIav0KiqFMYI88nMshA2wnFMBatRmoCs= @@ -20,10 +20,10 @@ cloud.google.com/go/monitoring v1.30.0 h1:r/d+JUbyKmJ8b07iznuKfzVzrIXTWxHQ3lBRm3 cloud.google.com/go/monitoring v1.30.0/go.mod h1:htlUR0QWVMrjFzZmN4LGnMAve9xB/eduwjmINxVZ8RM= cloud.google.com/go/recommender v1.20.0 h1:6nNp/5aXKYo8LXMwX8V6nNC0qVXRIDu3cDlCd7eS+fQ= cloud.google.com/go/recommender v1.20.0/go.mod h1:gf3NcTlopYDtblIZfQB+J5tDasCE3OztgqQFt6Qd2V4= -cloud.google.com/go/redis v1.24.0 h1:lV6xFUF7t3fm2ZRFjB4IVNkznG9EVwetYVJYwzmW8pc= -cloud.google.com/go/redis v1.24.0/go.mod h1:ebtw9WLFKswecHO2ifNykuteNJNwoPqMCHz4UI11kF4= -cloud.google.com/go/resourcemanager v1.16.0 h1:aDf2RuuQ1Z+kbHHDzHyJNMHPGRFK+cMYfZIhWRaeRX0= -cloud.google.com/go/resourcemanager v1.16.0/go.mod h1:Hn4HPkLRnTuiUhFEFJg736Brt7BwlS84xYU06sc3STc= +cloud.google.com/go/redis v1.29.0 h1:AoJGdFMQob09WpEzDl+k+RTsbe9Nnq3jkNBnXBBRV2I= +cloud.google.com/go/redis v1.29.0/go.mod h1:JOH480besJ3ODjttjT18BhysgvbeEnhCAgJrpi4/5ys= +cloud.google.com/go/resourcemanager v1.18.1 h1:xdaDmfzM08PA2Zs8hU8ej1TXQTJAcRoHbvQpaAEPYj0= +cloud.google.com/go/resourcemanager v1.18.1/go.mod h1:LjIioOpdFo5J1aFG9R51YqeBN5L55vElAG70dzFD/wg= cloud.google.com/go/storage v1.70.0 h1:LQNHn0rRF94jVFfF3e416IzdQqIufa5GfF6HilQxb80= cloud.google.com/go/storage v1.70.0/go.mod h1:W84cNa070TZIegvTW67CBY+f5rxux8EJMb7YyiHdrls= cloud.google.com/go/trace v1.16.0 h1:GmQovzFc5F0CNfl0VLgL64aoTtu7xsM0YajW2GlG9+E= @@ -74,30 +74,30 @@ github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/cloudmock v0 github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/cloudmock v0.57.0/go.mod h1:dzcEjy1WJ0Q4u9twNR3LcLhNoYMRCrMCMafpxa0TjPQ= github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/resourcemapping v0.57.0 h1:RoO5+d7uCmDqovLrHCr2/BuViUXvdcrNxyNM1pN9dDQ= github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/resourcemapping v0.57.0/go.mod h1:YqwkQPrWSC7+byyc1VlKbWLBF5JsW5IoL6xUkemYSXk= -github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261104073158-39dc6e76ed43 h1:XSrxaJ8RmRaNyqFTjI9LMFTNjEUkz85Bw+8eUDyqmn0= -github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261104073158-39dc6e76ed43/go.mod h1:pseCFRgm1rzBKomktjw6E0ayxmVE7XfHHiOmew4ka+g= -github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261104073158-39dc6e76ed43 h1:4mo8ao/sqPQgu00DtvfosogAKDes5F6gU3RHLkQQWoI= -github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261104073158-39dc6e76ed43/go.mod h1:6qNUs6GcB4Dn/mOEbd7Y+IG4tWzyV7Rtc/z0YwC2nwE= -github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261104073158-39dc6e76ed43 h1:A5KbgXxnZ9psdreid61aH5PbXiIKUvyR/WN+st6Lo24= -github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261104073158-39dc6e76ed43/go.mod h1:X+73EdStvYV6pqEVZZFyMfLG1frORlO9B1IsuK0LfOs= -github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261104073158-39dc6e76ed43 h1:+T6roXAS0IsEJoLhpG9OVxoMk5zXRzZB5ZVOmQo092o= -github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261104073158-39dc6e76ed43/go.mod h1:aj4d0YEmBg1A46rIXKG+GkTFc1d/xwmveJ97kDD1oPs= +github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261105181516-07b7b48d9463 h1:90Xb0+QAo8cReggdJg2vGuA9e1+X8JlwRjG3IeXdxT8= +github.com/LeanerCloud/cloud-commitments-go/pkg v0.0.0-20261105181516-07b7b48d9463/go.mod h1:l9V+ecJCfAigYr6XiK9kpIUemF9bnXOKHJN1s4TPsM0= +github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261105181516-07b7b48d9463 h1:edPHKpJCXpnpO5E9oroLrVeyCS/0jpn/ttBEli7afTA= +github.com/LeanerCloud/cloud-commitments-go/providers/aws v0.0.0-20261105181516-07b7b48d9463/go.mod h1:tsjVv5Rj/QGuyVQ6w+sZ0w8fn/imBTNL5l6okmEBJn8= +github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261105181516-07b7b48d9463 h1:HQkgVNCj/Q5C9jA6vBlXRX5cdJZU43p+BHQyfpwA8Lg= +github.com/LeanerCloud/cloud-commitments-go/providers/azure v0.0.0-20261105181516-07b7b48d9463/go.mod h1:X+73EdStvYV6pqEVZZFyMfLG1frORlO9B1IsuK0LfOs= +github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261105181516-07b7b48d9463 h1:QMRI04L8aIgdbRZ9RetgleaD2IukYb6E29jUaV6MnP0= +github.com/LeanerCloud/cloud-commitments-go/providers/gcp v0.0.0-20261105181516-07b7b48d9463/go.mod h1:kfbQ5CsDr1958iSuZq6edcuB0es62XRCXGn/hFFYBW0= github.com/aws/aws-sdk-go-v2 v1.47.5 h1:5yA+A+BiXbDq1ZLbYwPViwhEGDMdR0MEhL8Jh2LnLS4= github.com/aws/aws-sdk-go-v2 v1.47.5/go.mod h1:iNIkogrRvFwm+1OQIUOP2lPBtlXZboOIUWiCa+pHEMw= -github.com/aws/aws-sdk-go-v2/config v1.33.10 h1:RRb0GghYqq2ikMXzfT4r9NO9lVhOld3FIhJJWDIdk+w= -github.com/aws/aws-sdk-go-v2/config v1.33.10/go.mod h1:BDSA7QGh6yrNQA5Z5aBnHWKMWdJDMD4IOlB4QjYSp5E= -github.com/aws/aws-sdk-go-v2/credentials v1.20.10 h1:ItSjcLk+2M15RnRxO105uVIqLiVQn8y3gaeHC7W0iqs= -github.com/aws/aws-sdk-go-v2/credentials v1.20.10/go.mod h1:eO4GlmGXB+gx+zDbhu3IENEFOmjrbVKJtOptJiIhngc= -github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.4 h1:7ksj/zMap9+831SmNQZkcpmfuATp3DKr4BfLNnBdYXM= -github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.4/go.mod h1:zhi8vDrD1dj76ysTWS6Ny1y6/EEW1Jrq2y8lzKeoqfs= +github.com/aws/aws-sdk-go-v2/config v1.33.13 h1:u52x6ISQOx172tpwM0VRxhJzEsTJYpMcEYUGM2A1wrw= +github.com/aws/aws-sdk-go-v2/config v1.33.13/go.mod h1:/ixtz6XPHb42zekjQ0LqD9XjTpTysNWhIGwufY1OzI4= +github.com/aws/aws-sdk-go-v2/credentials v1.20.13 h1:j4z41OtspmQ3ftQycaDunJ26b69a9SHfaSVUPqgRv8k= +github.com/aws/aws-sdk-go-v2/credentials v1.20.13/go.mod h1:SgPA1oS3b+dlMxZb618jDmGNscpXSCaxz15igS52OlE= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.5 h1:iXjy2SFhGYNB1jWZBhQqq8HbhsbPF23w+/zbMvPXsTg= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.20.5/go.mod h1:k0RUiBnyXU0AXRJ9tJmY2jQke6XUIX2PNVnWtvgaPtc= github.com/aws/aws-sdk-go-v2/internal/configsources v1.5.8 h1:gzIWc3DTPfPbWKrQnmL6BV6WD7NPD1htxzgdk/bQ/Z4= github.com/aws/aws-sdk-go-v2/internal/configsources v1.5.8/go.mod h1:vvUA5cDAZWGo4R14FZPZfXfJCmgsafOWEq78Kg0D+ug= github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.8.8 h1:PWv+vG8aCLS8qd+HPdYhK7Vees90aKHWFFQ1AGYD/8E= github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.8.8/go.mod h1:xxPZEpflYHJA12366ZGyq66z9dHPCoeCIu99Jck+MPw= github.com/aws/aws-sdk-go-v2/internal/v4a v1.5.8 h1:WOp5De9iWdEHDPh2Kb0tBP3vGBm/dVAuRGh4a4tqduo= github.com/aws/aws-sdk-go-v2/internal/v4a v1.5.8/go.mod h1:z8W8YgfhbWl62XqcTtK+CxPrE+iHGRVUOtrrbIOp7ZY= -github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.3 h1:n41F2z+KbBLPZhAN9H8wnS4OQOEVvaAaKbAHZLvoNsQ= -github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.3/go.mod h1:kBJcNrSJh7iCpRJM6Up2l2IU/nFSi6+6cFpNzFXwVKk= +github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.5 h1:yoMP1GeXqKuEcbe2V/hrLYFANnx8Ypx83NSR6e2u0BA= +github.com/aws/aws-sdk-go-v2/service/costexplorer v1.74.5/go.mod h1:aYP4DYWZpu+W9v0Izt9D/nLllZ95eeG5b5FEQmVIpMU= github.com/aws/aws-sdk-go-v2/service/ec2 v1.343.0 h1:pOxNUJbUOy779gx205gEpySpT5fu3B0ifPD8jBxujZI= github.com/aws/aws-sdk-go-v2/service/ec2 v1.343.0/go.mod h1:khWfxrzSgMjGMAZIaYAHu3IobEo7KRRNwPYaHb1zpng= github.com/aws/aws-sdk-go-v2/service/elasticache v1.64.2 h1:8LoJKTkN9guyrImkZQyAdsMdRdtAHiIqg3q91s11DAc= @@ -110,20 +110,20 @@ github.com/aws/aws-sdk-go-v2/service/memorydb v1.42.8 h1:c6BUnr/ylsFcRXFryv1aP0O github.com/aws/aws-sdk-go-v2/service/memorydb v1.42.8/go.mod h1:ZJl5cb8+0steckQxAP8KsAsGHnh5iw2JNWbQ30oklRk= github.com/aws/aws-sdk-go-v2/service/opensearch v1.87.1 h1:LRiVk0MRbFFPvqSsGfZ8v9Pbahp1qTuPlT8e+oN+4cY= github.com/aws/aws-sdk-go-v2/service/opensearch v1.87.1/go.mod h1:fuFUaBWYP6zTqxiwBUg0btczrZ6owOV5XHvBls/nmB8= -github.com/aws/aws-sdk-go-v2/service/organizations v1.62.2 h1:X5tj7X0DVjs3BuFLeRXilnjMYur9KANyhsFnLFeZkD8= -github.com/aws/aws-sdk-go-v2/service/organizations v1.62.2/go.mod h1:NeeqgmO9OuZqxYS2QhN1gP5xsuWnbQRx1nmKeHyxELA= +github.com/aws/aws-sdk-go-v2/service/organizations v1.62.4 h1:amAwv6EBqkPkEVG/EAgiHU5MnAg8JwAv+bvT6Fph8ok= +github.com/aws/aws-sdk-go-v2/service/organizations v1.62.4/go.mod h1:DLYXemnX70yBq6rTxkFP7YopkQ/TlWIO1KAParzUnrw= github.com/aws/aws-sdk-go-v2/service/rds v1.131.2 h1:Rytfx+dmiAPJDxJKXCbK6X4staGfRUjfFDx8Lcy/LA8= github.com/aws/aws-sdk-go-v2/service/rds v1.131.2/go.mod h1:jh7YjzSQebRzJX2lw/h9tv/1wHo5wDJguuXmsX6SIDs= github.com/aws/aws-sdk-go-v2/service/redshift v1.71.6 h1:zs2Y6cncJortrymZejl7ojEYgemrkckWpO9MvoPkXcs= github.com/aws/aws-sdk-go-v2/service/redshift v1.71.6/go.mod h1:A1dvQydJomqM8AaVW5PViZ5vnqQE/T90OjBuDL16vOs= github.com/aws/aws-sdk-go-v2/service/savingsplans v1.41.1 h1:RTOKvHW2G6VJIZ0iRnB+vkwo83V7yKKuBl/ocd/Hv2E= github.com/aws/aws-sdk-go-v2/service/savingsplans v1.41.1/go.mod h1:H8SOLkY7cFy646J/xcrQz9ydpcYFDJL83vYR9ScBqU8= -github.com/aws/aws-sdk-go-v2/service/signin v1.10.5 h1:oFsZ3u5PPFSO1YZDGKFgyDuwgpbv/sTmVShEZfRnyaE= -github.com/aws/aws-sdk-go-v2/service/signin v1.10.5/go.mod h1:P+IzYJeldxO0mHt8fX4cglzexP3akO94C/UuEA2ojP0= -github.com/aws/aws-sdk-go-v2/service/sso v1.38.5 h1:EYD6E6CsgRQPazaOfZ6suyTgfZjg07HoT4S3qB9Exkg= -github.com/aws/aws-sdk-go-v2/service/sso v1.38.5/go.mod h1:hHg7OZNN1/U62f3Q5mebJYKO4f97vZC+s0fNAsPLnMk= -github.com/aws/aws-sdk-go-v2/service/ssooidc v1.43.5 h1:v6V0AnJ0aDmivAIie/6iT7sGpjnNmzaAdxZwZ0dhwqI= -github.com/aws/aws-sdk-go-v2/service/ssooidc v1.43.5/go.mod h1:P2Lqn27Kph9z400MFOYIebFnKjZEwyUIAva6fFFMiRY= +github.com/aws/aws-sdk-go-v2/service/signin v1.12.1 h1:WZLC+k/CZx11kZGQDqu9mpA8yhiXGX2I//jhuJE1FDo= +github.com/aws/aws-sdk-go-v2/service/signin v1.12.1/go.mod h1:wxAk0D2oVBSjuXEIzvcKxTZfM90zticdAbh/VD42L0Y= +github.com/aws/aws-sdk-go-v2/service/sso v1.39.1 h1:4VB/dnDo7pmXSLQMszSoBzWndENuc7mzwTpD6lQn77A= +github.com/aws/aws-sdk-go-v2/service/sso v1.39.1/go.mod h1:UGsEYgWz4Gi+46vDQ5zkFLqUgJziyOE2SXjZjgmfmHc= +github.com/aws/aws-sdk-go-v2/service/ssooidc v1.44.1 h1:w8yui2ZqdHmGwVBDGvazoIvKw/DnLENBLkYnN8q8iqo= +github.com/aws/aws-sdk-go-v2/service/ssooidc v1.44.1/go.mod h1:gJSdIY6YUzDvqQLcMtPVZgBRHrFwzHryvpE8Igzbxps= github.com/aws/aws-sdk-go-v2/service/sts v1.51.6 h1:BVjKrtRUtSYKztBCCfE1oAB+d3ViKcW2cKZfserOqMQ= github.com/aws/aws-sdk-go-v2/service/sts v1.51.6/go.mod h1:eSukFLeLkPMm+1OxDR+F0joauZdyBkF47Ow7MqjZiJw= github.com/aws/smithy-go v1.28.7 h1:h/n1SHrwVtaDYLz8mR1/Kq4Xh4RaFbFW7bOYckg9mfE= @@ -134,8 +134,8 @@ github.com/cncf/xds/go v0.0.0-20260202195803-dba9d589def2 h1:aBangftG7EVZoUb69Os github.com/cncf/xds/go v0.0.0-20260202195803-dba9d589def2/go.mod h1:qwXFYgsP6T7XnJtbKlf1HP8AjxZZyzxMmc+Lq5GjlU4= github.com/envoyproxy/go-control-plane v0.14.0 h1:hbG2kr4RuFj222B6+7T83thSPqLjwBIfQawTkC++2HA= github.com/envoyproxy/go-control-plane v0.14.0/go.mod h1:NcS5X47pLl/hfqxU70yPwL9ZMkUlwlKxtAohpi2wBEU= -github.com/envoyproxy/go-control-plane/envoy v1.37.0 h1:u3riX6BoYRfF4Dr7dwSOroNfdSbEPe9Yyl09/B6wBrQ= -github.com/envoyproxy/go-control-plane/envoy v1.37.0/go.mod h1:DReE9MMrmecPy+YvQOAOHNYMALuowAnbjjEMkkWOi6A= +github.com/envoyproxy/go-control-plane/envoy v1.39.1-0.20260819172001-e6e3fd93e4be h1:SWe0x6yfglnxuvOiYgTTnNq7QD/yvqthOh1RBI8Bj8w= +github.com/envoyproxy/go-control-plane/envoy v1.39.1-0.20260819172001-e6e3fd93e4be/go.mod h1:PYEOlng9XcrulfyWpm49jECTPV0LT4q8cO7fLW/xwgk= github.com/envoyproxy/go-control-plane/ratelimit v0.1.0 h1:/G9QYbddjL25KvtKTv3an9lx6VBE2cnb8wp1vEGNYGI= github.com/envoyproxy/go-control-plane/ratelimit v0.1.0/go.mod h1:Wk+tMFAFbCXaJPzVVHnPgRKdUdwW/KdbRt94AzgRee4= github.com/envoyproxy/protoc-gen-validate v1.3.3 h1:MVQghNeW+LZcmXe7SY1V36Z+WFMDjpqGAGacLe2T0ds= @@ -242,8 +242,8 @@ google.golang.org/genproto/googleapis/api v0.0.0-20261012220534-4341edf3f941 h1: google.golang.org/genproto/googleapis/api v0.0.0-20261012220534-4341edf3f941/go.mod h1:AuGAdi9KnXss7xbLxIKhCvk+Ro/SxpET/iS45DNYN+M= google.golang.org/genproto/googleapis/rpc v0.0.0-20261019180522-ce908d29299b h1:6WNWHZk91dp4gZ25642OALkuG1UVNZbwENJD19DnB8k= google.golang.org/genproto/googleapis/rpc v0.0.0-20261019180522-ce908d29299b/go.mod h1:OaIUM3+LpYcK2GXM4FTmhWoIq371Owdr+Cc7/BsYHHc= -google.golang.org/grpc v1.84.0 h1:soMyaPJ8pAak5PIQ0DGBUir0XRo2fRoMqhNWMLlLxO0= -google.golang.org/grpc v1.84.0/go.mod h1:ljCht0DrxQrXBDRTZp52Qxh3Ffk8CdYm2sj4O2QN2C0= +google.golang.org/grpc v1.85.0 h1:BPBCfuVRQ1qvBhKDOq9uvQllMvO59rKsYhXpp7Dd8vw= +google.golang.org/grpc v1.85.0/go.mod h1:0rQrOD58yjal/0EaVbGBANindixsCZNQPDV3VKtaKuQ= google.golang.org/protobuf v1.36.12 h1:pJOKDDOyeXErUroCihFAd5LQuwXBSpVnKGrj5o/fwxc= google.golang.org/protobuf v1.36.12/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= From fb2277d9ce82aff45b0b20d8de0fad14ea04bd1a Mon Sep 17 00:00:00 2001 From: Cristian Magherusan-Stanciu Date: Fri, 6 Nov 2026 07:30:46 +0100 Subject: [PATCH 2/2] fix(tools): drop reservation rows whose quantity rounded down to zero Since cloud-commitments-go#682 the library rounds fractional Cost Explorer RI quantities down, and a quantity below 1 becomes a row with Count 0 that the parser keeps (it only logs a warning). search_recommendations offered that row although it cannot be bought and the purchase guard refuses Count 0. fetchSearchCombos now skips non-Savings-Plan rows with Count below 1; Savings Plans are sized by hourly commitment and always stay. Tests cover a dropped zero-count reservation and a kept zero-count Savings Plan. Co-Authored-By: Claude Opus 5.5 --- tools/search_recommendations.go | 12 +++++- tools/search_recommendations_fanout_test.go | 42 +++++++++++++++++++++ 2 files changed, 53 insertions(+), 1 deletion(-) diff --git a/tools/search_recommendations.go b/tools/search_recommendations.go index d181126..dab02a1 100644 --- a/tools/search_recommendations.go +++ b/tools/search_recommendations.go @@ -269,7 +269,17 @@ func fetchSearchCombos( } return nil, fmt.Errorf("get recommendations (term=%s, payment_option=%s): %w", combo.term, combo.payment, err) } - recs = append(recs, got...) + for i := range got { + rec := &got[i] + // The library rounds fractional Cost Explorer quantities down + // (cloud-commitments-go#682), so a reservation can arrive with + // Count 0: it cannot be bought, so it is not offered. Savings Plans + // are sized by hourly commitment, not Count, and always stay. + if rec.CommitmentType != common.CommitmentSavingsPlan && rec.Count < 1 { + continue + } + recs = append(recs, *rec) + } } return recs, nil } diff --git a/tools/search_recommendations_fanout_test.go b/tools/search_recommendations_fanout_test.go index 95f6ecb..a4b5d63 100644 --- a/tools/search_recommendations_fanout_test.go +++ b/tools/search_recommendations_fanout_test.go @@ -188,3 +188,45 @@ func TestSearchRecommendationsEmptyResultIsEmptySliceNotNull(t *testing.T) { assert.NotNil(t, result.Recommendations) assert.Empty(t, result.Recommendations) } + +// TestSearchRecommendationsDropsZeroCountReservations pins that a reservation +// row whose recommended quantity rounded down to 0 (the library rounds +// fractional Cost Explorer quantities down since cloud-commitments-go#682) is +// not offered: it cannot be bought, and the purchase guard refuses Count 0. +func TestSearchRecommendationsDropsZeroCountReservations(t *testing.T) { + t.Parallel() + recs := []common.Recommendation{ + {Provider: common.ProviderAWS, ResourceType: "m5.large", Count: 0}, + {Provider: common.ProviderAWS, ResourceType: "t4g.nano", Count: 1}, + } + client := &fakeRecommendationsClient{recs: recs} + fp := &fakeProvider{name: "aws", services: []common.ServiceType{common.ServiceEC2}, recClient: client} + tool := newTestSearchTool(fp) + + _, result, err := tool.handle(context.Background(), nil, searchRecommendationsArgs{ + Provider: "aws", Service: "ec2", Region: "eu-west-1", TermYears: 1, PaymentOption: "no-upfront", + }) + + require.NoError(t, err) + require.Len(t, result.Recommendations, 1) + assert.Equal(t, "t4g.nano", result.Recommendations[0].ResourceType) + assert.Equal(t, 1, result.Count) +} + +// TestSearchRecommendationsKeepsSavingsPlansRegardlessOfCount pins that the +// zero-count filter never drops a Savings Plan: plans are sized by hourly +// commitment, so their Count is not a purchase quantity. +func TestSearchRecommendationsKeepsSavingsPlansRegardlessOfCount(t *testing.T) { + t.Parallel() + recs := []common.Recommendation{{Provider: common.ProviderAWS, CommitmentType: common.CommitmentSavingsPlan, Count: 0}} + client := &fakeRecommendationsClient{recs: recs} + fp := &fakeProvider{name: "aws", services: []common.ServiceType{common.ServiceSavingsPlansCompute}, recClient: client} + tool := newTestSearchTool(fp) + + _, result, err := tool.handle(context.Background(), nil, searchRecommendationsArgs{ + Provider: "aws", Service: "savings-plans-compute", + }) + + require.NoError(t, err) + assert.Len(t, result.Recommendations, 1) +}