diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json index 7dfe3ce6bd..66c355f493 100644 --- a/.devcontainer/devcontainer.json +++ b/.devcontainer/devcontainer.json @@ -9,8 +9,10 @@ "features": { "ghcr.io/devcontainers/features/node:1": {}, "ghcr.io/devcontainers/features/python:1": {}, - "ghcr.io/devcontainers/features/ruby:1": {}, - "ghcr.io/eitsupi/devcontainer-features/jq-likes:1": {}, + "ghcr.io/devcontainers/features/ruby:1": { + "version": "2.7" + }, + "ghcr.io/eitsupi/devcontainer-features/jq-likes:2": {}, "ghcr.io/devcontainers/features/aws-cli:1": {}, "ghcr.io/devcontainers/features/azure-cli:1": {}, "ghcr.io/devcontainers/features/docker-in-docker:2": {}, @@ -23,7 +25,7 @@ // "forwardPorts": [], // Use 'postCreateCommand' to run commands after the container is created. - "postCreateCommand": "rvm install `cat /workspaces/policy_templates/.ruby-version` && git clone https://github.com/flexera-public/policy_sdk /tmp/policy_sdk && cd /tmp/policy_sdk/cmd/fpt && go build -o fpt && sudo mv fpt /usr/local/bin/fpt && rm -rf /tmp/policy_sdk", + "postCreateCommand": "npm install && bundle install --without documentation --path bundle && git clone https://github.com/flexera-public/policy_sdk /tmp/policy_sdk && cd /tmp/policy_sdk/cmd/fpt && go build -o fpt && sudo mv fpt /usr/local/bin/fpt && rm -rf /tmp/policy_sdk", // Configure tool-specific properties. "customizations": { diff --git a/.github/workflows/generate-policy-master-permissions-json.yaml b/.github/workflows/generate-policy-master-permissions-json.yaml new file mode 100644 index 0000000000..f0ee64d4ef --- /dev/null +++ b/.github/workflows/generate-policy-master-permissions-json.yaml @@ -0,0 +1,50 @@ +name: Generate Policy Master Permissions JSON + +on: + # Trigger this workflow on pushes to master + push: + branches: + - master + - POL-918-create-master-policy-perm-list + + + # Workflow dispatch trigger allows manually running workflow + workflow_dispatch: + branches: + - master + - POL-918-create-master-policy-perm-list + + +jobs: + master-policy-permissions: + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v3 + with: + fetch-depth: 0 # Speed up checkout by not fetching history + + - name: Set up Ruby + uses: ruby/setup-ruby@v1 + + - name: Run Generate Policy Master Permissions Script + id: policy_permissions_json + run: | + ruby tools/policy_master_permission_generation/generate_policy_master_permissions.rb + + - name: Create Pull Request + id: cpr + uses: peter-evans/create-pull-request@v4 + with: + commit-message: "Update Policy Master Permissions List" + title: "Update Policy Master Permissions List" + body: "Update Policy Master Permissions List from GitHub Actions Workflow [${{ github.workflow }}](https://github.com/${{ github.repository }}/actions/runs/${{ github.run_id }})" + branch: "task/update-policy-master-permissions" + delete-branch: true + labels: "automation" + + - name: Check outputs + if: ${{ steps.cpr.outputs.pull-request-number }} + run: | + echo "Pull Request Number - ${{ steps.cpr.outputs.pull-request-number }}" + echo "Pull Request URL - ${{ steps.cpr.outputs.pull-request-url }}" diff --git a/.gitignore b/.gitignore index 1771568cbc..a1220f1aab 100644 --- a/.gitignore +++ b/.gitignore @@ -1,7 +1,6 @@ dist/ .DS_Store *.log -**/*.json !.devcontainer/** !.github/** *.js @@ -11,6 +10,12 @@ node_modules/ !package-lock.json !.vscode/*.json +# Ignore all JSON files at this level of directory +**/*.json + +# But exclude JSON files in this specific directory +!data/policy_permissions_list/*.json + # Bundler Artifacts bundle/ diff --git a/Dangerfile b/Dangerfile index efaa9c51b6..c6156062aa 100644 --- a/Dangerfile +++ b/Dangerfile @@ -1,4 +1,6 @@ require 'uri' +require 'yaml' + require_relative 'tools/lib/policy_parser' # DangerFile # https://danger.systems/reference.html @@ -192,3 +194,34 @@ changed_files.each do |file| fail "Textlint failed on #{file}" end end + +# check for new datasources +# print warning if new datasource is added to ensure the README permissions have been updated +permissions_verified_pt_file_yaml = YAML.load_file('tools/policy_master_permission_generation/validated_policy_templates.yaml') +has_app_changes.each do |file| + if file.end_with? ".pt" + # Get the diff to see only the new changes + diff = git.diff_for_file(file) + + # Use regex to look for blocks that have a "datasource", "request", and "auth" sections of the datasource + # Example String: + # "diff --git a/cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt b/cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt\nindex 14b3236f..bf6a161d 100644\n--- a/cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt\n+++ b/cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt\n@@ -193,6 +193,16 @@ datasource \"ds_applied_policy\" do\n end\n end\n \n+datasource \"ds_applied_policy_test_will_be_removed_later\" do\n+ request do\n+ auth $auth_flexera\n+ host rs_governance_host\n+ path join([\"/api/governance/projects/\", rs_project_id, \"/applied_policies/\", policy_id])\n+ header \"Api-Version\", \"1.0\"\n+ header \"Test\", \"True\"\n+ end\n+end\n+\n # Get region-specific Flexera API endpoints\n datasource \"ds_flexera_api_hosts\" do\n run_script $js_flexera_api_hosts, rs_optima_host" + regex = /datasource.*do(\s)+.*request.*do(\s)+.*auth.*([\s\S])+end([\s\+])+end/ + + # Print some debug info about diff patch + # puts "Diff Patch:" + # puts diff.patch + # puts "---" + + # First check if the PT file has been manually validated and enabled for permission generation + pt_file_enabled = permissions_verified_pt_file_yaml["validated_policy_templates"].select { |pt| pt.include?(file) } + if pt_file_enabled.empty? + # If the PT file has not been manually validated, then print an error message which will block the PR from being merged + # This will help improve coverage as we touch more PT files + fail "Policy Template file `#{file}` has **not** yet been enabled for automated permission generation. Please help us improve coverage by [following the steps documented in `tools/policy_master_permission_generation/`](https://github.com/flexera-public/policy_templates/tree/master/tools/policy_master_permission_generation) to resolve this" + elsif diff && diff.patch =~ regex + # If the PT file has been manually validated, but there are new datasources, then print a warning message + warn("Detected new request datasource in Policy Template file `#{file}`. Please verify the README.md has any new permissions that may be required.") + end + end +end diff --git a/compliance/google/unlabeled_resources/README.md b/compliance/google/unlabeled_resources/README.md index 32ceeae565..5099fdb178 100644 --- a/compliance/google/unlabeled_resources/README.md +++ b/compliance/google/unlabeled_resources/README.md @@ -1,6 +1,6 @@ # Google Unlabeled Resources -## What it does +## What It does Find all Google cloud resources(disks, images, instances, snapshots, buckets, vpnGateways) missing any of the user provided labels with the option to update the resources with the missing labels. @@ -26,33 +26,32 @@ The following policy actions are taken on any resources found to be out of compl ## Prerequisites -This policy uses [credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) for connecting to the cloud -- in order to apply this policy you must have a credential registered in the system that is compatible with this policy. If there are no credentials listed when you apply the policy, please contact your cloud admin and ask them to register a credential that is compatible with this policy. The information below should be consulted when creating the credential. - -### Credential configuration - -For administrators [creating and managing credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) to use with this policy, the following information is needed: - -Provider tag value to match this policy: `gce` - -Required permissions in the provider: - -- The `Monitoring Viewer` Role -- The `compute.disks.list` permission -- The `compute.instances.list` permission -- The `compute.disks.setLabels` permission -- The `compute.externalVpnGateways.list` permission -- The `compute.images.list` permission -- The `compute.externalVpnGateways.setLabels` permission -- The `compute.images.setLabels` permission -- The `compute.instances.setLabels` permission -- The `compute.snapshots.list` permission -- The `compute.snapshots.setLabels` permission -- The `compute.vpnGateways.list` permission -- The `compute.vpnGateways.setLabels` permission -- The `compute.images.setLabels` permission -- The `storage.buckets.list` permission -- The `storage.buckets.update` permission -- The `resourcemanager.projects.get` permission +This Policy Template requires that several APIs be enabled in your Google Cloud environment: + +- [Cloud Resource Manager API](https://console.cloud.google.com/flows/enableapi?apiid=cloudresourcemanager.googleapis.com) +- [Compute Engine API](https://console.cloud.google.com/flows/enableapi?apiid=compute.googleapis.com) + +This Policy Template uses [Credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) for authenticating to datasources -- in order to apply this policy you must have a Credential registered in the system that is compatible with this policy. If there are no Credentials listed when you apply the policy, please contact your Flexera Org Admin and ask them to register a Credential that is compatible with this policy. The information below should be consulted when creating the credential(s). + +- [**Google Cloud Credential**](https://docs.flexera.com/flexera/EN/Automation/ProviderCredentials.htm#automationadmin_4083446696_1121577) (*provider=gce*) which has the following: + - Permissions + - `compute.disks.list` + - `compute.disks.setLabels` + - `compute.externalVpnGateways.list` + - `compute.externalVpnGateways.setLabels` + - `compute.images.list` + - `compute.images.setLabels` + - `compute.instances.list` + - `compute.instances.setLabels` + - `compute.snapshots.list` + - `compute.snapshots.setLabels` + - `compute.vpnGateways.list` + - `compute.vpnGateways.setLabels` + - `resourcemanager.projects.get` + - `storage.buckets.list` + - `storage.buckets.update` + +The [Provider-Specific Credentials](https://docs.flexera.com/flexera/EN/Automation/ProviderCredentials.htm) page in the docs has detailed instructions for setting up Credentials for the most common providers. ## Supported Clouds diff --git a/cost/aws/unused_ip_addresses/README.md b/cost/aws/unused_ip_addresses/README.md index 0373fb17eb..a2e5567495 100644 --- a/cost/aws/unused_ip_addresses/README.md +++ b/cost/aws/unused_ip_addresses/README.md @@ -12,7 +12,7 @@ The policy utilizes the AWS EC2 API to get a list of unattached IP addresses and The policy includes the estimated monthly savings. The estimated monthly savings is recognized if the resource is terminated. -- The `Estimated Monthly Savings` is calculated using the per hour price of unused IPs, obtained from the AWS Pricing API, multiplied by 24 and then 30.44 to get an estimated monthly price. +- The `Estimated Monthly Savings` is calculated using the per hour price of unused IPs, obtained from the AWS Pricing API, multiplied by 24 and then 30.44 to get an estimated monthly price. - Since the prices of individual resources are *not* obtained from Flexera CCO, they will *not* take into account any Flexera adjustment rules or cloud provider discounts present in the Flexera platform. - The incident message detail includes the sum of each resource `Estimated Monthly Savings` as `Potential Monthly Savings`. - If the Flexera organization is configured to use a currency other than USD, the savings values will be converted from USD using the exchange rate at the time that the policy executes. @@ -50,6 +50,7 @@ This Policy Template uses [Credentials](https://docs.flexera.com/flexera/EN/Auto - `ec2:ReleaseAddress`* - `pricing:GetProducts` - `sts:GetCallerIdentity` + - `cloudtrail:LookupEvents` \* Only required for taking action (releasing an IP address); the policy will still function in a read-only capacity without these permissions. diff --git a/cost/azure/rightsize_compute_instances/README.md b/cost/azure/rightsize_compute_instances/README.md index c4718c9093..bccc3a1909 100644 --- a/cost/azure/rightsize_compute_instances/README.md +++ b/cost/azure/rightsize_compute_instances/README.md @@ -64,6 +64,9 @@ For administrators [creating and managing credentials](https://docs.flexera.com/ - [**Azure Resource Manager Credential**](https://docs.flexera.com/flexera/EN/Automation/ProviderCredentials.htm#automationadmin_109256743_1124668) (*provider=azure_rm*) which has the following permissions: - `Microsoft.Compute/virtualMachines/read` - `Microsoft.Compute/virtualMachines/write`* + - `Microsoft.Compute/virtualMachines/powerOff/action`* + - `Microsoft.Compute/virtualMachines/start/action`* + - `Microsoft.Compute/virtualMachines/delete`* - `Microsoft.Compute/skus/read` - `Microsoft.Insights/metrics/read` diff --git a/data/policy_permissions_list/README.md b/data/policy_permissions_list/README.md new file mode 100644 index 0000000000..1022cc55d3 --- /dev/null +++ b/data/policy_permissions_list/README.md @@ -0,0 +1,5 @@ +# Policy Permissions List + +The files in this directory are generated automatically and should **NOT** be manually modified. + +Please see [`tools/policy_master_permission_generation`](../../tools/policy_master_permission_generation/) for details diff --git a/data/policy_permissions_list/master_policy_permissions_list.json b/data/policy_permissions_list/master_policy_permissions_list.json new file mode 100644 index 0000000000..d409e2f8d3 --- /dev/null +++ b/data/policy_permissions_list/master_policy_permissions_list.json @@ -0,0 +1,1527 @@ +{ + "values": [ + { + "id": "./compliance/aws/untagged_resources/aws_untagged_resources.pt", + "name": "AWS Untagged Resources", + "version": "5.0", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + }, + { + "name": "config:TagResource", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "tag:GetResources", + "read_only": true, + "required": true + }, + { + "name": "ec2:CreateTags", + "read_only": false, + "required": false, + "description": "Only required for taking action (adding tags); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "tag:TagResources", + "read_only": false, + "required": false, + "description": "Only required for taking action (adding tags); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "rds:AddTagsToResources", + "read_only": false, + "required": false, + "description": "Only required for taking action (adding tags); the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./compliance/azure/azure_long_stopped_instances/long_stopped_instances_azure.pt", + "name": "Azure Long Stopped Compute Instances", + "version": "4.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Compute/virtualMachines/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Compute/virtualMachines/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./compliance/azure/azure_untagged_resources/untagged_resources.pt", + "name": "Azure Untagged Resources", + "version": "3.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Resources/subscriptions/providers/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/subscriptions/resources/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/tags/write", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./compliance/google/unlabeled_resources/unlabeled_resources.pt", + "name": "Google Unlabeled Resources", + "version": "2.5", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "compute.disks.list", + "read_only": true, + "required": true + }, + { + "name": "compute.disks.setLabels", + "read_only": true, + "required": true + }, + { + "name": "compute.externalVpnGateways.list", + "read_only": true, + "required": true + }, + { + "name": "compute.externalVpnGateways.setLabels", + "read_only": true, + "required": true + }, + { + "name": "compute.images.list", + "read_only": true, + "required": true + }, + { + "name": "compute.images.setLabels", + "read_only": true, + "required": true + }, + { + "name": "compute.instances.list", + "read_only": true, + "required": true + }, + { + "name": "compute.instances.setLabels", + "read_only": true, + "required": true + }, + { + "name": "compute.snapshots.list", + "read_only": true, + "required": true + }, + { + "name": "compute.snapshots.setLabels", + "read_only": true, + "required": true + }, + { + "name": "compute.vpnGateways.list", + "read_only": true, + "required": true + }, + { + "name": "compute.vpnGateways.setLabels", + "read_only": true, + "required": true + }, + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "storage.buckets.list", + "read_only": true, + "required": true + }, + { + "name": "storage.buckets.update", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/old_snapshots/aws_delete_old_snapshots.pt", + "name": "AWS Old Snapshots", + "version": "7.5", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeImages", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeSnapshots", + "read_only": true, + "required": true + }, + { + "name": "ec2:DeregisterImage", + "read_only": false, + "required": false, + "description": "Only required for taking action (deletion); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "ec2:DeleteSnapshot", + "read_only": false, + "required": false, + "description": "Only required for taking action (deletion); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "rds:DescribeDBInstances", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeDBSnapshots", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeDBClusters", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeDBClusterSnapshots", + "read_only": true, + "required": true + }, + { + "name": "rds:DeleteDBClusterSnapshot", + "read_only": false, + "required": false, + "description": "Only required for taking action (deletion); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "rds:DeleteDBSnapshot", + "read_only": false, + "required": false, + "description": "Only required for taking action (deletion); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + }, + { + "name": "cloudtrail:LookupEvents", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/reserved_instances/recommendations/aws_reserved_instance_recommendations.pt", + "name": "AWS Reserved Instances Recommendations", + "version": "3.4", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ce:GetReservationPurchaseRecommendation", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/rightsize_ebs_volumes/aws_volumes_rightsizing.pt", + "name": "AWS Rightsize EBS Volumes", + "version": "4.4", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeVolumes", + "read_only": true, + "required": true + }, + { + "name": "ec2:ModifyVolume", + "read_only": false, + "required": false, + "description": "Only required for taking action (upgrading to GP3); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "pricing:GetProducts", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt", + "name": "AWS Rightsize EC2 Instances", + "version": "4.5", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeInstances", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeInstanceStatus", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "ec2:DescribeTags", + "read_only": true, + "required": true + }, + { + "name": "ec2:ModifyInstanceAttribute", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "ec2:StartInstances", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "ec2:StopInstances", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "ec2:TerminateInstances", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "cloudwatch:GetMetricStatistics", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:GetMetricData", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:ListMetrics", + "read_only": true, + "required": true + }, + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt", + "name": "AWS Rightsize RDS Instances", + "version": "4.2", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:GetMetricStatistics", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:GetMetricData", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeDBInstances", + "read_only": true, + "required": true + }, + { + "name": "rds:ListTagsForResource", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeOrderableDBInstanceOptions", + "read_only": true, + "required": true + }, + { + "name": "rds:ModifyDBInstance", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "rds:DeleteDBInstance", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt", + "name": "AWS Rightsize RDS Instances", + "version": "4.2", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:GetMetricStatistics", + "read_only": true, + "required": true + }, + { + "name": "cloudwatch:GetMetricData", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeDBInstances", + "read_only": true, + "required": true + }, + { + "name": "rds:ListTagsForResource", + "read_only": true, + "required": true + }, + { + "name": "rds:DescribeOrderableDBInstanceOptions", + "read_only": true, + "required": true + }, + { + "name": "rds:ModifyDBInstance", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "rds:DeleteDBInstance", + "read_only": false, + "required": false, + "description": "Only required for taking action (terminating or downsizing); the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/savings_plan/recommendations/aws_savings_plan_recommendations.pt", + "name": "AWS Savings Plan Recommendations", + "version": "3.1", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ce:GetSavingsPlansPurchaseRecommendation", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/aws/unused_ip_addresses/aws_unused_ip_addresses.pt", + "name": "AWS Unused IP Addresses", + "version": "6.8", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeAddresses", + "read_only": true, + "required": true + }, + { + "name": "ec2:ReleaseAddress", + "read_only": false, + "required": false, + "description": "Only required for taking action (releasing an IP address); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "pricing:GetProducts", + "read_only": true, + "required": true + }, + { + "name": "sts:GetCallerIdentity", + "read_only": true, + "required": true + }, + { + "name": "cloudtrail:LookupEvents", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/old_snapshots/azure_delete_old_snapshots.pt", + "name": "Azure Old Snapshots", + "version": "6.2", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Compute/snapshots/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Compute/snapshots/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/reserved_instances/recommendations/azure_reserved_instance_recommendations.pt", + "name": "Azure Reserved Instances Recommendations", + "version": "3.3", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Billing/billingAccounts/read", + "read_only": true, + "required": false, + "description": "Only needed for currency conversion. Policy will still function without this permission but will provide a warning in the incident description about this." + }, + { + "name": "Microsoft.Consumption/reservationRecommendations/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/reserved_instances/utilization/azure_reserved_instance_utilization.pt", + "name": "Azure Reserved Instances Utilization", + "version": "3.0", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Billing/billingAccounts/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Consumption/reservationTransactions/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Consumption/reservationSummaries/read", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/rightsize_compute_instances/azure_compute_rightsizing.pt", + "name": "Azure Rightsize Compute Instances", + "version": "4.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Compute/virtualMachines/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Compute/virtualMachines/write", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting, powering off or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/virtualMachines/powerOff/action", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting, powering off or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/virtualMachines/start/action", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting, powering off or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/virtualMachines/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting, powering off or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/skus/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Insights/metrics/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/rightsize_managed_disks/azure_rightsize_managed_disks.pt", + "name": "Azure Rightsize Managed Disks", + "version": "1.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Compute/disks/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Compute/virtualMachines/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Insights/metrics/read", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/rightsize_sql_instances/azure_rightsize_sql_instances.pt", + "name": "Azure Rightsize SQL Databases", + "version": "4.4", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Sql/servers/databases/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Sql/servers/databases/metrics/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Sql/servers/databases/update", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Sql/servers/databases/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action (deleting or downsizing); the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Insights/metrics/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/savings_plan/recommendations/azure_savings_plan_recommendations.pt", + "name": "Azure Savings Plan Recommendations", + "version": "2.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.CostManagement/benefitRecommendations/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/unused_ip_addresses/azure_unused_ip_addresses.pt", + "name": "Azure Unused IP Addresses", + "version": "6.3", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Network/publicIPAddresses/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Network/publicIPAddresses/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Insights/eventtypes/values/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/unused_sql_databases/azure_unused_sql_databases.pt", + "name": "Azure Unused SQL Databases", + "version": "5.3", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Sql/servers/databases/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Sql/servers/databases/metrics/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Insights/metrics/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Sql/servers/databases/delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/azure/unused_volumes/azure_unused_volumes.pt", + "name": "Azure Unused Volumes", + "version": "7.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Compute/disks/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Compute/disks/write", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/snapshots/write", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/virtualMachines/read", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Compute/virtualMachines/write", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "Microsoft.Insights/metrics/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/google/cloud_sql_idle_instance_recommendations/google_sql_idle_instance_recommendations.pt", + "name": "Google Idle Cloud SQL Instance Recommender", + "version": "3.0", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "recommender.cloudsqlIdleInstanceRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "cloudsql.instances.list", + "read_only": true, + "required": true + }, + { + "name": "cloudsql.instances.update", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "cloudsql.instances.delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ], + "roles": [ + { + "name": "Cloud SQL Recommender Viewer", + "read_only": true, + "required": true + }, + { + "name": "Cloud SQL Recommender Admin", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/google/cud_recommendations/google_committed_use_discount_recommendations.pt", + "name": "Google Committed Use Discount Recommender", + "version": "4.0", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "compute.regions.list", + "read_only": true, + "required": true + }, + { + "name": "recommender.usageCommitmentRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "billing.resourceCosts.get", + "read_only": true, + "required": false, + "description": "Needed for recommendations to reflect custom contract pricing. Otherwise, recommendations will use list pricing." + }, + { + "name": "billing.accounts.getSpendingInformation", + "read_only": true, + "required": false, + "description": "Needed for recommendations to reflect custom contract pricing. Otherwise, recommendations will use list pricing." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/google/idle_ip_address_recommendations/google_idle_ip_address_recommendations.pt", + "name": "Google Idle IP Address Recommender", + "version": "3.0", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "recommender.computeAddressIdleResourceRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "compute.addresses.list", + "read_only": true, + "required": true + }, + { + "name": "compute.addresses.delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ], + "roles": [ + { + "name": "Compute Recommender Viewer", + "read_only": true, + "required": true + }, + { + "name": "Compute Recommender Admin", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/google/idle_persistent_disk_recommendations/google_idle_persistent_disk_recommendations.pt", + "name": "Google Idle Persistent Disk Recommender", + "version": "3.1", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "recommender.computeDiskIdleResourceRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "compute.disks.list", + "read_only": true, + "required": true + }, + { + "name": "logging.logEntries.list", + "read_only": true, + "required": true + }, + { + "name": "logging.privateLogEntries.list", + "read_only": true, + "required": true + }, + { + "name": "logging.views.access", + "read_only": true, + "required": true + }, + { + "name": "compute.disks.createSnapshot", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.disks.delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.globalOperations.get", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.zoneOperations.get", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.snapshots.create", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ], + "roles": [ + { + "name": "Monitoring Viewer", + "read_only": true, + "required": true + }, + { + "name": "Compute Recommender Viewer", + "read_only": true, + "required": true + }, + { + "name": "Compute Recommender Admin", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./cost/google/rightsize_vm_recommendations/google_rightsize_vm_recommendations.pt", + "name": "Google Rightsize VM Recommender", + "version": "2.1", + "providers": [ + { + "name": "gce", + "permissions": [ + { + "name": "recommender.computeInstanceMachineTypeRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "recommender.computeInstanceIdleResourceRecommendations.list", + "read_only": true, + "required": true + }, + { + "name": "resourcemanager.projects.get", + "read_only": true, + "required": true + }, + { + "name": "monitoring.metricDescriptors.list", + "read_only": true, + "required": true + }, + { + "name": "monitoring.timeSeries.list", + "read_only": true, + "required": true + }, + { + "name": "compute.instances.list", + "read_only": true, + "required": true + }, + { + "name": "compute.instances.get", + "read_only": true, + "required": true + }, + { + "name": "compute.instances.start", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.instances.stop", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.instances.setMachineType", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + }, + { + "name": "compute.instances.delete", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ], + "roles": [ + { + "name": "Monitoring Viewer", + "read_only": true, + "required": true + }, + { + "name": "Compute Recommender Viewer", + "read_only": true, + "required": true + }, + { + "name": "Compute Recommender Admin", + "read_only": false, + "required": false, + "description": "Only required for taking action; the policy will still function in a read-only capacity without these permissions." + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./operational/aws/tag_cardinality/aws_tag_cardinality.pt", + "name": "AWS Tag Cardinality Report", + "version": "3.0", + "providers": [ + { + "name": "aws", + "permissions": [ + { + "name": "tag:GetResources", + "read_only": true, + "required": true + }, + { + "name": "ec2:DescribeRegions", + "read_only": true, + "required": true + }, + { + "name": "eorganizations:ListAccounts", + "read_only": true, + "required": true + }, + { + "name": "organizations:ListTagsForResource", + "read_only": true, + "required": true + } + ] + } + ] + }, + { + "id": "./operational/azure/tag_cardinality/azure_tag_cardinality.pt", + "name": "Azure Tag Cardinality Report", + "version": "3.1", + "providers": [ + { + "name": "azure_rm", + "permissions": [ + { + "name": "Microsoft.Resources/subscriptions/resources/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/subscriptions/providers/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/subscriptions/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/resourceGroups/read", + "read_only": true, + "required": true + }, + { + "name": "Microsoft.Resources/tags/read", + "read_only": true, + "required": true + } + ] + }, + { + "name": "flexera", + "permissions": [ + { + "name": "billing_center_viewer", + "read_only": true, + "required": true + } + ] + } + ] + } + ] +} \ No newline at end of file diff --git a/data/policy_permissions_list/master_policy_permissions_list.yaml b/data/policy_permissions_list/master_policy_permissions_list.yaml new file mode 100644 index 0000000000..5b45544f40 --- /dev/null +++ b/data/policy_permissions_list/master_policy_permissions_list.yaml @@ -0,0 +1,929 @@ +--- +:values: +- id: "./compliance/aws/untagged_resources/aws_untagged_resources.pt" + name: AWS Untagged Resources + version: '5.0' + :providers: + - :name: aws + :permissions: + - name: sts:GetCallerIdentity + read_only: true + required: true + - name: config:TagResource + read_only: true + required: true + - name: ec2:DescribeRegions + read_only: true + required: true + - name: tag:GetResources + read_only: true + required: true + - name: ec2:CreateTags + read_only: false + required: false + description: Only required for taking action (adding tags); the policy will + still function in a read-only capacity without these permissions. + - name: tag:TagResources + read_only: false + required: false + description: Only required for taking action (adding tags); the policy will + still function in a read-only capacity without these permissions. + - name: rds:AddTagsToResources + read_only: false + required: false + description: Only required for taking action (adding tags); the policy will + still function in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./compliance/azure/azure_long_stopped_instances/long_stopped_instances_azure.pt" + name: Azure Long Stopped Compute Instances + version: '4.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Compute/virtualMachines/read + read_only: true + required: true + - name: Microsoft.Compute/virtualMachines/delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./compliance/azure/azure_untagged_resources/untagged_resources.pt" + name: Azure Untagged Resources + version: '3.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Resources/subscriptions/providers/read + read_only: true + required: true + - name: Microsoft.Resources/subscriptions/resources/read + read_only: true + required: true + - name: Microsoft.Resources/tags/write + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./compliance/google/unlabeled_resources/unlabeled_resources.pt" + name: Google Unlabeled Resources + version: '2.5' + :providers: + - :name: gce + :permissions: + - name: compute.disks.list + read_only: true + required: true + - name: compute.disks.setLabels + read_only: true + required: true + - name: compute.externalVpnGateways.list + read_only: true + required: true + - name: compute.externalVpnGateways.setLabels + read_only: true + required: true + - name: compute.images.list + read_only: true + required: true + - name: compute.images.setLabels + read_only: true + required: true + - name: compute.instances.list + read_only: true + required: true + - name: compute.instances.setLabels + read_only: true + required: true + - name: compute.snapshots.list + read_only: true + required: true + - name: compute.snapshots.setLabels + read_only: true + required: true + - name: compute.vpnGateways.list + read_only: true + required: true + - name: compute.vpnGateways.setLabels + read_only: true + required: true + - name: resourcemanager.projects.get + read_only: true + required: true + - name: storage.buckets.list + read_only: true + required: true + - name: storage.buckets.update + read_only: true + required: true +- id: "./cost/aws/old_snapshots/aws_delete_old_snapshots.pt" + name: AWS Old Snapshots + version: '7.5' + :providers: + - :name: aws + :permissions: + - name: ec2:DescribeRegions + read_only: true + required: true + - name: ec2:DescribeImages + read_only: true + required: true + - name: ec2:DescribeSnapshots + read_only: true + required: true + - name: ec2:DeregisterImage + read_only: false + required: false + description: Only required for taking action (deletion); the policy will still + function in a read-only capacity without these permissions. + - name: ec2:DeleteSnapshot + read_only: false + required: false + description: Only required for taking action (deletion); the policy will still + function in a read-only capacity without these permissions. + - name: rds:DescribeDBInstances + read_only: true + required: true + - name: rds:DescribeDBSnapshots + read_only: true + required: true + - name: rds:DescribeDBClusters + read_only: true + required: true + - name: rds:DescribeDBClusterSnapshots + read_only: true + required: true + - name: rds:DeleteDBClusterSnapshot + read_only: false + required: false + description: Only required for taking action (deletion); the policy will still + function in a read-only capacity without these permissions. + - name: rds:DeleteDBSnapshot + read_only: false + required: false + description: Only required for taking action (deletion); the policy will still + function in a read-only capacity without these permissions. + - name: sts:GetCallerIdentity + read_only: true + required: true + - name: cloudtrail:LookupEvents + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/reserved_instances/recommendations/aws_reserved_instance_recommendations.pt" + name: AWS Reserved Instances Recommendations + version: '3.4' + :providers: + - :name: aws + :permissions: + - name: ce:GetReservationPurchaseRecommendation + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/rightsize_ebs_volumes/aws_volumes_rightsizing.pt" + name: AWS Rightsize EBS Volumes + version: '4.4' + :providers: + - :name: aws + :permissions: + - name: ec2:DescribeRegions + read_only: true + required: true + - name: ec2:DescribeVolumes + read_only: true + required: true + - name: ec2:ModifyVolume + read_only: false + required: false + description: Only required for taking action (upgrading to GP3); the policy + will still function in a read-only capacity without these permissions. + - name: pricing:GetProducts + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt" + name: AWS Rightsize EC2 Instances + version: '4.5' + :providers: + - :name: aws + :permissions: + - name: ec2:DescribeRegions + read_only: true + required: true + - name: ec2:DescribeInstances + read_only: true + required: true + - name: ec2:DescribeInstanceStatus + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: ec2:DescribeTags + read_only: true + required: true + - name: ec2:ModifyInstanceAttribute + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: ec2:StartInstances + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: ec2:StopInstances + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: ec2:TerminateInstances + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: cloudwatch:GetMetricStatistics + read_only: true + required: true + - name: cloudwatch:GetMetricData + read_only: true + required: true + - name: cloudwatch:ListMetrics + read_only: true + required: true + - name: sts:GetCallerIdentity + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt" + name: AWS Rightsize RDS Instances + version: '4.2' + :providers: + - :name: aws + :permissions: + - name: sts:GetCallerIdentity + read_only: true + required: true + - name: cloudwatch:GetMetricStatistics + read_only: true + required: true + - name: cloudwatch:GetMetricData + read_only: true + required: true + - name: ec2:DescribeRegions + read_only: true + required: true + - name: rds:DescribeDBInstances + read_only: true + required: true + - name: rds:ListTagsForResource + read_only: true + required: true + - name: rds:DescribeOrderableDBInstanceOptions + read_only: true + required: true + - name: rds:ModifyDBInstance + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: rds:DeleteDBInstance + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt" + name: AWS Rightsize RDS Instances + version: '4.2' + :providers: + - :name: aws + :permissions: + - name: sts:GetCallerIdentity + read_only: true + required: true + - name: cloudwatch:GetMetricStatistics + read_only: true + required: true + - name: cloudwatch:GetMetricData + read_only: true + required: true + - name: ec2:DescribeRegions + read_only: true + required: true + - name: rds:DescribeDBInstances + read_only: true + required: true + - name: rds:ListTagsForResource + read_only: true + required: true + - name: rds:DescribeOrderableDBInstanceOptions + read_only: true + required: true + - name: rds:ModifyDBInstance + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - name: rds:DeleteDBInstance + read_only: false + required: false + description: Only required for taking action (terminating or downsizing); the + policy will still function in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/savings_plan/recommendations/aws_savings_plan_recommendations.pt" + name: AWS Savings Plan Recommendations + version: '3.1' + :providers: + - :name: aws + :permissions: + - name: ce:GetSavingsPlansPurchaseRecommendation + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/aws/unused_ip_addresses/aws_unused_ip_addresses.pt" + name: AWS Unused IP Addresses + version: '6.8' + :providers: + - :name: aws + :permissions: + - name: ec2:DescribeRegions + read_only: true + required: true + - name: ec2:DescribeAddresses + read_only: true + required: true + - name: ec2:ReleaseAddress + read_only: false + required: false + description: Only required for taking action (releasing an IP address); the + policy will still function in a read-only capacity without these permissions. + - name: pricing:GetProducts + read_only: true + required: true + - name: sts:GetCallerIdentity + read_only: true + required: true + - name: cloudtrail:LookupEvents + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/old_snapshots/azure_delete_old_snapshots.pt" + name: Azure Old Snapshots + version: '6.2' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Compute/snapshots/read + read_only: true + required: true + - name: Microsoft.Compute/snapshots/delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/reserved_instances/recommendations/azure_reserved_instance_recommendations.pt" + name: Azure Reserved Instances Recommendations + version: '3.3' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Billing/billingAccounts/read + read_only: true + required: false + description: Only needed for currency conversion. Policy will still function + without this permission but will provide a warning in the incident description + about this. + - name: Microsoft.Consumption/reservationRecommendations/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/reserved_instances/utilization/azure_reserved_instance_utilization.pt" + name: Azure Reserved Instances Utilization + version: '3.0' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Billing/billingAccounts/read + read_only: true + required: true + - name: Microsoft.Consumption/reservationTransactions/read + read_only: true + required: true + - name: Microsoft.Consumption/reservationSummaries/read + read_only: true + required: true +- id: "./cost/azure/rightsize_compute_instances/azure_compute_rightsizing.pt" + name: Azure Rightsize Compute Instances + version: '4.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Compute/virtualMachines/read + read_only: true + required: true + - name: Microsoft.Compute/virtualMachines/write + read_only: false + required: false + description: Only required for taking action (deleting, powering off or downsizing); + the policy will still function in a read-only capacity without these permissions. + - name: Microsoft.Compute/virtualMachines/powerOff/action + read_only: false + required: false + description: Only required for taking action (deleting, powering off or downsizing); + the policy will still function in a read-only capacity without these permissions. + - name: Microsoft.Compute/virtualMachines/start/action + read_only: false + required: false + description: Only required for taking action (deleting, powering off or downsizing); + the policy will still function in a read-only capacity without these permissions. + - name: Microsoft.Compute/virtualMachines/delete + read_only: false + required: false + description: Only required for taking action (deleting, powering off or downsizing); + the policy will still function in a read-only capacity without these permissions. + - name: Microsoft.Compute/skus/read + read_only: true + required: true + - name: Microsoft.Insights/metrics/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/rightsize_managed_disks/azure_rightsize_managed_disks.pt" + name: Azure Rightsize Managed Disks + version: '1.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Compute/disks/read + read_only: true + required: true + - name: Microsoft.Compute/virtualMachines/read + read_only: true + required: true + - name: Microsoft.Insights/metrics/read + read_only: true + required: true +- id: "./cost/azure/rightsize_sql_instances/azure_rightsize_sql_instances.pt" + name: Azure Rightsize SQL Databases + version: '4.4' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Sql/servers/databases/read + read_only: true + required: true + - name: Microsoft.Sql/servers/databases/metrics/read + read_only: true + required: true + - name: Microsoft.Sql/servers/databases/update + read_only: false + required: false + description: Only required for taking action (deleting or downsizing); the policy + will still function in a read-only capacity without these permissions. + - name: Microsoft.Sql/servers/databases/delete + read_only: false + required: false + description: Only required for taking action (deleting or downsizing); the policy + will still function in a read-only capacity without these permissions. + - name: Microsoft.Insights/metrics/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/savings_plan/recommendations/azure_savings_plan_recommendations.pt" + name: Azure Savings Plan Recommendations + version: '2.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.CostManagement/benefitRecommendations/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/unused_ip_addresses/azure_unused_ip_addresses.pt" + name: Azure Unused IP Addresses + version: '6.3' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Network/publicIPAddresses/read + read_only: true + required: true + - name: Microsoft.Network/publicIPAddresses/delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: Microsoft.Insights/eventtypes/values/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/unused_sql_databases/azure_unused_sql_databases.pt" + name: Azure Unused SQL Databases + version: '5.3' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Sql/servers/databases/read + read_only: true + required: true + - name: Microsoft.Sql/servers/databases/metrics/read + read_only: true + required: true + - name: Microsoft.Insights/metrics/read + read_only: true + required: true + - name: Microsoft.Sql/servers/databases/delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/azure/unused_volumes/azure_unused_volumes.pt" + name: Azure Unused Volumes + version: '7.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Compute/disks/read + read_only: true + required: true + - name: Microsoft.Compute/disks/write + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: Microsoft.Compute/snapshots/write + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: Microsoft.Compute/virtualMachines/read + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: Microsoft.Compute/virtualMachines/write + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: Microsoft.Insights/metrics/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/google/cloud_sql_idle_instance_recommendations/google_sql_idle_instance_recommendations.pt" + name: Google Idle Cloud SQL Instance Recommender + version: '3.0' + :providers: + - :name: gce + :permissions: + - name: recommender.cloudsqlIdleInstanceRecommendations.list + read_only: true + required: true + - name: resourcemanager.projects.get + read_only: true + required: true + - name: cloudsql.instances.list + read_only: true + required: true + - name: cloudsql.instances.update + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: cloudsql.instances.delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + :roles: + - name: Cloud SQL Recommender Viewer + read_only: true + required: true + - name: Cloud SQL Recommender Admin + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/google/cud_recommendations/google_committed_use_discount_recommendations.pt" + name: Google Committed Use Discount Recommender + version: '4.0' + :providers: + - :name: gce + :permissions: + - name: resourcemanager.projects.get + read_only: true + required: true + - name: compute.regions.list + read_only: true + required: true + - name: recommender.usageCommitmentRecommendations.list + read_only: true + required: true + - name: billing.resourceCosts.get + read_only: true + required: false + description: Needed for recommendations to reflect custom contract pricing. + Otherwise, recommendations will use list pricing. + - name: billing.accounts.getSpendingInformation + read_only: true + required: false + description: Needed for recommendations to reflect custom contract pricing. + Otherwise, recommendations will use list pricing. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/google/idle_ip_address_recommendations/google_idle_ip_address_recommendations.pt" + name: Google Idle IP Address Recommender + version: '3.0' + :providers: + - :name: gce + :permissions: + - name: recommender.computeAddressIdleResourceRecommendations.list + read_only: true + required: true + - name: resourcemanager.projects.get + read_only: true + required: true + - name: compute.addresses.list + read_only: true + required: true + - name: compute.addresses.delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + :roles: + - name: Compute Recommender Viewer + read_only: true + required: true + - name: Compute Recommender Admin + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/google/idle_persistent_disk_recommendations/google_idle_persistent_disk_recommendations.pt" + name: Google Idle Persistent Disk Recommender + version: '3.1' + :providers: + - :name: gce + :permissions: + - name: recommender.computeDiskIdleResourceRecommendations.list + read_only: true + required: true + - name: resourcemanager.projects.get + read_only: true + required: true + - name: compute.disks.list + read_only: true + required: true + - name: logging.logEntries.list + read_only: true + required: true + - name: logging.privateLogEntries.list + read_only: true + required: true + - name: logging.views.access + read_only: true + required: true + - name: compute.disks.createSnapshot + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.disks.delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.globalOperations.get + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.zoneOperations.get + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.snapshots.create + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + :roles: + - name: Monitoring Viewer + read_only: true + required: true + - name: Compute Recommender Viewer + read_only: true + required: true + - name: Compute Recommender Admin + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./cost/google/rightsize_vm_recommendations/google_rightsize_vm_recommendations.pt" + name: Google Rightsize VM Recommender + version: '2.1' + :providers: + - :name: gce + :permissions: + - name: recommender.computeInstanceMachineTypeRecommendations.list + read_only: true + required: true + - name: recommender.computeInstanceIdleResourceRecommendations.list + read_only: true + required: true + - name: resourcemanager.projects.get + read_only: true + required: true + - name: monitoring.metricDescriptors.list + read_only: true + required: true + - name: monitoring.timeSeries.list + read_only: true + required: true + - name: compute.instances.list + read_only: true + required: true + - name: compute.instances.get + read_only: true + required: true + - name: compute.instances.start + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.instances.stop + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.instances.setMachineType + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - name: compute.instances.delete + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + :roles: + - name: Monitoring Viewer + read_only: true + required: true + - name: Compute Recommender Viewer + read_only: true + required: true + - name: Compute Recommender Admin + read_only: false + required: false + description: Only required for taking action; the policy will still function + in a read-only capacity without these permissions. + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true +- id: "./operational/aws/tag_cardinality/aws_tag_cardinality.pt" + name: AWS Tag Cardinality Report + version: '3.0' + :providers: + - :name: aws + :permissions: + - name: tag:GetResources + read_only: true + required: true + - name: ec2:DescribeRegions + read_only: true + required: true + - name: eorganizations:ListAccounts + read_only: true + required: true + - name: organizations:ListTagsForResource + read_only: true + required: true +- id: "./operational/azure/tag_cardinality/azure_tag_cardinality.pt" + name: Azure Tag Cardinality Report + version: '3.1' + :providers: + - :name: azure_rm + :permissions: + - name: Microsoft.Resources/subscriptions/resources/read + read_only: true + required: true + - name: Microsoft.Resources/subscriptions/providers/read + read_only: true + required: true + - name: Microsoft.Resources/subscriptions/read + read_only: true + required: true + - name: Microsoft.Resources/resourceGroups/read + read_only: true + required: true + - name: Microsoft.Resources/tags/read + read_only: true + required: true + - :name: flexera + :permissions: + - name: billing_center_viewer + read_only: true + required: true diff --git a/operational/aws/tag_cardinality/README.md b/operational/aws/tag_cardinality/README.md index fafb148180..b7e483324c 100644 --- a/operational/aws/tag_cardinality/README.md +++ b/operational/aws/tag_cardinality/README.md @@ -25,33 +25,35 @@ This read-only policy is purely for reporting purposes and takes no action. ## Prerequisites -This policy uses [credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) for connecting to the cloud -- in order to apply this policy you must have a credential registered in the system that is compatible with this policy. If there are no credentials listed when you apply the policy, please contact your cloud admin and ask them to register a credential that is compatible with this policy. The information below should be consulted when creating the credential. - -### Credential configuration - -For administrators [creating and managing credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) to use with this policy, the following information is needed: - -Provider tag value to match this policy: `aws` , `aws_sts` - -Required permissions in the provider: - -```javascript -{ - "Version": "2012-10-17", - "Statement": [ - { - "Effect": "Allow", - "Action": [ - "tag:GetResources", - "ec2:DescribeRegions", - "organizations:ListAccounts", - "organizations:ListTagsForResource" - ], - "Resource": "*" - } - ] -} -``` +This Policy Template uses [Credentials](https://docs.flexera.com/flexera/EN/Automation/ManagingCredentialsExternal.htm) for authenticating to datasources -- in order to apply this policy you must have a Credential registered in the system that is compatible with this policy. If there are no Credentials listed when you apply the policy, please contact your Flexera Org Admin and ask them to register a Credential that is compatible with this policy. The information below should be consulted when creating the credential(s). + +- [**AWS Credential**](https://docs.flexera.com/flexera/EN/Automation/ProviderCredentials.htm#automationadmin_1982464505_1121575) (*provider=aws*) which has the following permissions: + - `tag:GetResources` + - `ec2:DescribeRegions` + - `eorganizations:ListAccounts` + - `organizations:ListTagsForResource` + + Example IAM Permission Policy: + + ```json + { + "Version": "2012-10-17", + "Statement": [ + { + "Effect": "Allow", + "Action": [ + "tag:GetResources", + "ec2:DescribeRegions", + "organizations:ListAccounts", + "organizations:ListTagsForResource" + ], + "Resource": "*" + } + ] + } + ``` + +The [Provider-Specific Credentials](https://docs.flexera.com/flexera/EN/Automation/ProviderCredentials.htm) page in the docs has detailed instructions for setting up Credentials for the most common providers. ## Supported Clouds diff --git a/tools/policy_master_permission_generation/README.md b/tools/policy_master_permission_generation/README.md new file mode 100644 index 0000000000..4bdb4a1cf2 --- /dev/null +++ b/tools/policy_master_permission_generation/README.md @@ -0,0 +1,32 @@ +# Generate Policy Permissions Script + +This script parses the `README.md` files for each Policy Template and generates a policy permission list dataset which can be used to generate other artifacts that require permissions. + +## Enabling a Policy Template for Automated Policy Permission Generation + +1. Open `.pt` file in code editor to review + +1. For each `datasource` which make a `request` and include an `auth` configuration (i.e. *auth_azure*, *auth_aws*, etc..) validate the permission required for that request is in the `README.md`. The goal here is to validate that all permissions that at needed by the `.pt` file are documented in the `README.md` + +1. Add the `.pt` file to list of files in [`tools/policy_master_permission_generation/validated_policy_templates.yaml`](./validated_policy_templates.yaml) + +1. Run [`tools/policy_master_permission_generation/generate_policy_master_permissions.rb`](./generate_policy_master_permissions.rb) + + ```sh + $ ruby tools/policy_master_permission_generation/generate_policy_master_permissions.rb + ``` + +1. For each permission in the `README.md`, validate that the permission is correctly added to the output datasets in [`data/policy_permissions_list`](../../data/policy_permissions_list) + +1. Commit and push changes to datasets in [`data/policy_permissions_list`](../../data/policy_permissions_list) and [`tools/policy_master_permission_generation/validated_policy_templates.yaml`](./validated_policy_templates.yaml) + + ```sh + # Stage the changes + $ git add data/policy_permissions_list/ tools/policy_master_permission_generation/validated_policy_templates.yaml + + # Commit the changes + $ git commit -m "task: enable PT for automated permissions" + + # Push changes to github for review; + # git push ..... + ``` diff --git a/tools/policy_master_permission_generation/generate_policy_master_permissions.rb b/tools/policy_master_permission_generation/generate_policy_master_permissions.rb new file mode 100644 index 0000000000..365c2db875 --- /dev/null +++ b/tools/policy_master_permission_generation/generate_policy_master_permissions.rb @@ -0,0 +1,250 @@ +#encoding: UTF-8 +require 'json' +require 'fileutils' +require 'yaml' + +# List of Policy Templates +# Open YAML and parse validated_policy_templates[] array +pt_files_yaml = YAML.load_file("./tools/policy_master_permission_generation/validated_policy_templates.yaml") +pt_files = pt_files_yaml["validated_policy_templates"] + +class Readme + attr_accessor :path, :credentials + + def initialize(path, credentials: []) + @path = path + @credentials = credentials + end +end + +class PolicyTemplate + attr_accessor :name, :path, :version + + def initialize(name, path, version) + @name = name + @path = path + @version = version + end +end + +readme_files = [] +pt_files.each do |pt| + # Get the README file for each Policy Template + readme_files += Dir.glob("#{File.dirname(pt)}/[Rr][Ee][Aa][Dd][Mm][Ee]*") +end + +# Initialize arrays to store README array of objects and Policy Template array of objects +policy_templates = [] +readmes = [] + +# Process Policy Template files +pt_files.each do |file| + pt_content = File.read(file) + pt_name = pt_content.match(/name "([^"]+)"/)&.captures&.first + + pt_version_match = pt_content.match(/version:\s*\"([^\"]+)\"/) + pt_version = pt_version_match[1] if pt_version_match + + policy_templates << PolicyTemplate.new(pt_name, file, pt_version) if pt_name +end + +# Process README files +def extract_permissions_from_readme(readme_content) + policy_credentials = [] + + # Identify Sections to look for Permissions, Roles, APIs + sections = [ + "[**AWS Credentials**]", + "[**AWS Credential**]", + "[**Azure Resource Manager Credential**]", + "[**Google Cloud Credential**]", + "[**Flexera Credential**]" + ] + + sections.each do |section| + case section + when "[**AWS Credentials**]", "[**AWS Credential**]" + provider = "aws" + when "[**Azure Resource Manager Credential**]" + provider = "azure_rm" + when "[**Google Cloud Credential**]" + provider = "gce" + when "[**Flexera Credential**]" + provider = "flexera" + end + + # If the Credential Section exists... + if section_start = readme_content.index(section) + # Extract the text from this section + section_text = readme_content[section_start..-1] + + # Find the line starting with '/*' to get any specific notes around permissions from the README + note = "" + section_text.each_line do |line| + break if line.strip.start_with?( "##", "###", "- [**") && !line.strip.start_with?(section) + + if line.strip.start_with?("\\*") + note = line.strip.sub(/^\\\*\s*/, '') + end + end + + # For each line within the Section get the list of permissions and roles and push to 'policy_credentials' object + credentials_section = "" + section_text.each_line do |line| + break if line.strip.start_with?( "##", "###", "- [**") && !line.strip.start_with?(section) + + if line.strip == "- Roles" || line.strip == "- Role" + credentials_section = "roles" + elsif line.strip == "- Permissions" || line.strip == "Permission" + credentials_section = "permissions" + else + line.scan(/-\s*`([^`]+)`\*?/) do |match| + permission = match.first + + # Set whether permission is read-only, required, and/or has a description + read_only_permission = true + required = true + if (permission.end_with?("*") == true || line.include?("*") == true) && !note.strip.empty? + required = false + if note.include?("Only required for taking action") + read_only_permission = false + end + + permission = permission.chomp("*") + + if credentials_section == "roles" + policy_credentials << { role: permission, provider: provider, read_only: read_only_permission, required: required, description: note } + elsif credentials_section == "permissions" + policy_credentials << { permission: permission, provider: provider, read_only: read_only_permission, required: required, description: note } + else + policy_credentials << { permission: permission, provider: provider, read_only: read_only_permission, required: required, description: note } + end + + else + if credentials_section == "roles" + policy_credentials << { role: permission, provider: provider, read_only: read_only_permission, required: required } + elsif credentials_section == "permissions" + policy_credentials << { permission: permission, provider: provider, read_only: read_only_permission, required: required } + else + policy_credentials << { permission: permission, provider: provider, read_only: read_only_permission, required: required } + end + end + end + end + end + end + end + + policy_credentials +end + +readme_files.each do |path| + begin + readme_content = File.read(path) + # ignore non-UTF-8 characters in readmes + readme_content.force_encoding('ISO-8859-1') + readme_content.encode('utf-8', replace: nil) + + # if path == "./cost/google/idle_persistent_disk_recommendations/README.md" + policy_credentials = extract_permissions_from_readme(readme_content) + # end + + readmes < e + puts "Error processing file: #{path}" + puts e.message + end +end + +# Create JSON structure for Master Policy Permissions Document +master_policy_permissions_doc = {} +values = [] + +readmes.each do |readme| + # Match READMEs with Policy Templates based on paths + matching_template = policy_templates.find { |template| readme.path.gsub("/README.md", "") == File.dirname(template.path) } + if matching_template + + policy_template_details = { + "id" => matching_template.path, + "name" => matching_template.name, + "version" => matching_template.version + } + + if readme.credentials + + cred_providers = [] + readme.credentials.each do |cred| + cred_providers.push({ name: cred[:provider] }) + end + cred_providers = cred_providers.uniq + + cred_providers.each do |provider| + cred_values = readme.credentials.select { |cred| cred[:provider] == provider[:name] } + + cred_permissions = [] + cred_roles = [] + cred_apis = [] + + cred_values.each do |credential| + if credential[:permission] + + permission_list = { + "name" => credential[:permission], + "read_only" => credential[:read_only], + "required" => credential[:required] + } + permission_list["description"] = credential[:description] if credential[:description] + + cred_permissions.push(permission_list) + elsif credential[:role] + + role_list = { + "name" => credential[:role], + "read_only" => credential[:read_only], + "required" => credential[:required] + } + role_list["description"] = credential[:description] if credential[:description] + + cred_roles.push(role_list) + end + end + + if cred_permissions.any? + provider[:permissions] = cred_permissions + end + if cred_roles.any? + provider[:roles] = cred_roles + end + end + + policy_template_details[:providers] = cred_providers if cred_providers.any? + end + + # Push each policy template permission details to the 'values' array + values.push(policy_template_details) + end +end + +# Sort values by id +# Opted for id over name, because sometimes the name of a PT does change but the filename (id) very rarely changes +values.sort_by! { |value| value["id"] } + +master_policy_permissions_doc[:values] = values +puts values + +# Create '.data/policy_permissions_list' directory +# permissions_list_dir = "./dist" +permissions_list_dir = "./data/policy_permissions_list" +FileUtils.mkdir_p(permissions_list_dir) unless Dir.exist?(permissions_list_dir) + +# Create JSON document in '.data/policy_permissions_list' directory +File.open("#{permissions_list_dir}/master_policy_permissions_list.json", "w") do |f| + f.write(JSON.pretty_generate(master_policy_permissions_doc)) +end + +# Create YAML document in '.data/policy_permissions_list' directory +File.open("#{permissions_list_dir}/master_policy_permissions_list.yaml", "w") do |f| + # Write YAML document + f.write(master_policy_permissions_doc.to_yaml) +end diff --git a/tools/policy_master_permission_generation/validated_policy_templates.yaml b/tools/policy_master_permission_generation/validated_policy_templates.yaml new file mode 100644 index 0000000000..1f61f1bae6 --- /dev/null +++ b/tools/policy_master_permission_generation/validated_policy_templates.yaml @@ -0,0 +1,37 @@ +# validated_policy_templates[] is a list of policy templates that are validated and ready to be used in the Policy Master. +# "Validated" in this context means: +# - The README.md next to the Policy Template file contains all permissions required for the Policy Template to run (any datasource with a request and auth) -- this confirms all required permissions are documented in the README.md +# - The `data/policy_permissions_list/master_policy_permissions_list` datasets contains all permissions from the README.md -- this confirms generate_policy_master_permissions.rb script parses README as expected +validated_policy_templates: +# AWS +- "./compliance/aws/untagged_resources/aws_untagged_resources.pt" +- "./cost/aws/rightsize_ec2_instances/aws_rightsize_ec2_instances.pt" +- "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt" +- "./cost/aws/old_snapshots/aws_delete_old_snapshots.pt" +- "./cost/aws/reserved_instances/recommendations/aws_reserved_instance_recommendations.pt" +- "./cost/aws/unused_ip_addresses/aws_unused_ip_addresses.pt" +- "./cost/aws/savings_plan/recommendations/aws_savings_plan_recommendations.pt" +- "./cost/aws/rightsize_rds_instances/aws_rightsize_rds_instances.pt" +- "./cost/aws/rightsize_ebs_volumes/aws_volumes_rightsizing.pt" +- "./operational/aws/tag_cardinality/aws_tag_cardinality.pt" +# Azure +- "./compliance/azure/azure_long_stopped_instances/long_stopped_instances_azure.pt" +- "./compliance/azure/azure_untagged_resources/untagged_resources.pt" +- "./cost/azure/unused_sql_databases/azure_unused_sql_databases.pt" +- "./cost/azure/rightsize_compute_instances/azure_compute_rightsizing.pt" +- "./cost/azure/unused_volumes/azure_unused_volumes.pt" +- "./cost/azure/old_snapshots/azure_delete_old_snapshots.pt" +- "./cost/azure/unused_ip_addresses/azure_unused_ip_addresses.pt" +- "./cost/azure/savings_plan/recommendations/azure_savings_plan_recommendations.pt" +- "./cost/azure/reserved_instances/recommendations/azure_reserved_instance_recommendations.pt" +- "./cost/azure/reserved_instances/utilization/azure_reserved_instance_utilization.pt" +- "./cost/azure/rightsize_sql_instances/azure_rightsize_sql_instances.pt" +- "./cost/azure/rightsize_managed_disks/azure_rightsize_managed_disks.pt" +- "./operational/azure/tag_cardinality/azure_tag_cardinality.pt" +# Google +- "./compliance/google/unlabeled_resources/unlabeled_resources.pt" +- "./cost/google/rightsize_vm_recommendations/google_rightsize_vm_recommendations.pt" +- "./cost/google/idle_persistent_disk_recommendations/google_idle_persistent_disk_recommendations.pt" +- "./cost/google/cloud_sql_idle_instance_recommendations/google_sql_idle_instance_recommendations.pt" +- "./cost/google/idle_ip_address_recommendations/google_idle_ip_address_recommendations.pt" +- "./cost/google/cud_recommendations/google_committed_use_discount_recommendations.pt"