palantir / gradle-docker

a Gradle plugin for orchestrating docker builds and pushes.
Apache License 2.0
747 stars 158 forks source link

composeup environment required #650

Closed vickyleu closed 1 year ago

vickyleu commented 1 year ago

What happened?

dockerCompose only have dockerComposeFile or Template configure,but i want adding docker compose environment for docker-compose.yml

dockerCompose { setDockerComposeFile("docker-compose.yaml") }

What did you want to happen?

open  class DockerComposeUpWithEnvironment : DockerComposeUp() {
    @Input
    lateinit var environments:HashMap<String,Any>
    @TaskAction
    override fun run() {
        execWithErrorMessage(project) {
            it.executable = "docker-compose"
            it.args("-f", dockerComposeFile!!.absolutePath, "up", "-d")
            if(::environments.isInitialized){
                environments.entries.forEach{entry->
                    it.environment(entry.key, entry.value)
                }
            }
        }
    }
    companion object {
        fun execWithErrorMessage(project: Project, execSpecAction: (ExecSpec) -> Unit) {
            val commandLine = mutableListOf<String>()
            val output = ByteArrayOutputStream()
            val execResult = project.exec {
                execSpecAction(this)
                this.isIgnoreExitValue = true
                this.standardOutput = TeeOutputStream(System.out, output)
                this.errorOutput = TeeOutputStream(System.err, output)
                commandLine.addAll(this.commandLine)
            }
            if (execResult.exitValue != 0) {
                throw RuntimeException(
                    "The command '$commandLine' failed with exit code ${execResult.exitValue}. Output:\n" +
                            output.toString(StandardCharsets.UTF_8.name())
                )
            }
        }
    }
}

so i can use

environments = hashMapOf<String, Any>(
        "app_image_name" to projectVersion,
        "app_port" to appPort.toInt(),
        "DATABASE_NAME" to mysqlDatabase,
        "MYSQL_ALLOW_EMPTY_PASSWORD" to false,
        "ROOT_PASSWORD" to mysqlPassword,
    )

now i can use gradle.propeties

app_image_name=com.ohhhhhhhhh.nnnnooooo/apppp:0.0.1
app_port=8080

val app_image_name: String by project
val app_port: String by project
services:
  app:
    image: ${app_image_name}
    ports:
      - ${app_port}:8080
    networks: [app-network]
    container_name: ${COMPOSE_PROJECT_NAME}_app
vickyleu commented 1 year ago

envs.env and gradle.properties are duplicated, there is no need to maintain two places

vickyleu commented 1 year ago

If you don't want to manually set the environments, you can even set the prefabricated prefix in gradle.properties, such as compose_service_name_key=value, and the environments are directly changed to the specified gradle.properties file, and all uncommented properties of gradle.properties are read in the code.

val lines = file(filePath). readLines()

for ((index, line) in lines. withIndex()) 
 // Ignore lines that start with '#' (after trimming leading whitespace)
    if (line. trimStart(). startsWith("#")) {continue}
 // Ignore lines that not start with 'compose_'
    if (!line. trimStart(). startsWith("compose_")) {continue}
it.environment(entry.key.replace("compose_", ""), entry.value)

gradle.properties

compose_app_image_name=abcdefg
compose_ppa_image_name=dfjdsfjsdf
services:
  app:
    image: ${app_image_name}
    ports:
      - ${app_port}:8080
  ppa:
    image: ${ppa_image_name}
    ports:
      - ${ppa_port}:8080
vickyleu commented 1 year ago

due to the lack of maintenance on the current issue, it has been closed. The solution can be found in the comments.