Cloud Network Security AWS Onboarding Script
This AWS shell script automates the onboarding of an AWS Account into the ACE Cloud Network Security. This template sets up the necessary AWS resources and permissions for Algosec to integrate with and monitor the AWS environment, with an automated onboarding process via the Lambda function.
The following is a breakdown of its sections and their purposes:
1. Template Version
AWSTemplateFormatVersion: "2010-09-09"
Purpose: Specifies the CloudFormation template version.
2. Define Resources
Resources:
Purpose: Begins the section where all AWS resources are defined.
3. Algosec Role
AlgosecRole:
Type: "AWS::IAM::Role"
Properties:
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Principal:
AWS: '347594369393'
Condition:
StringEquals:
sts:ExternalId: algosec-1b2aab45-8a3d-409d-81ba-e520a13beebe
Effect: "Allow"
Action:
- "sts:AssumeRole"
Purpose: Defines an IAM Role that Algosec can assume to access AWS resources. It specifies the trusted entity (Algosec's AWS account) and an external ID for additional security.
4. Onboarding Role
OnboardingFunctionRole:
Type: 'AWS::IAM::Role'
Properties:
AssumeRolePolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Principal:
Service:
- lambda.amazonaws.com
Action:
- 'sts:AssumeRole'
ManagedPolicyArns:
- 'arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole'
Purpose: Defines an IAM Role for the Lambda function, allowing it to be assumed by the Lambda service and granting basic execution permissions.
5 AlgoSec Notification Function
AlgosecNotificationFunction:
Type: 'AWS::Lambda::Function'
DependsOn:
- OnboardingFunctionRole
Properties:
FunctionName: 'AlgosecOnboardingNotification'
Code:
ZipFile: |
Purpose: Begins the definition of the Lambda function, specifying its name and that the code will be provided inline.
6. Modules
const response = require('cfn-response');
const https = require('https');
Purpose: Imports required modules.
7. Function Handler
exports.handler = async (event, context, callback) => {
Purpose: Defines the Lambda function handler.
8. Helper Function
const httpsRequest = (options, data) => {
return new Promise((resolve, reject) => {
const request = https.request(options, response => {
let responseBody = '';
response.on('data', chunk => responseBody += chunk.toString());
if (response.statusCode >= 200 && response.statusCode < 300) {
response.on('end', () => resolve(responseBody));
} else {
response.on('end', () => reject(responseBody));
}
});
request.on('error', err => reject(err));
request.write(data)
request.end();
});
};
Purpose: Defines a helper function for making HTTPS requests.
9. Login Access Keys
try {
const loginOptions = {
hostname: 'us.app.algosec.com',
path: '/api/algosaas/auth/v1/access-keys/login',
method: 'POST'
};
Purpose: Begins a try-catch block and sets up options for the login request.
10. Login Credentials
const additionals = Buffer.from('eyJ0ZW5hbnRJZCI6IjQ1NjkwNTg0MzM3MTY3MTgiLCJjbGllbnRJZCI6IjNnNGJ1bWh2ZmpxbmNtNmVsNDA4MnM5OGwzIiwiY2xpZW50U2VjcmV0IjoiMXFrcThlNW1tZnJwNTdmMjA3aWpiMzFib2diZTFzaG4yb2VwcjkzaHYyYm1obzJyOWhnaiJ9', 'base64').toString('utf-8');
Purpose: Decodes base64-encoded login credentials.
11. Login Request
const loginResponse = JSON.parse(await httpsRequest(loginOptions, additionals));
const loginResponse = JSON.parse(await httpsRequest(loginOptions, additionals));
Purpose: Sends login request and parses the response.
12. Role Assignment
const onboardingOptions = {
hostname: 'prod.cloudflow.algosec.com',
path: '/cloudflow/api/admin/v1/onboarding/aws',
method: 'POST',
headers: {
'Authorization': 'Bearer ' + loginResponse.access_token
}
};
Purpose: Sets up options for the onboarding request, including the auth token.
13. Onboarding Request
const onboardingData = JSON.stringify({ event, role_arn: process.env.algosecRole, external_id: process.env.externalId, supportChanges: false, flowLogs: true}); await httpsRequest(onboardingOptions, onboardingData);
Purpose: Sends the onboarding request.
14. Cloud Network Security Onboarding Call
callback(null, { 'Status': 'SUCCEEDED' });
response.send(event, context, response.SUCCESS);
Purpose: Sends success responses.
15. Response Handling
Handler: index.handler
MemorySize: 128
Runtime: nodejs18.x
Timeout: 10
Role: !GetAtt OnboardingFunctionRole.Arn
Environment:
Variables:
algosecRole: !GetAtt AlgosecRole.Arn
externalId: algosec-1b2aab45-8a3d-409d-81ba-e520a13beebe
Purpose: Configures the Lambda function's runtime settings and environment variables.
16. Lambda Function
AlgosecNotificationInvoke:
Type: Custom::OnboardingNotificationInvokation
Version: "1.0"
Properties:
ServiceToken: !GetAtt AlgosecNotificationFunction.Arn
Touch: 1742387171667
Purpose: Defines a custom resource to invoke the Lambda function.
17. Read Only Policy
CloudFlowReadOnlyPolicy:
Type: "AWS::IAM::Policy"
Properties:
PolicyName: "CloudFlowReadOnly"
Roles:
- Ref: "AlgosecRole"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Sid: "CloudFlowReadOnly"
Action:
# ... (list of allowed actions)
Effect: "Allow"
Resource: "*"
Purpose: Defines an IAM policy granting read-only access to various AWS services.
18. Flow Logs Policy
CloudFlowReadFlowLogsPolicy:
Type: "AWS::IAM::Policy"
Properties:
PolicyName: "CloudFlowReadFlowLogs"
Roles:
- Ref: "AlgosecRole"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Sid: "CloudFlowReadFlowLogs"
Action:
- "s3:GetObject*"
Effect: "Allow"
Resource: "*"
Purpose: Defines another IAM policy specifically for reading S3 objects (likely flow logs).