Categorygithub.com/ozankasikci/dockerfile-generator
modulepackage
1.0.0
Repository: https://github.com/ozankasikci/dockerfile-generator.git
Documentation: pkg.go.dev

# README

dfg - Dockerfile Generator

dfg is both a go library and an executable that produces valid Dockerfiles using various input channels.

Build Status GoDoc Coverage Status Go Report Card Mentioned in Awesome Go

Table of Contents

Overview

dfg is a Dockerfile generator that accepts input data from various sources, produces and redirects the generated Dockerfile to an output target such as a file or stdout.

It is especially useful for generating Dockerfile instructions conditionally since Dockerfile language has no control flow logic.

Installation

Installing as an Executable

  • MacOS
curl -o dfg -L https://github.com/ozankasikci/dockerfile-generator/releases/download/v0.1.0/dfg_v0.1.0_darwin_amd64
chmod +x dfg && sudo mv dfg /usr/local/bin
  • Linux
curl -o dfg -L https://github.com/ozankasikci/dockerfile-generator/releases/download/v0.1.0/dfg_v0.1.0_linux_amd64
chmod +x dfg && sudo mv dfg /usr/local/bin
  • Windows
curl -o dfg.exe -L https://github.com/ozankasikci/dockerfile-generator/releases/download/v0.1.0/dfg_v0.1.0_windows_amd64.exe

Installing as a Library

go get -u github.com/ozankasikci/dockerfile-generator

Getting Started

Using dfg as an Executable

Available commands:

dfg generate --input path/to/yaml --out Dockerfile generates a file named Dockerfile

dfg generate --input path/to/yaml --target-field ".server.dockerfile" --out Dockerfile generates a file named Dockerfile reading the .server.dockerfile field of the YAML file.

dfg generate --help lists available flags

Using dfg as a Library

When using dfg as a go library, you need to pass a []dfg.Stage slice as data. This approach enables and encourages multi staged Dockerfiles. Dockerfile instructions will be generated in the same order as in the []dfg.Instruction slice.

Some Instructions accept a runForm field which specifies if the Instruction should be run in the shell form or the exec form. If the runForm is not specified, it will be chosen based on Dockerfile best practices.

For detailed usage example please see Library Usage Example

Examples

Single YAML File per Dockerfile Example

stages:
  final:
    - from:
        image: kstaken/apache2
    - run:
        runForm: shell
        params:
          - apt-get update &&
          - apt-get install -y
          - php5
          - libapache2-mod-php5 &&
          - apt-get clean &&
          - rm -rf /var/lib/apt/lists/*
    - cmd:
        params:
          - /usr/sbin/apache2
          - -D
          - FOREGROUND

Use dfg as binary:

dfg generate -i ./example-input-files/apache-php.yaml --stdout

Or as a library

data, err := dfg.NewDockerFileDataFromYamlFile("./example-input-files/apache-php.yaml")
tmpl := dfg.NewDockerfileTemplate(data)
err = tmpl.Render(output)

Output

FROM kstaken/apache2
RUN apt-get update && apt-get install -y php5 libapache2-mod-php5 && apt-get clean && rm -rf /var/lib/apt/lists/*
CMD ["/usr/sbin/apache2", "-D", "FOREGROUND"]

YAML File Example With Multiple Configurations (Allows using an existing YAML file)

someConfig:
  key: value
serverConfig:
  dockerfile:
    stages:
      final:
        - from:
            image: kstaken/apache2
        - run:
            runForm: shell
            params:
              - apt-get update &&
              - apt-get clean &&
              - rm -rf /var/lib/apt/lists/*

Use dfg as binary:

dfg generate -i ./example-input-files/test-input-with-target-key-6.yaml --target-field ".serverConfig.dockerfile" --stdout

Or as a library

data, err := dfg.NewDockerFileDataFromYamlField("./example-input-files/test-input-with-target-key-6.yaml", ".serverConfig.dockerfile")
tmpl := dfg.NewDockerfileTemplate(data)
err = tmpl.Render(output)

Output

FROM kstaken/apache2
RUN apt-get update && apt-get clean && rm -rf /var/lib/apt/lists/*

Library Usage Example

package main

import dfg "github.com/ozankasikci/dockerfile-generator"

func main() {
	data := &dfg.DockerfileData{
		Stages: []dfg.Stage{
			// Stage 1 - Builder Image
			// An instruction is just an interface, so you can pass custom structs as well
			[]dfg.Instruction{
				dfg.From{
					Image: "golang:1.7.3", As: "builder",
				},
				dfg.User{
					User: "ozan",
				},
				dfg.Workdir{
					Dir: "/go/src/github.com/ozankasikci/dockerfile-generator/",
				},
				dfg.RunCommand{
					Params: []string{"go", "get", "-d", "-v", "golang.org/x/net/html"},
				},
				dfg.CopyCommand{
					Sources: []string{"app.go"}, Destination: ".",
				},
				dfg.RunCommand{
					Params: []string{"CGO_ENABLED=0", "GOOS=linux", "go", "build", "-a", "-installsuffix", "cgo", "-o", "app", "."},
				},
			},
			// Stage 2 - Final Image
			[]dfg.Instruction{
				dfg.From{
					Image: "alpine:latest", As: "final",
				},
				dfg.RunCommand{
					Params: []string{"apk", "--no-cache", "add", "ca-certificates"},
				},
				dfg.User{
					User: "root", Group: "admin",
				},
				dfg.Workdir{
					Dir: "/root/",
				},
				dfg.CopyCommand{
					From: "builder", Sources: []string{"/go/src/github.com/ozankasikci/dockerfile-generator/app"}, Destination: ".",
				},
				dfg.Cmd{
					Params: []string{"./app"},
				},
			},
		},
	}
	tmpl := dfg.NewDockerfileTemplate(data)
	
	// write to a file
	file, err := os.Create("Dockerfile")
	err = tmpl.Render(file)
	
	// or write to stdout
	err = tmpl.Render(os.Stdout)
}

Output

FROM golang:1.7.3 as builder
USER ozan
WORKDIR /go/src/github.com/ozankasikci/dockerfile-generator/
RUN go get -d -v golang.org/x/net/html
COPY app.go .
RUN CGO_ENABLED=0 GOOS=linux go build -a -installsuffix cgo -o app .

FROM alpine:latest as final
RUN apk --no-cache add ca-certificates
USER root:admin
WORKDIR /root/
COPY --from=builder /go/src/github.com/ozankasikci/dockerfile-generator/app .
CMD ["./app"]

TODO

  • Add reading Dockerfile data from an existing yaml file support
  • Implement json file input channel
  • Implement stdin input channel
  • Implement toml file input channel

# Packages

No description provided by the author

# Functions

NewDockerFileDataFromYamlField reads a YAML file and tries to extract Dockerfile data from the specified targetField option, examples: --target-field ".dev.dockerfileConfig" --target-field ".serverConfigs[0].docker.server".
NewDockerFileDataFromYamlFile reads a file and return a *DockerfileData.
NewDockerfileTemplate return a new NewDockerfileTemplate instance.

# Constants

CmdDefaultRunForm is the default RunForm for Cmd.
EntrypointDefaultRunForm is the default RunForm for Entrypoint.
ExecForm is essentially a json array of string, e.g.
RunCommandDefaultRunForm is the default RunForm for RunCommand.
ShellForm is the form of a usual terminal command, e.g.

# Structs

Arg represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#arg.
Cmd represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#cmd.
CopyCommand represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#copy.
DockerfileData struct can hold multiple stages for a multi-staged Dockerfile Check https://docs.docker.com/develop/develop-images/multistage-build/ for more information.
DockerfileDataYaml is used to decode yaml data.
DockerfileTemplate defines the template struct that generates Dockerfile output.
Entrypoint represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#entrypoint.
EnvVariable represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#env.
From represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#from.
HealthCheck represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#healthcheck.
Label represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#from.
Onbuild represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#onbuuild.
RunCommand represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#run.
Shell represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#shell.
User represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#user.
Volume represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#volume.
Workdir represents a Dockerfile instruction, see https://docs.docker.com/engine/reference/builder/#workdir.

# Interfaces

Instruction represents a Dockerfile instruction, e.g.

# Type aliases

Params is struct that supports rendering exec and shell form string.
RunForm specifies in which form the instruction string should be constructed.
Stage is a set of instructions, the purpose is to keep the order of the given instructions and generate a Dockerfile using the output of these instructions.