| name | guidewire-ci-integration |
| description | Configure CI/CD pipelines for Guidewire InsuranceSuite development.
Use when setting up automated builds, tests, and deployments for Guidewire projects.
Trigger with phrases like "guidewire ci", "guidewire pipeline",
"automated testing guidewire", "jenkins guidewire", "github actions guidewire".
|
| allowed-tools | Read, Write, Edit, Bash(gradle:*), Bash(git:*), Grep |
| version | 1.0.0 |
| license | MIT |
| author | Jeremy Longshore <jeremy@intentsolutions.io> |
Guidewire CI Integration
Overview
Configure continuous integration and continuous deployment pipelines for Guidewire InsuranceSuite projects using GitHub Actions, Jenkins, or Azure DevOps.
Prerequisites
- Git repository with Guidewire project
- CI/CD platform access (GitHub Actions, Jenkins, or Azure DevOps)
- Guidewire Cloud Console access for deployment credentials
- JDK 17 and Gradle available in CI environment
Instructions
Step 1: GitHub Actions Workflow
name: Guidewire CI/CD
on:
push:
branches: [main, develop]
pull_request:
branches: [main]
env:
JAVA_VERSION: '17'
GRADLE_VERSION: '8.5'
GW_TENANT_ID: ${{ secrets.GW_TENANT_ID }}
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set up JDK
uses: actions/setup-java@v4
with:
java-version: ${{ env.JAVA_VERSION }}
distribution: 'temurin'
cache: 'gradle'
- name: Grant Gradle execute permission
run: chmod
[, ]
Step 2: Jenkins Pipeline
// Jenkinsfile
pipeline {
agent {
docker {
image 'eclipse-temurin:17-jdk'
args '-v gradle-cache:/root/.gradle'
}
}
environment {
GRADLE_OPTS = '-Dorg.gradle.daemon=false'
GW_TENANT_ID = credentials('gw-tenant-id')
}
options {
timeout(time: 1, unit: 'HOURS')
disableConcurrentBuilds()
buildDiscarder(logRotator(numToKeepStr: '10'))
}
stages {
stage('Checkout') {
steps {
checkout scm
}
}
stage('Build') {
steps {
sh 'chmod +x gradlew'
sh './gradlew clean build'
}
post {
success {
archiveArtifacts artifacts: 'build/libs/*.jar', fingerprint: true
}
}
}
stage('Code Quality') {
parallel {
stage('Gosu Check') {
steps {
sh './gradlew gosucheck'
}
}
stage('Static Analysis') {
steps {
sh './gradlew spotbugsMain'
}
post {
always {
recordIssues(tools: [spotBugs(pattern: '**/build/reports/spotbugs/*.xml')])
}
}
}
}
}
stage('Test') {
steps {
sh './gradlew test integrationTest'
}
post {
always {
junit '**/build/test-results/**/*.xml'
publishHTML([
reportDir: 'build/reports/tests/test',
reportFiles: 'index.html',
reportName: 'Test Report'
])
}
}
}
stage('Security Scan') {
steps {
sh './gradlew dependencyCheckAnalyze'
}
post {
always {
dependencyCheckPublisher pattern: '**/dependency-check-report.xml'
}
}
}
stage('Deploy Sandbox') {
when {
branch 'develop'
}
environment {
GW_CLIENT_ID = credentials('gw-sandbox-client-id')
GW_CLIENT_SECRET = credentials('gw-sandbox-client-secret')
}
steps {
sh './scripts/deploy-to-cloud.sh sandbox'
sh './gradlew smokeTest -Penv=sandbox'
}
}
stage('Deploy Production') {
when {
branch 'main'
}
environment {
GW_CLIENT_ID = credentials('gw-prod-client-id')
GW_CLIENT_SECRET = credentials('gw-prod-client-secret')
}
steps {
input message: 'Deploy to production?', ok: 'Deploy'
sh './scripts/deploy-to-cloud.sh production'
}
}
}
post {
always {
cleanWs()
}
failure {
emailext(
subject: "Build Failed: ${env.JOB_NAME} [${env.BUILD_NUMBER}]",
body: "Check console output at ${env.BUILD_URL}",
recipientProviders: [developers()]
)
}
}
}
Step 3: Gradle Build Configuration
// build.gradle - CI-optimized configuration
plugins {
id 'com.guidewire.gradle' version '10.12.0'
id 'org.owasp.dependencycheck' version '9.0.0'
id 'com.github.spotbugs' version '6.0.0'
id 'jacoco'
}
java {
toolchain {
languageVersion = JavaLanguageVersion.of(17)
}
}
// Gosu compilation checks
tasks.named('gosucheck') {
reports {
xml.required = true
html.required = true
}
}
// Test configuration
test {
useJUnitPlatform()
maxParallelForks = Runtime.runtime.availableProcessors().intdiv(2) ?: 1
testLogging {
events 'passed', 'skipped', 'failed'
showStandardStreams = false
exceptionFormat = 'full'
}
finalizedBy jacocoTestReport
}
// Integration tests
tasks.register('integrationTest', Test) {
description = 'Runs integration tests'
group = 'verification'
testClassesDirs = sourceSets.integrationTest.output.classesDirs
classpath = sourceSets.integrationTest.runtimeClasspath
shouldRunAfter test
}
// Code coverage
jacocoTestReport {
dependsOn test
reports {
xml.required = true
html.required = true
}
}
jacocoTestCoverageVerification {
violationRules {
rule {
limit {
minimum = 0.7 // 70% coverage minimum
}
}
}
}
// Security scanning
dependencyCheck {
formats = ['HTML', 'XML', 'JSON']
failBuildOnCVSS = 7.0
suppressionFile = 'config/dependency-check-suppressions.xml'
}
// SpotBugs configuration
spotbugs {
effort = 'max'
reportLevel = 'medium'
excludeFilter = file('config/spotbugs-exclude.xml')
}
// CI-specific tasks
tasks.register('ci') {
description = 'Runs all CI checks'
group = 'verification'
dependsOn 'build', 'gosucheck', 'test', 'integrationTest',
'jacocoTestCoverageVerification', 'dependencyCheckAnalyze'
}
Step 4: Test Utilities
// Test utilities for CI
package gw.test.ci
uses gw.testharness.v3.PLTestCase
uses gw.api.database.Query
class CITestBase extends PLTestCase {
// Skip slow tests in CI
static property get SkipSlowTests() : boolean {
return System.getenv("CI") == "true" &&
System.getenv("RUN_SLOW_TESTS") != "true"
}
// Database health check
static function verifyDatabaseConnection() : boolean {
try {
var count = Query.make(Account).select().Count
return true
} catch (e : Exception) {
return false
}
}
// Clean test data
override function beforeClass() {
super.beforeClass()
cleanupTestData()
}
protected function cleanupTestData() {
// Remove test accounts created by previous runs
Query.make(Account)
.compare(Account#AccountNumber, StartsWith, "TEST-")
.select()
.each(\account -> {
gw.transaction.Transaction.runWithNewBundle(\bundle -> {
bundle.delete(bundle.add(account))
})
})
}
}
Step 5: Deployment Script
#!/bin/bash
set -e
ENV=${1:-sandbox}
echo "=== Deploying to Guidewire Cloud ($ENV) ==="
if [[ "$ENV" != "sandbox" && "$ENV" != "production" ]]; then
echo "Invalid environment: $ENV"
exit 1
fi
TOKEN=$(curl -s -X POST "${GW_HUB_URL}/oauth/token" \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=client_credentials&client_id=${GW_CLIENT_ID}&client_secret=${GW_CLIENT_SECRET}" \
| jq -r '.access_token')
if [ -z "$TOKEN" ] || [ "$TOKEN" == "null" ]; then
echo "Failed to obtain access token"
exit 1
fi
echo "Deploying configuration package..."
DEPLOYMENT_RESPONSE=$(curl -s -X POST "${GW_API_URL}/deployment/v1/packages" \
-H "Authorization: Bearer ${TOKEN}" \
-H "Content-Type: application/zip" \
--data-binary @build/libs/configuration-package.zip)
DEPLOYMENT_ID=$( | jq -r )
;
STATUS=$(curl -s \
-H \
| jq -r )
[ == ];
[ == ];
1
30
Output
- GitHub Actions workflow file
- Jenkins pipeline configuration
- Gradle build with CI tasks
- Test utilities for CI environment
- Cloud deployment script
Error Handling
| Error | Cause | Solution |
|---|
| Build timeout | Long-running tests | Increase timeout or parallelize |
| Database connection failed | Service not ready | Add health check wait |
| Deployment failed | Invalid package | Check build artifacts |
| Test flakiness | Race conditions | Add proper test isolation |
Resources
Next Steps
For deployment strategies, see guidewire-deploy-integration.