# Build and publish images with docker/podman

## SYNOPSIS

```gradle

plugins {
    id 'org.implab.gradle-container'
}

container {
    // if you want to use podman
    cliCmd = "podman"
}

configurations {
    app
}

dependencies {
    // the application that needs to be built and packed
    app project(":server")
}

// add custom task to copy application files
// to the docker build context.
task copyApp(type: Copy) {
    processResources.dependsOn it

    into container.contextDirectory.dir("root/opt/myapp")
    from configurations.app
}

task printVersion {
    doLast {
        println "tag: ${buildImage.imageTag.get()}"
        println "archive: ${saveImage.archiveFileName.get()}"
    }
}


```

## Description

This plugin is a simple wrapper around docker CLI. All the image
building process is delegated to the `Dockerfile` which will run
in the prepared build context.

## Project structure

* `build/` - this folder will be created during build, it can be useful while
  solving Dockerfile problems
  * `context/` - the build context where `docker build` command will run.
  * `imageid` - the file storing the id of the image has been built.
  * `image-name-1.2.3.tgz` - the exported image if `saveImage` has been executed.
* `src`
  * `main` - the source files which will be copied to the build context.

## Global properties

There are several global properties recognized by this plugin in the project.
These properties affect images naming and publication and they are useful in
multi-project environment.

`imagesAuthority` - the registry where the image should be published.
for example `docker.io`

`imagesGroup` - the path to the image in the repository.

`containerCli` - the command line cli, this property corresponds to
`container.cliCmd` in the project.

Properties defined in the project takes precedence over global properties.

## Image names

```gradle
plugins {
    id "org.implab.gradle-container"
}

container {
    // image authority, the repository for your images
    // defaults to global imagesAuthority property or none
    imageAuthority = "my.registry.org"

    // the image path 
    // defaults to global imagesGroup property or none
    imageGroup = "my/project"

    // the name of the image
    // defaults to project.name
    imageLocalName = "foo"
}

// provider for imageName, returns ImageName object
// ImageName consists of "{imageAuthority}/{imageGroup}/{imageLocalName}"
def imageNameProvider = container.imageName
```

## Tasks

Some tasks support passing additional options as additional command line
parameters. These task has the property `options` and some additional methods.

| Property | Description |
|--|--|
| `options` | A list of additional arguments passed to `docker build` command. |

| Method | Description |
|---|---|
| `option(String)` | Adds option to `options`. |
| `option(Closure)` | Converts the parameter to provider and adds it to `options`. |
| `option(Callable)` | Converts the parameter to provider and adds it to `options`. |
| `options(String...)` | Adds specified options to `options`. |
| `options(Closure)`| Converts the parameter to provider and adds it to `options`. |
| `options(Callable)`| Converts the parameter to provider and adds it to `options` |

### buildImage

`type: BuildImage`

The task builds the image. Wrapper around the `docker build` command.

| Property | Description |
|---|---|
| `contextDirectory` | A Dockerfile context directory. Set to `container.context`. |
| `buildArgs` | A dictionary with environment variables which are set during build. |
| `buildTarget` | A target image for the multi-stage builds. Defaults to none. |
| `imageName` | A name (tag) for the resulting image. |
| `imageIdFIle` | Output file name where image ref will be written. |

This task also supports additional command line options.

### saveImage

`type: SaveImage`

The task exports image as the .tar archive.

| Property | Description |
|-|-|
| `archiveFileName` | The file name of the bundle archive, defaults to `{archiveBaseName}-{archiveVersion}-{archiveClassifier}.{archiveExtension}`.|
| `archiveBaseName` | The base name of the archive, defaults to `{project.group}-{project.name}`. |
| `archiveVersion` | The archive version, defaults to `{project.version}`. |
| `exportImages` | A set of image names to include in the bundle. |

| Method | Description |
|-|-|
| `imageRefs(FileCollection)` | Adds a set of files with image refs to add to the bundle. |
| `imageRef(File)` | Adds an image name from the file with image reference. |

### pushImage

The task pushes the image to the remote repository (imageAuthority).

[Since v1.2] This task also supports additional command line options. You can use them to
push all tags for the image.

```gradle
pushImage {
    option "--all-tags"
}
```

### processResources

The copy task, it prepares the build context. Use this task to customize
the build context.

### tagImage

`type: TagImage`

since: 1.1

```gradle
task tagLatest(type: TagImage) {
    pushImage.dependsOn it

    srcImage = container.imageName

    tags.add(container.imageName.map { it.tag("latest") })
}

```

| Property | Description |
|-|-|
| `srcImage` | The source image name to add tag to. |
| `tags` | The set of tags to add to the image. |

## See also

* Creating [compose](compose.md) project
* Creating [bundle](bundle.md) project

## Changes

### 1.2

Added `org.implab.gradle-container-base`, `org.implab.gradle-container-compose`
plugins.

* `org.implab.gradle-container-base` registers base extension and task types.
* `org.implab.gradle-container-compose` registers conventional tasks.

### 1.1

Warning! This version isn't fully backward compatible with 1.0 version.

* Added `TagImage` task type
* `ImageTag` class is replaced with `ImageName` class
* `BuildImage`, `PushImage` tasks are now accepting only `imageName` property
* Added `imageName`, `imageShortName`, `imageTag` properties to `container` extension

### 1.0

Initial release. Default tasks to build and publish container images.
