Skip to content

Commit

Permalink
Release v3.4.0 into Main
Browse files Browse the repository at this point in the history
  • Loading branch information
estohlmann authored Dec 19, 2024
2 parents c1943ca + bff8388 commit 090ebfe
Show file tree
Hide file tree
Showing 88 changed files with 10,423 additions and 2,030 deletions.
2 changes: 1 addition & 1 deletion .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ repos:
args:
- --max-line-length=120
- --extend-immutable-calls=Query,fastapi.Depends,fastapi.params.Depends
- --ignore=B008,E203 # Ignore error for function calls in argument defaults
- --ignore=B008,E203, W503 # Ignore error for function calls in argument defaults
exclude: ^(__init__.py$|.*\/__init__.py$)


Expand Down
30 changes: 30 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,33 @@
# v3.4.0
## Key Features
### Vector Store Support
- Implemented support for multiple vector stores of the same type. For example, you can now configure more than 1 OpenSearch vector store with LISA.
- Introduced granular access control for vector stores based on a list of provided IDP groups. If a list isn’t provided the vector store is available to all LISA users.
- Expanded APIs for vector store file management to now include file listing and removal capabilities.

### Deployment Flexibility
- Enabled custom IAM role overrides with documented minimum permissions available on our [documentation site](https://awslabs.github.io/LISA/config/role-overrides)
- Introduced partition and domain override functionality

## Other System Enhancements
- Enhanced create model validation to ensure data integrity
- Upgraded to Python 3.11 runtime for improved performance
- Updated various third-party dependencies to maintain security and functionality
- Updated the ChatUI:
- Refined ChatUI for improved message display
- Upgraded markdown parsing capabilities
- Implemented a copy feature for AI-generated responses

## Coming soon
Happy Holidays! We have a lot in store for 2025. Our roadmap is customer driven. Please reach out to us via Github issues to talk more! Early in the new year you’ll see chatbot UI and vector store enhancements.

## Acknowledgements
* @bedanley
* @estohlmann
* @dustins

**Full Changelog**: https://github.com/awslabs/LISA/compare/v3.3.2...v3.4.0

# v3.3.2
## Bug Fixes
- Resolved issue where invalid schema import was causing create model api calls to fail
Expand Down
43 changes: 32 additions & 11 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
createTypeScriptEnvironment installTypeScriptRequirements \
deploy destroy \
clean cleanTypeScript cleanPython cleanCfn cleanMisc \
help dockerCheck dockerLogin listStacks modelCheck buildEcsDeployer
help dockerCheck dockerLogin listStacks modelCheck buildNpmModules

#################################################################################
# GLOBALS #
Expand Down Expand Up @@ -56,11 +56,22 @@ ifeq (${REGION},)
$(error region must be set in command line using REGION variable or config files)
endif

# URL_SUFFIX - used for the docker login
ifeq ($(findstring iso,${REGION}),)
URL_SUFFIX := amazonaws.com
ifeq (${PARTITION},)
PARTITION := $(shell cat $(PROJECT_DIR)/config-custom.yaml | yq .partition )
endif
ifeq (${PARTITION}, null)
PARTITION := aws
endif

# DOMAIN - used for the docker login
ifeq (${DOMAIN},)
ifeq ($(findstring isob,${REGION}),isob)
DOMAIN := sc2s.sgov.gov
else ifeq ($(findstring iso,${REGION}),iso)
DOMAIN := c2s.ic.gov
else
URL_SUFFIX := c2s.ic.gov
DOMAIN := amazonaws.com
endif
endif

# Arguments defined through config files
Expand Down Expand Up @@ -117,16 +128,18 @@ MODEL_BUCKET := $(shell cat $(PROJECT_DIR)/config-custom.yaml | yq '.s3BucketMod

## Bootstrap AWS Account with CDK bootstrap
bootstrap:
@printf "Bootstrapping: $(ACCOUNT_NUMBER) | $(REGION)\n"
@printf "Bootstrapping: $(ACCOUNT_NUMBER) | $(REGION) | $(PARTITION)\n"

ifdef PROFILE
@cdk bootstrap \
--profile $(PROFILE) \
aws://$(ACCOUNT_NUMBER)/$(REGION) \
--partition $(PARTITION) \
--cloudformation-execution-policies arn:aws:iam::aws:policy/AdministratorAccess
else
@cdk bootstrap \
aws://$(ACCOUNT_NUMBER)/$(REGION) \
--partition $(PARTITION) \
--cloudformation-execution-policies arn:aws:iam::aws:policy/AdministratorAccess
endif

Expand Down Expand Up @@ -217,6 +230,7 @@ cleanTypeScript:
@find . -type d -name "build" -exec rm -rf {} +
@find . -type d -name ".tscache" -exec rm -rf {} +
@find . -type d -name ".jest_cache" -exec rm -rf {} +
@find . -type d -name "node_modules" -exec rm -rf {} +


## Delete CloudFormation outputs
Expand All @@ -233,27 +247,29 @@ cleanMisc:
dockerLogin: dockerCheck
ifdef PROFILE
@$(foreach ACCOUNT,$(ACCOUNT_NUMBERS_ECR), \
aws ecr get-login-password --region ${REGION} --profile ${PROFILE} | $(DOCKER_CMD) login --username AWS --password-stdin ${ACCOUNT}.dkr.ecr.${REGION}.${URL_SUFFIX} >/dev/null 2>&1; \
aws ecr get-login-password --region ${REGION} --profile ${PROFILE} | $(DOCKER_CMD) login --username AWS --password-stdin ${ACCOUNT}.dkr.ecr.${REGION}.${DOMAIN} >/dev/null 2>&1; \
)
else
@$(foreach ACCOUNT,$(ACCOUNT_NUMBERS_ECR), \
aws ecr get-login-password --region ${REGION} | $(DOCKER_CMD) login --username AWS --password-stdin ${ACCOUNT}.dkr.ecr.${REGION}.${URL_SUFFIX} >/dev/null 2>&1; \
aws ecr get-login-password --region ${REGION} | $(DOCKER_CMD) login --username AWS --password-stdin ${ACCOUNT}.dkr.ecr.${REGION}.${DOMAIN} >/dev/null 2>&1; \
)
endif


listStacks:
@npx cdk list

buildEcsDeployer:
@cd ./ecs_model_deployer && npm install && npm run build
buildNpmModules:
npm run build

define print_config
@printf "\n \
DEPLOYING $(STACK) STACK APP INFRASTRUCTURE \n \
-----------------------------------\n \
Account Number $(ACCOUNT_NUMBER)\n \
Region $(REGION)\n \
Partition $(PARTITION)\n \
Domain $(DOMAIN)\n \
App Name $(APP_NAME)\n \
Deployment Stage $(DEPLOYMENT_STAGE)\n \
Deployment Name $(DEPLOYMENT_NAME)"
Expand All @@ -264,7 +280,7 @@ define print_config
endef

## Deploy all infrastructure
deploy: dockerCheck dockerLogin cleanMisc modelCheck buildEcsDeployer
deploy: dockerCheck dockerLogin cleanMisc modelCheck buildNpmModules
$(call print_config)
ifneq (,$(findstring true, $(HEADLESS)))
npx cdk deploy ${STACK} $(if $(PROFILE),--profile ${PROFILE}) --require-approval never -c ${ENV}='$(shell echo '${${ENV}}')';
Expand All @@ -280,11 +296,16 @@ endif
## Tear down all infrastructure
destroy: cleanMisc
$(call print_config)
ifneq (,$(findstring true, $(HEADLESS)))
npx cdk destroy ${STACK} --force $(if $(PROFILE),--profile ${PROFILE});
else
@printf "Is the configuration correct? [y/N] "\
&& read confirm_config &&\
if [ $${confirm_config:-'N'} = 'y' ]; then \
npx cdk destroy ${STACK} --force $(if $(PROFILE),--profile ${PROFILE}); \
fi;
endif



#################################################################################
Expand Down
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
3.3.2
3.4.0
2 changes: 2 additions & 0 deletions bin/lisa.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,8 @@ const mappings: EnvMapping[] = [
['PROFILE', 'profile'],
['DEPLOYMENT_NAME', 'deploymentName'],
['ACCOUNT_NUMBER', 'accountNumber'],
['PARTITION', 'partition'],
['DOMAIN', 'domain'],
['REGION', 'region'],
];
mappings.forEach(([envVar, configVar]) => {
Expand Down
56 changes: 56 additions & 0 deletions ecs_model_deployer/src/lib/ecs-schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -233,6 +233,62 @@ export class Ec2Metadata {
maxThroughput: 100,
vCpus: 192,
},
'g6.xlarge': {
memory: 16 * 1000,
gpuCount: 1,
nvmePath: '/dev/nvme1n1',
maxThroughput: 10,
vCpus: 4,
},
'g6.2xlarge': {
memory: 32 * 1000,
gpuCount: 1,
nvmePath: '/dev/nvme1n1',
maxThroughput: 10,
vCpus: 8,
},
'g6.4xlarge': {
memory: 64 * 1000,
gpuCount: 1,
nvmePath: '/dev/nvme1n1',
maxThroughput: 25,
vCpus: 16,
},
'g6.8xlarge': {
memory: 128 * 1000,
gpuCount: 1,
nvmePath: '/dev/nvme1n1',
maxThroughput: 25,
vCpus: 32,
},
'g6.16xlarge': {
memory: 256 * 1000,
gpuCount: 1,
nvmePath: '/dev/nvme1n1',
maxThroughput: 25,
vCpus: 64,
},
'g6.12xlarge': {
memory: 192 * 1000,
gpuCount: 4,
nvmePath: '/dev/nvme1n1',
maxThroughput: 40,
vCpus: 48,
},
'g6.24xlarge': {
memory: 384 * 1000,
gpuCount: 4,
nvmePath: '/dev/nvme1n1',
maxThroughput: 50,
vCpus: 96,
},
'g6.48xlarge': {
memory: 768 * 1000,
gpuCount: 8,
nvmePath: '/dev/nvme1n1',
maxThroughput: 100,
vCpus: 192,
},
'p4d.24xlarge': {
memory: 1152 * 1000,
gpuCount: 8,
Expand Down
67 changes: 41 additions & 26 deletions ecs_model_deployer/src/lib/ecsCluster.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
*/

// ECS Cluster Construct.
import { CfnOutput, Duration, RemovalPolicy } from 'aws-cdk-lib';
Expand All @@ -38,25 +38,29 @@ import {
Volume,
} from 'aws-cdk-lib/aws-ecs';
import { ApplicationLoadBalancer, BaseApplicationListenerProps } from 'aws-cdk-lib/aws-elasticloadbalancingv2';
import { IRole, ManagedPolicy, ServicePrincipal, Role } from 'aws-cdk-lib/aws-iam';
import { IRole, ManagedPolicy, Role, ServicePrincipal } from 'aws-cdk-lib/aws-iam';
import { StringParameter } from 'aws-cdk-lib/aws-ssm';
import { Construct } from 'constructs';

import { createCdkId } from './utils';
import { BaseProps, ECSConfig, Ec2Metadata, EcsSourceType } from './ecs-schema';
import { BaseProps, Ec2Metadata, ECSConfig, EcsSourceType } from './ecs-schema';

/**
* Properties for the ECSCluster Construct.
*
* @property {IVpc} vpc - The virtual private cloud (VPC).
* @property {SecurityGroups} securityGroups - The security group that the ECS cluster should use.
* @property {ISecurityGroup} securityGroup - The security group that the ECS cluster should use.
* @property {ECSConfig} ecsConfig - The configuration for the cluster.
* @property {string} taskRoleName? - The role applied to the task
* @property {string} executionRoleName? - The role used for executing the task
*/
type ECSClusterProps = {
ecsConfig: ECSConfig;
securityGroup: ISecurityGroup;
vpc: IVpc;
subnetSelection?: SubnetSelection;
taskRoleName?: string;
executionRoleName?: string;
} & BaseProps;

/**
Expand All @@ -79,7 +83,7 @@ export class ECSCluster extends Construct {
*/
constructor (scope: Construct, id: string, props: ECSClusterProps) {
super(scope, id);
const { config, vpc, securityGroup, ecsConfig, subnetSelection } = props;
const { config, vpc, securityGroup, ecsConfig, subnetSelection, taskRoleName, executionRoleName } = props;

// Create ECS cluster
const cluster = new Cluster(this, createCdkId([ecsConfig.identifier, 'Cl']), {
Expand Down Expand Up @@ -182,30 +186,17 @@ export class ECSCluster extends Construct {
environment.SSL_CERT_FILE = config.certificateAuthorityBundle;
}

const taskPolicyId = createCdkId([config.deploymentName, 'ECSPolicy']);
const taskPolicyStringParam = StringParameter.fromStringParameterName(this, 'taskPolicyStringParam',
`${config.deploymentPrefix}/policies/${taskPolicyId}`
);
const taskPolicy = ManagedPolicy.fromManagedPolicyArn(this, taskPolicyId, taskPolicyStringParam.stringValue);
const role_id = ecsConfig.identifier;
const roleName = createCdkId([config.deploymentName, role_id, 'Role']);
const taskRole = new Role(this, createCdkId([role_id, 'Role']), {
assumedBy: new ServicePrincipal('ecs-tasks.amazonaws.com'),
roleName,
description: `Allow ${role_id} ${role_id} ECS task access to AWS resources`,
managedPolicies: [taskPolicy],
});
new StringParameter(this, createCdkId([config.deploymentName, role_id, 'SP']), {
parameterName: `${config.deploymentPrefix}/roles/${role_id}`,
stringValue: taskRole.roleArn,
description: `Role ARN for LISA ${role_id} ${role_id} ECS Task`,
});
const roleId = ecsConfig.identifier;
const taskRole = taskRoleName ?
Role.fromRoleName(this, createCdkId([config.deploymentName, roleId]), taskRoleName) :
this.createTaskRole(config.deploymentName, config.deploymentPrefix, roleId);

// Create ECS task definition
const taskDefinition = new Ec2TaskDefinition(this, createCdkId([ecsConfig.identifier, 'Ec2TaskDefinition']), {
family: createCdkId([config.deploymentName, ecsConfig.identifier], 32, 2),
taskRole: taskRole,
const taskDefinition = new Ec2TaskDefinition(this, createCdkId([roleId, 'Ec2TaskDefinition']), {
family: createCdkId([config.deploymentName, roleId], 32, 2),
volumes: volumes,
taskRole,
...(executionRoleName && { executionRole: Role.fromRoleName(this, createCdkId([config.deploymentName, roleId, 'EX']), executionRoleName) }),
});

// Add container to task definition
Expand Down Expand Up @@ -351,4 +342,28 @@ export class ECSCluster extends Construct {
this.container = container;
this.taskRole = taskRole;
}

createTaskRole (deploymentName: string, deploymentPrefix: string | undefined, roleId: string): IRole {
const taskPolicyId = createCdkId([deploymentName, 'ECSPolicy']);
const taskPolicyStringParam = StringParameter.fromStringParameterName(this, 'taskPolicyStringParam',
`${deploymentPrefix}/policies/${taskPolicyId}`,
);

const taskPolicy = ManagedPolicy.fromManagedPolicyArn(this, taskPolicyId, taskPolicyStringParam.stringValue);
const roleName = createCdkId([roleId, 'Role']);
const role = new Role(this, roleName, {
assumedBy: new ServicePrincipal('ecs-tasks.amazonaws.com'),
roleName,
description: `Allow ${roleId} ECS task access to AWS resources`,
managedPolicies: [taskPolicy],
});

new StringParameter(this, createCdkId([deploymentName, roleId, 'SP']), {
parameterName: `${deploymentPrefix}/roles/${roleId}`,
stringValue: role.roleArn,
description: `Role ARN for LISA ${roleId} ECS Task`,
});

return role;
}
}
Loading

0 comments on commit 090ebfe

Please sign in to comment.