hub golang example go docker dockerfile docker-api

golang - Construir Docker Image From Go Code



docker sdk golang (3)

Intentando construir una imagen Docker usando las API Docker y Docker Go: https://github.com/docker/engine-api/

Ejemplo de código:

package main import ( "fmt" "github.com/docker/engine-api/client" "github.com/docker/engine-api/types" "golang.org/x/net/context" ) func main() { defaultHeaders := map[string]string{"User-Agent": "engine-api-cli-1.0"} cli, err := client.NewClient("unix:///var/run/docker.sock", "v1.22", nil, defaultHeaders) if err != nil { panic(err) } fmt.Print(cli.ClientVersion()) opt := types.ImageBuildOptions{ CPUSetCPUs: "2", CPUSetMems: "12", CPUShares: 20, CPUQuota: 10, CPUPeriod: 30, Memory: 256, MemorySwap: 512, ShmSize: 10, CgroupParent: "cgroup_parent", Dockerfile: "dockerSrc/docker-debug-container/Dockerfile", } _, err = cli.ImageBuild(context.Background(), nil, opt) if err == nil || err.Error() != "Error response from daemon: Server error" { fmt.Printf("expected a Server Error, got %v", err) }

  1. Carpeta existe en la ruta de compilación
  2. Intento relativo y camino absoluto
  3. Sin enlaces suaves en el camino
  4. probado la misma carpeta para archivos binarios y Docker
  5. Docker construye obras
  6. y un montón de otras cosas

El error es siempre el mismo:

Error response from daemon: Cannot locate specified Dockerfile: dockerSrc/docker-debug-container/Dockerfile

o

Error response from daemon: Cannot locate specified Dockerfile: Dockerfile

Otra opción era usar RemoteContext que parece que funciona, pero esto está bien solo para los archivos docker totalmente independientes ... y no para los que tienen "presencia local de archivos"

Actualización: Intenté pasar tar como buffer, pero lo mismo:

dockerBuildContext, err := os.Open("<path to>/docker-debug- container/docker-debug-container.tar") defer dockerBuildContext.Close() opt := types.ImageBuildOptions{ Context: dockerBuildContext, CPUSetCPUs: "2", CPUSetMems: "12", CPUShares: 20, CPUQuota: 10, CPUPeriod: 30, Memory: 256, MemorySwap: 512, ShmSize: 10, CgroupParent: "cgroup_parent", // Dockerfile: "Dockerfile", } _, err = cli.ImageBuild(context.Background(), nil, opt)


@Mangirdas: mirar una pantalla lo suficiente ayuda, al menos en mi caso. He estado atrapado con el mismo problema desde hace un tiempo. Tuviste razón en usar el archivo tar (tu segundo ejemplo). Si miras el documento API aquí https://docs.docker.com/engine/reference/api/docker_remote_api_v1.24/#/build-image-from-a-dockerfile , puedes ver que espera un tar. Lo que realmente me ayudó fue buscar otras implementaciones del cliente, perl y ruby ​​en mi caso. Ambos crean un alquitrán sobre la marcha cuando se les pide que construyan una imagen desde un directorio. De todos modos, solo necesitas poner tu dockerBuildContext en otro lugar (mira cli.ImageBuild ())

dockerBuildContext, err := os.Open("/Path/to/your/docker/tarfile.tar") defer dockerBuildContext.Close() buildOptions := types.ImageBuildOptions{ Dockerfile: "Dockerfile", // optional, is the default } buildResponse, err := cli.ImageBuild(context.Background(), dockerBuildContext, buildOptions) if err != nil { log.Fatal(err) } defer buildResponse.Body.Close()

No estoy allí nombrando las imágenes correctamente todavía, pero al menos puedo crearlas ... Espero que esto ayude. Aclamaciones


Estoy de acuerdo con la respuesta de Marcus Havranek, ese método me ha funcionado. Solo quiero agregar cómo agregar un nombre a una imagen, ya que parecía una pregunta abierta:

buildOptions := types.ImageBuildOptions{ Tags: []string{"imagename"}, }

¡Espero que esto ayude!


Lo siguiente funciona para mí;

package main import ( "archive/tar" "bytes" "context" "io" "io/ioutil" "log" "os" "github.com/docker/docker/api/types" "github.com/docker/docker/client" ) func main() { ctx := context.Background() cli, err := client.NewEnvClient() if err != nil { log.Fatal(err, " :unable to init client") } buf := new(bytes.Buffer) tw := tar.NewWriter(buf) defer tw.Close() dockerFile := "myDockerfile" dockerFileReader, err := os.Open("/path/to/dockerfile") if err != nil { log.Fatal(err, " :unable to open Dockerfile") } readDockerFile, err := ioutil.ReadAll(dockerFileReader) if err != nil { log.Fatal(err, " :unable to read dockerfile") } tarHeader := &tar.Header{ Name: dockerFile, Size: int64(len(readDockerFile)), } err = tw.WriteHeader(tarHeader) if err != nil { log.Fatal(err, " :unable to write tar header") } _, err = tw.Write(readDockerFile) if err != nil { log.Fatal(err, " :unable to write tar body") } dockerFileTarReader := bytes.NewReader(buf.Bytes()) imageBuildResponse, err := cli.ImageBuild( ctx, dockerFileTarReader, types.ImageBuildOptions{ Context: dockerFileTarReader, Dockerfile: dockerFile, Remove: true}) if err != nil { log.Fatal(err, " :unable to build docker image") } defer imageBuildResponse.Body.Close() _, err = io.Copy(os.Stdout, imageBuildResponse.Body) if err != nil { log.Fatal(err, " :unable to read image build response") } }