build.gradle.kts 3.1 KB
plugins {
    alias(libs.plugins.kotlin.jvm)
}

description = "vibe_erp reference plug-in: a hello-world printing-shop customer expressed entirely through api.v1."

// Marker that the root build.gradle.kts uses to apply the plug-in dependency
// rule (no `:platform:*`, no `:pbc:*`, only `:api:api-v1`).
extra["vibeerp.module-kind"] = "plugin"

java {
    toolchain {
        languageVersion.set(JavaLanguageVersion.of(21))
    }
}

kotlin {
    jvmToolchain(21)
}

// CRITICAL: this plug-in may depend on api/api-v1 ONLY. The root
// build.gradle.kts enforces this; adding `:platform:*` or `:pbc:*` here
// will fail the build with an architectural-violation error.
//
// This restriction is the entire point of having a "reference plug-in"
// in the repo: it is the executable proof that the framework can express
// a real customer's workflow using only the public plug-in API. If this
// plug-in needs more than api.v1 offers, the right answer is to grow
// api.v1 deliberately, NOT to reach into platform internals.
dependencies {
    implementation(project(":api:api-v1"))
    implementation(libs.kotlin.stdlib)
    compileOnly(libs.pf4j) // for @Extension annotations; provided by host at runtime
}

// Package this as a "fat plug-in JAR" — PF4J expects a single JAR with the
// plug-in's manifest in META-INF and all of its (non-host) dependencies
// inside it. Since this plug-in only depends on api.v1 (which is provided by
// the host) and the Kotlin stdlib (also provided), the resulting JAR is tiny.
tasks.jar {
    duplicatesStrategy = DuplicatesStrategy.EXCLUDE
    manifest {
        attributes(
            "Plugin-Id" to "printing-shop",
            "Plugin-Version" to project.version,
            "Plugin-Provider" to "vibe_erp reference",
            "Plugin-Class" to "org.vibeerp.reference.printingshop.PrintingShopPlugin",
            "Plugin-Description" to "Reference printing-shop customer plug-in",
            "Plugin-Requires" to "1.x",
        )
    }
    // src/main/resources is already on the resource path automatically; no
    // need for an explicit `from(...)` block — that was causing the
    // "duplicate plugin.yml" error because Gradle would try to copy it twice.
}

// Dev convenience: stage the built plug-in JAR into the repository's
// `plugins-dev/` directory so `./gradlew :distribution:bootRun` (which
// reads `vibeerp.plugins.directory: ./plugins-dev` from
// application-dev.yaml) finds it on boot. Older copies are deleted
// first so renaming the JAR (e.g. on a version bump) does not leave
// PF4J trying to load two copies of the same plug-in.
val installToDev by tasks.registering(Copy::class) {
    dependsOn(tasks.jar)
    from(layout.buildDirectory.dir("libs"))
    into(rootProject.layout.projectDirectory.dir("plugins-dev"))
    include("plugin-printing-shop-*.jar")
    doFirst {
        // Wipe any previous copies to avoid stale-version collisions.
        val target = rootProject.layout.projectDirectory.dir("plugins-dev").asFile
        target.mkdirs()
        target.listFiles { _, name -> name.startsWith("plugin-printing-shop-") && name.endsWith(".jar") }
            ?.forEach { it.delete() }
    }
}