Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(stepfunctions-tasks): bedrock createModelCustomizationJob integration #31913

Open
wants to merge 75 commits into
base: main
Choose a base branch
from

Conversation

badmintoncryer
Copy link
Contributor

This PR was previously created and passed the community review, but the maintainer review stopped midway, and it was eventually closed. There shouldn’t be any issues with the content, so I am submitting the PR again.

Issue # (if applicable)

Closes #29042

Reason for this change

AWS stepfunctions support optimized integration with AWS bedrock.
Currently, only invokeModel is supported by CDK, but I would like createModelCustomizationJob to be supported in the same manner.

Description of changes

I've added CreatemodelCustomizationJob class.

const taskConfig = {
  baseModel: model,
  clientRequestToken: 'MyToken',
  customizationType: CustomizationType.FINE_TUNING,
  kmsKey,
  customModelName: 'MyCustomModel',
  customModelTags: [{ key: 'key1', value: 'value1' }],
  hyperParameters: {
    batchSize: '10',
  },
  jobName: 'MyCustomizationJob',
  jobTags: [{ key: 'key2', value: 'value2' }],
  outputDataS3Uri: outputBucket.s3UrlForObject(),
  trainingDataS3Uri: trainingBucket.s3UrlForObject(),
  validationDataS3Uri: [validationBucket.s3UrlForObject()],
  vpcConfig: {
    securityGroups: [new ec2.SecurityGroup(stack, 'SecurityGroup', { vpc })],
    subnets: vpc.isolatedSubnets,
  },
};

const task1 = new BedrockCreateModelCustomizationJob(stack, 'CreateModelCustomizationJob1', taskConfig);

const chain = sfn.Chain
  .start(new sfn.Pass(stack, 'Start'))
  .next(task1)
  .next(new sfn.Pass(stack, 'Done'));

new sfn.StateMachine(stack, 'StateMachine', {
  definitionBody: sfn.DefinitionBody.fromChainable(chain),
  timeout: cdk.Duration.seconds(30),
});

Description of how you validated changes

I've added both unit and integ tests.

Checklist


By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license

@aws-cdk-automation aws-cdk-automation added the pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. label Oct 26, 2024
@moelasmar moelasmar added pr/needs-maintainer-review This PR needs a review from a Core Team Member and removed pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. labels Oct 26, 2024
@aws-cdk-automation aws-cdk-automation added pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. and removed pr/needs-maintainer-review This PR needs a review from a Core Team Member labels Oct 26, 2024
}

private validatePattern(name: string, pattern: RegExp, value?: string): void {
if (value !== undefined && !Token.isUnresolved(value) && !pattern.test(value)) {

Check failure

Code scanning / CodeQL

Polynomial regular expression used on uncontrolled data High

This
regular expression
that depends on
library input
may run slow on strings starting with '0' and with many repetitions of '-'.
@badmintoncryer badmintoncryer force-pushed the createModelCustomizationJob branch from 083ec3a to c209f7f Compare October 28, 2024 13:22
@badmintoncryer
Copy link
Contributor Author

@moelasmar It appears that the needs-maintainer-review label was attached, but it was automatically removed.

Additionally, I’m seeing a CodeQL error related to a regular expression, but this expression is directly from the CloudFormation documentation. In this case, I believe it’s acceptable to ignore the error. What are your thoughts?

Copy link

codecov bot commented Nov 27, 2024

Codecov Report

All modified and coverable lines are covered by tests ✅

Project coverage is 81.38%. Comparing base (b021efe) to head (068c110).
Report is 35 commits behind head on main.

Additional details and impacted files
@@           Coverage Diff           @@
##             main   #31913   +/-   ##
=======================================
  Coverage   81.38%   81.38%           
=======================================
  Files         222      222           
  Lines       13698    13698           
  Branches     2413     2413           
=======================================
  Hits        11148    11148           
  Misses       2271     2271           
  Partials      279      279           
Flag Coverage Δ
suite.unit 81.38% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

Components Coverage Δ
packages/aws-cdk 80.69% <ø> (ø)
packages/aws-cdk-lib/core 82.10% <ø> (ø)

@gracelu0 gracelu0 self-assigned this Dec 6, 2024
Copy link
Contributor

@gracelu0 gracelu0 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @badmintoncryer , thank you for working on this! I saw the previously open PR was approved (apologies that it got closed by our automation), I just have a few more comments.

Comment on lines 241 to 248
this.props.customModelKmsKey.addToResourcePolicy(new iam.PolicyStatement({
actions: ['kms:Decrypt', 'kms:GenerateDataKey', 'kms:DescribeKey', 'kms:CreateGrant'],
resources: ['*'],
principals: [new iam.ArnPrincipal(this._role.roleArn)],
}));
}
}

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To adhere to the best security practice stated here: https://docs.aws.amazon.com/bedrock/latest/userguide/encryption-custom-job.html#encryption-cm-statements, can we add a kms:ViaService condition to this policy to limit key access to the Amazon Bedrock service? There's an example under the Encrypt a model dropdown in that link

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated my code and executed integ test again!

S3Uri: this.props.outputData.bucket.s3UrlForObject(this.props.outputData.prefix),
},
RoleArn: this._role.roleArn,
TrainingDataConfig: {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When it was created, I remember handling all the parameters, so additional arguments might have been added later. Should I address this as well?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it's okay if we don't include it in this PR, but we should ensure the contract allows us to add this in the future (see my other comment about extending the interface)

@aws-cdk-automation aws-cdk-automation removed the pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. label Dec 7, 2024
@mergify mergify bot dismissed gracelu0’s stale review December 18, 2024 13:11

Pull request has been modified.

@aws-cdk-automation aws-cdk-automation added the pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. label Dec 21, 2024
@badmintoncryer
Copy link
Contributor Author

@gracelu0 Thank you for your kindness check. I've addressed all of your comments.

@aws-cdk-automation
Copy link
Collaborator

AWS CodeBuild CI Report

  • CodeBuild project: AutoBuildv2Project1C6BFA3F-wQm2hXv2jqQv
  • Commit ID: 068c110
  • Result: SUCCEEDED
  • Build Logs (available for 30 days)

Powered by github-codebuild-logs, available on the AWS Serverless Application Repository

Copy link
Contributor

@gracelu0 gracelu0 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for working on this! I left some comments to improve the interface design for extensibility, and we will need to check the policy updates with security reviewer (so there may be some additional comments to address).

bedrock.FoundationModelIdentifier.AMAZON_TITAN_TEXT_G1_EXPRESS_V1,
);

const task = new tasks.BedrockCreateModelCustomizationJob(this, 'CreateModelCustomizationJob2', {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

instead of all the // optional comments can we have a // required comment to point out the required properties?

*
* @see https://docs.aws.amazon.com/bedrock/latest/userguide/encryption-custom-job.html
*
* @default - no encryption
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

from the linked docs, By default, Amazon Bedrock encrypts custom models with AWS owned keys. - can we specify that as the default here?

*
* @default - no prefix
*/
readonly prefix?: string;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what is this prefix field for? since I see for the s3Uri property the pattern is ^s3://[a-z0-9][-.a-z0-9]{1,61}(?:/[-!_*'().a-z0-9A-Z]+(?:/[-!_*'().a-z0-9A-Z]+)*)?/?$ so the prefix is expected to be s3://.

*/
readonly role?: iam.IRole;

/**
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While I like the simplified BucketConfiguration interface here, I see that TrainingDataConfig already differs from ValidationDataConfig and OutputDataConfig with additional prop invocationLogsConfig.

To avoid making breaking changes in the future in case new sub-properties are added, can we make a base interface BucketConfiguration (maybe called DataBucketConfiguration) and create interfaces extending it for each of outputData, trainingData and validationData ?

*
* @see https://docs.aws.amazon.com/bedrock/latest/APIReference/API_Validator.html
*/
readonly validationData: BucketConfiguration[];
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like validationDataConfig is not required, so we need to update this and also the validation to allow minimum of 0 validators

S3Uri: this.props.outputData.bucket.s3UrlForObject(this.props.outputData.prefix),
},
RoleArn: this._role.roleArn,
TrainingDataConfig: {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it's okay if we don't include it in this PR, but we should ensure the contract allows us to add this in the future (see my other comment about extending the interface)

return this.props.role;
}
const role = new iam.Role(this, 'BedrockRole', {
assumedBy: new iam.ServicePrincipal('bedrock.amazonaws.com'),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From https://docs.aws.amazon.com/bedrock/latest/userguide/model-customization-iam-role.html#model-customization-iam-role-trust it mentions the option to restrict the scope using Condition:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "Service": "bedrock.amazonaws.com"
            },
            "Action": "sts:AssumeRole",
            "Condition": {
                "StringEquals": {
                    "aws:SourceAccount": "account-id"
                },
                "ArnEquals": {
                    "aws:SourceArn": "arn:aws:bedrock:us-east-1:account-id:model-customization-job/*"
                }
            }
        }
    ] 
}

Can we add this to adhere to PoLP and reduce the permissions scope?

@gracelu0 gracelu0 added the needs-security-review Related to feature or issues that needs security review label Jan 16, 2025
@aws-cdk-automation aws-cdk-automation removed the pr/needs-community-review This PR needs a review from a Trusted Community Member or Core Team Member. label Jan 16, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
distinguished-contributor [Pilot] contributed 50+ PRs to the CDK effort/medium Medium work item – several days of effort feature-request A feature should be added or improved. needs-security-review Related to feature or issues that needs security review p2
Projects
None yet
Development

Successfully merging this pull request may close these issues.

stepfunctions-tasks: support for bedrock createModelCustomizationJob task
4 participants