11#! /bin/bash
22
3- # Deployment Script for vTeam Ambient Agentic Runner
4- # Supports both OpenShift and standard Kubernetes (kind, etc.)
3+ # OpenShift Deployment Script for vTeam Ambient Agentic Runner
54# Usage: ./deploy.sh
65# Or with environment variables: NAMESPACE=my-namespace ./deploy.sh
76# Note: This script deploys pre-built images. Build and push images first.
@@ -31,27 +30,6 @@ command_exists() {
3130 command -v " $1 " > /dev/null 2>&1
3231}
3332
34- # Detect platform (OpenShift vs standard Kubernetes)
35- detect_platform () {
36- if command_exists oc && oc api-resources | grep -q " route.openshift.io" ; then
37- echo " openshift"
38- elif command_exists kubectl; then
39- echo " kubernetes"
40- else
41- echo " unknown"
42- fi
43- }
44-
45- # Get the appropriate CLI command
46- get_cli_cmd () {
47- local platform=$1
48- if [ " $platform " = " openshift" ]; then
49- echo " oc"
50- else
51- echo " kubectl"
52- fi
53- }
54-
5533# Helper: Run the OAuth setup (Route host, OAuthClient, Secret)
5634oauth_setup () {
5735 echo -e " ${YELLOW} Configuring OpenShift OAuth for the frontend...${NC} "
146124 oc -n ${NAMESPACE} rollout restart deployment/frontend
147125}
148126
149- # Detect platform
150- PLATFORM=$( detect_platform)
151- if [ " $PLATFORM " = " unknown" ]; then
152- echo -e " ${RED} ❌ Neither oc nor kubectl found. Please install one.${NC} "
153- exit 1
154- fi
155- CLI_CMD=$( get_cli_cmd " $PLATFORM " )
156-
157- echo -e " ${BLUE} Detected platform: ${GREEN}${PLATFORM}${NC} "
158- echo -e " ${BLUE} Using CLI: ${GREEN}${CLI_CMD}${NC} "
159- echo " "
160-
161127# Configuration
162128NAMESPACE=" ${NAMESPACE:- ambient-code} "
163129# Allow overriding images via CONTAINER_REGISTRY/IMAGE_TAG or explicit DEFAULT_*_IMAGE
@@ -170,13 +136,6 @@ DEFAULT_RUNNER_IMAGE="${DEFAULT_RUNNER_IMAGE:-${CONTAINER_REGISTRY}/vteam_claude
170136# Content service image (defaults to same as backend, but can be overridden)
171137CONTENT_SERVICE_IMAGE=" ${CONTENT_SERVICE_IMAGE:- ${DEFAULT_BACKEND_IMAGE} } "
172138
173- # Select overlay based on platform
174- if [ " $PLATFORM " = " openshift" ]; then
175- OVERLAY=" production"
176- else
177- OVERLAY=" kubernetes"
178- fi
179-
180139# Handle uninstall/clean command early
181140if [ " ${1:- } " = " uninstall" ] || [ " ${1:- } " = " clean" ]; then
182141 echo -e " ${YELLOW} Uninstalling vTeam from namespace ${NAMESPACE} ...${NC} "
267226 exit 0
268227fi
269228
270- echo -e " ${BLUE} 🚀 vTeam Ambient Agentic Runner Deployment${NC} "
271- echo -e " ${BLUE} ===========================================${NC} "
272- echo -e " Platform: ${GREEN}${PLATFORM}${NC} "
273- echo -e " Overlay: ${GREEN}${OVERLAY}${NC} "
229+ echo -e " ${BLUE} 🚀 vTeam Ambient Agentic Runner - OpenShift Deployment${NC} "
230+ echo -e " ${BLUE} ====================================================${NC} "
274231echo -e " Namespace: ${GREEN}${NAMESPACE}${NC} "
275232echo -e " Backend Image: ${GREEN}${DEFAULT_BACKEND_IMAGE}${NC} "
276233echo -e " Frontend Image: ${GREEN}${DEFAULT_FRONTEND_IMAGE}${NC} "
@@ -281,6 +238,11 @@ echo ""
281238
282239# Check prerequisites
283240echo -e " ${YELLOW} Checking prerequisites...${NC} "
241+ if ! command_exists oc; then
242+ echo -e " ${RED} ❌ OpenShift CLI (oc) not found. Please install it first.${NC} "
243+ exit 1
244+ fi
245+
284246if ! command_exists kustomize; then
285247 echo -e " ${RED} ❌ Kustomize not found. Please install it first.${NC} "
286248 exit 1
289251echo -e " ${GREEN} ✅ Prerequisites check passed${NC} "
290252echo " "
291253
292- # Check if logged in
293- echo -e " ${YELLOW} Checking cluster authentication...${NC} "
294- if ! $CLI_CMD cluster-info > /dev/null 2>&1 ; then
295- echo -e " ${RED} ❌ Not connected to cluster . Please configure kubectl/oc first.${NC} "
254+ # Check if logged in to OpenShift
255+ echo -e " ${YELLOW} Checking OpenShift authentication...${NC} "
256+ if ! oc whoami > /dev/null 2>&1 ; then
257+ echo -e " ${RED} ❌ Not logged in to OpenShift . Please run 'oc login' first.${NC} "
296258 exit 1
297259fi
298260
299- CURRENT_USER=$( $CLI_CMD auth whoami 2> /dev/null || echo " unknown" )
300- echo -e " ${GREEN} ✅ Authenticated as: ${CURRENT_USER}${NC} "
261+ echo -e " ${GREEN} ✅ Authenticated as: $( oc whoami) ${NC} "
301262echo " "
302263
303- # Prepare oauth secret env file for kustomize secretGenerator (OpenShift only)
304- if [ " $PLATFORM " = " openshift" ]; then
305- echo -e " ${YELLOW} Preparing oauth secret env for kustomize...${NC} "
306- OAUTH_ENV_FILE=" oauth-secret.env"
307- CLIENT_SECRET_VALUE=" ${OCP_OAUTH_CLIENT_SECRET:- } "
308- COOKIE_SECRET_VALUE=" ${OCP_OAUTH_COOKIE_SECRET:- } "
309- if [[ -z " $CLIENT_SECRET_VALUE " ]]; then
310- CLIENT_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
311- fi
312- # cookie_secret must be exactly 16, 24, or 32 bytes. Use 32 ASCII bytes by default.
313- if [[ -z " $COOKIE_SECRET_VALUE " ]]; then
314- COOKIE_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
315- fi
316- # If provided via .env, ensure it meets required length
317- COOKIE_LEN=${# COOKIE_SECRET_VALUE}
318- if [[ $COOKIE_LEN -ne 16 && $COOKIE_LEN -ne 24 && $COOKIE_LEN -ne 32 ]]; then
319- echo -e " ${YELLOW} Provided OCP_OAUTH_COOKIE_SECRET length ($COOKIE_LEN ) is invalid; regenerating 32-byte value...${NC} "
320- COOKIE_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
321- fi
322- cat > " $OAUTH_ENV_FILE " << EOF
264+ # Prepare oauth secret env file for kustomize secretGenerator
265+ echo -e " ${YELLOW} Preparing oauth secret env for kustomize...${NC} "
266+ OAUTH_ENV_FILE=" oauth-secret.env"
267+ CLIENT_SECRET_VALUE=" ${OCP_OAUTH_CLIENT_SECRET:- } "
268+ COOKIE_SECRET_VALUE=" ${OCP_OAUTH_COOKIE_SECRET:- } "
269+ if [[ -z " $CLIENT_SECRET_VALUE " ]]; then
270+ CLIENT_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
271+ fi
272+ # cookie_secret must be exactly 16, 24, or 32 bytes. Use 32 ASCII bytes by default.
273+ if [[ -z " $COOKIE_SECRET_VALUE " ]]; then
274+ COOKIE_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
275+ fi
276+ # If provided via .env, ensure it meets required length
277+ COOKIE_LEN=${# COOKIE_SECRET_VALUE}
278+ if [[ $COOKIE_LEN -ne 16 && $COOKIE_LEN -ne 24 && $COOKIE_LEN -ne 32 ]]; then
279+ echo -e " ${YELLOW} Provided OCP_OAUTH_COOKIE_SECRET length ($COOKIE_LEN ) is invalid; regenerating 32-byte value...${NC} "
280+ COOKIE_SECRET_VALUE=$( LC_ALL=C tr -dc ' A-Za-z0-9' < /dev/urandom | head -c 32)
281+ fi
282+ cat > " $OAUTH_ENV_FILE " << EOF
323283client-secret=${CLIENT_SECRET_VALUE}
324284cookie_secret=${COOKIE_SECRET_VALUE}
325285EOF
326- echo -e " ${GREEN} ✅ Generated ${OAUTH_ENV_FILE}${NC} "
327- echo " "
328- fi
286+ echo -e " ${GREEN} ✅ Generated ${OAUTH_ENV_FILE}${NC} "
287+ echo " "
329288
330289
331290# Deploy using kustomize
332- echo -e " ${YELLOW} Deploying using Kustomize...${NC} "
291+ echo -e " ${YELLOW} Deploying to OpenShift using Kustomize...${NC} "
333292
334- # Use appropriate overlay
335- cd overlays/${OVERLAY}
293+ # Use production overlay
294+ cd overlays/production
336295
337296# Set namespace if different from default
338297if [ " $NAMESPACE " != " ambient-code" ]; then
@@ -349,39 +308,35 @@ kustomize edit set image quay.io/ambient_code/vteam_claude_runner:latest=${DEFAU
349308
350309# Build and apply manifests
351310echo -e " ${BLUE} Building and applying manifests...${NC} "
352- kustomize build . | $CLI_CMD apply -f -
311+ kustomize build . | oc apply -f -
353312
354313# Return to manifests root
355314cd ../..
356315
357316# Check if namespace exists and is active
358317echo -e " ${YELLOW} Checking namespace status...${NC} "
359- if ! $CLI_CMD get namespace ${NAMESPACE} > /dev/null 2>&1 ; then
318+ if ! oc get namespace ${NAMESPACE} > /dev/null 2>&1 ; then
360319 echo -e " ${RED} ❌ Namespace ${NAMESPACE} does not exist${NC} "
361320 exit 1
362321fi
363322
364323# Check if namespace is active
365- NAMESPACE_PHASE=$( $CLI_CMD get namespace ${NAMESPACE} -o jsonpath=' {.status.phase}' )
324+ NAMESPACE_PHASE=$( oc get namespace ${NAMESPACE} -o jsonpath=' {.status.phase}' )
366325if [ " $NAMESPACE_PHASE " != " Active" ]; then
367326 echo -e " ${RED} ❌ Namespace ${NAMESPACE} is not active (phase: ${NAMESPACE_PHASE} )${NC} "
368327 exit 1
369328fi
370329echo -e " ${GREEN} ✅ Namespace ${NAMESPACE} is active${NC} "
371330
372- # Switch to the target namespace (OpenShift only)
373- if [ " $PLATFORM " = " openshift" ]; then
374- echo -e " ${BLUE} Switching to namespace ${NAMESPACE} ...${NC} "
375- oc project ${NAMESPACE}
376- fi
331+ # Switch to the target namespace
332+ echo -e " ${BLUE} Switching to namespace ${NAMESPACE} ...${NC} "
333+ oc project ${NAMESPACE}
377334
378335# ##############################################
379- # OAuth setup: Route host, OAuthClient, Secret (OpenShift only)
336+ # OAuth setup: Route host, OAuthClient, Secret
380337# ##############################################
381- if [ " $PLATFORM " = " openshift" ]; then
382- if ! oauth_setup; then
383- echo -e " ${YELLOW} OAuth setup completed with warnings/errors. You may need a cluster-admin to apply the OAuthClient.${NC} "
384- fi
338+ if ! oauth_setup; then
339+ echo -e " ${YELLOW} OAuth setup completed with warnings/errors. You may need a cluster-admin to apply the OAuthClient.${NC} "
385340fi
386341
387342# Apply git configuration if we created a patch
393348
394349# Update operator deployment with custom runner image
395350echo -e " ${BLUE} Updating operator with custom runner image...${NC} "
396- $CLI_CMD patch deployment agentic-operator -n ${NAMESPACE} -p " {\" spec\" :{\" template\" :{\" spec\" :{\" containers\" :[{\" name\" :\" agentic-operator\" ,\" env\" :[{\" name\" :\" AMBIENT_CODE_RUNNER_IMAGE\" ,\" value\" :\" ${DEFAULT_RUNNER_IMAGE} \" }]}]}}}}" --type=strategic
351+ oc patch deployment agentic-operator -n ${NAMESPACE} -p " {\" spec\" :{\" template\" :{\" spec\" :{\" containers\" :[{\" name\" :\" agentic-operator\" ,\" env\" :[{\" name\" :\" AMBIENT_CODE_RUNNER_IMAGE\" ,\" value\" :\" ${DEFAULT_RUNNER_IMAGE} \" }]}]}}}}" --type=strategic
397352
398353# Update backend deployment with content service image
399354echo -e " ${BLUE} Updating backend with content service image...${NC} "
400- $CLI_CMD patch deployment backend-api -n ${NAMESPACE} -p " {\" spec\" :{\" template\" :{\" spec\" :{\" containers\" :[{\" name\" :\" backend-api\" ,\" env\" :[{\" name\" :\" CONTENT_SERVICE_IMAGE\" ,\" value\" :\" ${CONTENT_SERVICE_IMAGE} \" },{\" name\" :\" IMAGE_PULL_POLICY\" ,\" value\" :\" Always\" }]}]}}}}" --type=strategic
355+ oc patch deployment backend-api -n ${NAMESPACE} -p " {\" spec\" :{\" template\" :{\" spec\" :{\" containers\" :[{\" name\" :\" backend-api\" ,\" env\" :[{\" name\" :\" CONTENT_SERVICE_IMAGE\" ,\" value\" :\" ${CONTENT_SERVICE_IMAGE} \" },{\" name\" :\" IMAGE_PULL_POLICY\" ,\" value\" :\" Always\" }]}]}}}}" --type=strategic
401356
402357echo " "
403358echo -e " ${GREEN} ✅ Deployment completed!${NC} "
404359echo " "
405360
406361# Wait for deployments to be ready
407362echo -e " ${YELLOW} Waiting for deployments to be ready...${NC} "
408- $CLI_CMD rollout status deployment/backend-api --namespace=${NAMESPACE} --timeout=300s
409- $CLI_CMD rollout status deployment/agentic-operator --namespace=${NAMESPACE} --timeout=300s
410- $CLI_CMD rollout status deployment/frontend --namespace=${NAMESPACE} --timeout=300s
363+ oc rollout status deployment/backend-api --namespace=${NAMESPACE} --timeout=300s
364+ oc rollout status deployment/agentic-operator --namespace=${NAMESPACE} --timeout=300s
365+ oc rollout status deployment/frontend --namespace=${NAMESPACE} --timeout=300s
411366
412- # Get service and ingress/ route information
413- echo -e " ${BLUE} Getting service information...${NC} "
367+ # Get service and route information
368+ echo -e " ${BLUE} Getting service and route information...${NC} "
414369echo " "
415370echo -e " ${GREEN} 🎉 Deployment successful!${NC} "
416371echo -e " ${GREEN} ========================${NC} "
@@ -419,71 +374,52 @@ echo ""
419374
420375# Show pod status
421376echo -e " ${BLUE} Pod Status:${NC} "
422- $CLI_CMD get pods -n ${NAMESPACE}
377+ oc get pods -n ${NAMESPACE}
423378echo " "
424379
425- # Show services
380+ # Show services and route
426381echo -e " ${BLUE} Services:${NC} "
427- $CLI_CMD get services -n ${NAMESPACE}
382+ oc get services -n ${NAMESPACE}
428383echo " "
429-
430- # Show routes (OpenShift) or ingress (Kubernetes)
431- if [ " $PLATFORM " = " openshift" ]; then
432- echo -e " ${BLUE} Routes:${NC} "
433- oc get route -n ${NAMESPACE} || true
434- if [[ -z " ${ROUTE_NAME:- } " ]]; then
435- if oc get route frontend-route -n ${NAMESPACE} > /dev/null 2>&1 ; then
436- ROUTE_NAME=" frontend-route"
437- elif oc get route frontend -n ${NAMESPACE} > /dev/null 2>&1 ; then
438- ROUTE_NAME=" frontend"
439- fi
384+ echo -e " ${BLUE} Routes:${NC} "
385+ oc get route -n ${NAMESPACE} || true
386+ if [[ -z " ${ROUTE_NAME:- } " ]]; then
387+ if oc get route frontend-route -n ${NAMESPACE} > /dev/null 2>&1 ; then
388+ ROUTE_NAME=" frontend-route"
389+ elif oc get route frontend -n ${NAMESPACE} > /dev/null 2>&1 ; then
390+ ROUTE_NAME=" frontend"
440391 fi
441- ROUTE_HOST=$( oc get route ${ROUTE_NAME:- frontend-route} -n ${NAMESPACE} -o jsonpath=' {.spec.host}' 2> /dev/null || true)
442- else
443- echo -e " ${BLUE} Ingress:${NC} "
444- $CLI_CMD get ingress -n ${NAMESPACE} || true
445- INGRESS_HOST=$( $CLI_CMD get ingress frontend-ingress -n ${NAMESPACE} -o jsonpath=' {.spec.rules[0].host}' 2> /dev/null || echo " vteam.local" )
446392fi
393+ ROUTE_HOST=$( oc get route ${ROUTE_NAME:- frontend-route} -n ${NAMESPACE} -o jsonpath=' {.spec.host}' 2> /dev/null || true)
447394echo " "
448395
449- # Cleanup generated files (OpenShift only)
450- if [ " $PLATFORM " = " openshift" ]; then
451- echo -e " ${BLUE} Cleaning up generated files...${NC} "
452- rm -f " $OAUTH_ENV_FILE "
453- fi
396+ # Cleanup generated files
397+ echo -e " ${BLUE} Cleaning up generated files...${NC} "
398+ rm -f " $OAUTH_ENV_FILE "
454399
455400echo -e " ${YELLOW} Next steps:${NC} "
456- if [ " $PLATFORM " = " openshift" ]; then
457- if [[ -n " ${ROUTE_HOST} " ]]; then
458- echo -e " 1. Access the frontend via Route:"
459- echo -e " ${BLUE} https://${ROUTE_HOST}${NC} "
460- else
461- echo -e " 1. Access the frontend (fallback via port-forward):"
462- echo -e " ${BLUE} oc port-forward svc/frontend-service 3000:3000 -n ${NAMESPACE}${NC} "
463- echo -e " Then open: http://localhost:3000"
464- fi
401+ if [[ -n " ${ROUTE_HOST} " ]]; then
402+ echo -e " 1. Access the frontend via Route:"
403+ echo -e " ${BLUE} https://${ROUTE_HOST}${NC} "
465404else
466- echo -e " 1. Access the frontend via Ingress:"
467- echo -e " ${BLUE} http://${INGRESS_HOST}${NC} "
468- echo -e " (Add '127.0.0.1 ${INGRESS_HOST} ' to /etc/hosts for local access)"
469- echo -e " Or via port-forward:"
470- echo -e " ${BLUE} kubectl port-forward svc/frontend-service 3000:3000 -n ${NAMESPACE}${NC} "
405+ echo -e " 1. Access the frontend (fallback via port-forward):"
406+ echo -e " ${BLUE} oc port-forward svc/frontend-service 3000:3000 -n ${NAMESPACE}${NC} "
471407 echo -e " Then open: http://localhost:3000"
472408fi
473409echo -e " 2. Configure secrets in the UI (Runner/API keys, project settings)."
474410echo -e " Open the app and follow Settings → Runner Secrets."
475411echo -e " 3. Monitor the deployment:"
476- echo -e " ${BLUE}${CLI_CMD} get pods -n ${NAMESPACE} -w${NC} "
412+ echo -e " ${BLUE} oc get pods -n ${NAMESPACE} -w${NC} "
477413echo -e " 4. View logs:"
478- echo -e " ${BLUE}${CLI_CMD} logs -f deployment/backend-api -n ${NAMESPACE}${NC} "
479- echo -e " ${BLUE}${CLI_CMD} logs -f deployment/agentic-operator -n ${NAMESPACE}${NC} "
480- echo -e " 5 . Monitor sessions :"
481- echo -e " ${BLUE}${CLI_CMD} get agenticsessions -n ${NAMESPACE}${NC} "
414+ echo -e " ${BLUE} oc logs -f deployment/backend-api -n ${NAMESPACE}${NC} "
415+ echo -e " ${BLUE} oc logs -f deployment/agentic-operator -n ${NAMESPACE}${NC} "
416+ echo -e " 4 . Monitor RFE workflows :"
417+ echo -e " ${BLUE} oc get agenticsessions -n ${NAMESPACE}${NC} "
482418echo " "
483419
484420# Restore kustomization if we modified it
485421echo -e " ${BLUE} Restoring kustomization defaults...${NC} "
486- cd overlays/${OVERLAY}
422+ cd overlays/production
487423if [ " $NAMESPACE " != " ambient-code" ]; then
488424 kustomize edit set namespace ambient-code
489425fi
0 commit comments