Date: 2026-02-19
Expose the Link service (port 9999) to the internet at link.getorcha.com and link.prod.getorcha.com, following the same infrastructure pattern as ERP and Admin services.
/health endpoint for health checkslink.getorcha.com as production URLInternet
│
▼
ALB (HTTPS:443)
│
├─ Host: app.* ──────────────► Target Group (8888) ──► EC2
├─ Host: admin.* ─► Cognito ─► Target Group (7777) ──► EC2
└─ Host: link.* ─────────────► Target Group (9999) ──► EC2
Management Account (getorcha.com zone)
├── CNAME: link.getorcha.com → link.prod.getorcha.com [NEW]
└── ACM validation CNAME for link.getorcha.com [NEW]
Prod Account (prod.getorcha.com zone - via CDK)
├── A: link.prod.getorcha.com → ALB [NEW]
└── ACM validation CNAME for link.prod.getorcha.com [NEW]
foundation_stack.py)Add ALB-to-EC2 rules for port 9999:
# Link service traffic ALB -> EC2 (port 9999)
self.alb_sg.add_egress_rule(
self.ec2_sg,
ec2.Port.tcp(9999),
"Link traffic to EC2",
)
self.ec2_sg.add_ingress_rule(
self.alb_sg,
ec2.Port.tcp(9999),
"Link port from ALB",
)
compute_stack.py)New target group for Link service:
self.link_target_group = elbv2.ApplicationTargetGroup(
self,
"LinkTargetGroup",
target_group_name="v1-orcha-link-tg",
vpc=vpc,
port=9999,
protocol=elbv2.ApplicationProtocol.HTTP,
target_type=elbv2.TargetType.INSTANCE,
health_check=elbv2.HealthCheck(
path="/health",
protocol=elbv2.Protocol.HTTP,
healthy_threshold_count=2,
unhealthy_threshold_count=3,
interval=Duration.seconds(30),
timeout=Duration.seconds(5),
),
deregistration_delay=Duration.seconds(60),
)
self.asg.attach_to_application_target_group(self.link_target_group)
compute_stack.py)Import manually-created certificate (cross-account DNS validation):
if env_name == "prod":
self.link_certificate = acm.Certificate.from_certificate_arn(
self,
"LinkCertificate",
certificate_arn="<ARN_FROM_SCRIPT>",
)
else:
self.link_certificate = acm.Certificate(
self,
"LinkCertificate",
domain_name=f"link.{env_name}.getorcha.com",
validation=acm.CertificateValidation.from_dns(hosted_zone),
)
compute_stack.py)Add certificate and host-based routing:
https_listener.add_certificates("LinkCerts", [self.link_certificate])
https_listener.add_action(
"LinkRouting",
priority=20,
conditions=[
elbv2.ListenerCondition.host_headers([
"link.prod.getorcha.com",
"link.getorcha.com",
])
],
action=elbv2.ListenerAction.forward([self.link_target_group]),
)
compute_stack.py)route53.ARecord(
self,
"LinkAliasRecord",
zone=hosted_zone,
record_name="link",
target=route53.RecordTarget.from_alias(
targets.LoadBalancerTarget(self.alb),
),
)
ops_stack.py)Pass link_target_group from ComputeStack and add alarm:
link_alb_unhealthy_alarm = cloudwatch.Alarm(
self,
"LinkAlbUnhealthyAlarm",
alarm_name="v1-orcha-link-unhealthy",
alarm_description="Link target group has no healthy targets",
metric=cloudwatch.Metric(
namespace="AWS/ApplicationELB",
metric_name="HealthyHostCount",
dimensions_map={
"TargetGroup": link_target_group.target_group_full_name,
"LoadBalancer": alb.load_balancer_full_name,
},
statistic="Minimum",
period=Duration.seconds(60),
),
threshold=1,
comparison_operator=cloudwatch.ComparisonOperator.LESS_THAN_THRESHOLD,
evaluation_periods=2,
treat_missing_data=cloudwatch.TreatMissingData.BREACHING,
)
link_alb_unhealthy_alarm.add_alarm_action(cw_actions.SnsAction(self.alert_topic))
deploy/docker-compose.yml)Expose port 9999:
ports:
- "8888:8888"
- "7777:7777"
- "9999:9999"
- "9878:9878"
Create ACM certificate:
cd infra
./scripts/create-cross-account-cert.sh \
--name link \
--primary-domain link.prod.getorcha.com \
--san link.getorcha.com
Add short link CNAME in management account:
AWS_PROFILE=orcha aws route53 change-resource-record-sets \
--hosted-zone-id Z02414383CQNYTPGX2EIK \
--change-batch '{
"Changes": [{
"Action": "CREATE",
"ResourceRecordSet": {
"Name": "link.getorcha.com",
"Type": "CNAME",
"TTL": 300,
"ResourceRecords": [{"Value": "link.prod.getorcha.com"}]
}
}]
}'
Update CDK code with certificate ARN from step 1
dig link.prod.getorcha.comcurl https://link.getorcha.com/healthcurl https://link.getorcha.com/.well-known/oauth-authorization-server| File | Changes |
|---|---|
infra/stacks/foundation_stack.py |
Security group rules for port 9999 |
infra/stacks/compute_stack.py |
Target group, certificate, listener rule, DNS record |
infra/stacks/ops_stack.py |
CloudWatch alarm for Link unhealthy hosts |
infra/app.py |
Pass link_target_group to OpsStack |
deploy/docker-compose.yml |
Expose port 9999 |
| Output | Value |
|---|---|
LinkTargetGroupArn |
Target group ARN |
LinkCertificateArn |
Certificate ARN |
LinkUrl |
https://link.{env}.getorcha.com |