Skip to content
This repository was archived by the owner on Oct 10, 2026. It is now read-only.

v0.5.0 - the set-operator tranche

Choose a tag to compare

@Dashtid Dashtid released this 01 Sep 08:12
· 42 commits to main since this release
6cbd388

ForAllValues: under an Allow fails open. AWS says not to use set operators
on single-valued context keys at all — this tranche shows what happens when you do.

The tranche

Seven vectors covering the ForAllValues: / ForAnyValue: qualifiers, plus
matcher support, a condition.qualifier schema property, and two new judgment
patterns. github-aws suite 0.5.0; the corpus is now 14 suites / 144 vectors.

AWS's own guidance is blunt:

Do not use condition set operators ForAllValues or ForAnyValue with
single-valued context keys. Using condition set operators with single-valued
context keys can lead to overly permissive policies.

Three results:

1. ForAllValues under an Allow fails open. It "also returns true if there
are no context keys in the request". So a trust policy scoped to a deployment
environment with ForAllValues:StringEquals admits every job that references no
environment — the ordinary case. ForAnyValue returns false on the same token, and
so does the plain operator. Same intent, same token, opposite verdict: the qualifier
alone decides whether an absent claim opens or closes the door.

2. Neither qualifier tightens a poisoned OR-list. ForAllValues reads as "the
subject must satisfy all the listed values", which would neutralise a loose value.
It does not. The qualifier ranges over the values the request supplies, not the
values in the policy — and a sub claim is single-valued. The policy's values are
still ORed and the loosest one still sets the boundary.

3. A correct aud pin does not rescue it. Context keys in a Condition block
are ANDed, but a clause that returns true on an absent claim contributes nothing to
a conjunction. The block ends up no stronger than its aud pin alone — and an aud
pin admits every repository on the issuer.

Matcher

condition.qualifier accepts ForAllValues or ForAnyValue on the AWS string
consumers. Set semantics are general: a list-valued claim gets real set evaluation,
not just the single-valued case. Python's all() / any() over an empty sequence
reproduce AWS's documented asymmetry exactly, so the implementation is three lines
and the comment is longer than the code.

Provenance

Unchanged at 11 observed, all in the AWS tranche, each linking a committed
transcript under
observations/.
The new vectors are documented, cited to AWS's single-vs-multivalued context keys
page and read against it before any were written.

Install

pip install subvectors==0.5.0

The wheel ships the entire corpus. The vectors are CC0; everything else is
Apache-2.0.