Blog

Überprüfen Sie Ihre IAM-Berechtigungen für Ihre Google Cloud Platform (GCP) mit einem praktischen Skript

Lars Prosec

Daan Heikens

Aktualisiert Oktober 15, 2025
5 Minuten

Die Überprüfung aller erteilten IAM-Berechtigungen in Ihrer Google Cloud-Organisation kann zu einer recht mühsamen Aufgabe werden und sehr zeitaufwändig sein. Wenn Ihre Organisation wächst, werden mit der Zeit mehr Teams beteiligt sein und mehr Projekte erstellt werden. Manche Organisationen haben Hunderte oder sogar Tausende von Bindungen. Die Berechtigungen können sich anhäufen, so dass es schwierig ist, den Überblick darüber zu behalten, wer auf was Zugriff hat. Um Ihnen zu helfen, haben wir bei Xebia ein einfaches Skript entwickelt, mit dem Sie alle erteilten IAM-Berechtigungen für Organisationen, Ordner und Projekte in einem für Menschen lesbaren Format exportieren können.

Verschaffen Sie sich mit diesem Skript einen Überblick und Einblick in Ihre aktuellen IAM-Berechtigungen. Um die Überprüfung von Berechtigungen zu vereinfachen, haben wir ein Bash-Skript erstellt, das einen schnellen und gründlichen Überblick über IAM-Bindungen/Rollen in der gesamten Google Cloud Platform bietet.

Beachten Sie, dass Ihr Konto die Berechtigung roles/iam.securityReviewer auf Organisationsebene haben muss, um dieses Skript in Google Cloud Shell auszuführen.

Bitte beachten Sie: Ressourcenspezifische Bindungen sind in diesem Skript nicht enthalten, können aber natürlich in dieses Skript aufgenommen werden. (z.B. gcloud storage buckets get-iam-policy gs://BUCKET --project=PROJECT_ID).

Schritte:

  1. Öffnen Sie Google Cloud Shell und erstellen Sie eine neue .sh Datei (z.B., nano export_permissions.sh).
  2. Bearbeiten Sie die Datei und fügen Sie den Code ein. Ersetzen Sie dabei den Platzhalter durch Ihre tatsächliche Organisations-ID.
  3. Wir haben auch eine Funktion eingebaut, mit der Sie bestimmte Ordner ausschließen können. Ersetzen Sie den Platzhalter durch die tatsächliche Ordner-ID, die Sie ausschließen möchten.
  4. Machen Sie das Skript ausführbar, indem Sie: chmod +x export_permissions.sh im Terminal.
  5. Führen Sie das Skript mit ./export_permissions.sh und beobachten Sie, wie sich die Magie entfaltet.
  6. Die resultierende .csv Datei wird direkt in Ihrer Cloud Shell gespeichert.
#!/bin/bash

# Set the organization ID for the specific customer
ORGANIZATION_ID="123456789"  # Replace with your actual organization ID

# Define folders to exclude (comma-separated list of folder IDs to ignore)
FOLDER_EXCLUSIONS="12345678910"  # Replace with actual folder IDs

# Output CSV file
OUTPUT_FILE="gcp_permissions.csv"

# Initialize CSV with headers
echo "Resource Type,Resource ID,Resource Name,Member,Role" > "$OUTPUT_FILE"

# Function to check if a folder should be excluded
is_excluded_folder() {
  local folder_id="$1"
  [[ ",$FOLDER_EXCLUSIONS," == *",$folder_id,"* ]]
}

# Function to handle IAM policy processing and append results to CSV
# Function to handle IAM policy processing and append results to CSV
process_policy() {
  local resource_type="$1"
  local resource_id="$2"
  local resource_name="$3"
  local policy_json="$4"
  echo "Processing IAM policy for $resource_type: $resource_id ($resource_name)"
  # Check if .bindings exists and is not null
  if jq -e '.bindings' <<< "$policy_json" >/dev/null; then
    jq -c '.bindings[]?' <<< "$policy_json" | while read -r binding; do
      # Check if role exists in binding, default to "UNKNOWN_ROLE" if null
      role=$(jq -r '.role // "UNKNOWN_ROLE"' <<< "$binding")

      # Check if members array exists and is not null
      if jq -e '.members' <<< "$binding" >/dev/null; then
        members=$(jq -r '.members[]?' <<< "$binding")

        # Process each member, defaulting to "UNKNOWN_MEMBER" if null
        for member in $members; do
          if [ -z "$member" ] || [ "$member" == "null" ]; then
            member="UNKNOWN_MEMBER"
            echo "Warning: Null or empty member found for role $role in $resource_type $resource_id"
          fi
          echo "$resource_type,$resource_id,$resource_name,$member,$role" >> "$OUTPUT_FILE"
        done
      else
        echo "Warning: No members found for role $role in $resource_type $resource_id"
      fi
    done
  else
    echo "Warning: No bindings found for $resource_type $resource_id ($resource_name)"
  fi
}

# Recursive function to process folders and their projects
process_folder() {
  local folder_id="$1"

  if is_excluded_folder "$folder_id"; then
    echo "Excluding Folder: $folder_id" >&2
    return
  fi

  # Fetch the folder name for clarity in output
  folder_name=$(gcloud resource-manager folders describe "$folder_id" --format="value(displayName)")
  echo "Processing Folder: $folder_id ($folder_name)"

  # Fetch and process folder IAM policy
  folder_policy=$(gcloud resource-manager folders get-iam-policy "$folder_id" --format=json)
  process_policy "Folder" "$folder_id" "$folder_name" "$folder_policy"

  # List and process all projects within the folder
  for project in $(gcloud projects list --filter="parent.id=$folder_id" --format="value(projectId)"); do
    project_name=$(gcloud projects describe "$project" --format="value(name)")
    echo "Processing Project: $project ($project_name)"
    project_policy=$(gcloud projects get-iam-policy "$project" --format=json)
    process_policy "Project" "$project" "$project_name" "$project_policy"
  done

  # Recursively process any subfolders
  for subfolder in $(gcloud resource-manager folders list --folder="$folder_id" --format="value(name)"); do
    process_folder "$subfolder"
  done
}

# Process organization-level IAM policy
echo "Processing Organization IAM policy for Org ID: $ORGANIZATION_ID"
org_name=$(gcloud organizations describe "$ORGANIZATION_ID" --format="value(displayName)")
org_policy=$(gcloud organizations get-iam-policy "$ORGANIZATION_ID" --format=json)
process_policy "Organization" "$ORGANIZATION_ID" "$org_name" "$org_policy"

# Process all top-level folders in the organization
echo "Listing top-level folders for Organization ID: $ORGANIZATION_ID"
for folder in $(gcloud resource-manager folders list --organization="$ORGANIZATION_ID" --format="value(name)"); do
  process_folder "$folder"
done

echo "Permissions export completed. Results saved to $OUTPUT_FILE"

Das Wichtigste zum Mitnehmen: Wir haben festgestellt, dass die Auflistung aller gewährten IAM-Berechtigungen in Ihrer Google Cloud-Organisation nicht so einfach ist, wie wir dachten. In der Cloud-Konsole listet der IAM-Service nur eine ausgewählte Ressource(n) auf. Alternativ können Sie dazu auch das Cloud Asset Inventory verwenden, was in manchen Fällen Ihren Bedürfnissen besser entspricht. Berücksichtigen Sie jedoch, dass Sie eine andere Ausgabe erhalten, bei der die Richtlinie im JSON-Format vorliegt. Dies muss in ein für den Menschen lesbares Format umgewandelt werden. Berücksichtigen Sie, dass, wenn Sie Infrastructure as Code für die Zuweisung der IAM-Bindung verwenden, diese bereits mehr Sichtbarkeit erhält. Aber auch mit Infrastructure as Code (z.B. Terraform) befinden sich die IAM-Bindings in einigen Fällen in verschiedenen Dateien und an verschiedenen Orten. Dieses Skript hat unsere Zeit für die Analyse der IAM-Berechtigungen erheblich reduziert und einen guten ersten Überblick über die Berechtigungen für eine IAM-Überprüfung in einer einzigen Datei geschaffen.

Abgesehen von diesem Blog finden Sie das vollständige Beispiel unserer Übung und den Quellcode hier: GitHub - xebia/gcp-iam-bindings-export

Haftungsausschluss: Berechtigungen sind sensible Daten. Stellen Sie immer sicher, dass Sie sich mit den relevanten Interessengruppen abstimmen, um festzulegen, wer Zugriff auf diese Informationen haben soll und wo sie gespeichert und mit wem sie geteilt werden sollen.

Verfasst von

Lars Prosec

I work as a Cloud Platform Engineer with Xebia, contributing to the GCP Cloud Control Team. Our focus is providing tailored-made assessments, reviews, scans, and assistance for your Google Cloud environment, offering various services including Managed Services. In addition to working with the cloud, I prioritize my health by regularly attending my local gym. I also enjoy spending my free time on music, particularly DJing and mixing a variety of tracks.

Contact

Let’s discuss how we can support your journey.