when I run bazel build //leeroy-web, build completes with no issues. However, when I run bazel build //..., I get the following error:
compilepkg: missing strict dependencies:
/private/var/tmp/_bazel_user/988b526f0a596b82369c6920f2962566/sandbox/darwin-sandbox/96/execroot/__main__/leeroy-web/web.go: import of "github.com/foo/project/leeroy-web/handlers"
/private/var/tmp/_bazel_user/988b526f0a596b82369c6920f2962566/sandbox/darwin-sandbox/96/execroot/__main__/leeroy-web/web.go: import of "github.com/foo/project/sum-pkg"
I was wondering how I can resolve this. I found something that might be related here: Bazel build docker container with local golang module but wasn't able to apply the solution to my issue. Thank you.
leeroy-web/web.go
package main
import (
"log"
"net/http"
"github.com/foo/project/leeroy-web/handlers"
sum "github.com/foo/project/sum-pkg"
)
func main() {
added := sum.Sum(8000, 80)
log.Printf("%d web server ready", added)
http.HandleFunc("/", handlers.Handler)
http.ListenAndServe(":8080", nil)
}
leeroy-web/handlers/handlers.go
package handlers
import (
"io"
"net/http"
)
func Handler(w http.ResponseWriter, r *http.Request) {
resp, err := http.Get("http://leeroy-app:50051")
if err != nil {
panic(err)
}
defer resp.Body.Close()
if _, err := io.Copy(w, resp.Body); err != nil {
panic(err)
}
}
skaffold.yaml
apiVersion: skaffold/v2beta29
kind: Config
build:
artifacts:
- image: leeroy-web
context: leeroy-web
bazel:
target: //:leeroy-web-img.tar
deploy:
kubectl:
manifests:
- leeroy-web/kubernetes/*
portForward:
- resourceType: deployment
resourceName: leeroy-web
port: 8080
localPort: 9000
profiles:
- name: gcb
build:
googleCloudBuild: {}
sum-pkg/sum.go
package sum
func Sum(a int, b int) int {
return a + b
}
leeroy-web/BUILD
load("#io_bazel_rules_go//go:def.bzl", "go_binary", "go_library")
load("#io_bazel_rules_docker//go:image.bzl", "go_image")
go_library(
name = "leeroy-web_lib",
srcs = ["web.go"],
importpath = "github.com/foo/project/leeroy-web",
visibility = ["//visibility:private"],
deps = [
"//leeroy-web/handlers",
"//sum-pkg",
],
)
go_binary(
name = "leeroy-web",
embed = [":leeroy-web_lib"],
visibility = ["//visibility:public"],
)
go_image(
name = "leeroy-web-img",
srcs = ["web.go"],
goarch = "amd64",
goos = "linux",
importpath = "github.com/foo/project/leeroy-web",
static = "on",
)
Related
I'm using a docker client with golang; in the following script, I'm trying to pass an environmental variable when a container is going to start.
package main
import (
"context"
"fmt"
"os/user"
"github.com/docker/docker/api/types"
"github.com/docker/docker/api/types/container"
"github.com/docker/docker/client"
)
func main() {
dockerClient, _ := client.NewClientWithOpts(client.FromEnv)
env := []string{}
for key, value := range map[string]string{"hi": "hoo"} {
env = append(env, fmt.Sprintf("%s=%s", key, value))
}
user, err := user.Current()
if err != nil {
fmt.Println(err)
}
config := container.Config{
User: fmt.Sprintf("%s:%s", user.Uid, user.Gid),
Image: "675d8442a90f",
Env: env,
}
response, err := dockerClient.ContainerCreate(context.Background(), &config, nil, nil, nil, "")
if err != nil {
fmt.Println(err)
}
if err = dockerClient.ContainerStart(context.Background(), response.ID, types.ContainerStartOptions{}); err != nil {
fmt.Println(err)
}
}
and my docker file is a simple one which I try to echo the hi env:
# Filename: Dockerfile
FROM ubuntu:latest
COPY . .
CMD ["echo", "$hi"]
When I built the image and passed the id to the script, it didn't echo the variable. Do you have any idea how I can use the environmental variables in the dockerfile, which are sent to the container by docker golang client?
On host machine I have docker-compose stack that have a service called
transactions-db
its a PostgreSQL container
I want to create a backup service using Golang to be able to create .sql to be used for restores later on
docker-compose.yml for backup service
version: "3.8"
services:
backup-service:
build:
context: .
dockerfile: Dockerfile
image: backup-service
container_name: backup-service
volumes:
- .:/app
- /var/run/docker.sock:/var/run/docker.sock
main.go
package main
import (
"context"
"fmt"
"os"
)
func main () {
result, err := ExecuteCommandOnContainer(context.Background(), ConnectToDocker(), "transactions-db")
if err != nil {
fmt.Println(err)
os.Exit(1)
}
fmt.Println(result.ExitCode)
}
docker.go
package main
import (
"context"
"fmt"
"github.com/docker/docker/api/types"
"github.com/docker/docker/client"
)
func ConnectToDocker() *client.Client {
cli, err := client.NewClientWithOpts()
if err != nil {
fmt .Println(err)
}
return cli
}
func ExecuteCommandOnContainer(ctx context.Context, cli *client.Client, containerID string) (types.ContainerExecInspect, error) {
command := []string{"pg_dumpall", "-c", "-U", "user", "|", "gzip", ">", "backup/tr.sql"}
execConfig := types.ExecConfig{
Tty: true,
AttachStdin: true,
AttachStderr: true,
AttachStdout: true,
Cmd: command,
}
create, err := cli.ContainerExecCreate(ctx, containerID, execConfig)
if err != nil {
fmt .Println(err)
}
inspect, err := cli.ContainerExecInspect(ctx, create.ID)
if err != nil {
fmt .Println(err)
}
return inspect, nil
}
basically nothing happens when I run this code. I only get the following:
backup-service | 0
backup-service exited with code 0
I tried to normally run: go run .
I've also tried using my docker-compose up
same result
note: I've tested listing container it works but when trying to execute a command nothing
I have created a DroneCI pipeline with the following content:
kind: pipeline
type: docker
name: Build auto git tagger
steps:
- name: test and build
image: golang
commands:
- go mod download
- go test ./test
- go build -o ./build/package ./cmd/git-tagger
- name: Build docker image
image: plugins/docker
pull: if-not-exists
settings:
username:
password:
repo:
dockerfile:
registry:
auto_tag:
trigger:
branch:
- master
The go test starts a gogs docker container for testing purpose, here is the code:
func createGogsContainer(dest, waitUrl string) (stopContainer, error) {
client, err := docker.NewClientFromEnv()
if err != nil {
return nil, err
}
ctx := context.Background()
gogs, err := client.CreateContainer(docker.CreateContainerOptions{
Name: "repo",
Config: &docker.Config{
Image: "gogs/gogs",
},
HostConfig: &docker.HostConfig{
PublishAllPorts: true,
AutoRemove: true,
Mounts: []docker.HostMount{
{
Type: "bind",
Source: dest,
Target: "/data",
}},
PortBindings: map[docker.Port][]docker.PortBinding{
"3000/tcp": {{HostIP: "0.0.0.0", HostPort: "8888"}},
"22/tcp": {{HostIP: "0.0.0.0", HostPort: "2222"}},
},
},
Context: ctx,
})
if err != nil {
return nil, err
}
err = client.StartContainer(gogs.ID, nil)
if err != nil {
return nil, err
}
//Wait for connection
host, err := url.Parse(waitUrl)
if err != nil {
return nil, err
}
err = waitHTTP(fmt.Sprintf("%s://%s", host.Scheme, host.Host), 3, 0)
if err != nil {
return nil, err
}
return func() error {
return client.StopContainerWithContext(gogs.ID, 5, ctx)
}, nil
}
The pipeline has been aborted with following error message:
latest: Pulling from library/golang
Digest: sha256:f30b0d05ea7783131d84deea3b5f4d418d9d930dfa3668a9a5fa253d1f9dce5a
Status: Image is up to date for golang:latest
+ go mod download
+ go test ./test
time="2020-04-23T17:58:24Z" level=error msg="Get \"http://0.0.0.0:8888/gat/WithoutTag.git/info/refs?service=git-upload-pack\": dial tcp 0.0.0.0:8888: connect: connection refused"
time="2020-04-23T17:58:24Z" level=error msg="Get \"http://0.0.0.0:8888/gat/WithoutTag.git/info/refs?service=git-upload-pack\": dial tcp 0.0.0.0:8888: connect: connection refused"
What am I doing wrong?
Have a look at Drone services. It allows you to bring up a container as part of your pipeline and access its ports.
In your case you can bring up the Gogs container like this:
services:
- name: gogs
image: gogs/gogs
And then use it like this in your pipeline steps:
steps:
- name: test and build
image: golang
commands:
- curl "http://gogs"
-
...
(this assumes the gogs container listens on port 80. If it's a different port then you need to adjust the URI).
Hint: the name of the service is the DNS name of the container.
I am trying to create a containerSource for knative service. When I use docker run for the image it gives the output ("or the error from the code"). However when I apply the yaml file then kubectl log shows 'standard_init_linux.go:211: exec user process caused "no such file or directory"'. docker run shows that it is able to find the exec file. So I am not able to understand whats wrong. Someone please guide me through.
my yaml file:
apiVersion: sources.eventing.knative.dev/v1alpha1
kind: ContainerSource
metadata:
labels:
controller-tools.k8s.io: "1.0"
name: cloudevents-source
spec:
image: docker.io/username/pkt-event:latest
args:
- '--debug=true'
sink:
apiVersion: serving.knative.dev/v1alpha1
kind: Service
name: event-display
my go code for the dockerimage is:
package main
import (
"context"
"flag"
"fmt"
"log"
"os"
"time"
"github.com/satori/go.uuid"
"knative.dev/eventing-contrib/pkg/kncloudevents"
"encoding/json"
// "io/ioutil"
// "knative.dev/eventing-contrib/vendor/github.com/cloudevents/sdk-go/pkg/cloudevents"
"github.com/cloudevents/sdk-go/pkg/cloudevents"
"github.com/cloudevents/sdk-go/pkg/cloudevents/types"
"github.com/kelseyhightower/envconfig"
)
var (
eventSource string
eventType string
sink string
)
//var u, _ = uuid.NewV4()
var debug = flag.Bool("debug", false, "Enable debug mode (print more information)")
var source = flag.String("source", uuid.NewV4().String(), "Set custom Source for the driver")
func init() {
flag.StringVar(&eventSource, "eventSource", "", "the event-source (CloudEvents)")
flag.StringVar(&eventType, "eventType", "dev.knative.eventing.samples.pkt", "the event-type (CloudEvents)")
flag.StringVar(&sink, "sink", "", "the host url to send pkts to")
}
type envConfig struct {
// Sink URL where to send heartbeat cloudevents
Sink string `envconfig:"SINK"`
}
func main() {
flag.Parse()
var env envConfig
if err := envconfig.Process("", &env); err != nil {
log.Printf("[ERROR] Failed to process env var: %s", err)
os.Exit(1)
}
if env.Sink != "" {
sink = env.Sink
}
if eventSource == "" {
eventSource = fmt.Sprintf("https://knative.dev/eventing-contrib/cmd/heartbeats/#local/demo")
log.Printf("Source: %s", eventSource)
}
client, err := kncloudevents.NewDefaultClient(sink)
if err != nil {
log.Fatalf("failed to create client: %s", err.Error())
}
var period time.Duration
period = time.Duration(1) * time.Second
ticker := time.NewTicker(period)
for {
content := "Send data"
data, err := json.Marshal(content)
if err != nil {
fmt.Println(err)
}
event := cloudevents.Event{
Context: cloudevents.EventContextV02{
Type: "packet.invoke",
Source: *types.ParseURLRef(eventSource),
/*Extensions: map[string]interface{}{
"the": 42,
"heart": "yes",
"beats": true,
},*/
}.AsV02(),
Data: data,
}
if *debug{
log.Printf("Sending event %v", event)
} else {
if _, err := client.Send(context.TODO(), event); err != nil {
log.Printf("failed to send cloudevent: %s", err.Error())
}
}
<-ticker.C
}
}
And Dockerfile is:
FROM golang:1.12 as builder
RUN go version
WORKDIR ${GOPATH}/src/Event-driver
COPY ./ ./
RUN curl https://raw.githubusercontent.com/golang/dep/master/install.sh | sh
##RUN dep ensure
RUN dep init
RUN dep ensure
RUN CGO_ENABLED=0 GOARCH=amd64 GOOS=linux go build -v -o my-event my-event.go
RUN pwd && ls
FROM scratch
#FROM ubuntu:disco
COPY --from=builder /go/src/Event-driver/my-event /
ENTRYPOINT ["/my-event"]
That problem occurs because you're trying to run your binary from bash, but scratch has no bash.
I'm normally using alpina instead. To build for alpina you need the same environment variables, so probably you only need to change a second stage image.
I am looking forward to do something below like this using docker golang api
cmd : docker run -t -i -p 8989:8080 "image-name" /bin/bash
Also I am using golang sdk https://github.com/moby/moby/client or https://godoc.org/github.com/moby/moby/client and my docker api version is 1.30 (Client & Server both)
Here is the piece of code I am using
package main
import (
"fmt"
"github.com/docker/docker/client"
"github.com/docker/docker/api/types"
"github.com/docker/docker/api/types/container"
"golang.org/x/net/context"
"github.com/docker/go-connections/nat"
//"github.com/docker/docker/vendor/github.com/docker/go-connections/nat"
)
func check(err error) {
if err != nil {
panic(err)
}
}
func main(){
ctx := context.Background()
cli, err := client.NewEnvClient()
check(err)
config := &container.Config{
Image : image-name,
ExposedPorts: nat.PortSet{
"8080/tcp": struct{}{},
},
Cmd : [] string {"sh","-c","while true; do sleep always; done","/bin/bash"},
}
host_config := &container.HostConfig{
PortBindings: nat.PortMap{
"8080/tcp": []nat.PortBinding{
{
HostIP: "0.0.0.0",
HostPort: "8989",
},
},
},
}
resp, err := cli.ContainerCreate(ctx,config,host_config, nil,"")
check(err)
if err := cli.ContainerStart(ctx, resp.ID, types.ContainerStartOptions{});
err != nil {
panic(err)
}
}
After Compiling this code I get the following error
# command-line-arguments
src\main\createcontainer1.go:53: cannot use "github.com/docker/go-connections/nat".PortSet literal (type "github.com/docker/go-connections/nat".PortSet) as type "github.com/docker/docker/vendor/github.com/docker/go-connections/nat".PortSet in field value
src\main\createcontainer1.go:65: cannot use "github.com/docker/go-connections/nat".PortMap literal (type "github.com/docker/go-connections/nat".PortMap) as type "github.com/docker/docker/vendor/github.com/docker/go-connections/nat".PortMap in field value
If somebody knows what could be the problem and how to fix it.
Please answer to it as I am beginner with docker.
This is a Golang issue with how vendor/ works.
Remove the nested vendor directory:
rm -rf vendor/github.com/docker/docker/vendor
If you are using glide, you should use glide install -v when installing the dependency.
For more details, check this reported issue
My solution for OSX:
mv /Users/<user>/go/src/github.com/docker/docker/vendor/github.com/docker/go-connections/{nat,nat.old}