From 736c28a67fa46fcdd8baeecc808fa9099b2420d8 Mon Sep 17 00:00:00 2001 From: puchy22 Date: Wed, 10 Apr 2024 13:14:39 +0200 Subject: [PATCH 1/6] doc(service): Improve some explanations and names to clarify --- docs/developer-guide/services.md | 28 +++++++++++++++------------- 1 file changed, 15 insertions(+), 13 deletions(-) diff --git a/docs/developer-guide/services.md b/docs/developer-guide/services.md index 1272f02b4a..525ef412a8 100644 --- a/docs/developer-guide/services.md +++ b/docs/developer-guide/services.md @@ -4,19 +4,21 @@ Here you can find how to create a new service, or to complement an existing one, ## Introduction -To create a new service, you will need to create a folder inside the specific provider, i.e. `prowler/providers//services//`. +In Prowler a service is basically a solution that is ofered by a cloud provider i.e. [ec2](https://aws.amazon.com/ec2/). Essentially it is a class that store all necessary stuff that we will need later in checks to audit some aspects of our Cloud account. + +To create a new service, you will need to create a folder inside the specific provider, i.e. `prowler/providers//services//`. Inside that folder, you MUST create the following files: - An empty `__init__.py`: to make Python treat this service folder as a package. -- A `_service.py`, containing all the service's logic and API calls. -- A `_client_.py`, containing the initialization of the service's class we have just created so the checks's checks can use it. +- A `_service.py`, containing all the service's logic and API calls. +- A `_client_.py`, containing the initialization of the service's class we have just created so the checks's checks can use it. ## Service The Prowler's service structure is the following and the way to initialise it is just by importing the service client in a check. -## Service Base Class +### Service Base Class All the Prowler provider's services inherits from a base class depending on the provider used. @@ -26,11 +28,11 @@ All the Prowler provider's services inherits from a base class depending on the Each class is used to initialize the credentials and the API's clients to be used in the service. If some threading is used it must be coded there. -## Service Class +### Service Class Due to the complexity and differencies of each provider API we are going to use an example service to guide you in how can it be created. -The following is the `_service.py` file: +The following is the `_service.py` file: ```python title="Service Class" from datetime import datetime @@ -176,9 +178,9 @@ class (ServiceParentClass): ) ``` -### Service Models +#### Service Models -For each class object we need to model we use the Pydantic's [BaseModel](https://docs.pydantic.dev/latest/api/base_model/#pydantic.BaseModel) to take advantage of the data validation. +Service models are classes that are used in the service to design all that we need to store in each class object extrated from API calls. We use the Pydantic's [BaseModel](https://docs.pydantic.dev/latest/api/base_model/#pydantic.BaseModel) to take advantage of the data validation. ```python title="Service Model" # In each service class we have to create some classes using @@ -202,7 +204,7 @@ class (BaseModel): tags: Optional[list] """[].tags""" ``` -### Service Objects +#### Service Objects In the service each group of resources should be created as a Python [dictionary](https://docs.python.org/3/tutorial/datastructures.html#dictionaries). This is because we are performing lookups all the time and the Python dictionary lookup has [O(1) complexity](https://en.wikipedia.org/wiki/Big_O_notation#Orders_of_common_functions). We MUST set as the dictionary key a unique ID, like the resource Unique ID or ARN. @@ -213,17 +215,17 @@ self.vpcs = {} self.vpcs["vpc-01234567890abcdef"] = VPC_Object_Class() ``` -## Service Client +### Service Client Each Prowler service requires a service client to use the service in the checks. -The following is the `_client.py` containing the initialization of the service's class we have just created so the service's checks can use them: +The following is the `_client.py` containing the initialization of the service's class we have just created so the service's checks can use them: ```python from prowler.providers..lib.audit_info.audit_info import audit_info -from prowler.providers..services.._service import +from prowler.providers..services.._service import -_client = (audit_info) +_client = (audit_info) ``` ## Permissions From d26d953a9d4050fc0f729914373955cc9a8d6c81 Mon Sep 17 00:00:00 2001 From: puchy22 Date: Wed, 10 Apr 2024 13:50:37 +0200 Subject: [PATCH 2/6] doc(service): Adding some specifications and explanations --- docs/developer-guide/checks.md | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/docs/developer-guide/checks.md b/docs/developer-guide/checks.md index d1f945c606..1f9646c9bd 100644 --- a/docs/developer-guide/checks.md +++ b/docs/developer-guide/checks.md @@ -5,9 +5,15 @@ Here you can find how to create new checks for Prowler. **To create a check is required to have a Prowler provider service already created, so if the service is not present or the attribute you want to audit is not retrieved by the service, please refer to the [Service](./services.md) documentation.** ## Introduction + +The checks are the foundamental piece of Prowler. A check is a simply piece of code that ensure if something is configured whith best cybersecurity practices, or is not and could be a breach of a cloud infrastructure. Furthemore, some information about the audition that is being doing over that resource (*metadata*). + To create a new check for a supported Prowler provider, you will need to create a folder with the check name inside the specific service for the selected provider. -We are going to use the `ec2_ami_public` check form the `AWS` provider as an example. So the folder name will `prowler/providers/aws/services/ec2/ec2_ami_public` (following the format `prowler/providers//services//`), with the name of check following the pattern: `service_subservice/resource_action`. +We are going to use the `ec2_ami_public` check form the `AWS` provider as an example. So the folder name will `prowler/providers/aws/services/ec2/ec2_ami_public` (following the format `prowler/providers//services//`), with the name of check following the pattern: `service_subservice_resource_action`. + +???+ note + A subservice is more specific part of a service that is gonna be audit. Sometime it could be the shortened name of the class attribute that is gonna be acceded in the check. Inside that folder, we need to create three files: @@ -101,7 +107,7 @@ All the checks MUST fill the `report.status` and `report.status_extended` with t - Status -- `report.status` - `PASS` --> If the check is passing against the configured value. - - `FAIL` --> If the check is passing against the configured value. + - `FAIL` --> If the check is failing against the configured value. - `MANUAL` --> This value cannot be used unless a manual operation is required in order to determine if the `report.status` is whether `PASS` or `FAIL`. - Status Extended -- `report.status_extended` - MUST end in a dot `.` @@ -111,7 +117,7 @@ All the checks MUST fill the `report.status` and `report.status_extended` with t All the checks MUST fill the `report.region` with the following criteria: -- If the audited resource is regional use the `region` attribute within the resource object. +- If the audited resource is regional use the `region` (the name changes depending on the provider) attribute within the resource object. - If the audited resource is global use the `service_client.region` within the service client object. ### Resource ID, Name and ARN @@ -140,7 +146,7 @@ All the checks MUST fill the `report.resource_id` and `report.resource_arn` with ### Python Model The following is the Python model for the check's class. -As per August 5th 2023 the `Check_Metadata_Model` can be found [here](https://github.com/prowler-cloud/prowler/blob/master/prowler/lib/check/models.py#L59-L80). +As per August 5th 2023 the `Check_Metadata_Model` can be found [here](https://github.com/prowler-cloud/prowler/blob/master/prowler/lib/check/models.py#L36-L82). ```python class Check(ABC, Check_Metadata_Model): From bd2bac36863b6dc172a7a02a37f232e657fcf7be Mon Sep 17 00:00:00 2001 From: puchy22 Date: Wed, 10 Apr 2024 13:59:19 +0200 Subject: [PATCH 3/6] docs(index): Change the requirements URL to be more precise --- docs/index.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/index.md b/docs/index.md index 61935ad5cb..d343889739 100644 --- a/docs/index.md +++ b/docs/index.md @@ -264,7 +264,7 @@ prowler aws --profile custom-profile -f us-east-1 eu-south-2 ???+ note By default, `prowler` will scan all AWS regions. -See more details about AWS Authentication in [Requirements](getting-started/requirements.md) +See more details about AWS Authentication in [Requirements](getting-started/requirements.md#aws) ### Azure @@ -284,7 +284,7 @@ prowler azure --browser-auth --tenant-id "XXXXXXXX" prowler azure --managed-identity-auth ``` -See more details about Azure Authentication in [Requirements](getting-started/requirements.md) +See more details about Azure Authentication in [Requirements](getting-started/requirements.md#azure) Prowler by default scans all the subscriptions that is allowed to scan, if you want to scan a single subscription or various specific subscriptions you can use the following flag (using az cli auth as example): ```console @@ -311,7 +311,7 @@ Prowler by default scans all the GCP Projects that is allowed to scan, if you wa prowler gcp --project-ids ... ``` -See more details about GCP Authentication in [Requirements](getting-started/requirements.md) +See more details about GCP Authentication in [Requirements](getting-started/requirements.md#google-cloud) ## Kubernetes From 79a6dee403e9db2016d5f38a881bcda3d70afd65 Mon Sep 17 00:00:00 2001 From: puchy22 Date: Thu, 11 Apr 2024 09:38:38 +0200 Subject: [PATCH 4/6] docs(check): Fix some misspellings and add region name correct for each provider --- docs/developer-guide/checks.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/docs/developer-guide/checks.md b/docs/developer-guide/checks.md index 1f9646c9bd..98b20815ad 100644 --- a/docs/developer-guide/checks.md +++ b/docs/developer-guide/checks.md @@ -6,14 +6,14 @@ Here you can find how to create new checks for Prowler. ## Introduction -The checks are the foundamental piece of Prowler. A check is a simply piece of code that ensure if something is configured whith best cybersecurity practices, or is not and could be a breach of a cloud infrastructure. Furthemore, some information about the audition that is being doing over that resource (*metadata*). +The checks are the foundamental piece of Prowler. A check is a simply piece of code that ensures if something is configured against cybersecurity best practices, and some metadata to give the final user more information of what is running and why. To create a new check for a supported Prowler provider, you will need to create a folder with the check name inside the specific service for the selected provider. -We are going to use the `ec2_ami_public` check form the `AWS` provider as an example. So the folder name will `prowler/providers/aws/services/ec2/ec2_ami_public` (following the format `prowler/providers//services//`), with the name of check following the pattern: `service_subservice_resource_action`. +We are going to use the `ec2_ami_public` check from the `AWS` provider as an example. So the folder name will be `prowler/providers/aws/services/ec2/ec2_ami_public` (following the format `prowler/providers//services//`), with the name of check following the pattern: `service_subservice_resource_action`. ???+ note - A subservice is more specific part of a service that is gonna be audit. Sometime it could be the shortened name of the class attribute that is gonna be acceded in the check. + A subservice is an specific component of a service that is gonna be audited. Sometimes it could be the shortened name of the class attribute that is gonna be accessed in the check. Inside that folder, we need to create three files: @@ -117,7 +117,7 @@ All the checks MUST fill the `report.status` and `report.status_extended` with t All the checks MUST fill the `report.region` with the following criteria: -- If the audited resource is regional use the `region` (the name changes depending on the provider) attribute within the resource object. +- If the audited resource is regional use the `region` (the name changes depending on the provider: `location` in Azure and GCP and `namespace` in K8s) attribute within the resource object. - If the audited resource is global use the `service_client.region` within the service client object. ### Resource ID, Name and ARN @@ -146,7 +146,7 @@ All the checks MUST fill the `report.resource_id` and `report.resource_arn` with ### Python Model The following is the Python model for the check's class. -As per August 5th 2023 the `Check_Metadata_Model` can be found [here](https://github.com/prowler-cloud/prowler/blob/master/prowler/lib/check/models.py#L36-L82). +As per April 11th 2024 the `Check_Metadata_Model` can be found [here](https://github.com/prowler-cloud/prowler/blob/master/prowler/lib/check/models.py#L36-L82). ```python class Check(ABC, Check_Metadata_Model): From 565df6fc8581493ae7b0174c2581436405c6156b Mon Sep 17 00:00:00 2001 From: puchy22 Date: Thu, 11 Apr 2024 09:40:27 +0200 Subject: [PATCH 5/6] docs(service): Fix the introduction redaction --- docs/developer-guide/services.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/developer-guide/services.md b/docs/developer-guide/services.md index 525ef412a8..73ca621bf8 100644 --- a/docs/developer-guide/services.md +++ b/docs/developer-guide/services.md @@ -4,7 +4,7 @@ Here you can find how to create a new service, or to complement an existing one, ## Introduction -In Prowler a service is basically a solution that is ofered by a cloud provider i.e. [ec2](https://aws.amazon.com/ec2/). Essentially it is a class that store all necessary stuff that we will need later in checks to audit some aspects of our Cloud account. +In Prowler, a service is basically a solution that is offered by a cloud provider i.e. [ec2](https://aws.amazon.com/ec2/). Essentially it is a class that stores all the necessary stuff that we will need later in the checks to audit some aspects of our Cloud account. To create a new service, you will need to create a folder inside the specific provider, i.e. `prowler/providers//services//`. From 168f2c11f69191f37ae190eff4427aef9c263e03 Mon Sep 17 00:00:00 2001 From: Pepe Fagoaga Date: Thu, 11 Apr 2024 11:37:26 +0200 Subject: [PATCH 6/6] chore: improve copy --- docs/developer-guide/checks.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/developer-guide/checks.md b/docs/developer-guide/checks.md index 98b20815ad..8db4a0f9b9 100644 --- a/docs/developer-guide/checks.md +++ b/docs/developer-guide/checks.md @@ -6,7 +6,7 @@ Here you can find how to create new checks for Prowler. ## Introduction -The checks are the foundamental piece of Prowler. A check is a simply piece of code that ensures if something is configured against cybersecurity best practices, and some metadata to give the final user more information of what is running and why. +The checks are the fundamental piece of Prowler. A check is a simply piece of code that ensures if something is configured against cybersecurity best practices. Then the check generates a finding with the result and includes the check's metadata to give the user more contextual information about the result, the risk and how to remediate it. To create a new check for a supported Prowler provider, you will need to create a folder with the check name inside the specific service for the selected provider.