Skip to content

Instantly share code, notes, and snippets.

@Eng-Fouad
Last active August 28, 2023 03:24
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Eng-Fouad/3adc188ddb4631a07d10b0481bde2070 to your computer and use it in GitHub Desktop.
Save Eng-Fouad/3adc188ddb4631a07d10b0481bde2070 to your computer and use it in GitHub Desktop.
Spring Boot Native with Mandrel
plugins {
id("com.bmuschko.docker-remote-api")
id("org.springframework.boot")
id("org.graalvm.buildtools.native")
java
id ("org.hibernate.orm")
}
group = "io.fouad"
version = "1.0"
repositories {
mavenCentral()
mavenLocal()
}
// project properties can be accessed via delegation
val springBootVersion: String by project
val testContainersVersion: String by project
dependencies {
implementation(platform(org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES))
implementation(platform("org.testcontainers:testcontainers-bom:${testContainersVersion}"))
implementation("org.springframework.boot:spring-boot-starter-web")
implementation("org.springframework.boot:spring-boot-starter-json")
implementation("org.springframework.boot:spring-boot-starter-security")
implementation("org.springframework.boot:spring-boot-starter-validation")
implementation("org.springframework.boot:spring-boot-starter-aop")
implementation("org.springframework.boot:spring-boot-starter-data-jpa")
implementation("org.springframework.boot:spring-boot-starter-data-redis")
implementation("org.springframework.security:spring-security-oauth2-resource-server")
implementation("org.springframework.security:spring-security-oauth2-jose")
testImplementation("org.projectlombok:lombok:1.18.28")
runtimeOnly("com.microsoft.sqlserver:mssql-jdbc")
compileOnly("org.projectlombok:lombok")
annotationProcessor("org.projectlombok:lombok:1.18.28")
annotationProcessor("org.hibernate.orm:hibernate-jpamodelgen:6.2.7.Final")
testImplementation("org.springframework.boot:spring-boot-starter-test")
testImplementation("org.springframework.boot:spring-boot-testcontainers")
testImplementation("org.apache.httpcomponents.client5:httpclient5:5.2.1") // necessary for TestRestTemplate
testImplementation("org.junit.platform:junit-platform-suite-engine:1.10.0")
testImplementation("org.junit.jupiter:junit-jupiter-engine:5.10.0")
testImplementation("org.hibernate.common:hibernate-commons-annotations:6.0.6.Final")
testImplementation("org.testcontainers:mssqlserver")
testImplementation("org.springframework.boot:spring-boot-devtools")
testCompileOnly("org.projectlombok:lombok")
testAnnotationProcessor("org.projectlombok:lombok:1.18.28")
}
hibernate {
enhancement {
enableLazyInitialization = true // Whether to incorporate lazy loading support into the enhanced bytecode.
enableDirtyTracking = true // Whether to incorporate dirty tracking into the enhanced bytecode.
enableAssociationManagement = true // Whether to add bidirectional association management into the enhanced bytecode
enableExtendedEnhancement = false
}
}
springBoot {
mainClass.set("io.fouad.backend.AppLauncher")
}
tasks.compileJava {
options.encoding = "UTF-8"
options.compilerArgs = listOf("-parameters", "-Xdoclint:none", "-Xlint:all", "-Xlint:-exports",
"-Xlint:-serial", "-Xlint:-try", "-Xlint:-requires-transitive-automatic",
"-Xlint:-requires-automatic", "-Xlint:-missing-explicit-ctor", "-Xlint:-processing")
}
tasks.compileTestJava {
options.encoding = "UTF-8"
options.compilerArgs = listOf("-parameters", "-Xdoclint:none", "-Xlint:all", "-Xlint:-exports",
"-Xlint:-serial", "-Xlint:-try", "-Xlint:-requires-transitive-automatic",
"-Xlint:-requires-automatic", "-Xlint:-missing-explicit-ctor", "-Xlint:-processing")
}
java {
toolchain {
//languageVersion.set(JavaLanguageVersion.of(20))
}
}
graalvmNative {
binaries {
named("main") {
javaLauncher.set(javaToolchains.launcherFor {
languageVersion.set(JavaLanguageVersion.of(20))
})
buildArgs.add("--initialize-at-build-time=org.slf4j.LoggerFactory,ch.qos.logback --initialize-at-run-time=io.netty.handler.ssl.BouncyCastleAlpnSslUtils")
}
}
}
tasks.test {
useJUnitPlatform()
}
val prepareDockerFiles by tasks.creating(Copy::class) {
from(rootProject.projectDir) {
include("src/", "gradle/", "gradle.properties", "gradlew", "settings.gradle.kts", "build.gradle.kts")
}
into("${project.projectDir}/build/docker")
}
tasks.create("buildNativeImage", com.bmuschko.gradle.docker.tasks.image.DockerBuildImage::class) {
group = "fouad"
//noCache.set(true)
dependsOn(prepareDockerFiles)
dockerFile.set(file("${project.projectDir}/build/docker/src/main/docker/Dockerfile"))
images.add("fouad/${project.name}:${project.version}")
platform.set("linux/amd64")
remove.set(true) // remove intermediate containers after a successful build
finalizedBy(":saveNativeRunnerAsFile")
}
tasks.create("saveDockerImageAsFile", com.bmuschko.gradle.docker.tasks.image.DockerSaveImage::class) {
group = "fouad"
images.add("fouad/${project.name}:${project.version}")
destFile.set(file("build/images/${project.name}-${project.version}.docker.image.tar"))
useCompression.set(true)
}
val createTempContainer by tasks.creating(com.bmuschko.gradle.docker.tasks.container.DockerCreateContainer::class) {
imageId.set("fouad/${project.name}:${project.version}")
}
val saveNativeRunnerAsFile by tasks.creating(com.bmuschko.gradle.docker.tasks.container.DockerCopyFileFromContainer::class) {
group = "fouad"
dependsOn(createTempContainer)
targetContainerId(createTempContainer.containerId)
remotePath.set("/code/build/native/nativeCompile/${project.name}")
hostPath.set("${project.projectDir}/build/${project.name}-${project.version}")
finalizedBy(":removeTempContainer")
}
tasks.create("removeTempContainer", com.bmuschko.gradle.docker.tasks.container.DockerRemoveContainer::class) {
dependsOn(saveNativeRunnerAsFile)
targetContainerId(saveNativeRunnerAsFile.containerId)
force.set(true)
}
# Based on RedHat OS
FROM registry.access.redhat.com/ubi8/ubi-minimal:8.8-1037
# Variables
ARG JAVA_VERSION=20
ARG MANDREL_VERSION=23.0.1.2-Final
ARG MANDREL_ARCH=amd64
ARG MANDREL_FILE_NAME=mandrel-java$JAVA_VERSION-linux-$MANDREL_ARCH-$MANDREL_VERSION.tar.gz
ARG MANDREL_URL=https://github.com/MANDREL/mandrel/releases/download/mandrel-$MANDREL_VERSION/$MANDREL_FILE_NAME
# Use root
USER root
# Set environemnt variables
ENV LANG=en_US.UTF-8 LANGUAGE=en_US:en LC_ALL=en_US.UTF-8
ENV JAVA_HOME=/opt/mandrel MANDREL_HOME=/opt/mandrel
ENV PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/opt/mandrel/bin
# Install required packages for the build
RUN microdnf --setopt=install_weak_deps=0 --setopt=tsflags=nodocs install -y tar gzip gcc glibc-devel zlib-devel shadow-utils unzip gcc-c++ glibc-langpack-en fontconfig freetype-devel findutils wget && rpm -q tar gzip gcc glibc-devel zlib-devel shadow-utils unzip gcc-c++ glibc-langpack-en fontconfig freetype-devel findutils wget
# Download Mandrel JDK
RUN wget $MANDREL_URL -O /tmp/$MANDREL_FILE_NAME
RUN mkdir -p /opt/mandrel && tar xzf /tmp/$MANDREL_FILE_NAME -C /opt/mandrel --strip-components=1 && rm -Rf /tmp/$MANDREL_FILE_NAME
# Copy gradle wrapper files
COPY gradle/ /code/gradle/
COPY gradlew /code/gradlew
# Set working directory
WORKDIR /code/
# Download gradle (to cache it)
RUN /code/gradlew --no-daemon
# Copy gradle config files
COPY build.gradle.kts /code/build.gradle.kts
COPY settings.gradle.kts /code/settings.gradle.kts
COPY gradle.properties /code/gradle.properties
# Download dependencies (to cache them)
RUN /code/gradlew dependencies --refresh-dependencies --no-daemon
# Copy source folder
COPY src/ /code/src/
# Compile the native executable file
RUN /code/gradlew nativeCompile -x test --no-daemon
# Set the entry point
ENTRYPOINT ["/code/build/native/nativeCompile/fouad-backend"]
org.gradle.logging.level=INFO
dockerPluginVersion=9.3.2
hibernatePluginVersion=6.2.7.Final
graalvmNativeBuildPluginVersion=0.9.24
testContainersVersion=1.19.0
springBootVersion=3.1.3
pluginManagement {
val dockerPluginVersion: String by settings
val hibernatePluginVersion: String by settings
val graalvmNativeBuildPluginVersion: String by settings
val springBootVersion: String by settings
repositories {
mavenLocal()
mavenCentral()
gradlePluginPortal()
}
plugins {
id("com.bmuschko.docker-remote-api") version dockerPluginVersion
id("org.hibernate.orm") version hibernatePluginVersion
id("org.graalvm.buildtools.native") version graalvmNativeBuildPluginVersion
id("org.springframework.boot") version springBootVersion
}
}
rootProject.name = "fouad-backend"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment