Skip to content

Commit d8ab73d

Browse files
Merge pull request #2 from PolicyEngine/bot/issue-1
Migrate from AWS to GCP Cloud Run
2 parents 296c2db + 3fdc5f2 commit d8ab73d

4 files changed

Lines changed: 282 additions & 580 deletions

File tree

.github/workflows/deploy.yml

Lines changed: 30 additions & 171 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
name: Deploy to AWS ECS
1+
name: Deploy to GCP Cloud Run
22

33
on:
44
push:
@@ -40,11 +40,14 @@ jobs:
4040
- name: Checkout code
4141
uses: actions/checkout@v4
4242

43-
- name: Configure AWS credentials
44-
uses: aws-actions/configure-aws-credentials@v4
43+
- name: Authenticate to Google Cloud
44+
uses: google-github-actions/auth@v2
4545
with:
46-
role-to-assume: ${{ secrets.AWS_ROLE_ARN }}
47-
aws-region: ${{ vars.AWS_REGION }}
46+
workload_identity_provider: ${{ secrets.GCP_WORKLOAD_IDENTITY_PROVIDER }}
47+
service_account: ${{ secrets.GCP_SERVICE_ACCOUNT }}
48+
49+
- name: Set up Cloud SDK
50+
uses: google-github-actions/setup-gcloud@v2
4851

4952
- name: Setup Terraform
5053
uses: hashicorp/setup-terraform@v3
@@ -75,181 +78,37 @@ jobs:
7578
TF_VAR_logfire_environment: prod
7679
run: terraform apply -auto-approve
7780

78-
- name: Login to Amazon ECR
79-
id: login-ecr
80-
uses: aws-actions/amazon-ecr-login@v2
81+
- name: Configure Docker for Artifact Registry
82+
run: gcloud auth configure-docker ${{ vars.GCP_REGION }}-docker.pkg.dev
8183

8284
- name: Build and push Docker image
8385
env:
84-
ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
85-
ECR_REPOSITORY: ${{ vars.ECR_REPOSITORY_NAME }}
86+
IMAGE_URL: ${{ vars.GCP_REGION }}-docker.pkg.dev/${{ vars.GCP_PROJECT_ID }}/${{ vars.PROJECT_NAME }}/${{ vars.PROJECT_NAME }}
8687
IMAGE_TAG: ${{ github.sha }}
8788
run: |
88-
docker build -t $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG .
89-
docker tag $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG $ECR_REGISTRY/$ECR_REPOSITORY:latest
90-
docker push $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG
91-
docker push $ECR_REGISTRY/$ECR_REPOSITORY:latest
89+
docker build -t $IMAGE_URL:$IMAGE_TAG .
90+
docker tag $IMAGE_URL:$IMAGE_TAG $IMAGE_URL:latest
91+
docker push $IMAGE_URL:$IMAGE_TAG
92+
docker push $IMAGE_URL:latest
9293
93-
- name: Update ECS service (API)
94+
- name: Deploy API to Cloud Run
9495
run: |
95-
aws ecs update-service \
96-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
97-
--service ${{ vars.ECS_API_SERVICE_NAME }} \
98-
--force-new-deployment \
99-
--region ${{ vars.AWS_REGION }}
96+
gcloud run services update-traffic ${{ vars.API_SERVICE_NAME }} \
97+
--region=${{ vars.GCP_REGION }} \
98+
--to-latest
10099
101-
- name: Update ECS service (Worker)
100+
- name: Deploy Worker to Cloud Run
102101
run: |
103-
aws ecs update-service \
104-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
105-
--service ${{ vars.ECS_WORKER_SERVICE_NAME }} \
106-
--force-new-deployment \
107-
--region ${{ vars.AWS_REGION }}
102+
gcloud run services update-traffic ${{ vars.WORKER_SERVICE_NAME }} \
103+
--region=${{ vars.GCP_REGION }} \
104+
--to-latest
108105
109-
- name: Monitor API deployment
110-
run: |
111-
echo "=== Monitoring API deployment ==="
112-
for i in {1..30}; do
113-
STATUS=$(aws ecs describe-services \
114-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
115-
--services ${{ vars.ECS_API_SERVICE_NAME }} \
116-
--region ${{ vars.AWS_REGION }} \
117-
--query 'services[0].deployments[0].{Status:rolloutState,Running:runningCount,Desired:desiredCount,Pending:pendingCount}' \
118-
--output json)
119-
120-
echo "[$i/30] $(date +%H:%M:%S) - $STATUS"
121-
122-
# Get latest task and show its logs
123-
TASK_ARN=$(aws ecs list-tasks \
124-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
125-
--service-name ${{ vars.ECS_API_SERVICE_NAME }} \
126-
--region ${{ vars.AWS_REGION }} \
127-
--query 'taskArns[0]' \
128-
--output text)
129-
130-
if [ -n "$TASK_ARN" ] && [ "$TASK_ARN" != "None" ]; then
131-
TASK_ID=$(echo $TASK_ARN | rev | cut -d'/' -f1 | rev)
132-
echo "--- Recent logs from task $TASK_ID ---"
133-
aws logs tail /ecs/policyengine-api-v2-alpha \
134-
--log-stream-name-prefix "api/$TASK_ID" \
135-
--since 30s \
136-
--format short \
137-
--region ${{ vars.AWS_REGION }} 2>&1 || echo "No logs available yet"
138-
echo "---"
139-
fi
140-
141-
# Check if stable
142-
if aws ecs describe-services \
143-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
144-
--services ${{ vars.ECS_API_SERVICE_NAME }} \
145-
--region ${{ vars.AWS_REGION }} \
146-
--query 'services[0].deployments | length(@) == `1`' \
147-
--output text | grep -q "True"; then
148-
echo "API deployment completed!"
149-
break
150-
fi
151-
152-
sleep 20
153-
done
154-
155-
- name: Monitor worker deployment
156-
run: |
157-
echo "=== Monitoring worker deployment ==="
158-
for i in {1..30}; do
159-
STATUS=$(aws ecs describe-services \
160-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
161-
--services ${{ vars.ECS_WORKER_SERVICE_NAME }} \
162-
--region ${{ vars.AWS_REGION }} \
163-
--query 'services[0].deployments[0].{Status:rolloutState,Running:runningCount,Desired:desiredCount,Pending:pendingCount}' \
164-
--output json)
165-
166-
echo "[$i/30] $(date +%H:%M:%S) - $STATUS"
167-
168-
# Get latest task and show its logs
169-
TASK_ARN=$(aws ecs list-tasks \
170-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
171-
--service-name ${{ vars.ECS_WORKER_SERVICE_NAME }} \
172-
--region ${{ vars.AWS_REGION }} \
173-
--query 'taskArns[0]' \
174-
--output text)
175-
176-
if [ -n "$TASK_ARN" ] && [ "$TASK_ARN" != "None" ]; then
177-
TASK_ID=$(echo $TASK_ARN | rev | cut -d'/' -f1 | rev)
178-
echo "--- Recent logs from task $TASK_ID ---"
179-
aws logs tail /ecs/policyengine-api-v2-alpha \
180-
--log-stream-name-prefix "worker/$TASK_ID" \
181-
--since 30s \
182-
--format short \
183-
--region ${{ vars.AWS_REGION }} 2>&1 || echo "No logs available yet"
184-
echo "---"
185-
fi
186-
187-
# Check if stable
188-
if aws ecs describe-services \
189-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
190-
--services ${{ vars.ECS_WORKER_SERVICE_NAME }} \
191-
--region ${{ vars.AWS_REGION }} \
192-
--query 'services[0].deployments | length(@) == `1`' \
193-
--output text | grep -q "True"; then
194-
echo "Worker deployment completed!"
195-
break
196-
fi
197-
198-
sleep 20
199-
done
200-
201-
- name: Final deployment status
202-
run: |
203-
echo "=== Final Deployment Status ==="
204-
echo "API Service:"
205-
aws ecs describe-services \
206-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
207-
--services ${{ vars.ECS_API_SERVICE_NAME }} \
208-
--region ${{ vars.AWS_REGION }} \
209-
--query 'services[0].{Status:status,Running:runningCount,Desired:desiredCount}' \
210-
--output table
211-
212-
echo ""
213-
echo "Worker Service:"
214-
aws ecs describe-services \
215-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
216-
--services ${{ vars.ECS_WORKER_SERVICE_NAME }} \
217-
--region ${{ vars.AWS_REGION }} \
218-
--query 'services[0].{Status:status,Running:runningCount,Desired:desiredCount}' \
219-
--output table
220-
221-
- name: Get API endpoint
106+
- name: Get API URL
222107
run: |
223108
echo "=== API Endpoint ==="
224-
TASK_ARN=$(aws ecs list-tasks \
225-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
226-
--service-name ${{ vars.ECS_API_SERVICE_NAME }} \
227-
--region ${{ vars.AWS_REGION }} \
228-
--desired-status RUNNING \
229-
--query 'taskArns[0]' \
230-
--output text)
231-
232-
if [ -n "$TASK_ARN" ] && [ "$TASK_ARN" != "None" ]; then
233-
NETWORK_INTERFACE_ID=$(aws ecs describe-tasks \
234-
--cluster ${{ vars.ECS_CLUSTER_NAME }} \
235-
--tasks $TASK_ARN \
236-
--region ${{ vars.AWS_REGION }} \
237-
--query 'tasks[0].attachments[0].details[?name==`networkInterfaceId`].value' \
238-
--output text)
239-
240-
PUBLIC_IP=$(aws ec2 describe-network-interfaces \
241-
--network-interface-ids $NETWORK_INTERFACE_ID \
242-
--region ${{ vars.AWS_REGION }} \
243-
--query 'NetworkInterfaces[0].Association.PublicIp' \
244-
--output text)
245-
246-
if [ -n "$PUBLIC_IP" ] && [ "$PUBLIC_IP" != "None" ]; then
247-
echo "API is available at: http://$PUBLIC_IP"
248-
echo "Health check: http://$PUBLIC_IP/health"
249-
echo "Documentation: http://$PUBLIC_IP/docs"
250-
else
251-
echo "Could not retrieve public IP"
252-
fi
253-
else
254-
echo "No running API tasks found"
255-
fi
109+
API_URL=$(gcloud run services describe ${{ vars.API_SERVICE_NAME }} \
110+
--region=${{ vars.GCP_REGION }} \
111+
--format='value(status.url)')
112+
echo "API is available at: $API_URL"
113+
echo "Health check: $API_URL/health"
114+
echo "Documentation: $API_URL/docs"

0 commit comments

Comments
 (0)