Skip to main content

Service Catalog Portfolios Should Be Shared Within an AWS Organization Only

Overview

This check verifies that AWS Service Catalog portfolios are shared exclusively through AWS Organizations integration rather than direct account-level sharing. Service Catalog portfolios let you organize and distribute approved AWS products (like CloudFormation templates) to your users.

When you share portfolios with individual AWS accounts instead of through your organization, you lose centralized control over who can access and launch those products.

Risk

Sharing Service Catalog portfolios outside your organization creates several security risks:

  • Unauthorized access: External accounts could gain access to sensitive resources or configurations
  • Privilege misuse: Recipients can import and launch products outside your centralized guardrails
  • Configuration drift: Products may be deployed without your standard security controls
  • Audit challenges: Tracking who has access becomes difficult without organizational boundaries
  • Cost exposure: Uncontrolled provisioning can lead to unexpected expenses

Remediation Steps

Prerequisites

You need:

  • Access to the AWS Console with permissions to manage Service Catalog portfolios
  • AWS Organizations integration enabled in Service Catalog
  • Your organization ID (starts with o-)
How to find your organization ID
  1. Go to the AWS Organizations console
  2. Your organization ID appears at the top of the page (format: o-xxxxxxxxxx)

Or use the CLI:

aws organizations describe-organization \
--query 'Organization.Id' \
--output text \
--region us-east-1
Enable AWS Organizations access in Service Catalog

Before you can share with your organization, you must enable the integration:

  1. Go to the Service Catalog console
  2. In the left navigation, choose Settings
  3. Under AWS Organizations access, choose Enable access

This must be done from your organization's management account or by a delegated administrator.

AWS Console Method

Step 1: Identify portfolios with account-level shares

  1. Open the Service Catalog console at https://console.aws.amazon.com/servicecatalog/
  2. In the left navigation, choose Portfolios
  3. Select a portfolio to review
  4. Choose the Share tab
  5. Look for shares with Type = "Account" - these need to be changed

Step 2: Remove account-level shares

  1. On the Share tab, select any share with Type "Account"
  2. Choose Actions > Unshare
  3. Confirm the removal
  4. Repeat for all account-level shares

Step 3: Create organization-level share

  1. On the Share tab, choose Share
  2. For Share with, select Organization
  3. Enter your organization ID (format: o-xxxxxxxxxx)
  4. Optionally enable Share tag options to share TagOptions with the portfolio
  5. Choose Share

Step 4: Verify the configuration

  1. Return to the Share tab
  2. Confirm the new share shows Type = "Organization"
  3. Confirm no shares remain with Type = "Account"
AWS CLI (optional)

List current shares for a portfolio:

# List account-level shares
aws servicecatalog describe-portfolio-shares \
--portfolio-id port-xxxxxxxxxx \
--type ACCOUNT \
--region us-east-1

# List organization-level shares
aws servicecatalog describe-portfolio-shares \
--portfolio-id port-xxxxxxxxxx \
--type ORGANIZATION \
--region us-east-1

Remove an account-level share:

aws servicecatalog delete-portfolio-share \
--portfolio-id port-xxxxxxxxxx \
--account-id 123456789012 \
--region us-east-1

Create an organization-level share:

aws servicecatalog create-portfolio-share \
--portfolio-id port-xxxxxxxxxx \
--organization-node Type=ORGANIZATION,Value=o-xxxxxxxxxx \
--share-tag-options \
--region us-east-1

Share with a specific organizational unit (OU) instead of the entire organization:

aws servicecatalog create-portfolio-share \
--portfolio-id port-xxxxxxxxxx \
--organization-node Type=ORGANIZATIONAL_UNIT,Value=ou-xxxx-xxxxxxxx \
--region us-east-1
CloudFormation (optional)

Important limitation: The AWS::ServiceCatalog::PortfolioShare CloudFormation resource currently only supports account-level sharing via AccountId. Organization-level sharing is not supported in CloudFormation.

For organization-level sharing, use one of these alternatives:

  • AWS Console (recommended)
  • AWS CLI
  • Terraform (see below)
  • AWS SDK

If you must use CloudFormation, you can create a Custom Resource that calls the Service Catalog API:

AWSTemplateFormatVersion: '2010-09-09'
Description: Service Catalog Portfolio with Organization Share (Custom Resource)

Parameters:
PortfolioName:
Type: String
Default: MyPortfolio
OrganizationId:
Type: String
Description: Your AWS Organization ID (e.g., o-xxxxxxxxxx)

Resources:
Portfolio:
Type: AWS::ServiceCatalog::Portfolio
Properties:
DisplayName: !Ref PortfolioName
ProviderName: IT Department

# Note: AWS::ServiceCatalog::PortfolioShare does not support organization sharing
# You must use a Custom Resource with Lambda or configure via CLI/Console

# Example account-level share (NOT recommended for this check):
# PortfolioShare:
# Type: AWS::ServiceCatalog::PortfolioShare
# Properties:
# PortfolioId: !Ref Portfolio
# AccountId: '123456789012'
# ShareTagOptions: true

Outputs:
PortfolioId:
Description: Portfolio ID for CLI-based organization sharing
Value: !Ref Portfolio
Export:
Name: !Sub '${AWS::StackName}-PortfolioId'

After deploying, share with your organization using the CLI:

aws servicecatalog create-portfolio-share \
--portfolio-id <PortfolioId-from-outputs> \
--organization-node Type=ORGANIZATION,Value=o-xxxxxxxxxx \
--region us-east-1
Terraform (optional)

Terraform supports organization-level sharing through the aws_servicecatalog_portfolio_share resource.

Organization-level share (recommended):

# Get the current organization
data "aws_organizations_organization" "current" {}

# Create the portfolio
resource "aws_servicecatalog_portfolio" "example" {
name = "MyPortfolio"
description = "Example portfolio shared within organization"
provider_name = "IT Department"
}

# Share with the entire organization
resource "aws_servicecatalog_portfolio_share" "organization" {
portfolio_id = aws_servicecatalog_portfolio.example.id
type = "ORGANIZATION"
principal_id = data.aws_organizations_organization.current.id
share_tag_options = true
}

Share with a specific organizational unit:

resource "aws_servicecatalog_portfolio_share" "ou_share" {
portfolio_id = aws_servicecatalog_portfolio.example.id
type = "ORGANIZATIONAL_UNIT"
principal_id = "ou-xxxx-xxxxxxxx"
share_tag_options = true
}

Migrating from account-level to organization-level sharing:

# Remove this (account-level share - NOT compliant):
# resource "aws_servicecatalog_portfolio_share" "account_share" {
# portfolio_id = aws_servicecatalog_portfolio.example.id
# type = "ACCOUNT"
# principal_id = "123456789012"
# }

# Replace with organization-level share:
resource "aws_servicecatalog_portfolio_share" "org_share" {
portfolio_id = aws_servicecatalog_portfolio.example.id
type = "ORGANIZATION"
principal_id = data.aws_organizations_organization.current.id
share_tag_options = true
}

Verification

After making changes, verify the configuration is correct:

  1. In the Service Catalog console, go to Portfolios
  2. Select your portfolio and choose the Share tab
  3. Confirm:
    • All shares show Type = "Organization" or "Organizational unit"
    • No shares show Type = "Account"
CLI verification commands

Check for any remaining account-level shares:

aws servicecatalog describe-portfolio-shares \
--portfolio-id port-xxxxxxxxxx \
--type ACCOUNT \
--query 'PortfolioShareDetails' \
--region us-east-1

An empty list [] means no account-level shares exist.

Confirm organization-level share exists:

aws servicecatalog describe-portfolio-shares \
--portfolio-id port-xxxxxxxxxx \
--type ORGANIZATION \
--query 'PortfolioShareDetails[*].{PrincipalId:PrincipalId,Accepted:Accepted}' \
--region us-east-1

Additional Resources

Notes

  • Management account required: Organization-level sharing must be configured from the organization's management account or a delegated administrator account.

  • Regional scope: Portfolio shares are regional. If you need to share portfolios across regions, you must configure sharing in each region separately.

  • Imported portfolios stay in sync: When you share through AWS Organizations, recipient accounts import a reference that automatically stays in sync with changes you make to the original portfolio.

  • Cannot re-share: Recipients cannot re-share products from imported portfolios. This helps maintain centralized control.

  • Gradual migration: When migrating from account-level to organization-level sharing, coordinate with recipient accounts as they may need to re-import the portfolio.

  • Organizational unit option: If you don't want to share with your entire organization, you can share with specific organizational units (OUs) instead. This provides more granular control while still using organizational boundaries.