aws-acmpca-sign-as-via-issue
Issue a certificate for an arbitrary subject/SAN signed by the CA's key.
match
A conjunctive graph pattern. Variables (?x) bind node ids; every clause must hold.
where
node_type(?ca) == AWS::ACMPCA::CertificateAuthority
?ca node_class ==
SigningKey
optional
Present → upgrade the emitted state; absent → downgrade (not a hard requirement).
{'principal': None}
CanRead {'ca': None}
emit
| source type | Identity |
|---|---|
| source | ?principal |
| target | ?ca |
| permissions | acm-pca:IssueCertificate acm-pca:GetCertificate |
| conditions | iam_permission condition_expression service_state |
| state logic | if CA.Status != ACTIVE: CONDITIONAL(service_state); elif not (matched(optional[0]) or principal has acm-pca:GetCertificate on ?ca): CONDITIONAL(iam_permission); elif acm-pca:TemplateArn condition pins issuance to a template that cannot express the forged subject/SAN: CONDITIONAL(condition_expression); else ACTIVE |
Narrative
{principal.name} can issue a certificate for an arbitrary subject/SAN signed by CA {ca.name} (acm-pca:IssueCertificate + acm-pca:GetCertificate), effectively signing as the CA's private key.
Raw rule rules/derived/aws/acmpca.yaml
id: aws-acmpca-sign-as-via-issue
emits: CanSignAs
description: Issue a certificate for an arbitrary subject/SAN signed by the CA's key.
match:
- - principal: null
- CanSignAs
- ca: null
where:
- node_type(?ca) == AWS::ACMPCA::CertificateAuthority
- ?ca node_class == SigningKey
optional:
- - principal: null
- CanRead
- ca: null
emit:
source_type: Identity
source: ?principal
target: ?ca
permissions:
- acm-pca:IssueCertificate
- acm-pca:GetCertificate
conditions:
- iam_permission
- condition_expression
- service_state
state_logic: 'if CA.Status != ACTIVE: CONDITIONAL(service_state); elif not (matched(optional[0]) or
principal has acm-pca:GetCertificate on ?ca): CONDITIONAL(iam_permission); elif acm-pca:TemplateArn
condition pins issuance to a template that cannot express the forged subject/SAN: CONDITIONAL(condition_expression);
else ACTIVE'
confidence: min(contributing_confidences) * 0.95
derived_from:
- <CanSignAs edge_id>
- <CanRead edge_id (optional GetCertificate)>
false_positive_note: 'IssueCertificate returns only an ARN; retrieving the usable PEM needs acm-pca:GetCertificate
-> without it, CONDITIONAL(iam_permission). A CA in DISABLED/PENDING_CERTIFICATE/EXPIRED status cannot
sign -> CONDITIONAL(service_state). Honor the acm-pca:TemplateArn condition: a policy pinning a narrow
non-APIPassthrough EndEntity template limits the forgeable fields -> CONDITIONAL(condition_expression)
if the needed subject/SAN is not expressible. This edge is the minting capability only; downstream
impersonation requires a trust consumer (separate rule).'
narrative: '{principal.name} can issue a certificate for an arbitrary subject/SAN signed by CA {ca.name}
(acm-pca:IssueCertificate + acm-pca:GetCertificate), effectively signing as the CA''s private key.'