AWS Cloud Financial Management
Introducing AWS Application Cost Profiler, offering user-based cost data of shared AWS resources
Voiced by Amazon Polly
October 6, 2021: This blog post is under construction. Please refer back to this post in a day or two for the most accurate and helpful information.
It has become increasingly common for customers to deploy applications that share infrastructure resources for the purpose of cloud cost optimization. As more organizations are moving to the shared infrastructure models, they continuously look for ways to understand the consumption of their end users or tenants. This is especially true with software-as-a-service (SaaS) providers, who often achieve economies of scale by sharing compute, storage, and other cloud services. Ideally, SaaS providers need access to metrics to apportion infrastructure costs at the tenant level to understand margins and consumption patterns. Adoption of SaaS technologies by customers and independent software vendors (ISVs) is growing, demanding the capability to monitor and track cost patterns of shared resources by various dimensions. Understanding cost per tenant in an accurate and standardized way is key to businesses running SaaS or any multi-tenant applications.
In a multi-tenant application, tenants share some or most of the infrastructure resources. As a result, allocating each tenant’s cost can be challenging. It becomes more complicated, as systems deployment and consumption can vary by service type (for example, compute vs storage, network vs databases). To get granular cost breakdown, application owners have to invest heavily on engineering and infrastructure resources to build custom solutions, query logs from multiple sources for ad-hoc analysis. Or they’d settle for using static, rough estimates, like number of users or gigabytes of data stored to re-distribute AWS costs across tenant base. The existing cloud management tools often lack the multi-tenancy consumption view to display tenant’s proportion of cost and usage, which adds complexity to manage applications with shared infrastructure.
Last week we announced the launch of AWS Application Cost Profiler (ACP), a service that allows customers, running multi-tenant applications, to get granular cost breakdown of shared AWS resources across tenant base. AWS Application Cost Profiler provides customers, especially SaaS ISVs, a standard mechanism to correlate and report their infrastructure cost for each customer or tenant. With the granular cost insights of AWS resource consumption, ISVs can develop go-to-market strategies with tier-based support or consumption-based pricing for their products and effectively manage costs of a multi-tenant architecture model. Or, organizations running multi-tenant applications can use the data to define accurate cost allocation model for chargeback purpose. Application Cost Profiler requires application owners to instrument their application for tenant metadata in a contextual format. We will cover what customers need to do in order to properly instrument their tenant metadata later in this blog.
Getting started with AWS Application Cost Profiler (ACP)
Getting started with AWS Application Cost Profiler (ACP), is a two-step process: step 1: a one-time setup to configure ACP for generating final consumption insights report; step 2: Instrument the application for tenant metadata. The two steps can be done in any order but both steps need to be completed before ACP can generate consumption insights. To save time for your initial set up, we created three AWS CloudFormation templates that you may find helpful. See details in the sections below.
Step 1: Configure the Application Cost Profiler for reporting consumption insights
Application Cost Profiler report configuration must be defined in the AWS Console, via the AWS Command Line Interface, or using one of the AWS SDKs. We will demonstrate how you configure this in the AWS console. The report configuration is to instruct AWS Application Cost Profiler where to deliver the tenant cost reports to. The destination is an Amazon Simple Storage Service (Amazon S3) bucket with the proper permissions for Application Cost Profiler to write the reports to.
Prerequisites
For this walkthrough, you should have the following prerequisites:
- An AWS account;
- AWS Identity and Access Management (IAM) user with console access and admin privileges;
- Enable AWS Cost Explorer.
Setup Amazon S3 bucket and report configuration
1. Log in to the AWS Console;
2. Verify that Cost Explorer has been enabled (Important as AWS Application Cost Profiler will not process tenant usage data without Cost Explorer being enabled);
3. Click on the launch stack button below to launch our first CloudFormation stack that will install and configure a S3 bucket with proper Application Cost Profiler permissions and server side encryption settings, an Amazon EventBridge rule, and an Amazon Simple Notification Service (Amazon SNS) Topic for AWS Application Cost Profiler events that you can optionally subscribe to;
4. Once the launch of the CloudFormation stack has completed, in the N. Virgina/us-east-1 region use the console search function to navigate to the “AWS Application Cost Profiler” landing page;
5. In the AWS Application Cost Profiler dashboard, click on “Get started now”.
6. Setup a new report configuration:
a. Report Name – This is user defined and cannot be changed once saved
b. Report Description – This is a user defined description of the report configuration (optional)
c. Amazon S3 Bucket Name – This is the Amazon S3 bucket where AWS Application Cost Profiler will deliver the reports to. This bucket was created using the previous CloudFormation template. Bucket is named “acp-{REGION}-{ACCOUNT_ID}”, substituting {REGION} with the AWS region that the CloudFormation template was deployed to, e.g. us-east-1, and {ACCOUNT_ID} with the actual AWS account id that was used to deploy the CloudFormation template. So for example “acp-us-east-1-987654321”. This Report Bucket name can also be found in the “Resources” section of the CloudFormation stack deployed above.
d. S3 Prefix – This is the prefix in the S3 bucket used above where AWS Application Cost Profiler will deliver the reports to. The s3 Bucket deployed in the CloudFormation template above enabled write permissions for AWS Application Cost Profiler to the “reports” prefix, therefore enter “reports” for S3 prefix here.
e. Time Frequency – Choose whether the report is generated on a Daily or Monthly cadence, or Both.
f. Report Output Format – Choose the type of file that will be created within your Amazon S3 bucket. If you choose CSV, Application Cost Profiler creates a comma-separated values text file with gzip compression for the reports. If you choose Parquet, a Parquet file is generated for the reports.
7. Click the “Configure” button. Application Cost Profiler will verify the existence of the Amazon S3 bucket defined above as well as the services write permissions to the prefix defined above. If successful you will see a confirmation.
8. Click “OK” to return to the AWS Application Cost Profiler
Now that you’ve set up a S3 bucket destination with permissions and set up a report configuration within the AWS Cost Application Profiler console, you are ready to prepare, upload, and import your tenant usage data.
Step 2: Reporting tenant usage data from your services – an example
In order to generate reports, AWS Application Cost Profiler requires you to provide tenant usage data. This information needs to be uploaded to an S3 location that AWS Application Cost Profiler has permissions to read from. The S3 bucket created in the first CloudFormation template above has granted AWS Application Cost Profiler read access to the “import/” prefix.
By giving Application Cost Profiler access to your usage data from S3 bucket, you allow Application Cost Profiler to temporarily copy such usage data objects to the US East (Northern Virginia) Region while processing reports. These data objects will be kept in the US East (Northern Virginia) Region until the monthly report generation is complete. To avoid incurring data transfer charges, you can configure requester pays on bucket.
As an example, let’s instrument a sample serverless application to track cost across your tenant base. Our second CloudFormation template will deploy a basic serverless application using Amazon API Gateway and AWS Lambda.
The Lambda function performs a few complex math operations to simulate business logic.
exports.handler = (event, context) => {
console.log("TENANT_ID\t%s", event.tenantId);
mySlowFunction(13);
const response = {
statusCode: 200,
body: "SUCCESS"
};
return response;
};
…
Deploy the sample serverless application
1. Log in to the AWS Console
2. Click on the launch stack button below to launch the second CloudFormation stack that will install and configure the sample serverless application. It’s important that this stack be launched in the same region as the CloudFormation stack launched previously.
3. Once this CloudFormation template has completed deploying, go to the Outputs section of the stack and note the the apiGatewayInvokeURL value, it will be in the following format:
https://i3pbggxbf2.execute-api.us-east-1.amazonaws.com/call?tenantId=123
4. Using the apiGatewayInvokeURL identified above, open a web browser and paste the value into the location window. This will execute the sample serverless application simulating use by tenant “123”. Now change the value after tenantId= in the browser location window to simulate multiple tenants, such as tenantId=10 or tenantId=20, etc. pressing enter each time to execute the sample serverless application. Invoking this endpoint in a browser will cause the Lambda function to execute and log an entry in the corresponding Amazon CloudWatch log. You can also use utilities like JMeter to simulate hundreds or even thousands of tenants invoking this sample serverless application.
Please Note: This serverless application is one of the several approaches you can use to track your tenant usage. AWS Application Cost Profiler requires the tenant usage report to be in CSV file format only, which is the end result of this example. As mentioned, there are many different ways to generate your tenant usage CSV report, depending on your application architecture and your current tenant model.
Now that you have the tenant ID available in the Lambda CloudWatch logs of the sample serverless application, it’s time to generate the tenant usage data file. This file will need to be structured in a format as described below. As a reminder, only CSV files with file name as “.csv, .csv.gz, .csv.gzip” are supported by ACP.
Application Tenant Usage Data Elements
- ApplicationId – Identifies the application or product in your system that is being used. Defines the scope of the tenant metadata.
- TenantId – An identifier in your system for the tenant who is consuming the specified resource. Application Cost Profiler aggregates to this level within the ApplicationId.
- TenantDesc – (Value Optional) Additional data about the tenant for your own additional reporting.
- UsageAccountId – The account that the resource runs in (important for accounts that are part of an organization).
- StartTime – Timestamp (in milliseconds) from Epoch, in UTC. Indicates the start time of the period for the usage by the specified tenant.
- EndTime – Timestamp (in milliseconds) from Epoch, in UTC. Indicates the end time of the period for the usage by the specified tenant.\
- ResourceId – Amazon Resource Name (ARN) for resource being used.
- Name – (Optional) As an alternative to specifying a ResourceId, you can specify a Name resource tag to attribute costs to a set of resources (the field must include the value you want to use for the Name tag). Resource tags are enabled as part of your AWS Cost and Usage Report. For more information about resource tags, see Resource tags details in the AWS Cost and Usage Report User Guide.
Please Note: ApplicationId, TenantId, TenantDesc, UsageAccountId, StartTime, EndTime, ResourceId* are AWS Application Cost Profiler-reserved Keywords and cannot be used as Name tag names.
In this example we are going to generate the tenant usage data according to the format above by processing and reading the information from the CloudWatch logs of the Lambda function we want to report on. For the instrumentation infrastructure, we will be using the following AWS resources:
- CloudWatch Logs: In this example, we will use CloudWatch Logs to provide us the needed information to generate tenant usage data files for the example Lambda. APN solutions like NewRelic and Splunk could also meet this need.
- CloudWatch Event: We will use AWS CloudWatch events to trigger the instrumentation Lambda hourly, and submit hourly tenant usage data to AWS Application Cost Profiler.
- Lambda Function: This Lambda will have the logic to extract information from CloudWatch Logs, generate the tenant usage data files and upload the files to the S3 bucket created in the CloudFormation template deployed above
- IAM: the right IAM policy needs to be in place for the Lambda function to write to the S3 bucket.
- CloudFormation Templates: we will use a CloudFormation template so you can easily deploy the sample function and trigger to generate the hourly tenant usage data.
Deploy the sample tenant usage generator
1. Log in to the AWS Console
2. Click on the launch stack button below to launch our third CloudFormation stack that will install and configure the CloudWatch tenant usage generator example. It’s important that this stack be launched in the same region as the CloudFormation stack launched previously. The default parameter for “LambdaName” is preset to “ACPSampleLambda” which is the name of the Lambda function that was deployed in the previous CloudFormation template. This is the Lambda function which the corresponding CloudWatch logs will be analyzed for tenant usage data.
With the above stack deployed and assuming the original AWS Lambda function to be reported on has been run in the last hour, you should now see a new file created in the acp-{REGION}-{ACCOUNT_ID} bucket under the “imports” prefix every hour that the InstrumentationLambda function executes on the schedule defined above. The file will contain tenant usage data in the csv format similar to this:
ApplicationId,TenantId,TenantDesc,UsageAccountId,StartTime,EndTime,ResourceId MyApp,Tenant1,,123456789012,1613681437032.9001,1613681437041.5312,arn:aws:ec2:useast-1:123456789012:instance/1234-abcd-example-1234 MyApp,Tenant2,,123456789012,1613681245531.4426,1613681245551.1323,arn:aws:ec2:useast-1:123456789012:instance/1234-abcd-example-1234 MyApp,Tenant1,,123456789012,1613681904815.3381,1613681904930.0972,arn:aws:ec2:useast-1:123456789012:instance/1234-abcd-example-1234 MyApp,Tenant2,,123456789012,1613681904765.1956,1613681904946.574,arn:aws:ec2:useast-1:123456789012:instance/1234-abcd-example-1234
The InstrumentationLambda function above also invoked the applicationcostprofiler.importApplicationUsage API which informed AWS Application Cost Profiler to process the generated file during the nightly and/or monthly report generation cycle.
Application Cost Profiler Data
If the time frequency for your Application Cost Profiler (ACP) report was set up to be daily, it can take up to 24 hours, after the InstumentationLambda run calls the ImportApplicationUsage API for the ACP data to be available in the S3 Report Bucket and prefixed configured. Using the above CloudFormation setup, the ACP data will be placed in S3://acp-{REGION}-{ACCOUNT_ID}/reports/YYYY/MM/DD/part-*.csv.gz accordingly. An Amazon EventBridge event will also be generated when ACP data is available in the following format:
{
"version": "0",
"id": "01234567-EXAMPLE",
"detail-type": "Application Cost Profiler Report Generated",
"source": "aws.application-cost-profiler",
"account": "123456789012",
"time": "2021-03-31T10:23:43Z",
"region": "us-east-1",
"resources": [],
"detail": {
"message": "Application Cost Profiler report delivered in bucket: acp-us-east-1-123456789, key: reports/2020/05/01/ part-c744af14-57bd-4c51-b1d4-badc155ef7ef-c000.csv.gz"
}
}
The following data is available in the tenant cost csv file generated by ACP
AWS Application Cost Profiler Tenant Cost Breakdown Elements on output file
- PayerAccountId – The management account ID in an organization, or the account ID if the account is not part of AWS Organizations.
- UsageAccountId – The account ID for the account with usage.
- LineItemType – The type of record. Always Usage.
- UsageStartTime – Timestamp (in milliseconds) from Epoch, in UTC. Indicates the start time of the period for the usage by the specified tenant.
- UsageEndTime – Timestamp (in milliseconds) from Epoch, in UTC. Indicates the end time of the period for the usage by the specified tenant.
- ApplicationIdentifier – The ApplicationId specified in the usage data sent to Application Cost Profiler.
- TenantIdentifier – The TenantId specified in the usage data sent to Application Cost Profiler. Data with no record in the usage data is collected in unattributed.
- TenantDescription – The TenantDesc specified in the usage data sent to Application Cost Profiler.
- ProductCode – The AWS product being billed (for example, AmazonEC2).
- UsageType – The type of usage being billed (for example, BoxUsage:c5.large).
- Operation – The operation being billed (for example, RunInstances).
- ResourceId – The resource ID or Amazon Resource Name (ARN) for the resource being billed.
- ScaleFactor – If a resource is over-allocated for an hour, for example, the usage data reported is equal to 2 hours instead of 1 hour, a scale factor is applied to make the total equal the actual billed amount (in this case, 0.5). This column reports the scale factor used for the specific resource for that hour. The scale factor is always greater than zero (0) and less than or equal to 1.
- TenantAttributionPercent – The percentage of the usage attributed to the specified tenant (between zero (0) and 1).
- UsageAmount – The amount of usage attributed to the specified tenant.
- CurrencyCode – The currency that the rate and cost are in (for example, USD).
- Rate – The billing rate for the usage, per unit.
- TenantCost – The total cost for that resource for the specified tenant.
- Region – The AWS Region of the resource.
- Name – If you created resource tags for your resources on the Cost and Usage report, or through the resource usage data, the Name tag is shown here. For more information about resource tags, see Resource tags details in the Cost and Usage Report User Guide.
The following is an example of the actual csv output in the ACP report.
This csv file can then be queried directly using Amazon Athena or integrated into your existing analytics and reporting tools such as Amazon QuickSight such as the example here.
Conclusion
In this walkthrough, you have setup a new AWS Application Cost Profiler (ACP) report configuration including a destination Amazon S3 Report Bucket with appropriate permissions. You then completed the process of generating tenant usage data for a sample Lambda application, imported the usage data into ACP, and then received the result reports.
Our service team provides reference implementation guidance for different architecture patterns to facilitate the instrumentation. We also have a dedicated Solution Architects team to support you through the instrumentation and facilitate on-boarding. If you need support for on-boarding, reach out to us at aws-acp@amazon.com or contact your account team to get support.
To better understand the value and importance of cost per tenant, please refer to the Calculating Tenant Costs in a SaaS Environment blog post, as well as the AWS re:Invent session that outlines the basic approach and challenges associated with capturing this information.
We’d like to extend our thanks to the service team, specifically our colleagues, Prerit Panwar (Senior Product Manager, AWS Partner), and Michael Kane (AWS Cloud Infrastructure Architect).