Commit e54d8a4
Feature/private appsync api (#259)
* feat: add AppSyncVisibility + LambdaSubnetIds parameters (private AppSync req #2, step 1/N)
Add two new CloudFormation parameters to enable private AppSync:
- AppSyncVisibility (GLOBAL default / PRIVATE) — controls API visibility
- LambdaSubnetIds (CommaDelimitedList) — private subnets for Lambda VPC config
Add UsePrivateAppSync condition.
Remaining changes (next commits):
- Visibility property on GraphQLApi
- Lambda Security Group
- AppSync + service VPC Interface Endpoints
- Lambda VpcConfig on all ~20 functions
- nested/appsync and patterns/unified updates
* feat: add LambdaVpcSecurityGroup + GraphQLApi Visibility (private AppSync req #2, step 2/N)
- Add LambdaVpcSecurityGroup (conditional on UsePrivateAppSync): EC2 security
group for Lambda functions in VPC, allows HTTPS egress to VPC endpoints only
- Add Visibility: !If [UsePrivateAppSync, PRIVATE, GLOBAL] to GraphQLApi
resource so the API becomes VPC-only when AppSyncVisibility=PRIVATE
* docs: add private AppSync implementation plan for next session
* feat: add VPC endpoints + LambdaRouteTableIds param + UsePrivateAppSyncWithRouteTables condition (private AppSync req #2, steps 3-4/N)
* feat: add VpcConfig to all 7 Lambda functions (private AppSync req #2, step 5/N)
* docs: update implementation plan — steps 1-5 complete, steps 6-8 remaining
* refactor: separate VPC endpoints into networking-team-owned scripts/vpc-endpoints.yaml
- Remove 14 VPC endpoint resources from template.yaml (app stack)
- Remove LambdaRouteTableIds param + UsePrivateAppSyncWithRouteTables condition
- Add LambdaVpcSecurityGroupId Output to template.yaml (used as input to vpc-endpoints.yaml)
- Create scripts/vpc-endpoints.yaml: standalone CFN template for networking team
- Takes VpcId, SubnetIds, LambdaSecurityGroupId (from IDP Output), optional RouteTableIds
- Creates VpcEndpointSecurityGroup + 12 Interface endpoints + 2 Gateway endpoints
- Fully tagged with IDPStack + Environment for traceability
Enterprise separation of concerns:
- App team deploys: template.yaml (AppSyncVisibility=PRIVATE, LambdaSubnetIds)
- Networking team deploys: scripts/vpc-endpoints.yaml (with LambdaVpcSecurityGroupId from Output)
* docs: update implementation plan with VPC endpoint refactor details
* fix: add UpdateReplacePolicy: Retain to GraphQLApi — Visibility is immutable on update
* revert: undo GraphQLApi rename + UpdateReplacePolicy — Visibility set once at deploy time, not changed
* feat: step 6 — add VPC config to nested/appsync resolver Lambdas (req #2)
nested/appsync/template.yaml:
- Add 3 new parameters: UsePrivateAppSync, LambdaSubnetIds, LambdaSecurityGroupId
- Add IsPrivateAppSync condition
- Add VpcConfig (!If [IsPrivateAppSync, ...]) to 4 resolver functions
that call AppSync (AbortWorkflow, CopyToBaseline, ProcessChanges,
ReprocessDocument) so they can reach the private AppSync endpoint
template.yaml:
- Pass the 3 new params to APPSYNCSTACK:
UsePrivateAppSync: !If [UsePrivateAppSync, 'true', 'false']
LambdaSubnetIds: !Join [",", !Ref LambdaSubnetIds] (when PRIVATE, else "")
LambdaSecurityGroupId: !Ref LambdaVpcSecurityGroup (when PRIVATE, else "")
* feat: add optional enterprise artifact bucket hardening (req #4 and #5)
- Add --kms-key-arn ARN flag: applies SSE-KMS with customer-managed CMK
to the artifact bucket via put_bucket_encryption (BucketKeyEnabled=True
to reduce KMS API costs). No-op when flag is not provided.
- Add --enterprise-bucket-policy flag: applies a bucket policy with two
Deny statements (DenyInsecureTransport + DenyExternalAccess) that enforce
SSL-only access and restrict requests to the same AWS account. No-op when
flag is not provided, preserving public deployment behaviour.
- Move account_id resolution before setup_artifacts_bucket() in run() so
the enterprise bucket policy has the account ID available.
- Update print_usage() in publish.py and publish.sh to document both flags.
Both flags are off by default so existing deployments (including the
standard aws-ml-blog-* public buckets) are unaffected.
* docs: add ALB private network deployment guide and test VPC template
- docs/deployment-private-network.md: Step-by-step guide for deploying
with ALB instead of CloudFront using the Publish+Deploy approach.
Includes prerequisites, publish.py tips (Python/Node gotchas), ALB
parameter reference, SSM port forwarding instructions, and
troubleshooting table.
- scripts/alb-test-vpc.yaml: CloudFormation template to create a test
VPC with 2 private subnets in different AZs plus a self-signed ACM
certificate (via Lambda custom resource). Used to simulate a customer
private network environment for ALB hosting tests. Outputs VpcId,
SubnetIds, CertificateArn, and a ready-to-use IDPDeployCommand.
* docs: add scope note to deployment-private-network.md
Clarify that this is the growing enterprise runbook (not just ALB hosting)
and will expand as additional private network requirements (AppSync,
SSO, etc.) are implemented. Reference alb-hosting.md for the
ALB-only technical reference.
* feat: add --tags flag for artifact bucket tagging (req #10)
Add optional --tags Key1=Value1,Key2=Value2 flag to publish.py and
publish.sh. Enterprise standards typically require tags on all S3
buckets for cost allocation, compliance, and inventory tracking.
- New _apply_bucket_tags() method calls put_bucket_tagging with the
parsed key/value pairs
- Flag is optional (no-op when not set) — no behaviour change for
existing deployments
- Composes with --kms-key-arn and --enterprise-bucket-policy for
fully-hardened enterprise bucket
* fix: update DenyExternalAccess to allow AWS service principals (CloudFormation, CodeBuild, Lambda)
The original condition only checked aws:PrincipalAccount which doesn't apply
to AWS service principals (they use aws:PrincipalIsAWSService instead).
This caused CloudFormation to be denied when reading templates from S3 via
--template-url, breaking all stack deployments.
Fix: add Bool condition on aws:PrincipalIsAWSService: false so the Deny
only applies to external human/machine principals, not AWS service calls.
* fix: ruff format publish.py
* docs: add CRITICAL warning to _apply_kms_encryption — never use a CFN stack key
When the IDP stack is deleted, CloudFormation deletes CustomerManagedEncryptionKey
and schedules it for deletion. If that key was used with --kms-key-arn for the
artifact bucket, ALL S3 objects (templates, Lambda zips, layers) become inaccessible,
blocking ALL future stack deployments.
Use a dedicated, standalone KMS key managed outside any deployable stack.
Recovery: aws kms cancel-key-deletion && aws kms enable-key
* fix: remove IDPDeployCommand from alb-test-vpc.yaml; update pr-description
- scripts/alb-test-vpc.yaml: remove IDPDeployCommand output — it had a
hardcoded personal email and doesn't belong in a VPC-only template;
the template's job is to create the VPC/subnets/cert, not prescribe
how to use them
- pr-description.md: add --tags (req #10) to table, usage examples, and
Related section; fix alb-test-vpc.yaml output list to match actual outputs;
update summary count from 'two' to 'three' flags; fix title to include #10
* feat: add Lambda subnet to alb-test-vpc.yaml; remove pr-description from git
- scripts/alb-test-vpc.yaml: add LambdaSubnet (10.1.3.0/24) in AZ[0],
separate from ALB subnets (PrivateSubnet1/2) — used to test IDP Lambdas
in a different subnet for private AppSync VPC config testing.
Output LambdaSubnetId exported as ${StackName}-LambdaSubnetId.
Updated Description to document 3-subnet layout.
- .gitignore: add pr-description.md (not tracked — used as clipboard for
GitHub PR form)
* chore: remove pr-description.md from .gitignore
pr-description.md is a local scratchpad for copy-pasting into the GitHub
PR form — it should not exist in the repo at all, not even in .gitignore.
* feat: add standalone KMS CMK to alb-test-vpc.yaml (req #4)
Add ArtifactBucketKey (AWS::KMS::Key) managed by THIS stack, not the IDP
stack. This ensures deleting the IDP stack never schedules the key for
deletion and makes S3 objects inaccessible.
Key properties:
- DeletionPolicy: Retain — key survives stack deletion
- EnableKeyRotation: true — automatic annual rotation
- Key policy: account root full control + S3 service GenerateDataKey/Decrypt
- Alias: alias/${StackName}-artifact-bucket-key
New outputs:
- ArtifactBucketKeyArn — pass as --kms-key-arn to publish.py/publish.sh
- ArtifactBucketKeyAlias — human-readable alias reference
* feat: step 7 — add VpcConfig to all processing Lambdas in patterns/unified (req #2)
Added IsPrivateAppSync condition and VpcConfig to 10 processing Lambda functions:
- BDAProcessResultsFunction
- OCRFunction
- ClassificationFunction
- ExtractionFunction
- AssessmentFunction
- ProcessResultsFunction (no Tracing)
- SummarizationFunction (no Tracing)
- EvaluationFunction
- RuleValidationFunction (no Tracing)
- RuleValidationOrchestrationFunction (no Tracing)
Pattern: VpcConfig: !If [IsPrivateAppSync, {SubnetIds: !Ref LambdaSubnetIds, SecurityGroupIds: [!Ref LambdaSecurityGroupId]}, !Ref AWS::NoValue]
Note: LambdaSubnetIds is CommaDelimitedList in this template (passed as string from main, parsed back).
InvokeBDAFunction and BDACompletionFunction skipped — they do not call AppSync.
* docs: step 8 — add private AppSync section to deployment-private-network.md; mark all steps complete (req #2)
- Added 'Private AppSync API (AppSyncVisibility=PRIVATE)' section to deployment-private-network.md:
- Architecture diagram (Lambda Subnets → VPC endpoints → AWS services)
- New parameters: AppSyncVisibility, LambdaSubnetIds
- Two-step deployment runbook (app team + networking team)
- VPC endpoint details (12 Interface + 2 Gateway)
- Test VPC reference values and ready-to-use deploy commands
- Updated private-appsync-implementation-plan.md: marked Steps 7 and 8 complete with commit refs
* chore: update memory bank — private AppSync impl all steps complete
* fix: pass UsePrivateAppSync/LambdaSubnetIds/LambdaSecurityGroupId to PATTERNSTACK (req #2)
PATTERNSTACK (patterns/unified) was missing the 3 private AppSync parameters,
causing all processing Lambdas to have UsePrivateAppSync=false even when the
main stack had AppSyncVisibility=PRIVATE.
Added to PATTERNSTACK Parameters block (same pattern as APPSYNCSTACK):
UsePrivateAppSync: !If [UsePrivateAppSync, "true", "false"]
LambdaSubnetIds: !If [UsePrivateAppSync, !Join [",", !Ref LambdaSubnetIds], ""]
LambdaSecurityGroupId: !If [UsePrivateAppSync, !Ref LambdaVpcSecurityGroup, ""]
* fix: add CreateSsmEndpoint param to vpc-endpoints.yaml to handle pre-existing SSM endpoint
When the VPC already has an SSM Interface endpoint (e.g. pre-created for EC2
SSM access), deploying a second SSM endpoint with PrivateDnsEnabled=true fails
with 'conflicting DNS domain' error.
Added CreateSsmEndpoint parameter (default 'true'): set to 'false' to skip
SSM endpoint creation when one already exists in the VPC.
* docs: add 'Disabling Internet-Facing Features' section to deployment-private-network.md
When deploying in a fully private/air-gapped environment, document that
EnableMCP=false and DocumentKnowledgeBase=DISABLED should be set to avoid
features that require public AWS endpoints:
- EnableMCP=false: disables Bedrock AgentCore Gateway (requires public endpoint)
- DocumentKnowledgeBase=DISABLED: disables KB creation (S3 Vectors/OpenSearch)
- Code Intelligence: already disabled by default
* docs: replace verbose Build Tools list with reference to deployment.md#dependencies
* feat: add check-vpc-endpoints.sh + per-endpoint CFN flags; rewrite deployment runbook
scripts/vpc-endpoints.yaml:
- Add Create<Service>Endpoint param (default 'true') for all 12 Interface endpoints
- Each endpoint gated on ShouldCreate<Service>Endpoint condition
- Allows skipping pre-existing endpoints to avoid PrivateDNS conflicts
scripts/check-vpc-endpoints.sh (new):
- Detects which IDP-required endpoints already exist in the VPC
- Reads LambdaSecurityGroupId and LambdaSubnetIds from the IDP stack automatically
- Prints a ready-to-run aws cloudformation deploy command with Create*=false
for any endpoints that already exist
- Usage: ./scripts/check-vpc-endpoints.sh --vpc-id <id> --stack-name IDP-PRIVATE
docs/deployment-private-network.md:
- Rewritten as a focused 4-step private-network-only runbook
- Removed: Switching sections, Security Notes, separate AppSync/MCP sections
- Unified: all private params in one deploy command in Step 2
- Step 3 uses check-vpc-endpoints.sh workflow
- Step 4 covers SSM port forwarding for testing
* feat: add deploy-vpc-endpoints.py — cross-platform endpoint deployer (Windows/macOS/Linux)
scripts/deploy-vpc-endpoints.py (new, cross-platform):
- Uses boto3 (already a project dependency)
- Auto-reads LambdaSubnetIds + LambdaVpcSecurityGroupId from IDP stack
- Checks all 12 required Interface endpoints against the VPC
- Deploys only the MISSING ones (passes Create*=false for existing ones)
- Waits for CREATE_COMPLETE and shows a clear success/failure summary
- Handles ROLLBACK_COMPLETE stacks by deleting and re-creating
- Supports --dry-run to preview without deploying
- Works on Windows PowerShell, macOS, and Linux
docs/deployment-private-network.md:
- Step 3 now uses deploy-vpc-endpoints.py (one command, works everywhere)
- Added Windows PowerShell syntax example
- Updated example output to match Python script format
* docs: add EC2 SSM bastion creation steps to Step 4 of deployment-private-network.md
Step 4 'Accessing via SSM port forwarding' previously said 'Ensure there is
an EC2 instance' without explaining how to create one. Added concrete commands to:
1. Create IAM role + instance profile with AmazonSSMManagedInstanceCore policy
2. Launch t3.nano in the private subnet with no public IP
3. Verify SSM agent registration (PingStatus: Online)
* fix: add ssmmessages + ec2messages endpoints to vpc-endpoints.yaml and deploy script
ssmmessages and ec2messages are required for SSM Session Manager port forwarding
(not just for the SSM heartbeat). Without them, 'StartSession' calls fail with
TargetNotConnected even when the instance shows PingStatus=Online.
vpc-endpoints.yaml:
- Added CreateSsmMessagesEndpoint param + ShouldCreateSsmMessagesEndpoint condition
- Added CreateEc2MessagesEndpoint param + ShouldCreateEc2MessagesEndpoint condition
- Added SsmMessagesVpcEndpoint and Ec2MessagesVpcEndpoint resources
deploy-vpc-endpoints.py:
- Added ssmmessages and ec2messages to REQUIRED_ENDPOINTS dict (12 → 14 endpoints)
* docs: clarify VPC endpoint requirements and add enterprise bucket hardening
- deployment-private-network.md:
- Step 1: add enterprise artifact bucket hardening section
(--kms-key-arn, --enterprise-bucket-policy, --tags flags)
- Step 3: clarify 12 IDP-app-required + 2 SSM-testing endpoints
- Step 4: fix sudo -> sudo -E to preserve env var credentials
when binding AppSync tunnel on port 443
- scripts/check-vpc-endpoints.sh:
- Add ssmmessages and ec2messages endpoints (12 -> 14 total)
- Add comment block distinguishing IDP-app-required vs
SSM-testing-bastion-only endpoints
- scripts/vpc-endpoints.yaml:
- Add structured comment block in Parameters section clarifying:
* 12 endpoints required by IDP application
* 2 endpoints required only for SSM Session Manager testing bastion
(ssmmessages, ec2messages) — not needed in production with VPN
* docs: update private network deployment — 2-step self-signed cert, 3-subnet TestVPC
- scripts/alb-test-vpc.yaml: remove ACM certificate custom resource (Lambda/IAM/SelfSignedCertificate). The cert is now created separately via generate_self_signed_cert.sh after deploy when the ELB hostname is known. Add LambdaSubnet (10.1.3.0/24) for dedicated Lambda VpcConfig subnet.
- scripts/generate_self_signed_cert.sh: add --cert-arn flag to reimport an existing ACM cert in-place (no stack update needed). Add 2-step usage documentation explaining why cert domain must match ALB hostname.
- docs/deployment-private-network.md: document the 2-step cert process; update TestVPC section (no CertificateArn output); add troubleshooting entries for cert domain mismatch and Cognito IDP internet requirement.
- memory-bank: update activeContext with private AppSync browser testing learnings; update projectbrief with correct alb-test-vpc description.
* docs: add Amazon WorkSpaces testing section to private network runbook
- Add 'Accessing via Amazon WorkSpaces (testing)' under Step 4
- Covers requirements (Directory Service, NAT GW in dedicated public subnet,
internet access enabled on directory)
- Key setup notes: NAT GW placement, enable internet before launch, 2-step cert
- Verification checklist: login, live doc status updates, WS tab in DevTools
- Documents AppSync WebSocket behavior: appsync-api endpoint handles both
HTTPS and WSS — no separate appsync-realtime-api endpoint needed
- Table of features degraded when WebSocket subscriptions fail
- Cost/cleanup note
* feat(cli): add --artifacts-bucket-kms-key-arn and --artifacts-bucket-tags to idp-cli publish
* docs: update deployment-private-network.md to use idp-cli publish with enterprise flags
* feat(template): add ArtifactsBucketKmsKeyArn parameter to grant CodeBuild kms:Decrypt on encrypted artifact bucket
- Add ArtifactsBucketKmsKeyArn optional parameter (empty by default)
- Add HasArtifactsBucketKmsKey condition
- Conditionally grant kms:Decrypt/GenerateDataKey/DescribeKey to UICodeBuildServiceRole
- Enables idp-cli publish --artifacts-bucket-kms-key-arn with end-to-end deployment support
* fix: add kms:Decrypt for artifact bucket CMK to CodeBuild and Lambda roles
When an artifact bucket is encrypted with a customer-managed KMS key
(via idp-cli publish --artifacts-bucket-kms-key-arn), several roles
lacked kms:Decrypt on that key, causing AccessDenied failures during
deployment.
Changes:
- patterns/unified/template.yaml: Add ArtifactsBucketKmsKeyArn parameter
and conditional kms:Decrypt grant to DockerBuildRole (HasArtifactsBucketKmsKey
condition). DockerBuildRole now receives kms:Decrypt/GenerateDataKey*/DescribeKey
on the artifact bucket CMK when the parameter is provided.
- template.yaml:
- Pass ArtifactsBucketKmsKeyArn to PATTERNSTACK so DockerBuildRole
receives the grant
- Add conditional kms:Decrypt grant to ConfigurationCopyFunction role
so it can read config files from a KMS-encrypted artifact bucket
(previously silently skipped all 39 files, causing UpdateDefaultConfig
NoSuchKey failure)
- docs/deployment-private-network.md:
- Replace aws cloudformation create-stack with idp-cli deploy
- Add enterprise KMS deploy note: ArtifactsBucketKmsKeyArn must be
passed at deploy time when using --artifacts-bucket-kms-key-arn
- Remove Docker from build tool prerequisites (not needed locally)
- Update troubleshooting: add KMS/AccessDenied rows, clean up stale entries
Tested end-to-end:
- IDP-ALB (private network, ALB, KMS): CREATE_COMPLETE, both CodeBuild SUCCEEDED
- IDP-CF (CloudFront default, no KMS): CREATE_COMPLETE, both CodeBuild SUCCEEDED
* fix(alb-test-vpc): add cfn_nag W79 and checkov suppressions with justifications
- ArtifactBucketKey: add cfn_nag W79 suppress for kms:* wildcard on root
principal — standard CMK admin access pattern; key is managed outside
the IDP stack by design to prevent key deletion on IDP stack delete
- ArtifactBucketKey: add checkov skip CKV_AWS_7 — key rotation is already
enabled via EnableKeyRotation: true
- VPC: add checkov skip CKV_AWS_178 — flow logs not required for this
test-only template (production VPCs should enable flow logs)
* chore: remove internal implementation plan (work complete)
* fix: address PR review feedback — VPC endpoints, CFn Interface metadata, docs
VPC Endpoints (missing services)
- scripts/vpc-endpoints.yaml: add textract + sts Interface endpoints with
CreateTextractEndpoint / CreateStsEndpoint flags (default true). OCR
pattern calls Textract API; BDA pattern calls STS AssumeRole — both time
out in private mode without these endpoints.
- scripts/deploy-vpc-endpoints.py: add textract + sts to REQUIRED_ENDPOINTS
dict (14 required total, was 12)
- scripts/check-vpc-endpoints.sh: add textract + sts to ENDPOINTS map,
update comment to '14 required'
CloudFormation::Interface metadata
- template.yaml: add 'Private Network' parameter group (AppSyncVisibility,
LambdaSubnetIds) and 'Advanced — Artifact Bucket' group (ArtifactsBucketKmsKeyArn)
so new params appear grouped in CloudFormation console instead of 'Other'
- template.yaml: add ParameterLabels for AppSyncVisibility, LambdaSubnetIds,
ArtifactsBucketKmsKeyArn
ALBVpcId dependency documentation
- template.yaml: update ALBVpcId description to explain it's also required
when AppSyncVisibility=PRIVATE (Lambda SG uses the same VPC)
- template.yaml: add inline comment on LambdaVpcSecurityGroup explaining
why ALBVpcId is used (PRIVATE AppSync always requires ALB hosting)
ArtifactsBucketKmsKeyArn description
- template.yaml: reword description — clarifies the pre-created bucket
pattern (customer creates compliant bucket, passes KMS key ARN at deploy)
Documentation
- docs/deployment-private-network.md: rewrite enterprise bucket hardening
section — replace publish CLI flags with pre-created bucket pattern
- docs/deployment-private-network.md: update Step 3 to say '14 required
endpoints' and update example summary line
- docs/deployment-private-network.md: add troubleshooting rows for Textract
and STS timeouts (missing VPC endpoints)
* chore: revert memory-bank/projectbrief.md to main branch version
Removes session-specific implementation notes added during development.
After this commit the file is identical to main and will not appear in the PR diff.
* revert: remove cli-publish-artifact-bucket-hardening code from this PR
The --artifacts-bucket-kms-key-arn and --artifacts-bucket-tags CLI flags
are not needed — customers should pre-create compliant artifact buckets
rather than having the CLI manage bucket encryption and tagging.
Reverts commit 07e5e96 (feat(cli): add --artifacts-bucket-kms-key-arn
and --artifacts-bucket-tags to idp-cli publish) which was merged from
feature/cli-publish-artifact-bucket-hardening.
Files reverted to main:
- lib/idp_cli_pkg/idp_cli/cli.py (removed 2 CLI options)
- lib/idp_sdk/idp_sdk/operations/publish.py (removed put_bucket_encryption/tagging calls)
- docs/idp-cli.md (removed flag documentation)
- docs/idp-sdk.md (removed SDK documentation)
- lib/idp_sdk/tests/unit/test_publish_operations.py (deleted — new file in hardening branch)
---------
Co-authored-by: “Sirirat <“siriratk@amazon.com”>
Co-authored-by: Bob Strahan <strahanr@amazon.com>1 parent d8fc24f commit e54d8a4
9 files changed
Lines changed: 2089 additions & 29 deletions
File tree
- docs
- nested/appsync
- patterns/unified
- scripts
Large diffs are not rendered by default.
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
200 | 200 | | |
201 | 201 | | |
202 | 202 | | |
203 | | - | |
| 203 | + | |
204 | 204 | | |
205 | 205 | | |
206 | 206 | | |
207 | 207 | | |
| 208 | + | |
| 209 | + | |
| 210 | + | |
| 211 | + | |
| 212 | + | |
| 213 | + | |
| 214 | + | |
| 215 | + | |
| 216 | + | |
| 217 | + | |
| 218 | + | |
| 219 | + | |
| 220 | + | |
| 221 | + | |
| 222 | + | |
| 223 | + | |
| 224 | + | |
208 | 225 | | |
209 | 226 | | |
210 | 227 | | |
| |||
218 | 235 | | |
219 | 236 | | |
220 | 237 | | |
| 238 | + | |
221 | 239 | | |
222 | 240 | | |
223 | 241 | | |
| |||
436 | 454 | | |
437 | 455 | | |
438 | 456 | | |
| 457 | + | |
| 458 | + | |
| 459 | + | |
| 460 | + | |
| 461 | + | |
| 462 | + | |
439 | 463 | | |
440 | 464 | | |
441 | 465 | | |
| |||
1191 | 1215 | | |
1192 | 1216 | | |
1193 | 1217 | | |
| 1218 | + | |
| 1219 | + | |
| 1220 | + | |
| 1221 | + | |
| 1222 | + | |
| 1223 | + | |
1194 | 1224 | | |
1195 | 1225 | | |
1196 | 1226 | | |
| |||
2475 | 2505 | | |
2476 | 2506 | | |
2477 | 2507 | | |
| 2508 | + | |
| 2509 | + | |
| 2510 | + | |
| 2511 | + | |
| 2512 | + | |
| 2513 | + | |
2478 | 2514 | | |
2479 | 2515 | | |
2480 | 2516 | | |
| |||
2724 | 2760 | | |
2725 | 2761 | | |
2726 | 2762 | | |
| 2763 | + | |
| 2764 | + | |
| 2765 | + | |
| 2766 | + | |
| 2767 | + | |
| 2768 | + | |
2727 | 2769 | | |
2728 | 2770 | | |
2729 | 2771 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
117 | 117 | | |
118 | 118 | | |
119 | 119 | | |
| 120 | + | |
| 121 | + | |
| 122 | + | |
| 123 | + | |
| 124 | + | |
| 125 | + | |
| 126 | + | |
| 127 | + | |
120 | 128 | | |
121 | 129 | | |
122 | 130 | | |
| |||
158 | 166 | | |
159 | 167 | | |
160 | 168 | | |
| 169 | + | |
| 170 | + | |
| 171 | + | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
161 | 186 | | |
162 | 187 | | |
163 | 188 | | |
| |||
182 | 207 | | |
183 | 208 | | |
184 | 209 | | |
| 210 | + | |
185 | 211 | | |
| 212 | + | |
186 | 213 | | |
187 | 214 | | |
188 | 215 | | |
| |||
2053 | 2080 | | |
2054 | 2081 | | |
2055 | 2082 | | |
| 2083 | + | |
| 2084 | + | |
| 2085 | + | |
| 2086 | + | |
| 2087 | + | |
| 2088 | + | |
| 2089 | + | |
| 2090 | + | |
| 2091 | + | |
| 2092 | + | |
| 2093 | + | |
2056 | 2094 | | |
2057 | 2095 | | |
2058 | 2096 | | |
| |||
2310 | 2348 | | |
2311 | 2349 | | |
2312 | 2350 | | |
2313 | | - | |
2314 | 2351 | | |
| 2352 | + | |
2315 | 2353 | | |
2316 | 2354 | | |
2317 | 2355 | | |
2318 | 2356 | | |
2319 | 2357 | | |
2320 | 2358 | | |
2321 | 2359 | | |
2322 | | - | |
| 2360 | + | |
2323 | 2361 | | |
2324 | 2362 | | |
2325 | 2363 | | |
| |||
2335 | 2373 | | |
2336 | 2374 | | |
2337 | 2375 | | |
| 2376 | + | |
| 2377 | + | |
| 2378 | + | |
| 2379 | + | |
| 2380 | + | |
| 2381 | + | |
2338 | 2382 | | |
2339 | 2383 | | |
2340 | 2384 | | |
| |||
2587 | 2631 | | |
2588 | 2632 | | |
2589 | 2633 | | |
| 2634 | + | |
| 2635 | + | |
| 2636 | + | |
| 2637 | + | |
| 2638 | + | |
| 2639 | + | |
2590 | 2640 | | |
2591 | 2641 | | |
2592 | 2642 | | |
| |||
2704 | 2754 | | |
2705 | 2755 | | |
2706 | 2756 | | |
| 2757 | + | |
| 2758 | + | |
| 2759 | + | |
| 2760 | + | |
| 2761 | + | |
| 2762 | + | |
2707 | 2763 | | |
2708 | 2764 | | |
2709 | 2765 | | |
| |||
2833 | 2889 | | |
2834 | 2890 | | |
2835 | 2891 | | |
| 2892 | + | |
| 2893 | + | |
| 2894 | + | |
| 2895 | + | |
| 2896 | + | |
| 2897 | + | |
2836 | 2898 | | |
2837 | 2899 | | |
2838 | 2900 | | |
| |||
2960 | 3022 | | |
2961 | 3023 | | |
2962 | 3024 | | |
| 3025 | + | |
| 3026 | + | |
| 3027 | + | |
| 3028 | + | |
| 3029 | + | |
| 3030 | + | |
2963 | 3031 | | |
2964 | 3032 | | |
2965 | 3033 | | |
| |||
3077 | 3145 | | |
3078 | 3146 | | |
3079 | 3147 | | |
| 3148 | + | |
| 3149 | + | |
| 3150 | + | |
| 3151 | + | |
| 3152 | + | |
| 3153 | + | |
3080 | 3154 | | |
3081 | 3155 | | |
3082 | 3156 | | |
| |||
3165 | 3239 | | |
3166 | 3240 | | |
3167 | 3241 | | |
| 3242 | + | |
| 3243 | + | |
| 3244 | + | |
| 3245 | + | |
| 3246 | + | |
| 3247 | + | |
3168 | 3248 | | |
3169 | 3249 | | |
3170 | 3250 | | |
| |||
3286 | 3366 | | |
3287 | 3367 | | |
3288 | 3368 | | |
| 3369 | + | |
| 3370 | + | |
| 3371 | + | |
| 3372 | + | |
| 3373 | + | |
| 3374 | + | |
3289 | 3375 | | |
3290 | 3376 | | |
3291 | 3377 | | |
| |||
3455 | 3541 | | |
3456 | 3542 | | |
3457 | 3543 | | |
| 3544 | + | |
| 3545 | + | |
| 3546 | + | |
| 3547 | + | |
| 3548 | + | |
| 3549 | + | |
3458 | 3550 | | |
3459 | 3551 | | |
3460 | 3552 | | |
| |||
3566 | 3658 | | |
3567 | 3659 | | |
3568 | 3660 | | |
| 3661 | + | |
| 3662 | + | |
| 3663 | + | |
| 3664 | + | |
| 3665 | + | |
| 3666 | + | |
3569 | 3667 | | |
3570 | 3668 | | |
3571 | 3669 | | |
| |||
0 commit comments